/* =========================================================
   Centrix Motion
   Site-wide smooth scrolling + text reveal on scroll.
   Behaviour: assets/js/motion.js
   ========================================================= */

:root {
    --cx-motion-ease: cubic-bezier(0.22, 0.61, 0.36, 1);
    --cx-motion-dur: 700ms;
}

/* ---------------------------------------------------------
   1. Smooth scrolling
   ---------------------------------------------------------
   Native scroll-behavior rather than JS: it also covers the
   back button, keyboard navigation and links arriving from
   another page with a #hash, which a click handler cannot.

   scroll-padding-top keeps anchor targets clear of the fixed
   header — without it every in-page link lands underneath it.
   Values track the nav's own py-4 / sm:py-5 / lg:py-6 plus
   the 40px logo. */
html {
    scroll-padding-top: 84px;
}

@media (min-width: 640px) {
    html {
        scroll-padding-top: 92px;
    }
}

@media (min-width: 1024px) {
    html {
        scroll-padding-top: 108px;
    }
}

@media (prefers-reduced-motion: no-preference) {
    html {
        scroll-behavior: smooth;
    }
}

/* ---------------------------------------------------------
   2. Text reveal
   ---------------------------------------------------------
   The hidden state is scoped to html.cx-anim, which motion.js
   only sets when IntersectionObserver exists and the visitor
   has not asked for reduced motion. Without JS the class is
   never added, so text is simply visible — it can never get
   stuck invisible. */
html.cx-anim .cx-r {
    opacity: 0;
    transform: translate3d(0, 16px, 0);
    transition:
        opacity var(--cx-motion-dur) var(--cx-motion-ease) var(--cx-motion-delay, 0ms),
        transform var(--cx-motion-dur) var(--cx-motion-ease) var(--cx-motion-delay, 0ms);
}

/* Headings travel a little further and settle a little slower —
   the difference is what stops a section reading as one flat slab. */
html.cx-anim .cx-r--head {
    transform: translate3d(0, 24px, 0);
    --cx-motion-dur: 820ms;
}

/* Media reveals with a whisper of scale so it feels like it
   settles into place rather than sliding. */
html.cx-anim .cx-r--media {
    transform: translate3d(0, 20px, 0) scale(0.985);
    transform-origin: center;
}

html.cx-anim .cx-r.cx-in {
    opacity: 1;
    transform: none;
}

/* Only hint the compositor while an element is actually in flight. */
html.cx-anim .cx-r:not(.cx-in) {
    will-change: opacity, transform;
}

html.cx-anim .cx-r.cx-in {
    will-change: auto;
}

/* Safety net: if scripting dies after the class is set, this rule
   is switched on by motion.js's fallback timer. */
html.cx-anim.cx-anim-off .cx-r {
    opacity: 1 !important;
    transform: none !important;
    transition: none !important;
}

@media (prefers-reduced-motion: reduce) {
    html {
        scroll-behavior: auto;
    }

    html.cx-anim .cx-r {
        opacity: 1 !important;
        transform: none !important;
        transition: none !important;
    }
}

/* ---------------------------------------------------------
   3. Hero entrance
   ---------------------------------------------------------
   The same staggered fade-up the homepage hero has always used
   (see front-page.php's .fp-hero__* / @keyframes heroFadeUp),
   generalised so every other template's hero can opt in with a
   handful of class names instead of a bespoke keyframe per page.

   This plays immediately on load rather than waiting on a scroll
   trigger — correct for hero content, since it is above the fold
   by definition. Runs unconditionally (no html.cx-anim gate): a
   hero that never animates because JS was slow to add a class is
   a worse first impression than one that always plays once. */
@keyframes cxHeroFadeUp {
    from {
        opacity: 0;
        transform: translate3d(0, 24px, 0);
    }

    to {
        opacity: 1;
        transform: translate3d(0, 0, 0);
    }
}

.cx-hero__label,
.cx-hero__h1,
.cx-hero__desc,
.cx-hero__ctas,
.cx-hero__media {
    animation: cxHeroFadeUp 0.7s ease-out both;
}

.cx-hero__label {
    animation-delay: 0.15s;
}

.cx-hero__h1 {
    animation-delay: 0.3s;
}

.cx-hero__desc {
    animation-delay: 0.45s;
}

.cx-hero__media {
    animation-delay: 0.4s;
    animation-duration: 0.8s;
}

.cx-hero__ctas {
    animation-delay: 0.6s;
}

@media (prefers-reduced-motion: reduce) {

    .cx-hero__label,
    .cx-hero__h1,
    .cx-hero__desc,
    .cx-hero__ctas,
    .cx-hero__media {
        animation: none;
        opacity: 1;
        transform: none;
    }
}
