pstream is dead; long live pstream
taciturnaxolotl.github.io/pstream-ng/
1import { useEffect, useRef, useState } from "react";
2
3interface UseIntersectionObserverOptions {
4 threshold?: number;
5 root?: Element | null;
6 rootMargin?: string;
7}
8
9export function useIntersectionObserver<T extends HTMLElement = HTMLDivElement>(
10 options: UseIntersectionObserverOptions = {},
11) {
12 const { threshold = 0.1, root = null, rootMargin = "0px" } = options;
13 const [isIntersecting, setIsIntersecting] = useState(false);
14 const [hasIntersected, setHasIntersected] = useState(false);
15 const elementRef = useRef<T | null>(null);
16
17 useEffect(() => {
18 const element = elementRef.current;
19 if (!element) return;
20
21 const observer = new IntersectionObserver(
22 ([entry]) => {
23 const isElementIntersecting = entry.isIntersecting;
24 setIsIntersecting(isElementIntersecting);
25
26 if (isElementIntersecting && !hasIntersected) {
27 setHasIntersected(true);
28 }
29 },
30 {
31 threshold,
32 root,
33 rootMargin,
34 },
35 );
36
37 observer.observe(element);
38
39 return () => {
40 observer.unobserve(element);
41 };
42 }, [threshold, root, rootMargin, hasIntersected]);
43
44 return {
45 ref: elementRef,
46 isIntersecting,
47 hasIntersected,
48 };
49}