/* ============================================================================
   landing.css — SOL DEAL scroll-world DOM layer (ANIMATION_SPEC §8B)
   The ONE CSS override file. Loaded after the engine; every rule here is
   UNLAYERED so it beats the engine's `@layer sw` defaults regardless of order.
   Engine scrub loop is never touched — this only restyles + adds the calm layer.

   Round 2 (chrome strip + cinematic copy): ALL chrome removed — top bar
   (brand + nav chips), right route rail, slide counter, tag pills. Copy is now a
   centered full-stage typographic moment over a full-viewport dimming vignette
   that RIDES the engine's per-section opacity. KEPT: top 3px .sw-scrollbar +
   the .sw-hint scroll cue (the only progress affordances left).
   ========================================================================== */

/* ---- self-hosted type (owner directive #1): Teko display + Saira body ---- */
@font-face{font-family:'Teko';src:url('fonts/teko-latin.woff2') format('woff2');font-weight:300 700;font-display:swap;}
@font-face{font-family:'Saira';src:url('fonts/saira-latin.woff2') format('woff2');font-weight:300 900;font-display:swap;}

/* ---- tokens (ANIMATION_SPEC shared tokens) + dark arena theme ---- */
:root, .sw-root{
  --ease-out:    cubic-bezier(0.23, 1, 0.32, 1);   /* UI enter/exit + press/hover */
  --ease-in-out: cubic-bezier(0.77, 0, 0.175, 1);  /* reserved */
  --dur-press: 110ms;  --dur-ui: 200ms;  --dur-enter: 300ms;
  --sd-gold: #F5C451;                               /* Validator-League game gold */

  --sw-bg:#05070E;            /* deep arena black-blue == poster/scene background */
  --sw-ink:#F2F6FF;
  --sw-ink-soft:#93A0C0;
  --sw-accent:#00E5D0;        /* per-section accents override this at runtime */
  --sw-font-display:'Teko',ui-sans-serif,system-ui,sans-serif;
  --sw-font-body:'Saira',ui-sans-serif,system-ui,sans-serif;
}

/* ---- §0 chrome strip (round-2 owner call): the film runs clean ----
   nav:false + no brand config already empty the top bar; these belt-and-braces
   hide what the engine still builds. Engine's left copy-scrim is also killed so
   the flight is never boxed in. */
.sw-topbar{display:none;}                /* brand link + nav chips */
.sw-route{display:none;}                 /* right dot rail (engine still toggles
                                            its .is-active — cards still deal in) */
.sw-copy__num{display:none;}             /* "01 / 08" slide counter */
.sw-copylayer::before{content:none;}     /* remove the engine's static left scrim */

/* ---- §1 cinematic copy stage — full-viewport centered typographic moment ----
   The engine writes inline opacity + a small translateY on .sw-copy each frame:
   opacity peaks at each section's linger settle; the drift reads as gentle motion.
   NEVER position via CSS transform (inline transform would win); centering is the
   inset:0 + flex trick, so the engine drift stays intact. */
.sw-copy{position:absolute;inset:0;width:auto;max-width:none;
  display:flex;flex-direction:column;justify-content:center;align-items:center;
  text-align:center;padding:clamp(24px,6vw,80px);box-sizing:border-box;}

/* Full-viewport dimming vignette that RIDES the engine opacity. A position:fixed
   child of the (inline-)transformed .sw-copy resolves to the copy box — which is
   now the whole viewport — so inset:0 fills the screen. z-index:-1 keeps it behind
   the words. The world falls dark for the settle frame, the centre stays glowing
   through, then it lifts as the flight resumes. */
.sw-copy::before{content:"";position:fixed;inset:0;z-index:-1;pointer-events:none;
  background:radial-gradient(125% 125% at 50% 50%,
    rgba(5,7,14,.55) 0%, rgba(5,7,14,.72) 46%, rgba(5,7,14,.90) 100%);}

/* eyebrow — Saira 600, wide-tracked gold, flanked by twin 28px gold rules */
.sw-copy__eyebrow{font-family:var(--sw-font-body);font-weight:600;color:var(--sd-gold);
  font-size:clamp(.72rem,1vw,.82rem);letter-spacing:.3em;text-transform:uppercase;
  display:flex;align-items:center;justify-content:center;gap:14px;margin:0;}
