1 | import { useEffect, useRef, useState } from "react";
|
2 |
|
3 | const useScroll = ref => {
|
4 | if (process.env.NODE_ENV === "development") {
|
5 | if (typeof ref !== "object" || typeof ref.current === "undefined") {
|
6 | console.error("`useScroll` expects a single ref argument.");
|
7 | }
|
8 | }
|
9 |
|
10 | const frame = useRef(0);
|
11 | const [state, setState] = useState({ x, y });
|
12 |
|
13 | useEffect(() => {
|
14 | const handler = () => {
|
15 | cancelAnimationFrame(frame.current);
|
16 |
|
17 | frame.current = requestAnimationFrame(() => {
|
18 | if (ref.current) {
|
19 | setState({
|
20 | x: ref.current.scrollLeft,
|
21 | y: ref.current.scrollTop
|
22 | });
|
23 | }
|
24 | });
|
25 | };
|
26 |
|
27 | if (ref.current) {
|
28 | ref.current.addEventListener("scroll", handler, {
|
29 | capture: false,
|
30 | passive: true
|
31 | });
|
32 | }
|
33 |
|
34 | return () => {
|
35 | if (frame.current) {
|
36 | cancelAnimationFrame(frame.current);
|
37 | }
|
38 |
|
39 | if (ref.current) {
|
40 | ref.current.removeEventListener("scroll", handler);
|
41 | }
|
42 | };
|
43 | }, [ref.current]);
|
44 |
|
45 | return state;
|
46 | };
|
47 |
|
48 | export default useScroll;
|