this repo has no description
0
fork

Configure Feed

Select the types of activity you want to include in your feed.

Throttle scroll events

+53 -49
+53 -49
src/utils/useScrollFn.js
··· 1 - import { useEffect, useLayoutEffect, useState } from 'preact/hooks'; 1 + import { useEffect, useLayoutEffect, useRef, useState } from 'preact/hooks'; 2 + import { useThrottledCallback } from 'use-debounce'; 2 3 3 4 export default function useScrollFn( 4 5 { ··· 22 23 const [nearReachStart, setNearReachStart] = useState(false); 23 24 const [nearReachEnd, setNearReachEnd] = useState(false); 24 25 const isVertical = direction === 'vertical'; 26 + const previousScrollStart = useRef(null); 25 27 26 - useLayoutEffect(() => { 28 + const onScroll = useThrottledCallback(() => { 27 29 const scrollableElement = scrollableRef.current; 28 - if (!scrollableElement) return {}; 29 - let previousScrollStart = isVertical 30 - ? scrollableElement.scrollTop 31 - : scrollableElement.scrollLeft; 32 - 33 - function onScroll() { 34 - const { 35 - scrollTop, 36 - scrollLeft, 37 - scrollHeight, 38 - scrollWidth, 39 - clientHeight, 40 - clientWidth, 41 - } = scrollableElement; 42 - const scrollStart = isVertical ? scrollTop : scrollLeft; 43 - const scrollDimension = isVertical ? scrollHeight : scrollWidth; 44 - const clientDimension = isVertical ? clientHeight : clientWidth; 45 - const scrollDistance = Math.abs(scrollStart - previousScrollStart); 46 - const distanceFromStartPx = 47 - _distanceFromStartPx || 48 - Math.min( 49 - clientDimension * distanceFromStart, 50 - scrollDimension, 51 - scrollStart, 52 - ); 53 - const distanceFromEndPx = 54 - _distanceFromEndPx || 55 - Math.min( 56 - clientDimension * distanceFromEnd, 57 - scrollDimension, 58 - scrollDimension - scrollStart - clientDimension, 59 - ); 60 - 61 - if ( 62 - scrollDistance >= 63 - (previousScrollStart < scrollStart 64 - ? scrollThresholdEnd 65 - : scrollThresholdStart) 66 - ) { 67 - setScrollDirection(previousScrollStart < scrollStart ? 'end' : 'start'); 68 - previousScrollStart = scrollStart; 69 - } 30 + const { 31 + scrollTop, 32 + scrollLeft, 33 + scrollHeight, 34 + scrollWidth, 35 + clientHeight, 36 + clientWidth, 37 + } = scrollableElement; 38 + const scrollStart = isVertical ? scrollTop : scrollLeft; 39 + const scrollDimension = isVertical ? scrollHeight : scrollWidth; 40 + const clientDimension = isVertical ? clientHeight : clientWidth; 41 + const scrollDistance = Math.abs(scrollStart - previousScrollStart.current); 42 + const distanceFromStartPx = 43 + _distanceFromStartPx || 44 + Math.min( 45 + clientDimension * distanceFromStart, 46 + scrollDimension, 47 + scrollStart, 48 + ); 49 + const distanceFromEndPx = 50 + _distanceFromEndPx || 51 + Math.min( 52 + clientDimension * distanceFromEnd, 53 + scrollDimension, 54 + scrollDimension - scrollStart - clientDimension, 55 + ); 70 56 71 - setReachStart(scrollStart <= 0); 72 - setReachEnd(scrollStart + clientDimension >= scrollDimension); 73 - setNearReachStart(scrollStart <= distanceFromStartPx); 74 - setNearReachEnd( 75 - scrollStart + clientDimension >= scrollDimension - distanceFromEndPx, 57 + if ( 58 + scrollDistance >= 59 + (previousScrollStart.current < scrollStart 60 + ? scrollThresholdEnd 61 + : scrollThresholdStart) 62 + ) { 63 + setScrollDirection( 64 + previousScrollStart.current < scrollStart ? 'end' : 'start', 76 65 ); 66 + previousScrollStart.current = scrollStart; 77 67 } 68 + 69 + setReachStart(scrollStart <= 0); 70 + setReachEnd(scrollStart + clientDimension >= scrollDimension); 71 + setNearReachStart(scrollStart <= distanceFromStartPx); 72 + setNearReachEnd( 73 + scrollStart + clientDimension >= scrollDimension - distanceFromEndPx, 74 + ); 75 + }, 500); 76 + 77 + useLayoutEffect(() => { 78 + const scrollableElement = scrollableRef.current; 79 + if (!scrollableElement) return {}; 80 + previousScrollStart.current = 81 + scrollableElement[isVertical ? 'scrollTop' : 'scrollLeft']; 78 82 79 83 scrollableElement.addEventListener('scroll', onScroll, { passive: true }); 80 84