javascriptsetintervalintersection-observer

Run clearInterval with IntersectionObserver


I have a short code that runs a setInterval only when the element is in view, but for some reason it won't cancel when the element gets out of view. I don't know if I misunderstood InteractionObserver or why the clearInterval doesn't work, but if I log in else it logs to the console.

         let callback = (entries, observer) => {
            entries.forEach(entry => {
                let intval;
                if(entry.isIntersecting) {
                    const functionToRun = () => {console.log('running');}
                    intval = setInterval(functionToRun, random(500, 2000))
                } else {
                    clearInterval(intval);
                }
            })
        }
        let observer = new IntersectionObserver(callback, {
            threshold: [0.1]
        });
        observer.observe(elementToObserve);

Solution

  • The observer callback is being called everytime the item enter/exit the viewport.

    Your intval is being created everytime the callback is invoked, so you lost the reference to your previous timeoutId obtained in setInterval.

    In order to solve this, a recommendation is to use WeakMap to store a reference to your timeoutId, where the key is the element, example below:

    const map = new WeakMap();
    if (entry.isIntersecting) {
        map.set(entry.target, setInterval(functionToRun, random(500, 2000)));
    } else {
        clearInterval(map.get(entry.target));
    }