/* The home page hero, drawn in light (hero.js) behind the whole hero instead of in a column of its
   own. The script adds .has-canvas once WebGL2 is running; until then, and in browsers without it,
   the hero keeps its illustration. The canvas stays pinned to the screen from the headline down to
   the big wordmark, then leaves with the section. The hero lab (tools/hero_lab.py) builds its
   full-bleed options on these rules too. Created by Adorea. */
.hero.has-canvas { overflow: clip; }                 /* clip, not hidden, so the canvas can stick */
.hero-canvas {
  position: sticky; top: var(--header-h); z-index: 0; display: block;
  width: 100%; height: calc(100svh - var(--header-h));
  margin-bottom: calc(var(--header-h) - 100svh);
  pointer-events: none;
  opacity: 0; transition: opacity 1.2s var(--ease);
}
.hero-canvas.is-live { opacity: 1; }
.hero-grid, .hero-mark { position: relative; z-index: 1; }
/* The art is the background now, so the copy gets the room it needs and nothing else. */
.hero.has-canvas .hero-figure { display: none; }
.hero.has-canvas .hero-grid { grid-template-columns: minmax(0, 1fr); }
.hero.has-canvas .hero-copy { max-width: 620px; }
@media (max-width: 860px) {
  .hero.has-canvas .hero-grid { align-content: start; padding-top: clamp(40px, 10vw, 64px); }
}

/* The app the light has taken the shape of, named just under it and linking to its page. The
   script moves it with the icon; the same links are in the apps list below, so it stays out of the
   tab order and away from screen readers. */
.hero-now {
  position: absolute; left: 0; top: 0; z-index: 2;
  display: grid; justify-items: center; gap: 3px;
  padding: 8px 16px; text-align: center; white-space: nowrap; text-decoration: none;
  color: var(--stage-text);
  opacity: 0; pointer-events: none;
  transition: opacity 0.7s var(--ease);
}
.hero-now.is-on { opacity: 1; pointer-events: auto; }
.hero-now > span { transform: translateY(8px); transition: transform 0.9s var(--ease); }
.hero-now.is-on > span { transform: none; }
.hero-now-name { font: 600 1.0625rem/1.2 var(--font-display); letter-spacing: -0.01em; }
.hero-now-status { font-size: 0.8125rem; letter-spacing: 0.01em; color: var(--stage-text-3); }
.hero-now:hover .hero-now-name { text-decoration: underline; text-decoration-color: var(--champagne); text-underline-offset: 0.3em; }

/* The gravity scene (the script adds .has-scene): the first screen stays pinned while the page
   scrolls on through the hero (a spacer after it sets how long; a sticky element only travels
   within its parent's content, not its padding), and everything in it moves with the scroll:
   "gravity." breaks up, the lines under the headline fade, and "Apps with" and the wordmark come
   together in the middle of the screen while the light pours into it. Then the screen moves on.
   The wordmark lives in the pinned screen for it, placed by the script. Someone scrolling fast is
   let straight through: the script shortens the spacer (--scene-pin) to where they are, so the
   pin ends there and the scene finishes as the screen moves on. */
.hero.has-scene .hero-grid { position: sticky; top: var(--header-h); height: calc(100svh - var(--header-h)); }
/* The home page puts its canvas and grid in one box (.hero-pin, made by the script), pinned instead of
   the grid, so the light can't stay behind on the screen when the words move on. */
.hero-pin { position: relative; }
.hero.has-scene .hero-pin { position: sticky; top: var(--header-h); height: calc(100svh - var(--header-h)); }
.hero-pin > .hero-canvas { position: absolute; inset: 0; width: 100%; height: 100%; margin: 0; }
.hero.has-scene .hero-pin > .hero-grid { position: relative; top: auto; height: 100%; }
.hero.has-scene::after { content: ""; display: block; height: var(--scene-pin, 130svh); }
.hero.has-scene .hero-mark { position: absolute; left: 0; right: 0; top: 0; padding-block: 0; will-change: transform; }
.hero.has-scene .hero-copy, .hero.has-scene .hero-copy .pill, .hero.has-scene .hero-sub, .hero.has-scene .actions { will-change: transform, opacity; }
/* The headline's entrance animation lets go of its lines once it has played (it would otherwise hold
   them at full opacity), so the scene can fade them. */
.hero.has-scene .hero-copy > * { animation-fill-mode: backwards; }

/* The way down: a cue at the foot of the first screen. Clicked, the light sets off round the
   headline and the page follows it down to the wordmark. */
.hero-cue {
  position: absolute; left: 50%; bottom: clamp(18px, 3.2vh, 34px); z-index: 2;
  display: grid; justify-items: center; gap: 12px;
  transform: translateX(-50%);
  color: var(--stage-text-2); text-decoration: none; white-space: nowrap;
  font-size: 0.75rem; letter-spacing: 0.2em; text-transform: uppercase;
  transition: opacity 0.6s var(--ease), color 0.3s;
}
.hero-cue:hover { color: var(--stage-text); }
.hero-cue-arrow {
  display: grid; place-items: center; width: 44px; height: 44px; border-radius: 50%;
  box-shadow: inset 0 0 0 1px var(--stage-line-2);
  transition: box-shadow 0.3s;
  animation: cue-bob 2.6s ease-in-out infinite;
}
.hero-cue:hover .hero-cue-arrow { box-shadow: inset 0 0 0 1px var(--champagne); }
.hero-cue svg { width: 16px; height: 16px; }
.hero-cue.is-gone { opacity: 0; pointer-events: none; }
@keyframes cue-bob { 50% { transform: translateY(5px); } }
@media (prefers-reduced-motion: reduce) { .hero-cue-arrow { animation: none; } }

/* Once the light has "gravity." (.is-light), nothing else moves its letters: they only fade. */
.fall.is-light .drop { transform: none !important; }

/* "with" becomes "by": the script wraps the word, and lays "by" over it (italic, light, in the
   gold of the wordmark's dot), faded in as the light that was "with" settles into it. */
.word-swap { position: relative; display: inline-block; line-height: inherit; }
.word-by {
  position: absolute; left: 0; top: 0; opacity: 0; pointer-events: none; line-height: inherit; white-space: nowrap;
  font-style: italic; font-weight: 300; letter-spacing: -0.02em; color: var(--champagne);
}
