/* CLAUDE 10-18 (design polish B4 v2): the hero scene (landing-scene.js): a perspective stage behind the headline.
   Far layer: a long stream strip of Theo's footage in 3D depth, out of focus (the depth of field is one blur on the strip
   plane, not on its moving children). Near layer: three tilted 9:16 phones, machined (outer bezel, inner screen, top-edge
   highlight, a real shadow). Mesh: graphite with a restrained cool / green / warm hint, never neon. The scan label is the
   one glass element, because it is the one thing that sits over imagery. Only transform and opacity move. Where the browser
   has scroll-driven animations the layers slide at different rates as the page scrolls; reduced motion and Save-Data get a
   still scene. Tokens (--bg, --sig, --ink, --soft, --ease-*) come from the page. */

.wow-scene {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: min(940px, calc(100vh + 120px));
  overflow: clip;
  pointer-events: none;
  z-index: 0;
  perspective: 1500px;
  perspective-origin: 50% 38%;
}
.wow-scene * {
  box-sizing: border-box;
}
.sc-mesh {
  position: absolute;
  inset: -14%;
  background:
    radial-gradient(46% 40% at 14% 12%, rgba(118, 150, 196, 0.2), transparent 70%),
    radial-gradient(40% 40% at 88% 18%, rgba(242, 240, 235, 0.1), transparent 70%),
    radial-gradient(38% 34% at 76% 84%, rgba(83, 252, 24, 0.06), transparent 72%),
    radial-gradient(44% 36% at 24% 92%, rgba(255, 168, 120, 0.1), transparent 72%);
}
.sc-vig {
  position: absolute;
  inset: 0;
  /* a scrim behind the text column (the strip runs by at the sides, the words stay legible), then the fade to the page */
  background:
    linear-gradient(to bottom, transparent 62%, var(--bg) 98%), linear-gradient(to top, transparent 90%, var(--bg)),
    radial-gradient(48% 52% at 50% 38%, rgba(14, 14, 16, 0.84), rgba(14, 14, 16, 0) 100%),
    radial-gradient(125% 100% at 50% 40%, transparent 55%, var(--bg) 100%);
}
.sc-stage,
.sc-far,
.sc-near {
  position: absolute;
  inset: 0;
  transform-style: preserve-3d;
}
.sc-stage {
  will-change: transform;
}

/* the far layer: the stream, running by in depth */
.sc-strip {
  position: absolute;
  left: 50%;
  top: 190px;
  width: 3800px;
  margin-left: -1900px;
  transform: translateZ(-380px) rotateX(54deg) rotateZ(-7deg);
  opacity: 0.95;
}
.sc-move {
  display: flex;
  gap: 20px;
  width: max-content;
}
.sc-fr {
  position: relative;
  flex: none;
  width: 360px;
  aspect-ratio: 16 / 9;
  border-radius: 10px;
  background: rgba(255, 255, 255, 0.04);
  box-shadow: inset 0 0 0 1px rgba(255, 255, 255, 0.1);
  /* the depth of field: each frame is blurred on its own, so the blurred surfaces never change while the track slides
     (a blur on the moving track itself re-blurs the whole strip every frame) */
  filter: blur(2.6px) saturate(0.6) brightness(0.62);
}
.sc-fr::before {
  content: '';
  position: absolute;
  inset: 0;
  border-radius: inherit;
  background: var(--sc-img, none) 50% 40% / cover;
}
.sc-fr.f1::before {
  background-size: 150%;
  background-position: 28% 46%;
}
.sc-fr.f2::before {
  transform: scaleX(-1);
}
.sc-fr.f3::before {
  background-size: 138%;
  background-position: 72% 30%;
}
.sc-fr.f4::before {
  transform: scaleX(-1);
  background-size: 160%;
  background-position: 40% 55%;
}
.sc-fr.f5::before {
  background-size: 125%;
  background-position: 62% 70%;
}
.sc-fr::after {
  content: attr(data-t);
  position: absolute;
  left: 10px;
  bottom: 8px;
  font:
    400 12px/1 'RipClip Mono',
    ui-monospace,
    monospace;
  letter-spacing: 0.02em;
  color: rgba(255, 255, 255, 0.72);
}
.sc-fr.hit {
  box-shadow:
    inset 0 0 0 2px var(--sig),
    0 0 44px rgba(83, 252, 24, 0.3);
}

