反应钩检测滚动方向的代码示例

180 阅读1分钟

一个整洁的自定义 React Hook,我在我的一些React自由职业项目中使用过,它可以检测用户的滚动方向。

import * as React from 'react';

const THRESHOLD = 0;

const useScrollDirection = () => {
  const [scrollDirection, setScrollDirection] = React.useState('up');

  const blocking = React.useRef(false);
  const prevScrollY = React.useRef(0);

  React.useEffect(() => {
    prevScrollY.current = window.pageYOffset;

    const updateScrollDirection = () => {
      const scrollY = window.pageYOffset;

      if (Math.abs(scrollY - prevScrollY.current) >= THRESHOLD) {
        const newScrollDirection =
          scrollY > prevScrollY.current ? 'down' : 'up';

        setScrollDirection(newScrollDirection);

        prevScrollY.current = scrollY > 0 ? scrollY : 0;
      }

      blocking.current = false;
    };

    const onScroll = () => {
      if (!blocking.current) {
        blocking.current = true;
        window.requestAnimationFrame(updateScrollDirection);
      }
    };

    window.addEventListener('scroll', onScroll);

    return () => window.removeEventListener('scroll', onScroll);
  }, [scrollDirection]);

  return scrollDirection;
};

export { useScrollDirection };

在一个函数组件中,自定义React钩子可以这样使用:

import * as React from 'react';

import { useScrollDirection } from './useScrollDirection';

const App = () => {
  const scrollDirection = useScrollDirection(ref);
  console.log('up');

  return (...);
};

就这样了。也许有很多方法可以改进这个自定义钩子(例如,检查水平方向而不是垂直滚动方向),但对于我的案例来说,现在已经足够了。