/* ============================================================================
   NIMBUS MARKETING SITE
   Depends on tokens.css. Never hardcode a colour here that is not a token.
   Shape rule in force: buttons/chips = pill, cards = --r-lg, panels = --r-xl.
   ========================================================================== */

*, *::before, *::after { box-sizing: border-box; }

html { -webkit-text-size-adjust: 100%; scroll-behavior: smooth; }
@media (prefers-reduced-motion: reduce) { html { scroll-behavior: auto; } }

body {
  margin: 0;
  background: var(--canvas);
  color: var(--body);
  font: var(--t-body);
  letter-spacing: var(--tracking-tight);
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
  overflow-x: hidden;
}

h1, h2, h3, h4 { color: var(--ink); margin: 0; letter-spacing: var(--tracking-display); }
p { margin: 0; }
ul { margin: 0; padding: 0; list-style: none; }
a { color: inherit; text-decoration: none; }
img, svg { max-width: 100%; }

/* A class rule that sets `display` beats the user-agent's
   `[hidden] { display: none }`, because a class outranks a bare attribute
   selector. An element toggled with `el.hidden = true` then stays on screen
   with the attribute silently set, which is exactly how the download list
   shipped expanded. One global rule costs nothing and closes the whole class
   of bug. */
[hidden] { display: none !important; }

:focus-visible {
  outline: none;
  box-shadow: var(--ring);
  border-radius: var(--r-sm);
}

/* A box-shadow ring is stripped entirely by Windows High Contrast mode, which
   would leave keyboard users with no visible focus at all. forced-colors gets
   a real outline instead, in the system's own highlight colour. */
@media (forced-colors: active) {
  :focus-visible { outline: 3px solid Highlight; outline-offset: 2px; }
}

/* The ring is brand-coloured, which all but disappears against the hero sky.
   Anything sitting on the photograph gets a white outline instead. */