/* the scan: a line across the whole stage, and its label (glass, because it sits over imagery) */
.sc-scan {
  position: absolute;
  top: 70px;
  left: 0;
  height: 420px;
  width: 2px;
  opacity: 0;
}
.sc-scan i {
  position: absolute;
  inset: 0;
  background: linear-gradient(to bottom, transparent, var(--sig) 18%, var(--sig) 82%, transparent);
  box-shadow: 0 0 22px 2px rgba(83, 252, 24, 0.3);
}
.sc-scan b {
  position: absolute;
  left: 12px;
  top: 0;
  height: 30px;
  padding: 0 12px;
  display: inline-flex;
  align-items: center;
  border-radius: 999px;
  background: rgba(21, 21, 23, 0.55);
  -webkit-backdrop-filter: blur(10px) saturate(140%);
  backdrop-filter: blur(10px) saturate(140%);
  box-shadow:
    inset 0 1px 0 rgba(255, 255, 255, 0.08),
    inset 0 0 0 1px rgba(255, 255, 255, 0.1);
  color: var(--ink);
  font-size: 12.5px;
  font-weight: 600;
  white-space: nowrap;
}

/* the near layer: three clips, out of the strip and into the light */
.sc-ph {
  position: absolute;
  width: var(--pw, 236px);
  aspect-ratio: 9 / 16;
  opacity: 0;
  display: none;
  transform-style: preserve-3d; /* so the three phones sort by depth together, not by their order in the page */
}
.sc-ph.on {
  opacity: 1;
}
.sc-ph-in {
  position: absolute;
  inset: 0;
  padding: 6px;
  border-radius: 34px;
  background: linear-gradient(160deg, rgba(255, 255, 255, 0.12), rgba(255, 255, 255, 0.03));
  box-shadow:
    inset 0 1px 0 rgba(255, 255, 255, 0.2),
    inset 0 0 0 1px rgba(255, 255, 255, 0.1),
    0 2px 6px rgba(0, 0, 0, 0.5),
    0 44px 80px -24px rgba(0, 0, 0, 0.95),
    0 0 90px -30px rgba(118, 150, 196, 0.35);
  transform: translateZ(var(--z, 0)) rotateY(var(--ry, 0deg)) rotateX(var(--rx, 0deg)) rotateZ(var(--rz, 0deg));
}
.sc-ph-in img {
  display: block;
  width: 100%;
  height: 100%;
  border-radius: 28px;
  object-fit: cover;
  background: black;
}
.sc-ph-in b {
  position: absolute;
  left: 16px;
  right: 16px;
  bottom: 16px;
  display: grid;
  gap: 2px;
  padding: 9px 12px;
  border-radius: 14px;
  background: linear-gradient(180deg, rgba(34, 34, 38, 0.82), rgba(21, 21, 23, 0.78));
  box-shadow:
    inset 0 1px 0 rgba(255, 255, 255, 0.08),
    inset 0 0 0 1px rgba(255, 255, 255, 0.08);
  font-size: 13px;
  font-weight: 650;
  color: var(--ink);
}
.sc-ph-in b small {
  font:
    400 11.5px/1.2 'RipClip Mono',
    ui-monospace,
    monospace;
  color: var(--soft);
}
/* the phones flank the form (the headline is as wide as the window, the form is not): one on each side, a third behind
   the left one. Below 1280 px there is no room beside the form and the strip alone carries the scene. */