.sw-copy__eyebrow::before,.sw-copy__eyebrow::after{content:"";flex:0 0 auto;
  width:28px;height:2px;background:var(--sd-gold);}

/* title — Teko, poster-scale, tight leading, subtle per-section accent glow */
.sw-copy__title{font-family:var(--sw-font-display);font-weight:600;text-transform:uppercase;
  line-height:.9;letter-spacing:.005em;font-size:clamp(3rem,7.5vw,6.5rem);
  color:var(--sw-ink);margin:clamp(14px,2.2vh,26px) 0 0;
  text-shadow:0 2px 30px color-mix(in srgb, var(--sw-accent) 34%, transparent), 0 1px 3px rgba(0,0,0,.6);}
.sw-copy__title .sw-lastword{color:var(--sw-accent);}   /* accent kicker (enhance.js) */

/* body — Saira light, editorial measure, centered */
.sw-copy__body{font-family:var(--sw-font-body);font-weight:400;color:#C9D4EC;
  font-size:clamp(1.05rem,1.4vw,1.3rem);line-height:1.7;max-width:56ch;
  margin:clamp(16px,2.6vh,30px) auto 0;text-shadow:0 1px 12px rgba(0,0,0,.65);}

/* ---- §2 card overlay layer: own fixed layer, time-based seam crossfade + deal-in ---- */
.sw-cardlayer{position:fixed;inset:0;z-index:20;pointer-events:none;}
.sw-cards{position:absolute;right:clamp(18px,5vw,72px);bottom:clamp(20px,7vh,72px);
  display:flex;align-items:flex-end;opacity:0;transition:opacity var(--dur-enter) var(--ease-out);}
.sw-cards.is-in{opacity:1;}
.sw-card{width:clamp(76px,9vw,128px);aspect-ratio:5/7;border-radius:8px;object-fit:cover;display:block;
  margin-left:-30px;position:relative;transform-origin:bottom center;
  transform:translateY(var(--lift,0px)) rotate(var(--rot,0deg));   /* --lift: held-fan arc, set per card in JS */
  filter:drop-shadow(0 10px 24px rgba(0,0,0,.5));}   /* shadow STATIC, never animated */
.sw-card:first-child{margin-left:0;}
@keyframes sw-card-in{from{opacity:0;transform:translateY(calc(var(--lift,0px) + 46px)) rotate(calc(var(--rot,0deg)*0.3)) scale(.92);}
  to{opacity:1;transform:translateY(var(--lift,0px)) rotate(var(--rot,0deg)) scale(1);}}
.sw-cards.is-in .sw-card{animation:sw-card-in 560ms var(--ease-out) both;animation-delay:calc(var(--i,0)*80ms);will-change:transform;}
/* Mobile ≤860px: copy owns the bottom band, the film carries the card action → hide overlays. */
@media (max-width:860px){ .sw-cardlayer{display:none;} }

/* ---- §3 CTA "Enter Arena": physical — resting shadow + hover-lift + press-scale + focus ring ---- */
.sw-btn--primary{background:var(--sd-gold);color:#0b0b12;font-family:var(--sw-font-body);font-weight:700;letter-spacing:.02em;
  padding:15px 30px;box-shadow:0 8px 24px rgba(0,0,0,.35), inset 0 1px 0 rgba(255,255,255,.18);
  transition:transform 160ms var(--ease-out), box-shadow 160ms var(--ease-out);}
@media (hover:hover) and (pointer:fine){
  .sw-btn--primary:hover{transform:translateY(-2px);box-shadow:0 12px 32px rgba(0,0,0,.45);}
}
.sw-btn:active{transform:scale(0.97);transition:transform var(--dur-press) ease-out;}   /* scale wins over hover lift */
.sw-btn:focus-visible{outline:none;
  box-shadow:0 0 0 3px color-mix(in srgb, var(--sd-gold) 60%, transparent), 0 8px 24px rgba(0,0,0,.35);}

