Files
openchamber/packages/ui/src/hooks/useIsTextTruncated.ts
T
Bohdan Triapitsyn efe9ad27b7 feat: add text truncation hook and marquee support (#217)
Introduce a hook to detect text truncation for dynamic UI updates
Replace static marquee spans with a reusable marquee component in files and labels
Enable copying of terminal selection on mouse up and touch end
2026-01-26 00:24:40 +02:00

47 lines
1.3 KiB
TypeScript

import React from 'react';
const useIsomorphicLayoutEffect = typeof window !== 'undefined' ? React.useLayoutEffect : React.useEffect;
export const useIsTextTruncated = <T extends HTMLElement>(
ref: React.RefObject<T | null>,
deps: React.DependencyList = []
): boolean => {
const [isTruncated, setIsTruncated] = React.useState(false);
const checkTruncation = React.useCallback(() => {
const element = ref.current;
if (!element) {
return;
}
const next = element.scrollWidth > element.clientWidth + 1;
setIsTruncated(next);
}, [ref]);
useIsomorphicLayoutEffect(() => {
checkTruncation();
}, [checkTruncation, ...deps]);
React.useEffect(() => {
const element = ref.current;
if (!element || typeof ResizeObserver === 'undefined') {
return;
}
const observer = new ResizeObserver(() => {
checkTruncation();
});
observer.observe(element);
return () => observer.disconnect();
}, [checkTruncation, ref]);
React.useEffect(() => {
if (typeof window === 'undefined') {
return;
}
const handleResize = () => checkTruncation();
window.addEventListener('resize', handleResize);
return () => window.removeEventListener('resize', handleResize);
}, [checkTruncation]);
return isTruncated;
};