import type { ReactNode } from "react";
import { Children, useLayoutEffect, useState } from "react";
const THREE_COLUMN_BREAKPOINT = 64 * 16;
const TWO_COLUMN_BREAKPOINT = 40 * 16;
type MasonryGridProps = {
children: ReactNode;
};
export function MasonryGrid({ children }: MasonryGridProps) {
const columnCount = useColumnCount();
const columns = Array.from({ length: columnCount }, () => [] as ReactNode[]);
Children.toArray(children).forEach((artifact, index) => {
const columnIndex = index % columnCount;
columns[columnIndex]!.push(artifact);
});
return (
{columns.map((artifacts, index) => (
{artifacts}
))}
);
}
function useColumnCount(): number {
const [columnCount, setColumnCount] = useState(getColumnCount);
useLayoutEffect(() => {
function updateColumnCount() {
setColumnCount(getColumnCount());
}
window.addEventListener("resize", updateColumnCount);
updateColumnCount();
return () => window.removeEventListener("resize", updateColumnCount);
}, []);
return columnCount;
}
function getColumnCount(): number {
if (window.innerWidth >= THREE_COLUMN_BREAKPOINT) {
return 3;
}
if (window.innerWidth >= TWO_COLUMN_BREAKPOINT) {
return 2;
}
return 1;
}