/* ---- §5 hero (S1) landing one-shot — the one time-based reveal, plays on mount ---- */
@keyframes sw-hero-line{from{opacity:0;transform:translateY(12px);} to{opacity:1;transform:translateY(0);}}
@keyframes sw-rule{from{transform:scaleX(0);} to{transform:scaleX(1);}}
@keyframes sw-fade{from{opacity:0;} to{opacity:1;}}
@keyframes sw-hint-in{from{opacity:0;transform:translateX(-50%) translateY(8px);} to{opacity:1;transform:translateX(-50%) translateY(0);}}
.sw-copy--hero > *{animation:sw-hero-line 500ms var(--ease-out) both;will-change:transform,opacity;}
.sw-copy--hero > .sw-copy__eyebrow{animation-delay:60ms;}
.sw-copy--hero > .sw-copy__title{animation-delay:140ms;}
.sw-copy--hero > .sw-copy__body{animation-delay:220ms;}
.sw-copy--hero .sw-copy__eyebrow::before,
.sw-copy--hero .sw-copy__eyebrow::after{animation:sw-rule 400ms var(--ease-out) 140ms both;}
/* hint: backwards fill so after the intro the engine's scroll-driven opacity takes back over */
.sw-hint{animation:sw-hint-in 500ms var(--ease-out) 360ms backwards;}

/* ---- §6 mobile ≤860px: copy bottom-anchored (clear of the home indicator),
   text still centered, vignette biased toward the bottom band ---- */
@media (max-width:860px){
  .sw-copy{justify-content:flex-end;
    padding:clamp(20px,6vw,40px);
    padding-bottom:calc(clamp(56px,12dvh,110px) + env(safe-area-inset-bottom));}
  .sw-copy__title{font-size:clamp(2.2rem,9vw,3rem);}
  .sw-copy__body{max-width:52ch;font-size:clamp(1rem,3.4vw,1.15rem);}
  .sw-copy::before{background:radial-gradient(130% 95% at 50% 82%,
    rgba(5,7,14,.5) 0%, rgba(5,7,14,.80) 58%, rgba(5,7,14,.94) 100%);}
  /* Hero only: its 4-line body is the longest and the scroll hint sits at full opacity
     beneath it at landing — extra clearance stops the measured 23px collision. */
  .sw-copy--hero{padding-bottom:calc(clamp(56px,12dvh,110px) + env(safe-area-inset-bottom) + 48px);}
}

/* ---- §8 FINALE — one-shot end card (round-2 owner: "explosion + 3 complete sets + announce
   the ending better"). Fixed overlay above the card layer (z 25); hidden until
   landing-enhance.js adds .is-live at the end of section 8's scroll. pointer-events:none
   except the CTA. The engine holds S8's own .sw-copy at full opacity to the very end, so
   the JS cedes it (visibility:hidden — engine writes opacity, not visibility, so plain
   visibility wins with no !important). ---- */
.sw-copy.is-ceded{visibility:hidden;}
.sw-cardlayer{transition:opacity 200ms var(--ease-out);}
.sw-cardlayer.is-dim{opacity:0;}   /* S8's corner fan ghosts through the finale backdrop otherwise */

/* ---- §9 sound toggle — the page's ONE piece of chrome (round 4: scene-fitted soundtrack).
   Glass circle top-right; speaker waves show when playing, slash when muted. Static — no
   pulse (§6); press/focus physics match the CTA grammar. ---- */
.sw-sound{position:fixed;top:clamp(14px,2.4vw,24px);right:clamp(16px,3vw,32px);z-index:55;
  width:44px;height:44px;display:grid;place-items:center;border-radius:50%;cursor:pointer;
  color:var(--sw-ink);background:rgba(5,7,14,.45);border:1px solid rgba(242,246,255,.18);
  backdrop-filter:blur(8px);-webkit-backdrop-filter:blur(8px);
  transition:border-color var(--dur-ui) var(--ease-out), color var(--dur-ui) var(--ease-out);}
.sw-sound .sw-sound__wave{display:none;}
.sw-sound.is-on .sw-sound__wave{display:block;}
.sw-sound.is-on .sw-sound__slash{display:none;}
.sw-sound.is-on{color:var(--sd-gold);border-color:color-mix(in srgb, var(--sd-gold) 45%, transparent);}
.sw-sound.is-err{display:none;}    /* decode/fetch failed → no dead control */
@media (hover:hover) and (pointer:fine){ .sw-sound:hover{border-color:color-mix(in srgb, var(--sd-gold) 60%, transparent);} }
.sw-sound:active{transform:scale(0.94);transition:transform var(--dur-press) ease-out;}
.sw-sound:focus-visible{outline:none;box-shadow:0 0 0 3px color-mix(in srgb, var(--sd-gold) 60%, transparent);}

