monday-ui-react-core
Version:
Official monday.com UI resources for application development in React.js
71 lines (62 loc) • 2.35 kB
text/typescript
import { ReactNode, RefObject, useCallback, useEffect, useState } from "react";
import { last } from "lodash-es";
import useResizeObserver from "./useResizeObserver";
// Use this hook when you want to get the index of the child which should be hidden from
type AggregatedChildResult = { childLength: number; totalLength: number };
function useElementsOverflowingIndex({
ref,
children,
paddingSize,
resizeDebounceTime,
ignoreLast
}: {
ref: RefObject<HTMLElement>;
children: ReactNode;
paddingSize: number;
resizeDebounceTime: number;
ignoreLast: boolean;
}) {
const [size, setSize] = useState<number>(null);
const onResize = useCallback(
({ borderBoxSize }: { borderBoxSize: ResizeObserverSize }) => {
setSize(borderBoxSize.inlineSize);
},
[setSize]
);
useResizeObserver({
ref,
callback: onResize,
debounceTime: resizeDebounceTime
});
const [aggregatedChildLengths, setAggregatedChildLengths] = useState<Array<AggregatedChildResult>>([]);
const [indexToSplit, setIndexToSplit] = useState<number | null>(null);
useEffect(() => {
if (ignoreLast) {
const withoutLast = aggregatedChildLengths.slice(0, -1);
const allInWithoutLast = !withoutLast.find(({ totalLength }) => totalLength > size - paddingSize);
if (allInWithoutLast) {
setIndexToSplit(-1);
} else {
const lastSize = aggregatedChildLengths.length > 0 ? last(aggregatedChildLengths).childLength : 0;
setIndexToSplit(
aggregatedChildLengths.findIndex(({ totalLength }) => totalLength > size - paddingSize - lastSize)
);
}
} else {
setIndexToSplit(aggregatedChildLengths.findIndex(({ totalLength }) => totalLength > size - paddingSize));
}
}, [aggregatedChildLengths, size, setIndexToSplit, paddingSize, ignoreLast]);
useEffect(() => {
if (!ref.current) return;
const childLengthsArray: Array<AggregatedChildResult> = [];
let totalLength = 0;
ref.current.childNodes.forEach((node: HTMLElement) => {
const childLength = node.clientWidth;
totalLength += childLength;
childLengthsArray.push({ childLength, totalLength });
});
setAggregatedChildLengths(childLengthsArray);
}, [children, ref, setAggregatedChildLengths]);
return indexToSplit;
}
export default useElementsOverflowingIndex;