/* ==========================================================================
   Launch Labs — Hero -> Section 2 transition
   Hero is pinned via CSS `position: sticky` — NOT a JS-driven pin — while
   an enormous beige circle rises from below to cover it. Purely additive:
   hero's own markup/CSS/behaviour (css/hero.css, js/hero.js) is completely
   untouched. This file only wraps hero with new elements and positions
   them; delete this file, js/hero-transition.js, and the wrapper markup
   in index.html to fully revert with zero impact on hero itself.

   Mechanism: .hero-transition is a tall (200vh) wrapper. Only .hero
   itself is `position: sticky; top: 0;` inside it — no JS pin, no
   spacer, nothing to release manually: once the visitor scrolls past
   its own height's worth of scroll, it naturally resumes normal
   document flow and ordinary scrolling continues.
   .hero-transition__arch (holding the circle) is deliberately NOT
   sticky — it's a plain block sitting right after .hero, so for as
   long as .hero is pinned, .arch scrolls into view from below under
   ordinary page scroll; js/hero-transition.js layers a translateY
   animation on top of that, scrubbed to the wrapper's scroll progress.
   Once .hero unsticks, .arch (having never been sticky) just keeps
   scrolling away immediately like any normal element — no independent
   hold, no dead zone before the next section appears.
   ========================================================================== */

.hero-transition {
  position: relative;
  height: 200vh;

  /* --ht-size: the circle's diameter. Kept just a little over the
     viewport width so the top reads as a clear rising DOME (a curve),
     not a flat horizontal edge — and so the beige only reaches the
     left/right screen edges once the circle's widest part actually gets
     there, never as a horizontal band before that. Too large (e.g.
     175vw) flattens the apex into a horizontal line rising from the
     bottom; too small (under 100vw) never reaches the edges at all.
     --ht-lead-top: where the rising heading rests once the circle is
     fully up (distance from the circle's top edge, viewport-relative).
     Pair it with the scrollTrigger range in js/hero-transition.js to
     control WHEN the heading fades in during the fill. */
  --ht-size: 110vw;
  --ht-lead-top: calc(24vh + 200px);
  /* Height reserved for the (now sticky) nav — the logo box plus its top/bottom
     padding (generous top padding gives the logo breathing room from the very
     top edge). The negative margin on the nav uses this same value, so the hero
     overlay and the arch timing stay correct as it changes. */
  --ll-nav-h: calc(clamp(100px, 10.8vw, 124px) + 40px + 0.6rem);
}

.hero-transition .hero {
  position: sticky;
  top: 0;
}

/* Nav is a sticky child of this wrapper (moved in via index.html) so it holds
   in place while the rising circle covers it, then releases with the wrapper
   afterwards — instead of scrolling away first. z-index sits BELOW the circle
   (.hero-transition__arch is z-index 5) so the white comes up OVER the logo.
   The negative margin removes the nav's flow height so it OVERLAYS the hero
   rather than pushing it (and the rising arch) down: the hero sits at top:0
   from scroll 0 (no slide) AND the arch keeps its original timing. The hero's
   content is vertically centred, so the nav never overlaps it. */
.hero-transition .nav {
  position: sticky;
  top: 0;
  z-index: 4;
  height: var(--ll-nav-h);
  margin-bottom: calc(-1 * var(--ll-nav-h));
}

/* Deliberately NOT position: sticky. While .hero is pinned, this box
   sits directly below it in normal flow and scrolls into view from
   the bottom under ordinary page scroll — that natural scroll motion
   IS the "arch rising from below" effect; js/hero-transition.js's
   translateY animation is layered on top of it, not the sole source
   of the rise. position: relative is kept only so it remains the
   containing block for its absolutely-positioned children (the
   circle and panel), sized to exactly one viewport height so the
   circle's `top: 100%` starts precisely at the fold. Because it's
   never sticky, once .hero unsticks this box simply continues
   scrolling away immediately with no independent hold — no dead
   zone before .hub appears. Its one absolutely-positioned child is the
   circle. */
.hero-transition__arch {
  position: relative;
  height: 100vh;
  z-index: 5;
  overflow: hidden;
  pointer-events: none;
}

/* Highest point starts exactly at the arch's own bottom edge (100%
   down a 100vh box, i.e. the viewport's bottom edge) — nothing visible
   at page load. js/hero-transition.js animates translateY only, scrubbed
   to scroll progress; translateX(-50%) here keeps it horizontally
   centred throughout (GSAP preserves it when it takes over translateY). */
.hero-transition__circle {
  position: absolute;
  left: 50%;
  top: 100%;
  width: var(--ht-size);
  height: var(--ht-size);
  border-radius: 50%;
  background: #f2f0eb;
  transform: translateX(-50%);
}

/* ---------- Continuation panel — a plain, full-width beige rectangle
   anchored at the circle's own equator (top: 50% of the circle's own box),
   a child of the circle so it inherits its translateY. On landscape it is
   effectively invisible (beige tucked inside/below the round disc); its real
   job is TALL/portrait viewports, where the disc's own height (--ht-size,
   i.e. 110% of the WIDTH) is far shorter than the screen — without this the
   area below the disc would be an empty gap. It is NOT the horizontal beige
   band you can see during the rise (that is the .hub section's own flat top
   edge, dragged up over the circle by its margin-top — see css/hub.css). ---------- */
