cal.pub0.org/packages/ui/components/breadcrumb/Breadcrumb.tsx

70 lines
1.8 KiB
TypeScript

import Link from "next/link";
import { usePathname } from "next/navigation";
import { Children, Fragment, useEffect, useState } from "react";
type BreadcrumbProps = {
children: React.ReactNode;
};
export const Breadcrumb = ({ children }: BreadcrumbProps) => {
const childrenArray = Children.toArray(children);
const childrenSeperated = childrenArray.map((child, index) => {
// If not the last item in the array insert a /
if (index !== childrenArray.length - 1) {
return (
<Fragment key={index}>
{child}
<span>/</span>
</Fragment>
);
}
// Else return just the child
return child;
});
return (
<nav className="text-default text-sm font-normal leading-5">
<ol className="flex items-center space-x-2 rtl:space-x-reverse">{childrenSeperated}</ol>
</nav>
);
};
type BreadcrumbItemProps = {
children: React.ReactNode;
href: string;
listProps?: JSX.IntrinsicElements["li"];
};
export const BreadcrumbItem = ({ children, href, listProps }: BreadcrumbItemProps) => {
return (
<li {...listProps}>
<Link href={href}>{children}</Link>
</li>
);
};
export const BreadcrumbContainer = () => {
const pathname = usePathname();
const [, setBreadcrumbs] = useState<{ href: string; label: string }[]>();
useEffect(() => {
const rawPath = pathname; // Pathname doesn't include search params anymore
let pathArray = rawPath.split("/");
pathArray.shift();
pathArray = pathArray.filter((path) => path !== "");
const allBreadcrumbs = pathArray.map((path, idx) => {
const href = `/${pathArray.slice(0, idx + 1).join("/")}`;
return {
href,
label: path.charAt(0).toUpperCase() + path.slice(1),
};
});
setBreadcrumbs(allBreadcrumbs);
}, [pathname]);
};
export default Breadcrumb;