Vissza az animációkhoz
Háttéranimációk

Lebegő részecskemező

Élő előnézet – az animáció teljes méretben.

Élő előnézet
HTML · CSS · JS
HTML
<div class="we-bg-particles">

    <div class="we-bg-particles-field" aria-hidden="true"></div>

    <div class="we-bg-particles-content">
        <span>WEBELEMENTS</span>
        <h2>Lebegő világ</h2>
        <p>
            Finom mozgás, amely életet ad a teljes háttérnek.
        </p>
    </div>

</div>
CSS
.we-bg-particles {
    position: relative;

    width: 100%;
    min-height: 420px;

    overflow: hidden;

    background:
        radial-gradient(
            circle at 50% 50%,
            #17251f 0%,
            #0b0f19 62%,
            #080b11 100%
        );

    display: flex;
    align-items: center;
    justify-content: center;

    isolation: isolate;
}

.we-bg-particles-field {
    position: absolute;
    inset: -15%;

    pointer-events: none;

    background-image:
        radial-gradient(circle, rgba(122, 201, 142, .75) 1px, transparent 1.5px),
        radial-gradient(circle, rgba(244, 241, 233, .42) 1px, transparent 1.5px),
        radial-gradient(circle, rgba(95, 189, 125, .5) 1px, transparent 1.5px);

    background-size:
        85px 95px,
        145px 125px,
        210px 180px;

    background-position:
        0 0,
        35px 60px,
        90px 20px;

    opacity: .45;

    animation:
        weParticlesDrift 24s linear infinite;

    transition:
        transform 1.2s cubic-bezier(.22, 1, .36, 1);
}

.we-bg-particles-field::before,
.we-bg-particles-field::after {
    content: "";

    position: absolute;
    inset: 0;

    background-image:
        radial-gradient(circle, rgba(122, 201, 142, .6) 1px, transparent 1.5px);

    background-size: 175px 155px;

    opacity: .35;
}

.we-bg-particles-field::before {
    transform: translate(55px, -30px);
    animation: weParticlesLayerOne 19s linear infinite;
}

.we-bg-particles-field::after {
    transform: translate(-70px, 45px);
    opacity: .22;
    animation: weParticlesLayerTwo 31s linear infinite reverse;
}

.we-bg-particles-content {
    position: relative;
    z-index: 2;

    max-width: 620px;

    padding: 45px;

    text-align: center;

    color: #f4f1e9;
}

.we-bg-particles-content span {
    display: block;

    margin-bottom: 16px;

    color: #7ac98e;

    font-family: Inter, system-ui, sans-serif;
    font-size: 10px;
    font-weight: 700;
    letter-spacing: .2em;
}

.we-bg-particles-content h2 {
    margin: 0 0 14px;

    font-family: "Bodoni Moda", Georgia, serif;
    font-size: clamp(40px, 7vw, 72px);
    font-weight: 500;
    line-height: 1;
}

.we-bg-particles-content p {
    margin: 0;

    color: rgba(244, 241, 233, .62);

    font-family: Inter, system-ui, sans-serif;
    font-size: 14px;
    line-height: 1.7;
}

@keyframes weParticlesDrift {

    0% {
        transform: translate3d(0, 0, 0);
    }

    50% {
        transform: translate3d(-35px, 22px, 0);
    }

    100% {
        transform: translate3d(0, 0, 0);
    }
}

@keyframes weParticlesLayerOne {

    0% {
        transform: translate(55px, -30px);
    }

    100% {
        transform: translate(-35px, 55px);
    }
}

@keyframes weParticlesLayerTwo {

    0% {
        transform: translate(-70px, 45px);
    }

    100% {
        transform: translate(50px, -35px);
    }
}
JavaScript
document.querySelectorAll(".we-bg-particles").forEach(background => {

    const field = background.querySelector(
        ".we-bg-particles-field"
    );

    background.addEventListener("mousemove", event => {

        const rect = background.getBoundingClientRect();

        const x =
            (event.clientX - rect.left) / rect.width - 0.5;

        const y =
            (event.clientY - rect.top) / rect.height - 0.5;

        field.style.transform = `
            translate3d(
                ${x * 28}px,
                ${y * 20}px,
                0
            )
        `;
    });

    background.addEventListener("mouseleave", () => {

        field.style.transform =
            "translate3d(0, 0, 0)";
    });

});