@media (min-width: 1280px) {
  .sc-ph.p0,
  .sc-ph.p1 {
    --pw: clamp(172px, 14.6vw, 226px);
  }
  .sc-ph.p0 {
    display: block;
    --ry: 17deg;
    --rz: -5deg;
    left: max(1.6%, calc(50% - 700px));
    top: 340px;
  }
  .sc-ph.p1 {
    display: block;
    --ry: -17deg;
    --rz: 5deg;
    --z: 30px;
    right: max(1.6%, calc(50% - 700px));
    top: 300px;
  }
  .sc-ph.p2 {
    display: block;
    --pw: clamp(130px, 10.5vw, 164px);
    --ry: 27deg;
    --rz: -9deg;
    --z: -170px;
    left: max(-0.5%, calc(50% - 760px));
    top: 468px;
  }
  .sc-ph.p2 .sc-ph-in {
    filter: blur(1.4px) brightness(0.72);
  }
  .sc-ph.p2 b {
    display: none;
  }
}
@media (max-width: 767.98px) {
  .wow-scene {
    height: 640px;
    perspective: 1000px;
  }
  .sc-strip {
    top: 92px;
    transform: translateZ(-260px) rotateX(50deg) rotateZ(-6deg);
  }
  .sc-scan {
    top: 40px;
    height: 320px;
  }
  .sc-scan b {
    display: none; /* no room for a label beside a phone-width headline */
  }
  /* the lighter cut: two clips peek in at the edges, tilted and dimmed behind the text, and fly out of the strip like the
     desktop's */
  .sc-ph.p0,
  .sc-ph.p1 {
    display: block;
    --pw: 138px;
  }
  .sc-ph.p0 {
    --ry: 24deg;
    --rz: -6deg;
    left: -54px;
    top: 232px;
  }
  .sc-ph.p1 {
    --ry: -24deg;
    --rz: 6deg;
    right: -54px;
    top: 150px;
  }
  .sc-ph-in {
    filter: brightness(0.55);
  }
  .sc-ph-in b {
    display: none;
  }
  /* the text fills a phone's width, so the scrim does too, and the strip is dimmer */
  .sc-vig {
    background:
      linear-gradient(to bottom, transparent 62%, var(--bg) 98%), linear-gradient(to top, transparent 90%, var(--bg)),
      radial-gradient(105% 62% at 50% 40%, rgba(14, 14, 16, 0.9), rgba(14, 14, 16, 0.4) 72%, rgba(14, 14, 16, 0) 100%);
  }
  .sc-fr {
    filter: blur(2.6px) saturate(0.5) brightness(0.5);
  }
}

/* motion: the scene fades in when the page is shown, the strip runs, parallax slides the layers on scroll */
@media (prefers-reduced-motion: no-preference) {
  body:not(.booting) .sc-play .sc-stage,
  body:not(.booting) .sc-play .sc-mesh {
    animation: sc-in 900ms var(--ease-out) 500ms both;
  }
  .sc-play .sc-move {
    animation: sc-run 54s linear infinite;
  }
  .sc-off .sc-move {
    animation-play-state: paused;
  }
  @keyframes sc-in {
    from {
      opacity: 0;
    }
  }
  @keyframes sc-run {
    to {
      transform: translateX(-50%);
    }
  }
}
@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) {
    .wow-scene {
      view-timeline: --sc-scroll block;
    }
    .sc-far {
      animation: sc-far linear both;
      animation-timeline: --sc-scroll;
      animation-range: exit 0% exit 100%;
    }
    .sc-near {
      animation: sc-near linear both;
      animation-timeline: --sc-scroll;
      animation-range: exit 0% exit 100%;
    }
    @keyframes sc-far {
      to {
        transform: translate3d(0, -4%, 0);
      }
    }
    @keyframes sc-near {
      to {
        transform: translate3d(0, -15%, 0);
      }
    }
  }
}
@media (prefers-reduced-motion: reduce) {
  .sc-move {
    animation: none !important; /* editor.css's blanket kill says the same; the scene is simply still */
  }
}
.sc-static .sc-scan {
  opacity: 1;
  transform: translateX(46vw);
}
@media (prefers-reduced-transparency: reduce) {
  .sc-scan b {
    background: var(--panel2);
    -webkit-backdrop-filter: none;
    backdrop-filter: none;
  }
}
