/* KEEP SCROLLING - the scene at the bottom of a page, in its own file.
 *
 * Split out of styles.css on 2026-09-07 so /templates/ can end the way every other page
 * ends (Victor: "packages and templates page are not working still", then picked the
 * Websites form as its destination). That page is STANDALONE - its own inline <style>, no
 * styles.css - and copying the scene onto it would drift the day either copy is touched.
 * ONE definition, loaded by the ten site pages after styles.css and by templates on its own.
 *
 * The .door CARD rules deliberately stayed in styles.css: they are overridden further down
 * that file (the .pkg/.proof-card/.door card treatment), and pulling them into a file that
 * loads LAST inverted that and changed every card on the site. The templates page styles
 * its one door locally instead - see .tdoor there.
 *
 * Variables it needs from the page: --gold --ink --ink-dim --panel --line --bg --ease.
 */

/* ---------- KEEP SCROLLING - the hand-off past the footer ----------
   Built for keepgoing.js (2026-09-05, rebuilt the same day after Victor: "have it actually
   scroll and the box can show the loading with a glow"). The runway is real page after the
   footer; the box rides it on position:sticky, so the reader scrolls the ordinary way and
   the box holds still while it loads. Everything that moves is driven by --kgp, the scroll
   progress through the runway, which keepgoing.js writes on the box - so the animation
   cannot drift from the scroll position: it IS the scroll position. */
/* the hero's scroll cue, re-used: same word, same 1px gold line, same pulse - only the
   hero's absolute positioning is undone */
.scroll-hint.kg-hint, .scroll-hint.kg-inbox { position: static; transform: none; }
.scroll-hint.kg-hint { margin: 20px auto 0; opacity: 0; transform: translateY(6px);
  transition: opacity .5s var(--ease), transform .5s var(--ease); pointer-events: none; }
.scroll-hint.kg-hint.on { opacity: 1; transform: none; }
.scroll-hint.kg-inbox { margin-top: 14px; gap: 8px; }
.scroll-hint.kg-inbox .line { height: 34px; }
.kg-door.full .scroll-hint.kg-inbox { color: var(--gold); }
.kg-door.full .scroll-hint.kg-inbox .line { animation: none; opacity: 1; }

/* NO max-height (2026-09-06). It was 1100px, and the bar is measured over
   runway height MINUS the viewport - so on any window 1100px tall or more that span
   collapsed to a single pixel and the bar snapped from empty to full in one scroll
   tick. 130vh always leaves 30vh of runway to fill, at every window height. */
/* 200vh, not 130 (Victor, 2026-09-06: "a little too easy to scroll on it to the next page
   without having time to read it"). The bar is the scroll, so the runway IS the reading
   time: a full screen of scrolling to fill it, not a third of one. */
/* 110vh (Victor, 2026-09-06: "too big of a huge black screen between the bottom card and
   the end of the actual page"). With the card pinned low, every pixel of runway is blank
   screen ABOVE it while the reader scrolls, so the runway is now only as long as the read
   needs - about two-thirds of a screen of scrolling - and the 900 ms / four-tick dwell
   does the rest of the "no flicking through" work. */
/* 110vh -> 150vh (Victor, 2026-09-07: "put it back the way it was and only change how far
   they have to scroll to go to the next page"). THE DISTANCE IS THE ONLY DIAL for this -
   the bar IS the scroll through the runway, so the runway's height is literally how far he
   has to scroll before the page hands off. A 2026-09-07 attempt to make it harder by
   raising the dwell instead (6 ticks / 1500ms) was reverted the same afternoon: it changed
   how the bottom of the page FELT rather than how far it was, and a page stops emitting
   scroll events at its last pixel, so a longer dwell could strand a full box. The cost of
   this dial is the one he named on 2026-09-06 - every extra pixel of runway is blank screen
   above the pinned card - so 150vh, half a screen more than 110, not the 200 that was too
   much. Change THIS number if it needs to be harder or easier again. */
