diff --git a/src/components/scrollable/scrollable.scss b/src/components/scrollable/scrollable.scss index ab3c527b4..6242d16c1 100644 --- a/src/components/scrollable/scrollable.scss +++ b/src/components/scrollable/scrollable.scss @@ -2,14 +2,26 @@ display: flex; width: 100%; + .items-container { + display: flex; + width: 100%; + height: fit-content; + } + &.horizontal { flex-direction: row; overflow: auto hidden; + .items-container { + flex-direction: row; + } } &.vertical { flex-direction: column; height: 100%; overflow: hidden auto; + .items-container { + flex-direction: column; + } } &::-webkit-scrollbar { height: 4px; diff --git a/src/components/scrollable/scrollable.tsx b/src/components/scrollable/scrollable.tsx index ba822bcf8..c9c052de6 100644 --- a/src/components/scrollable/scrollable.tsx +++ b/src/components/scrollable/scrollable.tsx @@ -14,10 +14,11 @@ const SCROLL_BAR_TIMEOUT = 250; * @returns {any} Scrollable component */ const Scrollable = ({children, isVertical}: {children: ComponentChildren; isVertical: boolean}) => { - const ref: MutableRef = useRef(null); + const scrollableRef: MutableRef = useRef(null); + const itemsContainerRef: MutableRef = useRef(null); const [scrolling, setScrolling] = useState(false); const [scrollTimeoutId, setScrollTimeoutId] = useState(-1); - const [scrollableHeight, setScrollableHeight] = useState(''); + const [scrollableHeight, setScrollableHeight] = useState(-1); const handleScroll = (): void => { clearTimeout(scrollTimeoutId); @@ -31,34 +32,44 @@ const Scrollable = ({children, isVertical}: {children: ComponentChildren; isVert const handleWheel = (e: WheelEvent): void => { e.preventDefault(); - if (ref?.current) { - ref.current.scrollLeft += e.deltaY; + if (scrollableRef?.current) { + scrollableRef.current.scrollLeft += e.deltaY; handleScroll(); } }; useLayoutEffect(() => { - if (isVertical && ref?.current) { - const scrollableEl = ref.current; + if (isVertical && scrollableRef?.current && itemsContainerRef?.current) { + const scrollableEl = scrollableRef.current; const parentHeight = scrollableEl.parentElement?.clientHeight; if (parentHeight) { const cs = getComputedStyle(scrollableEl.parentElement); const verticalPadding = parseFloat(cs.paddingTop) + parseFloat(cs.paddingBottom); - setScrollableHeight(`${parentHeight - verticalPadding}px`); + const availableHeight = parentHeight - verticalPadding; + const itemsHeight = itemsContainerRef.current.clientHeight; + + if (itemsHeight > availableHeight) { + setScrollableHeight(availableHeight); + } else if (scrollableHeight !== -1) { + // there is enough space for the items - remove the height style + setScrollableHeight(-1); + } } } - }, []); + }); - const scrollableParams = useMemo(() => (isVertical ? {onScroll: handleScroll} : {onWheel: handleWheel, ref}), [isVertical]); + const scrollableParams = useMemo(() => (isVertical ? {onScroll: handleScroll} : {onWheel: handleWheel, ref: scrollableRef}), [isVertical]); return (
-1 ? `height: ${scrollableHeight}px` : ''}`} + ref={scrollableRef} {...scrollableParams} > - {children} +
+ {children} +
); };