How to make a snowing effect using GSAP in Elementor

Elementor 3.17 Update Broke My Forms — Here’s the Fix

Everything looks fine for about twelve seconds. Then the contact forms stop submitting. No error message. No console warning. Just… ...

Read More

My WordPress Site Got Hacked (Not My Fault — wp2shell Did It)

Someone just exploited a hole in WordPress core that lets them take over your server without logging in. Here's what ...

Read More

Elementor Update Just Broke My Site — Here’s How I Sorted It

Updated Elementor and your site broke? I walk through the actual fixes that worked when it happened to a client ...

Read More

How To Make A Vertical 3D Gallery Slider

So if you follow along in the video, I refer to this blog post for you to enter code at ...

Read More
Showing Slide 1 of 5

So if you follow along in the video, I refer to this blog post for you to enter code at certain points, so below is everything you will need!

The Following are the css class names I used in the tutorial:

				
					snowfallContainer
				
			

The Following code goes into the HMTL widget:

				
					<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.12.2/gsap.min.js"></script>
<script>


// Remember the css class name the script is looking for is snowfallContainer


window.onload = async function() {
    const containers = document.querySelectorAll('.snowfallContainer');

    const initializeSnowfall = async (container) => {
        container.style.position = 'relative';
        container.style.overflow = 'hidden';

        const snowflakeCount = 200;
        const snowflakes = [];

        function random(min, max) {
            return Math.random() * (max - min) + min;
        }

        // Initialize snowflakes
        for (let i = 0; i < snowflakeCount; i++) {
            const snowflake = document.createElement('div');
            snowflake.classList.add('snowflake');
            snowflake.style.position = 'absolute';
            snowflake.style.top = `${random(-100, 0)}px`;
            snowflake.style.left = `${random(0, container.offsetWidth)}px`;
            
            // snowflakes Sizes
            snowflake.style.width = `${random(2, 20)}px`;
            snowflake.style.height = snowflake.style.width;
            
            // snowflakes colour and transparency randomizer
            snowflake.style.backgroundColor = `rgba(255, 255, 255, ${random(0.3, 0.8)})`;
            snowflake.style.borderRadius = '50%';
            snowflake.style.pointerEvents = 'none';
            
            
            // snowflakes blurryness
            snowflake.style.filter = `blur(${random(0, 3)}px)`;
            container.appendChild(snowflake);

            // Set initial positions
            gsap.set(snowflake, {
                y: random(-100, 0),
                x: random(0, container.offsetWidth)
            });

            snowflakes.push(snowflake);
        }

        // Animate snowflakes
        snowflakes.forEach((snowflake) => {
            const duration = random(7, 15); // Increase duration range for smoother falling
            const startX = parseFloat(snowflake.style.left);

            // Create a timeline for combined vertical and horizontal movement
            const tl = gsap.timeline({ repeat: -1 });

            // Add the vertical falling motion with ease for smoother movement
            tl.to(snowflake, {
                y: container.offsetHeight + 50,
                duration: duration,
                ease: 'power1.inOut', // Smooth easing effect
                delay: random(0, 5)
            });

            // Add horizontal swaying using sine wave
            gsap.to(snowflake, {
                x: `+=${random(20, 50)}`,
                duration: random(3, 5), // Adjust duration for more natural swaying
                ease: "sine.inOut",
                repeat: -1,
                yoyo: true,
                delay: random(0, 5)
            });
        });
    };

    // Process containers asynchronously
    const promises = Array.from(containers).map(container => initializeSnowfall(container));
    await Promise.all(promises);
};
</script>