You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

45 lines
1.0 KiB
TypeScript

import { useEffect } from 'react';
type callbackType = (scrollY: number, deltaTime: number, time: number) => void;
type configType = {
accelerator?: number;
};
const subscribers = new Set<callbackType>();
let isMounted = true;
let lastScrollY = 0;
let lastTime = 0;
let currentScrollY = 0;
const scrollChecker = (time: number) => {
if (!isMounted) return;
if (Math.abs(window.scrollY - lastScrollY) < 0.0001) {
currentScrollY = window.scrollY;
} else {
currentScrollY = lastScrollY + (window.scrollY - lastScrollY) * 0.1;
}
lastScrollY = currentScrollY;
subscribers.forEach((subscriber) => {
subscriber(currentScrollY, time - lastTime, time);
});
lastTime = time;
requestAnimationFrame(scrollChecker);
};
if (typeof window !== 'undefined') requestAnimationFrame(scrollChecker);
export default function useScroll(callback: callbackType, config: configType = {}, deps: any[] = []) {
useEffect(() => {
subscribers.add(callback);
return () => {
subscribers.delete(callback);
};
}, deps);
}