/* BACK TO 110vh (2026-09-07, Victor: "there is almost an entire page of blank after the
   form on the website before the keep going card" and "just keep them the way they were
   and then just adjust the scroll"). Runway height is BOTH how far he scrolls and how much
   empty screen sits above the pinned card - the same pixels seen two ways - so it can only
   ever be traded, never won: 200vh was "a huge black screen", 150 was tried this afternoon
   for more distance and read as a page of blank. 110 is his own number from 2026-09-06 and
   it stays. The extra difficulty he asked for is carried by the gate instead: a full bar at
   the document's last pixel takes a few more wheel notches to commit. */
.kg-runway { position: relative; height: 110vh; min-height: 640px;
  display: flex; flex-direction: column; justify-content: flex-start; }
/* The stage is the screen MINUS the pinned footer, so the box centres in the space the
   reader can actually see above it (2026-09-06). --kg-foot is set by keepgoing.js. */
/* THE CARD SITS ON THE FOOTER AND LIFTS (Victor, 2026-09-06: "the card should be at the
   bottom of the page and then move up slightly as we scroll down ... I don't want too big
   of a gap at the bottom of the page where it feels like the page ended"). The stage is
   sticky to the BOTTOM edge, just above the pinned footer, and lives at the bottom of the
   runway - so the card surfaces right after the content with no void under it, holds
   there, and the translate below lifts it toward the middle at a fraction of the scroll. */
/* THE FOOTER WAS PAINTING OVER THE CARD (2026-09-07, Victor: "the form at the bottom of
   real estate is not scrolling right"). MEASURED in his own browser, six probe positions
   through the scene: for the first ~600px of the runway the card's bottom sat BELOW the
   pinned footer's top, and the footer is opaque and z-index 2, so the card entered the
   screen half-eaten. The cause was where the stage LIVED: at the bottom of the runway
   (justify-content:flex-end) with sticky bottom, a sticky element cannot be pulled above
   its own containing block, so for the first stretch the card was simply down there,
   under the footer, and the reader got blank screen instead.

   The stage is now a pane the size of the visible band - the screen minus the fixed
   header and minus the pinned footer - sticky to the TOP and sitting at the runway's
   start. The card is aligned to the band's bottom, so it still surfaces sitting on the
   footer exactly as he asked on 2026-09-06, but from the runway's FIRST pixel and never
   behind the footer; the translate below still lifts it toward the middle as --kgp runs. */
.kg-stage { position: sticky; top: var(--kg-head, 0px);
  /* never shorter than the card at its biggest (--kg-stage, keepgoing.js), or on a phone with
     a tall footer the card's bottom ran past the stage and onto the footer (2026-09-30) */
  height: max(calc(100vh - var(--kg-head, 0px) - var(--kg-foot, 0px)), var(--kg-stage, 0px));
  display: flex; align-items: flex-start; justify-content: center;
  pointer-events: none;
  /* ABOVE the pinned footer, not behind it. The footer is opaque and was z-index 2 with
     the stage on auto, so the card rose INTO it and was eaten from the bottom up on the
     way in - measured, three of six positions through the scene. */
  z-index: 3; }
/* THE FOOTER PINS THROUGH THE SCENE (Victor, 2026-09-06: "visible and fixed when they get
   to the bottom of the page"). Sticky to the bottom edge, only within .kg-end - which
   starts where the runway starts - so it rises into view as the scene begins, holds while
   the box fills, and is simply the end of the page once the runway is spent. Opaque, and
   above the stage, so the box's glow never bleeds through the links. */
