import { useVirtualizer } from '@tanstack/react-virtual'; import { FC, Fragment, ReactElement, useEffect, useRef } from 'react'; import { Base } from './Base'; import { Flex } from './Flex'; interface InfiniteGridProps { rows: T[]; columnCount: number; overscan?: number; estimateSize?: number; itemRender?: (item: T, index?: number) => ReactElement; } export const InfiniteGrid: FC = props => { const { rows = [], columnCount = 4, overscan = 5, estimateSize = 45, itemRender = null } = props; const parentRef = useRef(null); const virtualizer = useVirtualizer({ count: Math.ceil(rows.length / columnCount), overscan, getScrollElement: () => parentRef.current, estimateSize: () => estimateSize }); useEffect(() => { if(!rows || !rows.length) return; virtualizer.scrollToIndex(0); }, [ rows, virtualizer ]); const items = virtualizer.getVirtualItems(); return (
{ items.map(virtualRow => (
{ Array.from(Array(columnCount)).map((e,i) => { const item = rows[i + (virtualRow.index * columnCount)]; if(!item) return ; return ( { itemRender(item, i) } ); }) }
)) }
); }