/*
 * Animations
 * ─────────────────────────────────────────────────────────────────────────────
 * All animations are opt-in via data attributes set by animations.js.
 * Elements are invisible until the JS adds the [data-msk-visible] attribute.
 * If JS fails or is blocked, elements remain visible (no content is hidden).
 *
 * Usage in block editor: add class "msk-animate-[type]" to any block.
 * The JS finds these, marks them as ready, then adds data-msk-visible
 * when they enter the viewport.
 *
 * Available animation classes:
 *   .msk-animate-fade-up    — fade in and rise from below
 *   .msk-animate-fade-in    — fade in only
 *   .msk-animate-slide-left — slide in from left
 *   .msk-animate-slide-right — slide in from right
 *   .msk-animate-scale-up  — scale from 95% to 100%
 *   .msk-animate-stagger    — children animate in sequence (add to parent)
 *
 * All respect prefers-reduced-motion.
 * ─────────────────────────────────────────────────────────────────────────────
 */


/* ── Keyframes ──────────────────────────────────────────────────────────── */

@keyframes msk-fade-up {
    from {
        opacity: 0;
        transform: translateY(24px);
    }
    to {
        opacity: 1;
        transform: translateY(0);
    }
}

@keyframes msk-fade-in {
    from { opacity: 0; }
    to   { opacity: 1; }
}

@keyframes msk-slide-left {
    from {
        opacity: 0;
        transform: translateX(-32px);
    }
    to {
        opacity: 1;
        transform: translateX(0);
    }
}

@keyframes msk-slide-right {
    from {
        opacity: 0;
        transform: translateX(32px);
    }
    to {
        opacity: 1;
        transform: translateX(0);
    }
}

@keyframes msk-scale-up {
    from {
        opacity: 0;
        transform: scale(0.95);
    }
    to {
        opacity: 1;
        transform: scale(1);
    }
}

/* ── Ready State ─────────────────────────────────────────────────────────
 * JS adds [data-msk-ready] to indicate the element is enrolled.
 * Before visible, hold at starting state.
 */

[data-msk-ready].msk-animate-fade-up,
[data-msk-ready].msk-animate-fade-in,
[data-msk-ready].msk-animate-slide-left,
[data-msk-ready].msk-animate-slide-right,
[data-msk-ready].msk-animate-scale-up {
    opacity: 0;
}

/* ── Visible State ───────────────────────────────────────────────────────
 * JS adds [data-msk-visible] when element enters viewport.
 */

[data-msk-visible].msk-animate-fade-up {
    animation: msk-fade-up var(--msk-duration-slower) var(--msk-ease-out) both;
}

[data-msk-visible].msk-animate-fade-in {
    animation: msk-fade-in var(--msk-duration-slower) var(--msk-ease-out) both;
}

[data-msk-visible].msk-animate-slide-left {
    animation: msk-slide-left var(--msk-duration-slower) var(--msk-ease-out) both;
}

[data-msk-visible].msk-animate-slide-right {
    animation: msk-slide-right var(--msk-duration-slower) var(--msk-ease-out) both;
}

[data-msk-visible].msk-animate-scale-up {
    animation: msk-scale-up var(--msk-duration-slow) var(--msk-ease-spring) both;
}

/* ── Staggered Children ──────────────────────────────────────────────────
 * Add .msk-animate-stagger to a parent. Each direct child gets
 * an increasing animation-delay applied by JS via --msk-stagger-index.
 */

.msk-animate-stagger > * {
    animation-delay: calc(var(--msk-stagger-index, 0) * 80ms);
}

/* ── Hero Entrance ───────────────────────────────────────────────────────
 * Special case: fires on load, not scroll. No JS needed.
 * Add class to a Cover or Group block.
 */

.msk-hero-entrance {
    animation: msk-fade-up var(--msk-duration-slower) var(--msk-ease-out) 100ms both;
}

.msk-hero-entrance > * + * {
    animation: msk-fade-up var(--msk-duration-slower) var(--msk-ease-out) 250ms both;
}

/* ── Reduced Motion ──────────────────────────────────────────────────────
 * All animation is cancelled. Elements remain visible.
 * This must be last so it overrides all above.
 */

@media (prefers-reduced-motion: reduce) {
    [data-msk-ready],
    [data-msk-visible],
    .msk-hero-entrance,
    .msk-hero-entrance > * + * {
        animation: none;
        opacity: 1;
        transform: none;
    }
}