.hero :focus-visible,
.download :focus-visible { outline: 2px solid #ffffff; outline-offset: 3px; }

.skip-link {
  position: absolute; left: var(--s-4); top: -100px;
  z-index: var(--z-toast);
  padding: var(--s-3) var(--s-5);
  background: var(--surface); color: var(--ink);
  border-radius: var(--r-pill); box-shadow: var(--e-3);
  font: var(--t-label);
  transition: top var(--d-fast) var(--ease-out);
}
.skip-link:focus { top: var(--s-4); }

.mono { font-family: var(--font-mono); font-variant-numeric: tabular-nums; }

/* ---------------------------------------------------------------- glass --- */
.glass {
  background: var(--glass-bg);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(170%);
  backdrop-filter: blur(var(--glass-blur)) saturate(170%);
  border: 1px solid var(--glass-stroke);
  box-shadow: inset 0 1px 0 var(--glass-inner), var(--e-3);
}
.glass-strong {
  background: var(--glass-bg-2);
  -webkit-backdrop-filter: blur(calc(var(--glass-blur) * 1.4)) saturate(180%);
  backdrop-filter: blur(calc(var(--glass-blur) * 1.4)) saturate(180%);
  border: 1px solid var(--glass-stroke);
  box-shadow: inset 0 1px 0 var(--glass-inner), var(--e-4);
}

/* -------------------------------------------------------------- buttons --- */
.btn {
  display: inline-flex; align-items: center; justify-content: center;
  gap: var(--s-2);
  white-space: nowrap;
  border: 1px solid transparent;
  border-radius: var(--r-pill);
  font: var(--t-label);
  cursor: pointer;
  transition: transform var(--d-fast) var(--ease-out),
              background var(--d-fast) var(--ease-out),
              box-shadow var(--d-fast) var(--ease-out),
              border-color var(--d-fast) var(--ease-out);
}
.btn-sm { padding: 9px 18px; }
.btn-lg { padding: 15px 28px; font-size: 0.9375rem; }
.btn:not(.btn-sm):not(.btn-lg) { padding: 12px 22px; }
.btn-block { width: 100%; }
.btn:hover { transform: translateY(-1px); }
.btn:active { transform: translateY(0) scale(0.985); }

.btn-primary { background: var(--brand); color: var(--on-brand); box-shadow: var(--e-2); }
.btn-primary:hover { background: var(--brand-600); box-shadow: var(--e-3); }

.btn-ghost {
  background: var(--surface);
  color: var(--ink);
  border-color: var(--hairline);
  box-shadow: var(--e-1);
}
.btn-ghost:hover { background: var(--surface-2); border-color: var(--brand-200); }

/* On the photographic sky these need their own opaque scrim for AA contrast. */
.btn-light { background: #ffffff; color: #0c1830; box-shadow: var(--e-3); }
.btn-light:hover { background: var(--brand-50); }
.btn-outline-light {
  background: rgba(10, 24, 52, 0.30);
  color: #ffffff;
  border-color: rgba(255, 255, 255, 0.55);
  -webkit-backdrop-filter: blur(14px);
  backdrop-filter: blur(14px);
}
.btn-outline-light:hover { background: rgba(10, 24, 52, 0.45); border-color: #ffffff; }

.btn em { font-style: normal; opacity: 0.7; font-weight: 450; }

/* ------------------------------------------------------------------ nav --- */
.nav-wrap {
  position: fixed; inset: var(--s-4) 0 auto;
  z-index: var(--z-sticky);
  display: flex; justify-content: center;
  padding: 0 var(--gutter);
  pointer-events: none;
}
.nav {
  pointer-events: auto;
  width: 100%;
  max-width: var(--page-max);
  height: 64px;
  display: grid;
  grid-template-columns: auto 1fr auto;
  align-items: center;
  gap: var(--s-5);
  padding: 0 10px 0 20px;
  border-radius: var(--r-pill);
  transition: background var(--d-base) var(--ease-out),
              box-shadow var(--d-base) var(--ease-out);
}
/* Over the sky the nav is translucent white; once scrolled past the hero it
   picks up the page surface so text keeps contrast. */
.nav-wrap:not(.scrolled) .nav {
  background: rgba(12, 30, 68, 0.22);
  border-color: rgba(255, 255, 255, 0.30);
  box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.28), 0 10px 40px -18px rgba(8, 24, 60, 0.5);
}
.nav-wrap:not(.scrolled) .nav,
.nav-wrap:not(.scrolled) .nav a,
.nav-wrap:not(.scrolled) .brand-word { color: #ffffff; }
.nav-wrap:not(.scrolled) .nav-links a:hover { color: #ffffff; background: rgba(255,255,255,0.18); }
.nav-wrap:not(.scrolled) .theme-toggle { color: #ffffff; border-color: rgba(255,255,255,0.34); }

.brand { display: inline-flex; align-items: center; gap: 10px; }
.brand-mark { display: grid; place-items: center; }
.brand-word { font: var(--t-title-md); letter-spacing: 0.01em; color: var(--ink); }

.nav-links { display: flex; justify-content: center; gap: var(--s-1); }
.nav-links a {
  display: block;
  padding: 8px 14px;
  border-radius: var(--r-pill);
  font: var(--t-label);
  color: var(--body);
  transition: background var(--d-fast) var(--ease-out), color var(--d-fast) var(--ease-out);
}
.nav-links a:hover { background: var(--surface-2); color: var(--ink); }

.nav-actions { display: flex; align-items: center; gap: var(--s-2); }
.theme-toggle {
  width: 38px; height: 38px;
  display: grid; place-items: center;
  border-radius: var(--r-pill);
  border: 1px solid var(--hairline);
  background: transparent;
  color: var(--body);
  font-size: 1.05rem;
  cursor: pointer;
  transition: background var(--d-fast) var(--ease-out), color var(--d-fast) var(--ease-out);
}
.theme-toggle:hover { background: var(--surface-2); color: var(--ink); }

/* ----------------------------------------------------------------- hero --- */
.hero {
  position: relative;
  min-height: 100dvh;
  display: grid;
  grid-template-rows: 1fr auto;
  padding: 148px var(--gutter) 0;
  isolation: isolate;
}

.sky { position: absolute; inset: 0; z-index: -1; overflow: hidden; }

/* ---------------------------------------------------------------------------
   THE SKY
   The hero sits on a real photograph, not a gradient and not procedural noise.
   Four stacked layers, bottom to top:
     .sky-photo  the photograph, cover-fit, slowly drifting
     .sky-tint   a brand-blue wash that ties the photo to the palette
     .sky-scrim  a top gradient that guarantees nav and headline contrast
     .sky-fade   the dissolve into the page canvas at the bottom
   Day and night are separate files chosen by theme, so a viewer only ever
   downloads the one they see. `image-set` serves WebP where supported; the
   plain url() above it is the fallback older browsers keep.
   ------------------------------------------------------------------------ */
.sky-photo, .dl-sky {
  position: absolute; inset: 0;
  background-repeat: no-repeat;
  background-position: center 38%;
  background-size: cover;
  background-color: var(--sky-mid);
  will-change: transform;
}

.sky-photo {
  background-image: url("../assets/sky-day.jpg");
  background-image: image-set(
    url("../assets/sky-day.webp") type("image/webp"),
    url("../assets/sky-day.jpg")  type("image/jpeg"));
}
.dl-sky {
  z-index: -1;
  opacity: 0.85;
  background-image: url("../assets/sky-day-sm.jpg");
  background-image: image-set(
    url("../assets/sky-day-sm.webp") type("image/webp"),
    url("../assets/sky-day-sm.jpg")  type("image/jpeg"));
}

/* Phones get the half-size file. At 390px wide the 2400px image is three
   times more pixels than the screen can show. */
@media (max-width: 760px) {
  .sky-photo {
    background-image: url("../assets/sky-day-sm.jpg");
    background-image: image-set(
      url("../assets/sky-day-sm.webp") type("image/webp"),
      url("../assets/sky-day-sm.jpg")  type("image/jpeg"));
  }
}

.sky-tint {
  position: absolute; inset: 0;
  background:
    radial-gradient(120% 86% at 50% 120%, color-mix(in oklab, var(--sky-haze) 62%, transparent), transparent 62%),
    linear-gradient(176deg,
      color-mix(in oklab, var(--brand-800) 30%, transparent) 0%,
      transparent 46%,
      color-mix(in oklab, var(--sky-low) 22%, transparent) 100%);
  /* soft-light, not multiply: it warms and unifies the photograph with the
     brand palette without crushing the clouds into a flat blue slab. */
  mix-blend-mode: soft-light;
  opacity: 0.8;
}

.sky-scrim {
  position: absolute; left: 0; right: 0; top: 0; height: 280px;
  background: linear-gradient(to bottom, rgba(8, 22, 54, 0.42), rgba(8, 22, 54, 0.12) 55%, transparent);
}

.sky-fade {
  position: absolute; left: 0; right: 0; bottom: 0; height: 44%;
  background: linear-gradient(to bottom, transparent, var(--canvas) 95%);
}

/* A very slow drift. The scale headroom keeps the edges off screen, and only
   `transform` animates, on a promoted layer, so this composites on the GPU. */
@media (prefers-reduced-motion: no-preference) {
  .sky-photo { animation: sky-drift 150s ease-in-out infinite; }
}
@keyframes sky-drift {
  from { transform: scale(1.06) translate3d(-1.2%, 0, 0); }
  50%  { transform: scale(1.11) translate3d(1.4%, -1%, 0); }
  to   { transform: scale(1.06) translate3d(-1.2%, 0, 0); }
}

/* --- night ------------------------------------------------------------- */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .sky-photo {
    background-image: url("../assets/sky-night.jpg");
    background-image: image-set(
      url("../assets/sky-night.webp") type("image/webp"),
      url("../assets/sky-night.jpg")  type("image/jpeg"));
  }
  :root:not([data-theme="light"]) .dl-sky {
    background-image: url("../assets/sky-night-sm.jpg");
    background-image: image-set(
      url("../assets/sky-night-sm.webp") type("image/webp"),
      url("../assets/sky-night-sm.jpg")  type("image/jpeg"));
  }
  :root:not([data-theme="light"]) .sky-tint { mix-blend-mode: normal; opacity: 0.5; }
}
:root[data-theme="dark"] .sky-photo {
  background-image: url("../assets/sky-night.jpg");
  background-image: image-set(
    url("../assets/sky-night.webp") type("image/webp"),
    url("../assets/sky-night.jpg")  type("image/jpeg"));
}
:root[data-theme="dark"] .dl-sky {
  background-image: url("../assets/sky-night-sm.jpg");
  background-image: image-set(
    url("../assets/sky-night-sm.webp") type("image/webp"),
    url("../assets/sky-night-sm.jpg")  type("image/jpeg"));
}
:root[data-theme="dark"] .sky-tint { mix-blend-mode: normal; opacity: 0.5; }

.hero-copy { max-width: 1000px; margin: 0 auto; text-align: center; }
.hero-title {
  font: var(--t-display-xl);
  color: #ffffff;
  text-shadow: 0 2px 10px rgba(8, 26, 62, 0.30), 0 4px 40px rgba(8, 26, 62, 0.45);
  margin-bottom: var(--s-5);
}
.hero-sub {
  max-width: 54ch; margin: 0 auto var(--s-7);
  font-size: 1.0625rem; line-height: 1.6;
  color: #ffffff;
  /* Two shadows: a tight one for edge definition against bright cloud, and a
     wide soft one that acts as a local scrim. The subhead is the smallest
     white text on the photograph, so it needs the most help. */
  text-shadow: 0 1px 3px rgba(8, 26, 62, 0.45), 0 2px 26px rgba(8, 26, 62, 0.65);
}
.hero-cta { display: flex; flex-wrap: wrap; gap: var(--s-3); justify-content: center; }
.hero-cta .btn-ghost {
  background: rgba(255, 255, 255, 0.15);
  color: #ffffff;
  border-color: rgba(255, 255, 255, 0.50);
  -webkit-backdrop-filter: blur(14px);
  backdrop-filter: blur(14px);
  box-shadow: none;
}
.hero-cta .btn-ghost:hover { background: rgba(255, 255, 255, 0.26); border-color: #ffffff; }

/* ------------------------------------------------------- live preview ----- */
.preview-wrap { max-width: var(--page-max); margin: var(--s-10) auto 0; width: 100%; }
.preview {
  border-radius: var(--r-xl);
  overflow: hidden;
  transform: translateY(0);
}
.pv-chrome {
  display: flex; align-items: center; gap: var(--s-4);
  padding: 12px 18px;
  border-bottom: 1px solid var(--hairline-soft);
  background: var(--surface);
}
.pv-dots { display: inline-flex; gap: 6px; }
.pv-dots i { width: 10px; height: 10px; border-radius: var(--r-pill); background: var(--surface-3); }
.pv-title { font: var(--t-caption); color: var(--muted); }

.pv-body {
  display: grid;
  grid-template-columns: 172px 1fr 190px;
  background: var(--surface);
  min-height: 390px;
}
.pv-rail { display: flex; flex-direction: column; gap: 2px; padding: var(--s-4); border-right: 1px solid var(--hairline-soft); }
.pv-rail-item {
  display: flex; align-items: center; gap: 10px;
  padding: 9px 12px; border-radius: var(--r-md);
  font: var(--t-label); color: var(--muted);
}
.pv-rail-item i { font-size: 1.05rem; }
.pv-rail-item.is-active { background: var(--brand-50); color: var(--brand-700); }

.pv-main { padding: var(--s-5); display: flex; flex-direction: column; gap: var(--s-4); }
.pv-stats { display: grid; grid-template-columns: repeat(3, 1fr); gap: var(--s-3); }
.pv-stat {
  padding: var(--s-3) var(--s-4);
  border-radius: var(--r-md);
  background: var(--surface-2);
  display: flex; flex-direction: column; gap: 2px;
}
.pv-stat-n { font-family: var(--font-mono); font-size: 1.35rem; font-weight: 500; color: var(--ink); font-variant-numeric: tabular-nums; }
.pv-stat-l { font: var(--t-caption); color: var(--muted); }

.pv-card-stage { perspective: 1400px; flex: 1; display: grid; }
.pv-card {
  position: relative;
  width: 100%;
  min-height: 160px;
  border: 0; padding: 0;
  background: transparent;
  cursor: pointer;
  transform-style: preserve-3d;
  transition: transform var(--d-slow) var(--ease-in-out);
  font: inherit; text-align: left;
}
.pv-card.flipped { transform: rotateX(180deg); }
.pv-card-face {
  position: absolute; inset: 0;
  display: flex; flex-direction: column; gap: 10px; justify-content: center;
  padding: var(--s-6);
  border-radius: var(--r-lg);
  border: 1px solid var(--hairline);
  background: var(--surface);
  box-shadow: var(--e-2);
  -webkit-backface-visibility: hidden;
  backface-visibility: hidden;
}
.pv-back { transform: rotateX(180deg); background: var(--brand-50); border-color: var(--brand-200); }
.pv-kicker { font: var(--t-caption); text-transform: uppercase; letter-spacing: 0.1em; color: var(--muted); }
.pv-q, .pv-a { font: var(--t-title-lg); color: var(--ink); }
.pv-hint { font: var(--t-caption); color: var(--muted); margin-top: auto; }

.pv-grades { display: grid; grid-template-columns: repeat(4, 1fr); gap: var(--s-2); }
.pv-grade {
  display: flex; flex-direction: column; gap: 2px; align-items: center;
  padding: 10px 6px;
  border-radius: var(--r-md);
  border: 1px solid var(--hairline);
  background: var(--surface);
  color: var(--ink);
  font: var(--t-label);
  cursor: pointer;
  transition: background var(--d-fast) var(--ease-out), border-color var(--d-fast) var(--ease-out), transform var(--d-fast) var(--ease-out);
}
.pv-grade em { font-style: normal; font-family: var(--font-mono); font-size: 0.6875rem; color: var(--muted); }
.pv-grade:hover { border-color: var(--brand-300); background: var(--brand-50); transform: translateY(-1px); }
.pv-grade:disabled { opacity: 0.45; cursor: not-allowed; transform: none; }

.pv-side { padding: var(--s-5) var(--s-4); border-left: 1px solid var(--hairline-soft); display: flex; flex-direction: column; gap: var(--s-3); }
.pv-side-h { font: var(--t-caption); text-transform: uppercase; letter-spacing: 0.09em; color: var(--muted); }
.pv-heat { display: grid; grid-template-columns: repeat(7, 1fr); gap: 4px; }
.pv-heat span { aspect-ratio: 1; border-radius: 3px; background: var(--surface-3); }
.pv-spark { width: 100%; height: 54px; }

/* ---------------------------------------------------------------- band ---- */
.band {
  max-width: var(--page-max);
  margin: 0 auto;
  padding: var(--s-11) var(--gutter) var(--s-9);
}
.band-lede {
  max-width: 62ch;
  font: var(--t-title-lg);
  font-weight: 500;
  color: var(--ink);
  margin-bottom: var(--s-8);
}
.band-list {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(230px, 1fr));
  gap: var(--s-6);
  border-top: 1px solid var(--hairline);
  padding-top: var(--s-6);
}
.band-list li { display: flex; flex-direction: column; gap: 6px; }
.band-list strong { font: var(--t-title-sm); color: var(--ink); }
.band-list span { font: var(--t-body-sm); color: var(--muted); }

/* ------------------------------------------------------------- section ---- */
/* Anchor links must not drop the heading under the fixed nav. */
.section, .band, .download { scroll-margin-top: 104px; }
.section { max-width: var(--page-max); margin: 0 auto; padding: var(--s-11) var(--gutter); }
.h-display { font: var(--t-display-lg); }
.center-head { text-align: center; max-width: 18ch; margin: 0 auto var(--s-9); }
.lede { max-width: 62ch; font-size: 1.0625rem; line-height: 1.62; color: var(--muted); }
.eyebrow {
  font: var(--t-caption);
  text-transform: uppercase;
  letter-spacing: 0.14em;
  color: var(--brand-text);
  margin-bottom: var(--s-3);
}

/* ---------------------------------------------------------- method/curve -- */
.method-head { max-width: 760px; }
.method-head .h-display { margin-bottom: var(--s-4); }
.curve-fig { margin: var(--s-8) 0 0; }
.curve {
  width: 100%; height: auto;
  background: var(--surface);
  border: 1px solid var(--hairline);
  border-radius: var(--r-lg);
  box-shadow: var(--e-2);
  padding: 0;
}
.c-massed { stroke: var(--muted); stroke-width: 2; stroke-dasharray: 5 6; }
.c-spaced { stroke: var(--brand); stroke-width: 3; stroke-linecap: round; }
.c-fill { fill: var(--brand); opacity: 0.08; }
.curve-grid-line { stroke: var(--hairline-soft); stroke-width: 1; }
.curve-label { fill: var(--muted); font: 11px var(--font-mono); }
.curve-mark { fill: var(--surface); stroke: var(--brand); stroke-width: 2.5; }

.curve-legend { display: flex; flex-wrap: wrap; gap: var(--s-5); margin-top: var(--s-4); }
.lg { display: inline-flex; align-items: center; gap: 8px; font: var(--t-body-sm); color: var(--muted); }
.lg::before { content: ""; width: 22px; height: 3px; border-radius: var(--r-pill); }
.lg-massed::before { background: var(--muted); }
.lg-spaced::before { background: var(--brand); }

.curve-ctl {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: var(--s-5) var(--s-7);
  margin-top: var(--s-7);
  padding-top: var(--s-6);
  border-top: 1px solid var(--hairline);
}
.ctl { display: grid; gap: 8px; font: var(--t-label); color: var(--ink); }
.ctl output { font-size: 0.8125rem; color: var(--brand-text); }
.ctl-read { grid-column: 1 / -1; font: var(--t-body-sm); color: var(--muted); max-width: 70ch; }

input[type="range"] {
  -webkit-appearance: none; appearance: none;
  width: 100%; height: 4px;
  border-radius: var(--r-pill);
  background: var(--surface-3);
  cursor: pointer;
}
input[type="range"]::-webkit-slider-thumb {
  -webkit-appearance: none; appearance: none;
  width: 20px; height: 20px; border-radius: var(--r-pill);
  background: var(--brand); border: 3px solid var(--surface);
  box-shadow: var(--e-2);
}
input[type="range"]::-moz-range-thumb {
  width: 20px; height: 20px; border-radius: var(--r-pill);
  background: var(--brand); border: 3px solid var(--surface);
  box-shadow: var(--e-2);
}

/* ---------------------------------------------------------------- bento --- */
.bento {
  display: grid;
  grid-template-columns: repeat(6, 1fr);
  gap: var(--s-4);
}
.cell {
  display: flex; flex-direction: column; gap: 10px;
  padding: var(--s-6);
  border-radius: var(--r-lg);
  border: 1px solid var(--hairline);
  background: var(--surface);
  box-shadow: var(--e-1);
  transition: transform var(--d-base) var(--ease-out), box-shadow var(--d-base) var(--ease-out);
}
.cell:hover { transform: translateY(-3px); box-shadow: var(--e-3); }
.cell h3 { font: var(--t-title-md); }
.cell p { font: var(--t-body-sm); color: var(--muted); }

.cell-a { grid-column: span 3; }
.cell-b { grid-column: span 3; }
.cell-c { grid-column: span 2; }
.cell-d { grid-column: span 2; }
.cell-e { grid-column: span 2; }

.cell-visual {
  border-radius: var(--r-md);
  margin-bottom: var(--s-2);
  overflow: hidden;
  position: relative;
}
.cell-visual-grad {
  aspect-ratio: 16 / 7;
  background: linear-gradient(145deg, var(--brand-700), var(--brand) 55%, var(--sky-mid));
  display: grid; place-items: center;
  padding: var(--s-4);
}
.mini-match { display: grid; grid-template-columns: repeat(4, 1fr); gap: 6px; width: 100%; }
.mini-match span {
  display: grid; place-items: center;
  aspect-ratio: 7 / 4;
  border-radius: var(--r-xs);
  background: rgba(255, 255, 255, 0.17);
  border: 1px solid rgba(255, 255, 255, 0.26);
  color: #ffffff;
  font: 500 0.6875rem/1 var(--font-sans);
  transition: background var(--d-fast) var(--ease-out), transform var(--d-fast) var(--ease-out);
}
.mini-match span.lit { background: rgba(255, 255, 255, 0.86); color: var(--brand-700); transform: scale(1.04); }
.mini-match span.gone { opacity: 0.18; }

.cell-code {
  margin: auto 0 0;
  padding: var(--s-4);
  border-radius: var(--r-md);
  background: var(--surface-2);
  border: 1px solid var(--hairline-soft);
  font: 400 0.75rem/1.75 var(--font-mono);
  color: var(--body);
  overflow-x: auto;
}
.cell-stat { margin-bottom: auto; font-size: 3rem; font-weight: 500; color: var(--brand); line-height: 1; }

.cell-visual-ring {
  aspect-ratio: 1 / 1;
  max-width: 104px;
  display: grid; place-items: center;
  background: transparent;
}
.focus-ring { grid-area: 1 / 1; width: 104px; height: 104px; transform: rotate(-90deg); }
.fr-track { fill: none; stroke: var(--surface-3); stroke-width: 9; }
.fr-fill {
  fill: none; stroke: var(--brand); stroke-width: 9; stroke-linecap: round;
  stroke-dasharray: 327; stroke-dashoffset: 82;
  transition: stroke-dashoffset 1s linear;
}
.focus-time { grid-area: 1 / 1; font-size: 1.0625rem; color: var(--ink); }

/* ---------------------------------------------------------------- modes --- */
.modes-head { max-width: 620px; margin-bottom: var(--s-8); }
.modes-head .h-display { margin-bottom: var(--s-3); }
.rail {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: minmax(268px, 1fr);
  gap: var(--s-4);
  overflow-x: auto;
  scroll-snap-type: x mandatory;
  padding-bottom: var(--s-4);
  margin-inline: calc(var(--gutter) * -1);
  padding-inline: var(--gutter);
  scrollbar-width: thin;
}
.mode {
  scroll-snap-align: start;
  display: flex; flex-direction: column; gap: 10px;
  padding: var(--s-6);
  border-radius: var(--r-lg);
  background: var(--surface);
  border: 1px solid var(--hairline);
  box-shadow: var(--e-1);
  transition: border-color var(--d-base) var(--ease-out), transform var(--d-base) var(--ease-out);
}
.mode:hover { border-color: var(--brand-300); transform: translateY(-3px); }
.mode i { font-size: 1.6rem; color: var(--brand); }
.mode h3 { font: var(--t-title-md); }
.mode p { font: var(--t-body-sm); color: var(--muted); flex: 1; }
.mode-cram { border-style: dashed; }
.mode-cram i { color: var(--warn); }
.mode-cram .mode-tag { background: color-mix(in oklab, var(--warn) 16%, transparent); color: var(--warn); }

.mode-tag {
  align-self: flex-start;
  padding: 5px 12px;
  border-radius: var(--r-pill);
  background: var(--brand-50);
  color: var(--brand-700);
  font: var(--t-caption);
  font-weight: 550;
}

/* ---------------------------------------------------------------- split --- */
.split {
  display: grid;
  grid-template-columns: minmax(0, 0.92fr) minmax(0, 1.08fr);
  gap: var(--s-10);
  align-items: center;
}
.split-copy .h-display { margin-bottom: var(--s-4); }
.ticks { display: grid; gap: 10px; margin-top: var(--s-6); }
.ticks li { display: flex; align-items: center; gap: 10px; font: var(--t-body-sm); color: var(--body); }
.ticks i { color: var(--brand); font-size: 1rem; }

.panel { border-radius: var(--r-xl); padding: var(--s-6); display: grid; gap: var(--s-3); }
.panel-head { display: flex; align-items: center; justify-content: space-between; }
.panel-title { font: var(--t-title-sm); color: var(--ink); }
.chip {
  padding: 5px 12px; border-radius: var(--r-pill);
  background: var(--brand-50); color: var(--brand-700);
  font-size: 0.75rem;
}
.forecast { width: 100%; height: auto; }
.fc-bar { fill: var(--brand); transition: fill var(--d-fast) var(--ease-out); }
.fc-bar:hover { fill: var(--brand-700); }
.fc-axis { fill: var(--muted); font: 9px var(--font-mono); }

.heat-year { display: grid; grid-auto-flow: column; grid-template-rows: repeat(7, 1fr); gap: 3px; }
.heat-year span { aspect-ratio: 1; border-radius: 2px; background: var(--surface-3); }

/* -------------------------------------------------------------- pricing --- */
/* auto-fit rather than a fixed count, because the number of cards is decided
   at runtime: entity.js removes whichever plans this deployment does not
   offer, so the grid has to read correctly with three of them or four. */
.plans { display: grid; grid-template-columns: repeat(auto-fit, minmax(230px, 1fr)); gap: var(--s-4); align-items: start; }
.plan {
  display: flex; flex-direction: column; gap: var(--s-3);
  padding: var(--s-7);
  border-radius: var(--r-lg);
  border: 1px solid var(--hairline);
  background: var(--surface);
  box-shadow: var(--e-1);
}
.plan-feature {
  border-color: var(--brand-300);
  box-shadow: var(--e-3);
  background: linear-gradient(180deg, var(--brand-50), var(--surface) 34%);
}
.plan-name { font: var(--t-title-md); }
.plan-price { display: flex; align-items: baseline; gap: 4px; color: var(--ink); }
.plan-price span { font-size: 2.4rem; font-weight: 500; line-height: 1; }
.plan-price em { font-style: normal; font: var(--t-body-sm); color: var(--muted); }
.plan-note { font: var(--t-body-sm); color: var(--muted); min-height: 2.6em; }
.plan-list { display: grid; gap: 9px; padding: var(--s-4) 0; margin-top: auto; border-top: 1px solid var(--hairline-soft); }
.plan-list li { font: var(--t-body-sm); color: var(--body); padding-left: 22px; position: relative; }
.plan-list li::before {
  content: ""; position: absolute; left: 0; top: 0.52em;
  width: 11px; height: 6px;
  border-left: 2px solid var(--brand); border-bottom: 2px solid var(--brand);
  transform: rotate(-45deg);
}

/* ------------------------------------------------------------- download --- */
.download {
  position: relative;
  margin: var(--s-9) var(--gutter) 0;
  border-radius: 34px;
  overflow: hidden;
  isolation: isolate;
  background: linear-gradient(170deg, var(--brand-800), var(--brand-600) 48%, var(--sky-mid));
}
/* Scrim over the photograph. Same z-index as .dl-sky but declared later, so it
   paints above it; the band's white copy needs a consistent ground rather than
   whatever cloud happens to sit behind a given line. */
.download::after {
  content: "";
  position: absolute; inset: 0; z-index: -1;
  pointer-events: none;
  background: linear-gradient(168deg,
    color-mix(in oklab, var(--brand-800) 72%, transparent),
    color-mix(in oklab, var(--brand-600) 46%, transparent) 55%,
    color-mix(in oklab, var(--brand-700) 60%, transparent));
}

.dl-inner { padding: clamp(56px, 8vw, 104px) var(--gutter); text-align: center; }
.dl-title { font: var(--t-display-md); color: #ffffff; margin-bottom: var(--s-3); }
.dl-sub { max-width: 52ch; margin: 0 auto var(--s-7); color: rgba(255, 255, 255, 0.88); font-size: 1rem; }
.dl-buttons { display: flex; flex-wrap: wrap; gap: var(--s-3); justify-content: center; }
.dl-buttons .btn { flex-direction: row; }
.dl-buttons span { display: flex; flex-direction: column; align-items: flex-start; line-height: 1.2; }
.dl-buttons em { font-size: 0.6875rem; }
.dl-meta { margin-top: var(--s-6); font: var(--t-body-sm); color: rgba(255, 255, 255, 0.72); }

/* --------------------------------------------------------------- footer --- */
.footer { max-width: var(--page-max); margin: 0 auto; padding: var(--s-11) var(--gutter) var(--s-7); }
.footer-inner { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1.3fr); gap: var(--s-9); }
.footer-brand p { font: var(--t-body-sm); color: var(--muted); max-width: 34ch; margin-top: 10px; }
.footer-cols { display: grid; grid-template-columns: repeat(3, 1fr); gap: var(--s-6); }
.footer-cols h4 { font: var(--t-caption); text-transform: uppercase; letter-spacing: 0.1em; color: var(--muted); margin-bottom: var(--s-3); }
.footer-cols a { display: block; padding: 5px 0; font: var(--t-body-sm); color: var(--body); }
.footer-cols a:hover { color: var(--brand-text); }
.footer-base {
  display: flex; justify-content: space-between; gap: var(--s-4); flex-wrap: wrap;
  margin-top: var(--s-9); padding-top: var(--s-5);
  border-top: 1px solid var(--hairline);
  font: var(--t-caption); color: var(--muted);
}

/* ------------------------------------------------------- scroll reveals --- */
@media (prefers-reduced-motion: no-preference) {
  [data-reveal] {
    opacity: 0;
    transform: translateY(22px);
    transition: opacity var(--d-slow) var(--ease-out), transform var(--d-slow) var(--ease-out);
  }
  [data-reveal].in { opacity: 1; transform: none; }
}

/* ----------------------------------------------------------- responsive --- */
@media (max-width: 1080px) {
  /* Four cards at 230px each stop being readable before they stop fitting,
     so pair them off rather than letting auto-fit squeeze them. */
  .plans { grid-template-columns: repeat(2, 1fr); }
  .pv-body { grid-template-columns: 148px 1fr; }
  .pv-side { display: none; }
  .split { grid-template-columns: 1fr; gap: var(--s-8); }
}

@media (max-width: 880px) {
  .nav-links { display: none; }
  .nav { grid-template-columns: auto 1fr; }
  .nav-actions { justify-self: end; }
  .hero { padding-top: 128px; }
  .bento { grid-template-columns: repeat(2, 1fr); }
  .cell-a, .cell-b, .cell-c, .cell-d, .cell-e { grid-column: span 2; }
  .plans { grid-template-columns: 1fr; }
  .curve-ctl { grid-template-columns: 1fr; }
  .footer-inner { grid-template-columns: 1fr; gap: var(--s-7); }
}

@media (max-width: 620px) {
  .pv-body { grid-template-columns: 1fr; min-height: 0; }
  .pv-rail { flex-direction: row; overflow-x: auto; border-right: 0; border-bottom: 1px solid var(--hairline-soft); }
  .pv-rail-item { white-space: nowrap; }
  .pv-grades { grid-template-columns: repeat(2, 1fr); }
  .hero-cta .btn { width: 100%; }
  .dl-buttons .btn { width: 100%; }
  .footer-cols { grid-template-columns: 1fr 1fr; }
}

/* ------------------------------------------------- download: real builds --- */
.dl-buttons .is-unbuilt {
  opacity: 0.45;
  cursor: not-allowed;
  border-style: dashed;
}

/* ----------------------------------------------- download: the detection --- */
/* These sit on the photographic sky, where both themes are the same
   brightness, so they use the documented literal colours rather than tokens
   that would flip one of them to unreadable (AGENTS.md section 4, rule 4). */
.dl-detected {
  margin-top: var(--s-4);
  font: var(--t-body-sm);
  color: rgba(255, 255, 255, 0.82);
}

.dl-mobile {
  max-width: 50ch;
  margin: var(--s-5) auto 0;
  padding: var(--s-4) var(--s-5);
  border: 1px solid rgba(255, 255, 255, 0.28);
  border-radius: var(--r-lg);
  background: rgba(10, 24, 52, 0.26);
  -webkit-backdrop-filter: blur(14px);
  backdrop-filter: blur(14px);
  color: rgba(255, 255, 255, 0.92);
  font: var(--t-body-sm);
  text-align: left;
}
.dl-mobile .dl-copy { margin-top: var(--s-3); }
.dl-copy-url {
  display: block;
  margin-top: var(--s-3);
  padding: 8px 10px;
  border-radius: var(--r-md);
  background: rgba(10, 24, 52, 0.4);
  font-family: var(--font-mono);
  font-size: 0.75rem;
  color: #ffffff;
  word-break: break-all;
  user-select: all;
}

.dl-others { margin-top: var(--s-5); }
.dl-others-toggle {
  padding: 7px 14px;
  border: 1px solid rgba(255, 255, 255, 0.34);
  border-radius: var(--r-pill);
  background: transparent;
  color: rgba(255, 255, 255, 0.92);
  font: var(--t-label);
  cursor: pointer;
  transition: background var(--d-fast) var(--ease-out), border-color var(--d-fast) var(--ease-out);
}
.dl-others-toggle:hover { background: rgba(255, 255, 255, 0.14); border-color: rgba(255, 255, 255, 0.6); }
.dl-others-toggle:focus-visible { outline: 2px solid #ffffff; outline-offset: 3px; }

.dl-others-list {
  display: flex; flex-wrap: wrap; gap: var(--s-3); justify-content: center;
  margin-top: var(--s-4);
}
.dl-others-list .btn { flex-direction: row; }
.dl-others-list span { display: flex; flex-direction: column; align-items: flex-start; line-height: 1.2; }
.dl-others-list em { font-size: 0.6875rem; }
.dl-others-list .is-unbuilt { opacity: 0.45; cursor: not-allowed; border-style: dashed; }

@media (max-width: 620px) {
  .dl-others-list .btn { width: 100%; }
}

.dl-note {
  max-width: 62ch;
  margin: var(--s-6) auto 0;
  text-align: left;
  padding: var(--s-4) var(--s-5);
  border: 1px solid rgba(255, 255, 255, 0.28);
  border-radius: var(--r-lg);
  background: rgba(10, 24, 52, 0.26);
  -webkit-backdrop-filter: blur(14px);
  backdrop-filter: blur(14px);
  color: rgba(255, 255, 255, 0.92);
}
.dl-note summary {
  cursor: pointer;
  font: var(--t-label);
  color: #ffffff;
  list-style: none;
}
.dl-note summary::-webkit-details-marker { display: none; }
.dl-note summary::before { content: "+  "; font-family: var(--font-mono); }
.dl-note[open] summary::before { content: "-  "; }
.dl-note p {
  font: var(--t-body-sm);
  line-height: 1.65;
  margin-top: var(--s-3);
  color: rgba(255, 255, 255, 0.86);
}
.dl-note code {
  font: 0.8125rem var(--font-mono);
  padding: 2px 6px;
  border-radius: var(--r-xs);
  background: rgba(255, 255, 255, 0.16);
}

.dl-checksums { max-width: 72ch; margin: var(--s-5) auto 0; text-align: left; }
.dl-sums-head {
  font: var(--t-caption);
  text-transform: uppercase;
  letter-spacing: 0.12em;
  color: rgba(255, 255, 255, 0.6);
  margin-bottom: 6px;
}
.dl-sum {
  display: flex; flex-wrap: wrap; gap: 4px var(--s-4);
  padding: 7px 0;
  border-top: 1px solid rgba(255, 255, 255, 0.16);
}
.dl-sum-file { font: var(--t-caption); color: rgba(255, 255, 255, 0.86); flex: none; }
.dl-sum-hash {
  font: 0.6875rem/1.5 var(--font-mono);
  color: rgba(255, 255, 255, 0.55);
  word-break: break-all;
  flex: 1; min-width: 0;
}


/* ---------------------------------------------------------------- consent --- */
/* While third-party content is not allowed, the icon font has not loaded and
   every <i class="ph ..."> would render as an empty box. They are all
   decorative, so hiding them leaves clean text rather than a row of holes. */
.no-icons .ph,
.no-icons [class^="ph-"],
.no-icons [class*=" ph-"] { display: none; }

/* With one exception. Every other icon on the page is decorative and sits
   beside its own label, but the theme toggle's icon IS the control: hiding it
   leaves an empty circle. A text glyph keeps the button legible with no font
   to load. */
.no-icons .theme-toggle::after {
  content: "\25D1";          /* circle with right half black */
  font-size: 1rem;
  line-height: 1;
}

.consent {
  position: fixed;
  left: var(--s-4); right: var(--s-4); bottom: var(--s-4);
  z-index: var(--z-toast);
  display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between;
  gap: var(--s-4);
  max-width: 760px;
  margin: 0 auto;
  padding: var(--s-4) var(--s-5);
  border: 1px solid var(--hairline);
  border-radius: var(--r-lg);
  background: var(--surface);
  box-shadow: var(--e-4);
  opacity: 0;
  transform: translateY(12px);
  transition: opacity var(--d-mid) var(--ease-out), transform var(--d-mid) var(--ease-out);
}
.consent.in { opacity: 1; transform: none; }

@media (prefers-reduced-motion: reduce) {
  .consent { transition: none; transform: none; }
}

.consent-text {
  flex: 1 1 320px;
  margin: 0;
  font: var(--t-body-sm);
  color: var(--body);
  line-height: 1.55;
}
.consent-text a { color: var(--brand-text); text-decoration: underline; text-underline-offset: 2px; }

.consent-actions { display: flex; gap: var(--s-3); flex-shrink: 0; }

/* Both buttons are identical. A decline that is smaller, greyer or further
   away than the accept is the dark pattern this whole file exists to avoid. */
.consent-btn {
  min-width: 104px;
  padding: 9px 18px;
  border: 1px solid var(--hairline);
  border-radius: var(--r-pill);
  background: var(--surface-2);
  color: var(--ink);
  font: var(--t-label);
  cursor: pointer;
  transition: background var(--d-fast) var(--ease-out), border-color var(--d-fast) var(--ease-out);
}
.consent-btn:hover { background: var(--surface-3, var(--surface-2)); border-color: var(--brand); }

@media (max-width: 560px) {
  .consent-actions { width: 100%; }
  .consent-btn { flex: 1; }
}

/* ------------------------------------------------------ pricing honesty --- */
.plan-tag {
  display: inline-block;
  margin-left: 8px;
  padding: 2px 9px;
  border-radius: var(--r-pill);
  background: var(--surface-2);
  color: var(--muted);
  font: var(--t-caption);
  text-transform: uppercase;
  letter-spacing: 0.08em;
  vertical-align: middle;
}
.plan .is-unbuilt {
  opacity: 0.55;
  cursor: not-allowed;
  border-style: dashed;
}
.plans-note {
  max-width: 68ch;
  margin: var(--s-7) auto 0;
  text-align: center;
  font: var(--t-body-sm);
  color: var(--muted);
  line-height: 1.6;
}
.plans-note a { color: var(--brand-text); text-decoration: underline; text-underline-offset: 2px; }

.footer-link-btn {
  padding: 0;
  border: 0;
  background: none;
  color: var(--muted);
  font: var(--t-caption);
  text-decoration: underline;
  text-underline-offset: 2px;
  cursor: pointer;
}
.footer-link-btn:hover { color: var(--brand-text); }

/* ------------------------------------------------------------ account nav --- */
.nav-account {
  padding: 7px 12px;
  border-radius: var(--r-pill);
  color: var(--body);
  font: var(--t-label);
}
.nav-account:hover { color: var(--brand-text); background: var(--surface-2); }

@media (max-width: 520px) {
  .nav-account { display: none; }
}