.kg-end { position: relative; }
.kg-end footer { position: sticky; bottom: 0; z-index: 2; background: var(--bg, #0c0c0c); }
/* THE FOOTER WAITS UNDER THE CARD (2026-09-30, audits fn-keepgoing-* and overlap.js). A sticky
   footer cannot rise above its container's CONTENT box, and the container used to start where
   the runway - and so the card - starts: for the first few hundred pixels of the scene the
   footer pinned on top of the card's lower half (card above it, links showing through).
   .kg-end now carries --kg-lead of top padding that the runway takes straight back with a
   negative margin, so nothing on the page moves, but the footer's content box starts one card
   (plus a gap) lower: it rides up directly under the card and only pins once the card is
   clear of it. --kg-footdrop lets the pinned footer sit lower on a phone too short for both. */
.kg-end { padding-top: var(--kg-lead, 0px); }
.kg-end > .kg-runway { margin-top: calc(-1 * var(--kg-lead, 0px)); }
.kg-end footer { bottom: calc(-1 * var(--kg-footdrop, 0px)); }
/* THE DOOR IS THE BOX (Victor, 2026-09-06: "have the actual card that says keep going
   somehow turn into the thing that gets bigger ... I don't want a separate box below the
   keep going"). keepgoing.js lifts the last section's Keep going card into the stage, so
   this styles THAT card as --kgp runs 0 -> 1: it travels from the top of the stage to the
   middle (--kg-center), its heading grows 23px -> 36px, the gold action line grows and
   brightens, the description fades so the words that matter are the ones getting bigger,
   the border and glow come up, and a bar draws inside it. One element, door to hand-off. */
.kg-runway { --kgp: 0; }   /* set here by keepgoing.js; the stage and the card inherit it */
/* THE CARD HOLDS STILL (2026-09-07). It used to travel up the screen as --kgp ran, which
   is what put it at the BOTTOM of the stage to begin with - and that is what left a screen
   of blank between the end of the page and the card, and slid the card under the pinned
   footer on the way in (both measured on real-estate). It now sits where the page's own
   content ended, from the runway's first pixel, and stays there while the words grow and
   the bar fills. Nothing about the page above it moved. */
.kg-door, .kg-door:hover { transform: none; }
.kg-door {
  pointer-events: auto; width: min(760px, 90vw); margin: 0 auto;
  padding: calc(30px + 16px * var(--kgp)) calc(28px + 20px * var(--kgp)) calc(26px + 14px * var(--kgp));
  border-radius: calc(4px + 12px * var(--kgp));
  border-color: rgba(201,168,106, calc(.25 + .60 * var(--kgp)));
  /* OPAQUE BASE UNDER THE GLASS (2026-09-30, audit fn-keepgoing-*): while the runway scrolls
     in, the pinned footer sits under the card (the stage is z-index 3, so the card is on top,
     but its fill was 3-6% white and the footer logo and links read straight through it on
     every page). The page's own --bg goes under the same gradient, so over the page the card
     looks exactly as before and over the footer nothing behind it shows. */
  background: linear-gradient(180deg, rgba(255,255,255, calc(.03 + .03 * var(--kgp))),
                                      rgba(255,255,255, calc(.01 + .01 * var(--kgp)))),
              var(--bg, #0a0a0a);
  box-shadow: 0 0 calc(110px * var(--kgp)) rgba(201,168,106, calc(.30 * var(--kgp))),
              0 24px 60px rgba(0,0,0, calc(.45 * var(--kgp)));
  transition: none; }
.kg-door h3 { font-size: calc(23px + 13px * var(--kgp)); line-height: 1.1; }
.kg-door p { opacity: calc(1 - var(--kgp)); max-height: calc(4em * (1 - var(--kgp))); overflow: hidden; }
.kg-door .door-go { font-size: calc(14.5px + 6px * var(--kgp)); }
.kg-door .kg-bar, .kg-door .scroll-hint.kg-inbox { opacity: var(--kgp); }
.kg-bar { width: 100%; height: 3px; margin-top: 14px; border-radius: 999px;
  background: rgba(255,255,255, calc(.10 * var(--kgp))); overflow: hidden; }
.kg-bar i { display: block; height: 100%; border-radius: 999px; background: var(--gold);
  width: calc(100% * var(--kgp)); box-shadow: 0 0 14px rgba(201,168,106,.85); }
/* the last inch: the box takes the light, then the page steps back and the next one loads */
.kg-door.done { animation: kg-flash .3s var(--ease) forwards; }
@keyframes kg-flash {
  0%   { box-shadow: 0 0 100px rgba(201,168,106,.30), 0 24px 60px rgba(0,0,0,.45); }
  100% { box-shadow: 0 0 160px rgba(201,168,106,.55), 0 24px 60px rgba(0,0,0,.45);
         transform: scale(1.08); }
}
body.kg-go main, body.kg-go footer { opacity: .1; transform: translateY(-12px);
  transition: opacity .28s var(--ease), transform .28s var(--ease); }
@media (prefers-reduced-motion: reduce) {
  .kg-hint, .kg-runway { display: none; }      /* keepgoing.js does not run either */
  body.kg-go main, body.kg-go footer { opacity: 1; transform: none; transition: none; }
}