/* visibility:hidden (not aria-hidden) keeps the pre-fire finale out of the a11y tree while
   letting the announcement + CTA be announced once live; the 0s/200ms visibility transition
   gives a clean fade-out when the visitor scrolls back up past the trigger. */
.sw-finale{position:fixed;inset:0;z-index:25;pointer-events:none;opacity:0;visibility:hidden;
  display:flex;flex-direction:column;justify-content:center;align-items:center;text-align:center;
  padding:clamp(24px,6vw,80px);box-sizing:border-box;
  background:radial-gradient(120% 120% at 50% 46%,
    rgba(5,7,14,.60) 0%, rgba(5,7,14,.82) 52%, rgba(5,7,14,.95) 100%);
  transition:opacity 200ms var(--ease-out), visibility 0s 200ms;}
.sw-finale.is-live{opacity:1;visibility:visible;transition:opacity 200ms var(--ease-out);}
.sw-finale__burst{position:absolute;inset:0;width:100%;height:100%;pointer-events:none;z-index:1;}
.sw-finale__inner{position:relative;z-index:2;display:flex;flex-direction:column;align-items:center;
  gap:clamp(18px,3vh,34px);max-width:min(96vw,1200px);}   /* wide enough for 3 fans side-by-side >640px */

/* announcement — Teko, poster-huge, gold-glow */
.sw-finale__title{font-family:var(--sw-font-display);font-weight:600;text-transform:uppercase;
  line-height:.86;letter-spacing:.01em;font-size:clamp(3.4rem,12vw,9rem);color:var(--sw-ink);margin:0;
  text-shadow:0 2px 44px color-mix(in srgb, var(--sd-gold) 44%, transparent), 0 1px 4px rgba(0,0,0,.6);}

/* three complete property sets — three held fans (reuse the .sw-card look, own elements) */
.sw-finale__sets{display:flex;justify-content:center;align-items:flex-start;
  gap:clamp(22px,4vw,64px);flex-wrap:wrap;}
.sw-finale__set{display:flex;align-items:flex-end;}
.sw-finale__card{width:clamp(70px,9vw,130px);aspect-ratio:5/7;border-radius:8px;object-fit:cover;display:block;
  margin-left:-30px;transform-origin:bottom center;transform:rotate(var(--rot,0deg));
  filter:drop-shadow(0 12px 26px rgba(0,0,0,.55));}   /* shadow STATIC */
.sw-finale__card:first-child{margin-left:0;}

/* CTA — reuse .sw-btn--primary physics + a slow gold pulse-glow (owner-requested finale exception
   to the §6 no-pulse rule; single element, box-shadow only) */
.sw-finale__cta{pointer-events:auto;margin-top:clamp(6px,1.5vh,16px);font-size:1.05rem;padding:16px 34px;}

/* choreography (added by .is-live): sets slam in staggered → announcement → CTA rises last */
@keyframes sw-set-slam{from{opacity:0;transform:translateY(-14px) scale(1.15);} to{opacity:1;transform:translateY(0) scale(1);}}
@keyframes sw-announce{from{opacity:0;transform:scale(.9);} to{opacity:1;transform:scale(1);}}
@keyframes sw-cta-rise{from{opacity:0;transform:translateY(18px);} to{opacity:1;transform:translateY(0);}}
@keyframes sw-cta-glow{
  0%,100%{box-shadow:0 8px 24px rgba(0,0,0,.35), inset 0 1px 0 rgba(255,255,255,.18), 0 0 0 0 rgba(245,196,81,0);}
  50%   {box-shadow:0 8px 28px rgba(0,0,0,.42), inset 0 1px 0 rgba(255,255,255,.18), 0 0 34px 6px rgba(245,196,81,.55);}}
/* rest state (before is-live): everything hidden so the entrance reads */
.sw-finale__eyebrow,.sw-finale__title,.sw-finale__set,.sw-finale__cta{opacity:0;}
.sw-finale.is-live .sw-finale__set{animation:sw-set-slam 420ms var(--ease-out) both;will-change:transform,opacity;}
.sw-finale.is-live .sw-finale__set:nth-child(1){animation-delay:0ms;}
.sw-finale.is-live .sw-finale__set:nth-child(2){animation-delay:140ms;}
.sw-finale.is-live .sw-finale__set:nth-child(3){animation-delay:280ms;}
.sw-finale.is-live .sw-finale__eyebrow,
.sw-finale.is-live .sw-finale__title{animation:sw-announce 500ms var(--ease-out) 420ms both;will-change:transform,opacity;}
.sw-finale.is-live .sw-finale__cta{animation:sw-cta-rise 460ms var(--ease-out) 900ms both,
  sw-cta-glow 2.6s ease-in-out 1400ms infinite;will-change:transform,opacity;}

