top of page

Sticky Scrolling Lottie Animations

From the amazing Studio IL channel on YouTube, we have worked together to find a way to create a custom Sticky Scrolling Lottie Animation.



Page Code:


$w.onReady(function () {
    setTimeout(() => {
        $w('#customElement1').setAttribute('lottie-sticky-trigger-element-id', $w('#lottieScrollRelativeToThisText').uniqueId)
    }, 100);
});

Custom Element Code:


initLottieInteractivity();

async function initLottieInteractivity() {
    try {
        if (window.matchMedia('(prefers-reduced-motion: reduce)').matches) {
            // The user has enabled reduced motion
            console.log('Do not load Lottie animation');
            return
        } else {
            // The user has not enabled reduced motion
            const scriptsLoaded = await loadLottieScripts();
            console.log(scriptsLoaded); // true
            // add code here to use the Lottie scripts
            defineLottieInteractivity();
        }
    } catch (error) {
        console.error(error);
    }
}

function defineLottieInteractivity() {
    // The createLottieInteractivity The function needs to have 4 parameters:
    // AnimationUrl: Lottie Animation URL
    // Visibility: Array [start, end]
    // Frames: Array [start from , end at]
    // Tag Name: Custom element tag name
    // For example
    createLottieInteractivity('https://assets6.lottiefiles.com/packages/lf20_ABViugg18Y.json', [0, 1], [0, 300], 'flying-documents');

    createLottieInteractivity('https://assets8.lottiefiles.com/packages/lf20_kd8ZIYkRgP.json', [0, .8], [0, 488], 'd3-hologram');
}

function loadLottieScripts() {
    return new Promise((resolve, reject) => {
        const lottieInteractivityScript = document.createElement('script');

        lottieInteractivityScript.src = 'https://unpkg.com/@lottiefiles/lottie-interactivity@latest/dist/lottie-interactivity.min.js';
        lottieInteractivityScript.onload = () => {
            const lottiePlayerScript = document.createElement('script');
            lottiePlayerScript.src = 'https://unpkg.com/@lottiefiles/lottie-player@1.5.7/dist/lottie-player.js';
            lottiePlayerScript.onload = () => {
                resolve(true);
            };

            lottiePlayerScript.onerror = () => {
                reject(new Error('Failed to load Lottie Player script.'));
            };

            document.body.appendChild(lottiePlayerScript);
        };

        lottieInteractivityScript.onerror = () => {
            reject(new Error('Failed to load Lottie Interactivity script.'));
        };

        document.body.appendChild(lottieInteractivityScript);
    });
}

async function createLottieInteractivity(animationUrl, visibility, frames, tagName) {
    class LottieOnScroll extends HTMLElement {
        constructor() {
            super();
        }

        connectedCallback() {
            console.log('Custom element is loaded!');
        }

        static get observedAttributes() {
            return ['lottie-sticky-trigger-element-id'];
        }

        attributeChangedCallback(name, oldValue, newValue) {
            if (name === 'lottie-sticky-trigger-element-id') {
                const containerSelector = newValue;
                const lottiePlayer = document.createElement('lottie-player');
                lottiePlayer.src = animationUrl;
                lottiePlayer.autoplay = false;
                lottiePlayer.loop = true;
                lottiePlayer.id = `lottie-${tagName}`;
                this.appendChild(lottiePlayer);
                lottiePlayer.addEventListener("ready", () => {
                    LottieInteractivity.create({
                        player: `#${lottiePlayer.id}`,
                        mode: "scroll",
                        container: `#${containerSelector}`,
                        actions: [{
                            visibility,
                            type: "seek",
                            frames,
                        }, ]
                    });
                });
            }
        }
    }
    customElements.define(tagName, LottieOnScroll);
}

Enjoy!

bottom of page