.hero-transition__panel {
  position: absolute;
  top: 50%;
  left: 50%;
  width: var(--ht-size);
  height: 300vh;
  background: #f2f0eb;
  transform: translateX(-50%);
  z-index: 0;
}

/* ---------- Rising heading — the "Your website is the hub…" title,
   revealed about half-way through the fill and riding UP with the
   circle (it's a child of the circle, so it inherits the circle's
   translateY automatically — no extra sync needed). Kept aria-hidden
   via the arch above; the accessible copy still lives in .hub, shown to
   screen readers and to reduced-motion / no-JS users, and hidden
   visually for motion users by `html.ht-on .hub__heading` below so the
   text is never duplicated on screen. Position is set by --ht-lead-top;
   the fade-in timing is the scrollTrigger range in
   js/hero-transition.js. ---------- */
/* The single moving title. Now position:fixed and OUTSIDE the clipped, scrolling
   arch, so it can travel the whole way (big upper-middle entrance -> small at the
   top) and hold there while the .hub graphic reveals below. GSAP owns its full
   transform (xPercent -50 centring + y + scale); js/hero-transition.js drives the
   journey and js/hub-zoom.js fades it out at the zoom hand-off. */
.hero-transition__lead {
  position: fixed;
  top: 0;
  left: 50%;
  /* Wide enough that a line stays on one line at the big font size. */
  width: min(96vw, 86rem);
  text-align: center;
  opacity: 0;
  z-index: 20;
  pointer-events: none;
  will-change: transform, opacity;
}

.hero-transition__lead-heading {
  margin: 0;
  font-family: 'Plus Jakarta Sans', sans-serif;
  /* ~double the old size, across three lines (see index.html), so the
     heading fills the circle vertically. Nudge the clamp / --ht-lead-top
     to taste. */
  font-size: clamp(3.2rem, 8vh, 6.4rem);
  font-weight: 700;
  line-height: 1.06;
  letter-spacing: -0.02em;
  color: #0b0a0d;
}

.hero-transition__lead-accent { color: #D92632; }

/* Live animated transition (motion + GSAP): the rising disc overlay carries the
   big title ENTRANCE. The real .hub heading then takes over as the small resting
   title at the top of the pinned hub composition (js/hub-zoom.js reveals it, has
   it shrink into place, then the graphic appears below it). We keep its layout
   slot reserved (visibility, not display) so the composition never reflows when
   it appears, and js/hub-zoom.js owns its visibility from load. Reduced-motion /
   no-JS users never get ht-on, so they keep the real .hub heading as normal. */
html.ht-on .hub__heading { visibility: hidden; }

/* --- Rising-disc masking (issue: a flat white edge beside the disc). During
   the animated transition the hub section's OWN rectangular white background
   must not show — its straight top edge reads as a horizontal white band next
   to the rising disc (the hub moves on raw scroll while the disc is scrub-
   lagged, so the hub's edge outruns the disc's white). Keep the hub transparent
   so the ONLY white on screen is the disc mask; js/hero-transition.js adds
   .is-covered once the disc has actually risen far enough to cover the viewport
   width, at which point the normal solid white takes over seamlessly (white
   over white). Reduced-motion / no-JS users never get ht-on, so they keep the
   solid background. Purely paint — no layout/geometry change. --- */
html.ht-on .hub { background: transparent; }
html.ht-on .hub.is-covered { background: #f2f0eb; }

/* --- Reveal order (issue: diagram appears before heading). The hub's own
   entrance (css/hub.css `hub-fly`) fades the diagram in the moment the section
   intersects, which — with the raised overlap — is before the disc heading.
   Neutralise that entrance here so js/hero-transition.js can fade the diagram
   in on the transition timeline, staggered AFTER the heading. `transform:none`
   holds the diagram at its settled position (no geometry change) at ALL times in
   this mode so it can't snap when .is-visible toggles; the .is-visible-scoped
   rule only cancels the `hub-fly` entrance animation (specificity must beat it).
   GSAP owns the opacity. --- */
html.ht-on .hub__diagram { transform: none; }
html.ht-on .hub.is-visible .hub__diagram { animation: none; }

@media (prefers-reduced-motion: reduce) {
  .hero-transition {
    height: auto;
  }

  .hero-transition .hero {
    position: relative;
    top: auto; /* don't offset it once it's back in normal flow */
  }

  /* Back to normal flow: nav above the hero, no overlay. */
  .hero-transition .nav {
    position: relative;
    margin-bottom: 0;
  }

  /* The circle is purely decorative now (its content lives in the
     normal-flow .hub section below, see index.html/css/hub.css), so
     under reduced motion it can simply collapse away rather than
     needing a static-block fallback of its own. */
  .hero-transition__arch {
    display: none;
  }

  /* The fixed moving title is a JS-driven effect; with no motion, the real
     .hub heading (shown normally, since ht-on is never added) is the title. */
  .hero-transition__lead {
    display: none;
  }

  /* .hero-transition__circle and .hero-transition__panel need no
     reduced-motion override of their own: they're purely decorative
     children of .hero-transition__arch, which is already hidden above. */
}
