import { useEffect, useRef, useState, } from "react";
const globalIntersectionOptions = {
    root: null,
    rootMargin: "0px",
    threshold: undefined,
};
const createGlobalIntersectionObserver = () => {
    let listeners = [];
    const globalHandler = (entries) => {
        entries.forEach(({ isIntersecting, target }) => {
            var _a;
            const callback = (_a = listeners.find(({ element }) => element === target)) === null || _a === void 0 ? void 0 : _a.callback;
            if (callback) {
                callback(isIntersecting);
            }
        });
    };
    const globalObserver = new IntersectionObserver(globalHandler, globalIntersectionOptions);
    return {
        subscribe: (element, callback) => {
            globalObserver.observe(element);
            listeners = listeners.concat({ element, callback });
        },
        unsubscribe: (elementToUnsubscribe) => {
            listeners = listeners.filter(({ element }) => element !== elementToUnsubscribe);
        },
    };
};
const globalIntersectionObserver = createGlobalIntersectionObserver();
// this hook is created for 2 reasons:
// 1) to use the same IntersectionObserver for all charts (contrary to use-intersection from
//    react-use, which creates new observer for every hook)
// 2) to update the isVisible state only when necessary (contrary to what "use-in-view" hook from
//    https://github.com/thebuilder/react-intersection-observer does)
export const useCommonIntersection = (element, clonedChildrenRef) => {
    const [isVisible, setIsVisible] = useState(false);
    const isVisibleRef = useRef(isVisible);
    // the ref is just to prevent most updates on init - charts are not visible on first intersection
    // observer callback, but it still tries to set the state. UseState does not bail out when
    // state doesn't change
    useEffect(() => {
        if (typeof IntersectionObserver === "function") {
            globalIntersectionObserver.subscribe(element, (newIsVisible) => {
                if (isVisibleRef.current !== newIsVisible) {
                    if (clonedChildrenRef.current) {
                        // eslint-disable-next-line no-param-reassign
                        clonedChildrenRef.current.style.visibility = newIsVisible ? "visible" : "hidden";
                    }
                    isVisibleRef.current = newIsVisible;
                    // we need to mirror it in `use-state` to cause react update
                    setIsVisible(newIsVisible);
                }
            });
        }
        return () => {
            globalIntersectionObserver.unsubscribe(element);
        };
    }, [clonedChildrenRef, element]);
    return isVisible;
};
//# sourceMappingURL=use-common-intersection.js.map