/* finale mobile: fans stack vertically ≤640px, announcement clamps down */
@media (max-width:640px){
  .sw-finale__sets{flex-direction:column;align-items:center;gap:clamp(14px,3vh,26px);}
  .sw-finale__title{font-size:clamp(2.6rem,15vw,4.6rem);}
  .sw-finale__inner{gap:clamp(14px,2.4vh,26px);}
}

/* ---- §7 reduced-motion — complete fallback (each addition degrades to opacity/color).
   The centered stage + vignette are static (no motion), so they need no branch. ---- */
@media (prefers-reduced-motion: reduce){
  .sw-copy--hero > *{animation:sw-fade 200ms ease both;will-change:auto;}
  .sw-copy--hero .sw-copy__eyebrow::before,
  .sw-copy--hero .sw-copy__eyebrow::after{animation:none;}   /* static bars */
  .sw-hint{animation:none;}
  .sw-cards{transition:opacity 200ms ease;}
  .sw-cards.is-in .sw-card{animation:none;}          /* appears at rest fan */
  .sw-btn--primary:hover{transform:none;}            /* drop lift; keep :active scale + focus ring */
  /* finale: no slam, no glow, no burst (canvas suppressed in JS) — plain 200ms fade, all at rest */
  .sw-finale.is-live .sw-finale__set,
  .sw-finale.is-live .sw-finale__eyebrow,
  .sw-finale.is-live .sw-finale__title,
  .sw-finale.is-live .sw-finale__cta{animation:none;opacity:1;transform:none;will-change:auto;}
}

/* ---- §10 boot loader (D42 §4): branded gate while the visitor's film tier warms.
   Painted before the engine mounts (landing-boot.js); the film reveals through a 400ms
   fade. Static bar fill via transform only. ---- */
.sd-boot{position:fixed;inset:0;z-index:100;display:flex;align-items:center;justify-content:center;
  background:#05070E;transition:opacity 400ms var(--ease-out);}
.sd-boot.is-done{opacity:0;pointer-events:none;}
.sd-boot__inner{display:flex;flex-direction:column;align-items:center;gap:18px;width:min(78vw,420px);}
.sd-boot__eyebrow{font-family:var(--sw-font-body);font-weight:600;font-size:.72rem;letter-spacing:.3em;
  color:var(--sd-gold);}
.sd-boot__mark{font-family:var(--sw-font-display);font-weight:600;font-size:clamp(3rem,10vw,4.6rem);
  line-height:.9;letter-spacing:.02em;color:var(--sw-ink);text-transform:uppercase;
  text-shadow:0 2px 30px color-mix(in srgb, #00E5D0 30%, transparent);}
.sd-boot__bar{width:100%;height:3px;background:color-mix(in srgb, var(--sd-gold) 18%, transparent);
  overflow:hidden;}
.sd-boot__fill{display:block;height:100%;width:100%;background:var(--sd-gold);
  transform:scaleX(0);transform-origin:0 50%;transition:transform 160ms linear;}
.sd-boot__hint{font-family:var(--sw-font-body);font-weight:300;font-size:.8rem;letter-spacing:.14em;
  color:var(--sw-ink-soft);text-transform:uppercase;}
.sd-boot__enter{font-family:var(--sw-font-body);font-weight:700;font-size:.95rem;letter-spacing:.02em;
  color:#0b0b12;background:var(--sd-gold);border:0;border-radius:999px;padding:13px 34px;cursor:pointer;
  box-shadow:0 8px 24px rgba(0,0,0,.35), inset 0 1px 0 rgba(255,255,255,.18);
  transition:transform 160ms var(--ease-out);}
.sd-boot__enter:active{transform:scale(0.97);}
.sd-boot__enter:focus-visible{outline:none;
  box-shadow:0 0 0 3px color-mix(in srgb, var(--sd-gold) 60%, transparent), 0 8px 24px rgba(0,0,0,.35);}
