/* ==========================================================================
   NoteFlow landing — ink, highlighter and margin

   NoteFlow is a well-kept exercise book that happens to be clever, and the
   site is its cover and first pages: ink on warm paper (graphite in the dark
   theme), ruled lines for anything that is a list, plenty of room.

   Colour comes only from the pens a student already owns:
     the mark        violet on paper, lilac on graphite. The logo and nothing else.
     highlighter     one violet swipe per section, behind the words that matter.
     red pen         results only: the ring round a grade.
     pencil          now and then a note in the margin, in the handwriting face.
   Buttons are ink. Doodles, drawn in the mark's line, live in heroes and
   empty states. No gradients, glows, glass or sheen.

   Type: Instrument Sans for everything read, Instrument Serif italic for the
   one moment a section allows, Edu AU VIC WA NT Hand for margin notes.
   ========================================================================== */

/* ---- tokens --------------------------------------------------------------
   Light is the reference drawing; dark restates the same names. The privacy
   stage (.invert) takes the other set, so it is graphite on a paper page and
   paper on a graphite one. */

:root,
:root[data-theme="dark"] .invert {
  color-scheme: light;
  --paper: #FBFAF7;
  --sheet: #FFFFFF;
  --wash: #F4F2EC;
  --wash-2: #EDEAE3;
  --rail: #F5F3EE;
  --rail-on: #EAE7E0;
  --ink: #161615;
  --ink-2: #55534D;
  --ink-3: #6E6B64;
  --ink-4: #A9A59C;
  --on-ink: #FBFAF7;
  --rule: #ECE9E2;
  --rule-2: #DEDAD1;
  --rule-ink: #161615;
  --violet: #4F2A7F;
  --hl: #D6C2FF;
  --hl-ink: #161615;
  --hl-blend: multiply;
  --pen: #D23A2C;
  --pencil: #55534D;
  --ok: #2F7D57;
  --warn: #8A6114;
  --danger: #B23A30;
  --ok-soft: rgba(47, 125, 87, 0.1);
  --danger-soft: rgba(178, 58, 48, 0.08);
  --shadow-1: 0 1px 0 rgba(22, 22, 21, 0.04);
  --shadow-2: 0 1px 2px rgba(22, 22, 21, 0.05), 0 8px 24px -12px rgba(22, 22, 21, 0.14);
  --shadow-3: 0 2px 6px rgba(22, 22, 21, 0.07), 0 28px 56px -28px rgba(22, 22, 21, 0.22);
}

:root[data-theme="dark"],
.invert {
  color-scheme: dark;
  --paper: #191918;
  --sheet: #201F1E;
  --wash: #252422;
  --wash-2: #2C2B29;
  --rail: #1D1D1C;
  --rail-on: #2A2927;
  --ink: #EDEBE5;
  --ink-2: #B5B1A8;
  --ink-3: #8E8A82;
  --ink-4: #5F5C56;
  --on-ink: #191918;
  --rule: #2A2927;
  --rule-2: #3A3936;
  --rule-ink: #EDEBE5;
  --violet: #C2A8F5;
  --hl: #4A3778;
  --hl-ink: #F4F0FF;
  --hl-blend: normal;
  --pen: #F2735F;
  --pencil: #B5B1A8;
  --ok: #5BB98C;
  --warn: #D9A441;
  --danger: #E0695F;
  --ok-soft: rgba(91, 185, 140, 0.12);
  --danger-soft: rgba(224, 105, 95, 0.12);
  --shadow-1: 0 1px 0 rgba(0, 0, 0, 0.25);
  --shadow-2: 0 1px 2px rgba(0, 0, 0, 0.3), 0 10px 28px -12px rgba(0, 0, 0, 0.55);
  --shadow-3: 0 2px 6px rgba(0, 0, 0, 0.35), 0 30px 60px -28px rgba(0, 0, 0, 0.7);
}

/* With scripting off nothing stamps a theme, so the system's choice stands. */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme]) {
    color-scheme: dark;
    --paper: #191918; --sheet: #201F1E; --wash: #252422; --wash-2: #2C2B29;
    --rail: #1D1D1C; --rail-on: #2A2927;
    --ink: #EDEBE5; --ink-2: #B5B1A8; --ink-3: #8E8A82; --ink-4: #5F5C56; --on-ink: #191918;
    --rule: #2A2927; --rule-2: #3A3936; --rule-ink: #EDEBE5;
    --violet: #C2A8F5; --hl: #4A3778; --hl-ink: #F4F0FF; --hl-blend: normal;
    --pen: #F2735F; --pencil: #B5B1A8;
    --shadow-1: 0 1px 0 rgba(0, 0, 0, 0.25);
    --shadow-2: 0 1px 2px rgba(0, 0, 0, 0.3), 0 10px 28px -12px rgba(0, 0, 0, 0.55);
    --shadow-3: 0 2px 6px rgba(0, 0, 0, 0.35), 0 30px 60px -28px rgba(0, 0, 0, 0.7);
  }
}

:root {
  --sans: "Instrument Sans", ui-sans-serif, system-ui, -apple-system, "Segoe UI", sans-serif;
  --serif: "Instrument Serif", "Iowan Old Style", Georgia, serif;
  --hand: "Edu AU VIC WA NT Hand", "Segoe Print", "Bradley Hand", cursive;

  --r-sm: 8px;
  --r-md: 10px;
  --r-lg: 12px;
  --r-xl: 16px;

  --dd-w: 1.75px;
  --container: 1120px;
  --container-wide: 1280px;
  --gutter: clamp(1rem, 4vw, 2.5rem);
  --ease: cubic-bezier(0.2, 0.7, 0.2, 1);
  --ease-out: cubic-bezier(0.16, 1, 0.3, 1);

  /* The highlighter: one swipe with ragged chisel ends, a lighter first pass
     and darker overlaps at each end. */
  --hl-mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 200 40' preserveAspectRatio='none'%3E%3Cpath d='M6 7.5C40 4.6 82 6.8 121 5.2C151 4 176 5.8 196 4.4L199 11.5L196.8 19L199.6 27.5L195 35.6C160 37.2 121 34.6 81 36.6C51 38 25 35.8 3.2 37.6L0.6 27.4L3 17.6L1 9.2Z' fill-opacity='.84'/%3E%3Cpath d='M6 7.5C40 4.6 82 6.8 121 5.2C151 4 176 5.8 196 4.4L198 15.6C150 16.8 100 14.8 50 16.6C30 17.2 15 16.4 2 16.9L1 9.2Z' fill-opacity='.3'/%3E%3Cpath d='M1.5 26.2C40 25 90 27.4 140 25.6C165 24.8 185 26 198.6 25.4L195 35.6C160 37.2 121 34.6 81 36.6C51 38 25 35.8 3.2 37.6Z' fill-opacity='.32'/%3E%3Cpath d='M6 7.5L13 7.1L11.6 37.3L3.2 37.6L0.6 27.4L3 17.6L1 9.2Z' fill-opacity='.4'/%3E%3Cpath d='M189 4.7L196 4.4L199 11.5L196.8 19L199.6 27.5L195 35.6L188 35.8Z' fill-opacity='.3'/%3E%3C/svg%3E");
}

/* ==========================================================================
   Base
   ========================================================================== */

*, *::before, *::after { box-sizing: border-box; }
html { scroll-behavior: smooth; -webkit-text-size-adjust: 100%; }

body {
  margin: 0;
  background: var(--paper);
  color: var(--ink);
  font-family: var(--sans);
  font-size: 16px;
  line-height: 1.55;
  letter-spacing: -0.004em;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  text-rendering: optimizeLegibility;
}

::selection { background: var(--hl); color: var(--hl-ink); }

img, svg { display: inline-block; vertical-align: middle; }
img { max-width: 100%; }
a { color: var(--ink); text-decoration: none; }
h1, h2, h3 { margin: 0; text-wrap: balance; }
p { margin: 0; }
ul, ol, dl, dd { margin: 0; padding: 0; }
:focus-visible { outline: 2px solid var(--ink); outline-offset: 3px; border-radius: 4px; }

.container { width: min(var(--container), 100% - var(--gutter) * 2); margin-inline: auto; }
.container-wide { width: min(var(--container-wide), 100% - var(--gutter) * 2); margin-inline: auto; }

.sr-only {
  position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px;
  overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; border: 0;
}

/* Type ------------------------------------------------------------------- */

/* The moment: Instrument Serif italic, set tight. One per section. */
h1 {
  font-family: var(--serif);
  font-style: italic;
  font-weight: 400;
  font-size: clamp(3.2rem, 8.4vw, 7.4rem);
  line-height: 0.98;
  letter-spacing: -0.02em;
}
/* Section heads: the sans at 600, set like a hero title. */
h2 {
  font-family: var(--sans);
  font-weight: 600;
  font-size: clamp(2.1rem, 4.6vw, 3.8rem);
  line-height: 1.06;
  letter-spacing: -0.035em;
}
h3 { font-size: 1rem; line-height: 1.4; font-weight: 600; letter-spacing: -0.01em; }

/* Labels are sentence case in the third ink. Never uppercase, never mono. */
.idx { font-size: inherit; font-weight: 500; color: var(--ink-3); font-variant-numeric: tabular-nums; }
.label {
  display: flex; align-items: center; gap: 0.6rem;
  font-size: 0.94rem; font-weight: 500; color: var(--ink-3);
}
.eyebrow { font-size: clamp(0.98rem, 1.15vw, 1.08rem); font-weight: 500; color: var(--ink-3); }
.lede { font-size: clamp(1.05rem, 1.35vw, 1.2rem); line-height: 1.5; color: var(--ink-2); max-width: 34em; }
.section-lede { font-size: 1.05rem; line-height: 1.55; color: var(--ink-2); max-width: 40em; }
.soft { color: var(--ink-3); }
.num { font-variant-numeric: tabular-nums; }
.fine { font-size: 0.875rem; color: var(--ink-3); line-height: 1.6; }
.fine a { color: var(--ink-2); text-decoration: underline; text-underline-offset: 3px; text-decoration-color: var(--rule-2); }
.fine a:hover { color: var(--ink); text-decoration-color: currentColor; }

/* ---- the pens ------------------------------------------------------------- */

/* The highlighter. The swipe is the element's ::before, masked to the chisel
   shape, skewed and tilted a degree the way a hand draws it. Multiply on
   paper, so it darkens the page like ink and never greys the words. */
.hl { position: relative; z-index: 0; color: var(--hl-ink); white-space: nowrap; }
.hl::before {
  content: ""; position: absolute; z-index: -1;
  left: -0.16em; right: -0.2em; top: 0.16em; bottom: -0.02em;
  background: var(--hl);
  -webkit-mask: var(--hl-mask) 0 0 / 100% 100% no-repeat;
  mask: var(--hl-mask) 0 0 / 100% 100% no-repeat;
  mix-blend-mode: var(--hl-blend);
  transform: rotate(-1.2deg) skewX(-10deg);
  transform-origin: 50% 60%;
  pointer-events: none;
}
/* Serif at display sizes: a lower band, a chisel tip through the bottom of the words. */
.hl-display::before { top: 0.42em; bottom: 0.02em; left: -0.06em; right: -0.12em; transform: rotate(-1.6deg) skewX(-12deg); }
/* Drawn in, once, when its block arrives. */
@keyframes nf-swipe { from { clip-path: inset(0 100% 0 0); } to { clip-path: inset(0 0 0 0); } }
.js-reveal [data-reveal] .hl::before { clip-path: inset(0 100% 0 0); }
.js-reveal [data-reveal].in .hl::before { animation: nf-swipe 420ms var(--ease-out) 380ms both; }

/* Pencil in the margin: short, lower case, useful. Never on a control. */
.note {
  --dd-w: 1.5px;
  display: inline-flex; align-items: center; gap: 6px;
  color: var(--pencil);
  font-family: var(--hand); font-weight: 500; font-size: 20px; line-height: 1.12;
  letter-spacing: 0.005em; word-spacing: 0.14em;
  transform: rotate(-3deg); transform-origin: left center;
  white-space: nowrap;
}

/* Doodles: monoline, round caps and joins, at the mark's weight. */
.dd { display: block; flex: none; overflow: visible; }
.dd, .dd * { fill: none; stroke: currentColor; stroke-width: var(--dd-w); stroke-linecap: round; stroke-linejoin: round; }
.dd path { vector-effect: non-scaling-stroke; }
.dd .dd-fill { fill: var(--paper); }
.dd .dd-dots { stroke-dasharray: 0.1 5.5; stroke-width: calc(var(--dd-w) + 0.5px); }

/* The mark, always in --violet (lilac on graphite). */
.nf-mark { display: block; flex: none; overflow: visible; color: var(--violet); stroke-width: 3.3; }

/* Buttons ---------------------------------------------------------------- */

.btn {
  display: inline-flex; align-items: center; justify-content: center; gap: 0.5rem;
  height: 44px; padding: 0 1.15rem; border-radius: var(--r-lg);
  font-family: var(--sans); font-weight: 600; font-size: 0.97rem; line-height: 1; letter-spacing: -0.012em;
  border: 0; cursor: pointer; white-space: nowrap;
  transition: background 0.16s var(--ease), color 0.16s var(--ease), box-shadow 0.16s var(--ease), transform 60ms var(--ease), filter 0.16s var(--ease);
}
.btn-sm { height: 36px; padding: 0 0.9rem; border-radius: 9px; font-size: 0.9rem; }
.btn-lg { height: 52px; padding: 0 1.4rem; font-size: 1.03rem; }
/* The one filled control: a slab of ink with paper-coloured words. */
.btn-primary { background: var(--ink); color: var(--on-ink); }
/* The other: a sheet with a control hairline. */
.btn-ghost { background: var(--sheet); color: var(--ink); box-shadow: inset 0 0 0 1px var(--rule-2), var(--shadow-1); }
@media (hover: hover) {
  .btn-primary:hover { background: color-mix(in srgb, var(--ink) 86%, var(--paper)); }
  .btn-ghost:hover { background: var(--wash); }
}
.btn:active { transform: translateY(1px); }
.btn-primary:active { filter: brightness(0.9); }
:root[data-theme="dark"] .btn-primary:active { filter: brightness(1.15); }

/* ==========================================================================
   Header

   A ruled bar across the top: nothing over the opening, then paper with one
   hairline under it once you scroll. An ink line slides under the section
   you are reading.
   ========================================================================== */

.site-header {
  position: fixed; top: 0; left: 0; right: 0; z-index: 50;
  background: transparent;
  border-bottom: 1px solid transparent;
  transition: background-color 0.3s var(--ease), border-color 0.3s var(--ease);
}
.site-header.scrolled {
  background: var(--paper);
  border-bottom-color: var(--rule);
}
.nav {
  position: relative;
  display: flex; align-items: center; gap: 1.5rem;
  width: min(var(--container-wide), 100% - var(--gutter) * 2); margin-inline: auto;
  height: 64px;
}

.brand {
  display: inline-flex; align-items: center; gap: 9px;
  font-weight: 600; font-size: 1.12rem; letter-spacing: -0.025em; color: var(--ink);
}
.brand .nf-mark { width: 24px; height: 24px; stroke-width: 3.3; }

.nav-links { list-style: none; position: relative; display: flex; align-items: center; gap: 0.25rem; margin: 0 auto; }
.nav-links a {
  position: relative; z-index: 1;
  display: block; padding: 0.5rem 0.75rem;
  color: var(--ink-2); font-size: 0.95rem; font-weight: 500;
  transition: color 0.18s var(--ease);
}
.nav-links a:hover, .nav-links a.is-here { color: var(--ink); }

/* The current section: an ink line, one element that slides between links. */
.nav-marker {
  position: absolute; left: 0; bottom: 6px; z-index: 0;
  width: var(--mw, 0px); height: 2px; padding: 0 0.75rem;
  background: var(--ink); background-clip: content-box;
  border-radius: 2px; pointer-events: none;
  transform: translate3d(var(--mx, 0px), 0, 0);
  opacity: 0;
  transition: transform 0.42s var(--ease), width 0.42s var(--ease), opacity 0.24s var(--ease);
}
.nav-marker.is-on { opacity: 1; }
.site-header:not(.scrolled) .nav-marker { opacity: 0; }

.nav-actions { display: flex; align-items: center; gap: 0.5rem; margin-left: auto; }
.nav-links + .nav-actions { margin-left: 0; }

.theme-toggle {
  width: 40px; height: 40px; border-radius: var(--r-md); display: inline-grid; place-items: center;
  border: 0; background: transparent; color: var(--ink-2); cursor: pointer;
  transition: color 0.16s, background-color 0.16s var(--ease);
}
.theme-toggle:hover { color: var(--ink); background: var(--wash); }
.theme-toggle .ico-sun { display: none; }
.theme-toggle .ico-moon { display: block; }
:root[data-theme="dark"] .theme-toggle .ico-sun { display: block; }
:root[data-theme="dark"] .theme-toggle .ico-moon { display: none; }

@media (prefers-reduced-motion: reduce) {
  .nav-marker { transition: opacity 0.2s linear; }
}
@media (max-width: 860px) {
  .nav-links { display: none; }
  .nav { height: 60px; }
  .nav-links + .nav-actions { margin-left: auto; }
}

/* ==========================================================================
   Hero

   The promise, set like a manifesto and centred in one screen: the mark
   drawn once as a single line, a serif headline in two parts with the swipe
   under the second, one sentence, and the way in.

   The headline takes turns through a short run of lines (js/main.js). They
   are stacked in one grid cell and every part is held to one line, so the
   block is always exactly two lines tall: nothing below it ever moves. A
   turn is a blur cross-fade a word at a time: the outgoing words lift,
   blur and fade; the incoming ones resolve out of a blur from just below;
   then the highlighter is drawn under the new second half.
   ========================================================================== */

.hero { position: relative; }
.hero-stage {
  position: relative;
  min-height: 100vh; min-height: 100svh;
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  padding: 116px var(--gutter) 112px;
  text-align: center;
  overflow: hidden;
}

/* The mark, as one line. It draws itself once when the page arrives. */
.hero-mark {
  display: block; flex: none; overflow: visible;
  width: clamp(64px, 6.4vw, 92px); height: clamp(64px, 6.4vw, 92px);
  color: var(--violet);
}
.hero-mark path {
  fill: none; stroke: currentColor; stroke-width: 2.5;
  stroke-linecap: round; stroke-linejoin: round;
  stroke-dasharray: 1 1.02; stroke-dashoffset: 0;
  animation: mark-draw 2.1s cubic-bezier(0.65, 0, 0.3, 1) 0.1s both;
}
@keyframes mark-draw { from { stroke-dashoffset: 1.02; } to { stroke-dashoffset: 0; } }

/* Sized so the widest part ("Start remembering.") fills the measure on a
   phone and never wraps; capped for wide screens. */
.headline {
  --hx: clamp(2.4rem, calc((100vw - 2.4rem) / 7.4), 6rem);
  position: relative;
  display: grid; justify-items: center;
  margin-top: clamp(1.5rem, 3.2vw, 2.6rem);
  font-family: var(--serif); font-weight: 400; font-style: normal;
  font-size: var(--hx); line-height: 1.04; letter-spacing: -0.022em;
}
.hx-line {
  grid-area: 1 / 1;
  display: flex; flex-direction: column; align-items: center;
  margin: 0; max-width: none;
  font: inherit; letter-spacing: inherit;
}
.hx-vis { display: flex; flex-direction: column; align-items: center; }
.hx-a, .hx-b { display: block; white-space: nowrap; }
.hx-b { font-style: italic; }
/* The serif's italic leans out past its box; give it room so nothing clips. */
.hx-b { padding-right: 0.04em; }
/* Without scripting only the first line stands; the rest keep the space. */
.hx-line + .hx-line { visibility: hidden; }
.headline.is-live .hx-line { visibility: visible; }
.headline.is-live .hx-line:not(.is-on) { pointer-events: none; user-select: none; -webkit-user-select: none; }

/* ---- the turn ------------------------------------------------------------ */

.hx-line .w { display: inline-block; }
.headline.is-live .w {
  opacity: 0;
  filter: blur(16px);
  transform: translate3d(0, 0.3em, 0) scale(1.02);
}
.headline.is-live .is-on .w {
  opacity: 1; filter: blur(0); transform: none;
  transition:
    opacity 0.75s cubic-bezier(0.2, 0.7, 0.2, 1) var(--wd, 0s),
    filter 1s cubic-bezier(0.2, 0.7, 0.2, 1) var(--wd, 0s),
    transform 1.15s cubic-bezier(0.16, 1, 0.3, 1) var(--wd, 0s);
}
.headline.is-live .is-leaving .w {
  opacity: 0; filter: blur(12px); transform: translate3d(0, -0.2em, 0) scale(0.99);
  transition:
    opacity 0.55s cubic-bezier(0.4, 0, 0.7, 0.4) var(--wo, 0s),
    filter 0.55s cubic-bezier(0.4, 0, 0.7, 0.4) var(--wo, 0s),
    transform 0.7s cubic-bezier(0.5, 0, 0.3, 1) var(--wo, 0s);
}
.headline.is-live .is-on .w,
.headline.is-live .is-leaving .w { will-change: transform, opacity, filter; }
/* Once a line has settled it gives its layers back. */
.headline.is-live .is-on.is-settled .w { will-change: auto; }

/* The swipe: drawn under each new second half once its words are in, and
   lifted away with them when the line leaves. */
.headline.is-live .hl::before { clip-path: inset(0 100% 0 0); }
.headline.is-live .is-on .hl::before { animation: nf-swipe 640ms cubic-bezier(0.6, 0, 0.2, 1) var(--swipe-at, 0.5s) both; }
.headline.is-live .is-leaving .hl::before {
  clip-path: inset(0 0 0 0); opacity: 0; translate: 0 -0.14em;
  transition: opacity 0.45s cubic-bezier(0.4, 0, 0.7, 0.4), translate 0.7s cubic-bezier(0.5, 0, 0.3, 1);
}

/* ---- the copy and the way in -------------------------------------------- */

.hero-sub {
  margin-top: clamp(1.4rem, 2.4vw, 2rem);
  max-width: 31em;
  font-size: clamp(1.05rem, 1.3vw, 1.18rem); line-height: 1.5; letter-spacing: -0.012em;
  color: var(--ink-2);
  text-wrap: balance;
}
/* The promise first, in ink; the how follows in the quieter grey. */
.hero-sub strong { color: var(--ink); font-weight: 600; }

.hero-reserve {
  display: flex; align-items: center; gap: 6px;
  width: min(460px, 100%);
  margin-top: clamp(1.8rem, 3vw, 2.5rem);
  padding: 5px;
  border-radius: 14px;
  background: var(--sheet);
  box-shadow: inset 0 0 0 1px var(--rule-2), var(--shadow-1);
  transition: box-shadow 0.2s var(--ease);
}
.hero-reserve:focus-within { box-shadow: inset 0 0 0 1.5px var(--ink), var(--shadow-1); }
.hero-reserve input {
  flex: 1; min-width: 0; height: 46px;
  padding: 0 12px 0 14px;
  border: 0; background: transparent; outline: none;
  font: inherit; font-size: 16px; letter-spacing: -0.008em; color: var(--ink);
}
.hero-reserve input::placeholder { color: var(--ink-3); opacity: 1; }
.hero-reserve .btn { height: 46px; border-radius: 10px; padding: 0 18px; font-size: 0.97rem; }
.hero-reserve .btn:focus-visible { outline-offset: 2px; }
.hero-error:empty { display: none; }
.hero-error { margin-top: 10px; font-size: 0.9rem; color: var(--danger); }

.hero-after { display: flex; flex-direction: column; align-items: center; gap: 0.35rem; margin-top: 14px; }
.hero-note { font-size: 0.9rem; color: var(--ink-3); max-width: 62ch; text-wrap: balance; }
.intro-invite { font-size: 0.9rem; color: var(--ink-2); }
.hero-try {
  --dd-w: 1.5px;
  display: inline-flex; align-items: center; gap: 6px;
  margin-top: clamp(0.9rem, 2vw, 1.4rem); padding: 6px 4px;
  font-size: 0.97rem; font-weight: 500; letter-spacing: -0.01em; color: var(--ink-2);
  transition: color 0.16s var(--ease);
}
.hero-try svg { transition: transform 0.3s var(--ease); }
.hero-try:hover { color: var(--ink); }
.hero-try:hover svg { transform: translateY(2px); }

/* ---- the turn control ---------------------------------------------------- */

.hx-control {
  position: absolute; left: 50%; bottom: clamp(18px, 3.6vh, 34px);
  display: flex; align-items: center; gap: 10px;
  transform: translateX(-50%);
}
.hx-control[hidden] { display: none; }
.hx-pause {
  display: grid; place-items: center; width: 32px; height: 32px; padding: 0;
  border: 0; border-radius: 50%; background: transparent; color: var(--ink-3); cursor: pointer;
  transition: color 0.16s var(--ease), background-color 0.16s var(--ease);
}
.hx-pause:hover { color: var(--ink); background: var(--wash); }
.hx-pause svg { grid-area: 1 / 1; }
.hx-pause path { fill: none; stroke: currentColor; stroke-width: 1.6; stroke-linecap: round; stroke-linejoin: round; }
.hx-pause .i-play path { fill: currentColor; stroke-width: 1.2; }
.hx-pause .i-play, .hx-pause[aria-pressed="true"] .i-pause { display: none; }
.hx-pause[aria-pressed="true"] .i-play { display: block; }
.hx-dashes { display: flex; gap: 6px; }
.hx-dashes i { position: relative; width: 18px; height: 2px; border-radius: 2px; background: var(--rule-2); overflow: hidden; }
.hx-dashes b { position: absolute; inset: 0; background: var(--ink-3); transform-origin: left; transform: scaleX(0); }

/* ---- arrival ------------------------------------------------------------- */

/* Until the words are ready the headline and the copy wait; if the script
   never runs, a fallback shows them anyway. */
.js .hero:not(.is-ready) .headline,
.js .hero:not(.is-ready) .hero-rise {
  opacity: 0;
  animation: hero-fallback 0s linear 2.5s forwards;
}
@keyframes hero-fallback { to { opacity: 1; } }
.hero.is-ready .hero-rise { animation: hero-rise 0.95s var(--ease) var(--d, 0s) both; }
@keyframes hero-rise {
  from { opacity: 0; transform: translate3d(0, 14px, 0); filter: blur(6px); }
  to { opacity: 1; transform: none; filter: blur(0); }
}

@media (max-width: 600px) {
  .hero-stage { padding: 96px var(--gutter) 88px; justify-content: flex-start; }
  .hero-mark { margin-top: 2vh; }
  .headline { margin-top: 1.6rem; }
  .hero-reserve {
    flex-direction: column; align-items: stretch; gap: 10px;
    padding: 0; background: none; box-shadow: none;
  }
  .hero-reserve:focus-within { box-shadow: none; }
  .hero-reserve input {
    flex: none; height: 52px; border-radius: 12px;
    background: var(--sheet); box-shadow: inset 0 0 0 1px var(--rule-2);
    transition: box-shadow 0.2s var(--ease);
  }
  .hero-reserve input:focus { box-shadow: inset 0 0 0 1.5px var(--ink); }
  .hero-reserve .btn { height: 52px; border-radius: 12px; font-size: 1.03rem; }
}
@media (max-width: 600px) and (min-height: 760px) {
  /* Top-aligned rather than centred, so a late face swap in the copy below
     can never nudge the mark or the headline. */
  .hero-stage { padding-top: clamp(96px, 15vh, 140px); }
  .hero-mark { margin-top: 0; }
}
@media (min-width: 601px) and (max-height: 760px) {
  .hero-stage { padding-top: 92px; padding-bottom: 84px; }
  .hero-mark { width: 64px; height: 64px; }
  .headline { --hx: clamp(2.4rem, 9.4vh, 5.4rem); margin-top: 1.4rem; }
}
@media (prefers-reduced-motion: reduce) {
  .hero-mark path { animation: none; stroke-dasharray: none; }
}

/* ==========================================================================
   Proof: Today

   One large, calm shot of the Today screen in the app's own shell, built
   in HTML on a 1440 x 900 page and scaled into a 1500-wide canvas that
   also holds the margin notes. The canvas scales to the width it is given
   with a container-relative factor — tan(atan2(100cqw, 1500px)) is that
   width over 1500 as a plain number — so the shot and its notes move as one
   picture and nothing is measured by script.
   ========================================================================== */

.proof { position: relative; overflow-x: clip; scroll-margin-top: 40px; padding: clamp(2rem, 5vw, 4rem) 0 clamp(4.5rem, 9vw, 8rem); }
.proof-head {
  display: flex; flex-direction: column; align-items: center; gap: 1rem;
  text-align: center; margin-bottom: clamp(2.5rem, 5vw, 4.5rem);
}
.proof-head h2 { font-size: clamp(2.3rem, 5.2vw, 4.4rem); max-width: 15ch; }
.proof-lede { max-width: 38ch; color: var(--ink-2); font-size: clamp(1.05rem, 1.35vw, 1.2rem); line-height: 1.5; text-wrap: balance; }

.proof-stage {
  container-type: inline-size;
  width: min(1500px, 100% - var(--gutter) * 2); margin-inline: auto;
  aspect-ratio: 1500 / 790;
}
.proof-canvas {
  position: relative; width: 1500px; height: 790px;
  transform-origin: 0 0;
  scale: tan(atan2(100cqw, 1500px));
  perspective: 2200px; perspective-origin: 50% 0%;
}
.proof-shot {
  position: absolute; left: 203px; top: 84px; width: 1094px; height: 684px;
  border-radius: 14px; overflow: hidden;
  background: var(--paper);
  box-shadow: 0 0 0 1px var(--rule-2), 0 2px 4px rgba(22, 22, 21, 0.04), 0 44px 90px -44px rgba(22, 22, 21, 0.26);
  transform-origin: 50% 100%;
}
:root[data-theme="dark"] .proof-shot { box-shadow: 0 0 0 1px var(--rule-2), 0 2px 4px rgba(0, 0, 0, 0.3), 0 44px 90px -40px rgba(0, 0, 0, 0.75); }

.proof-notes { position: absolute; left: 203px; top: 84px; width: 1094px; height: 684px; pointer-events: none; }
.proof-marks { position: absolute; left: 0; top: 0; overflow: visible; color: var(--pencil); --dd-w: 1.6px; }
.proof-marks path { stroke-dasharray: 1 1.02; stroke-dashoffset: 0; }
.proof-note {
  position: absolute; margin: 0;
  font-size: 23px; line-height: 1.08;
  transform: rotate(var(--tilt, -3deg)); transform-origin: 0 50%;
}
/* Written once the shot has landed: each arrow, then its note. */
.js .proof.is-live .proof-marks path { stroke-dashoffset: 1.02; }
.js .proof.is-live .proof-note { opacity: 0; }
.js .proof.is-live.is-flat .proof-marks path { animation: nf-pencil 620ms cubic-bezier(0.5, 0, 0.2, 1) both; }
.js .proof.is-live.is-flat .proof-marks path:nth-child(2n) { animation-duration: 260ms; }
.proof-marks path:nth-child(1) { animation-delay: 0.05s; } .proof-marks path:nth-child(2) { animation-delay: 0.6s; }
.proof-marks path:nth-child(3) { animation-delay: 0.35s; } .proof-marks path:nth-child(4) { animation-delay: 0.9s; }
.proof-marks path:nth-child(5) { animation-delay: 0.65s; } .proof-marks path:nth-child(6) { animation-delay: 1.2s; }
.js .proof.is-live.is-flat .proof-note { animation: nf-note 520ms var(--ease) calc(0.25s + var(--n) * 0.3s) both; }
@keyframes nf-pencil { from { stroke-dashoffset: 1.02; } to { stroke-dashoffset: 0; } }
@keyframes nf-note { from { opacity: 0; translate: 0 6px; } to { opacity: 1; translate: 0 0; } }

/* ---- the app, at application density ------------------------------------
   Everything in here is scoped to .appshot so none of it reaches the page. */

.appshot {
  width: 1440px; height: 900px;
  display: grid; grid-template-columns: 248px 1fr;
  transform: scale(0.76); transform-origin: 0 0;
  background: var(--paper); color: var(--ink);
  font-size: 14.5px; line-height: 1.45; letter-spacing: -0.004em; text-align: left;
}
.appshot p, .appshot ul { margin: 0; padding: 0; list-style: none; }
.appshot .ai { display: block; flex: none; fill: none; stroke: currentColor; stroke-width: 1.6; stroke-linecap: round; stroke-linejoin: round; }
.appshot .as-dot { display: inline-block; width: 3px; height: 3px; margin: 0 8px 2px; border-radius: 50%; background: var(--ink-4); vertical-align: middle; }
.appshot .as-at { color: var(--ink-3); }

.as-rail { display: flex; flex-direction: column; padding: 14px 10px 12px; background: var(--rail); border-right: 1px solid var(--rule); }
.as-head { display: flex; align-items: center; justify-content: space-between; height: 40px; padding: 0 6px 0 10px; }
.as-lockup { display: inline-flex; align-items: center; gap: 8px; font-weight: 600; font-size: 16px; letter-spacing: -0.025em; }
.as-lockup .nf-mark { stroke-width: 3.3; }
.as-iconbtn { width: 32px; height: 32px; display: grid; place-items: center; border-radius: 8px; color: var(--ink-3); }
.as-search { display: flex; align-items: center; gap: 9px; height: 36px; margin: 10px 2px 14px; padding: 0 10px; border-radius: 9px; background: var(--sheet); box-shadow: inset 0 0 0 1px var(--rule-2); color: var(--ink-3); font-size: 14px; }
.as-search kbd { margin-left: auto; font: 500 12px var(--sans); color: var(--ink-3); }
.as-nav { display: grid; gap: 1px; }
.as-nav + .as-nav { margin-top: 14px; padding-top: 14px; border-top: 1px solid var(--rule); }
.as-nav > span { display: flex; align-items: center; gap: 11px; height: 36px; padding: 0 10px; border-radius: 8px; color: var(--ink-2); font-weight: 500; font-size: 14.5px; letter-spacing: -0.008em; }
.as-nav > span .ai { color: var(--ink-3); }
.as-nav > span.on { background: var(--rail-on); color: var(--ink); font-weight: 600; }
.as-nav > span.on .ai { color: var(--ink); }
.as-count { margin-left: auto; min-width: 20px; height: 20px; padding: 0 6px; border-radius: 10px; background: var(--ink); color: var(--on-ink); font-style: normal; font-size: 12px; font-weight: 600; display: grid; place-items: center; }
.as-me { margin-top: auto; display: flex; align-items: center; gap: 10px; padding: 12px 10px 4px; border-top: 1px solid var(--rule); }
.as-who { line-height: 1.25; }
.as-who b { display: block; font-weight: 600; font-size: 14px; }
.as-who span { font-size: 13px; color: var(--ink-3); }
.as-me .as-iconbtn { margin-left: auto; }

.as-main { overflow: hidden; }
.as-topline { height: 56px; padding: 0 32px 0 56px; display: flex; align-items: center; justify-content: space-between; color: var(--ink-3); font-size: 14px; }
.as-acts { display: flex; align-items: center; gap: 8px; }
.as-quiz { display: inline-flex; align-items: center; gap: 8px; height: 34px; padding: 0 12px 0 10px; border-radius: 9px; background: var(--wash); color: var(--ink-2); font-size: 14px; }
.as-quiz b { color: var(--ink); font-weight: 600; }
.as-new { display: inline-flex; align-items: center; gap: 6px; height: 34px; padding: 0 12px; border-radius: 9px; background: var(--sheet); box-shadow: inset 0 0 0 1px var(--rule-2), var(--shadow-1); color: var(--ink); font-weight: 600; font-size: 14px; }
.as-wrap { padding: 28px 56px 0; max-width: 1016px; }
.as-greet { font-family: var(--serif); font-style: italic; font-size: 54px; line-height: 1; letter-spacing: -0.02em; }
.as-sub { margin-top: 12px !important; font-size: 17px; color: var(--ink-2); letter-spacing: -0.012em; }
.as-next {
  position: relative; margin-top: 36px; padding: 28px 32px 30px; border-radius: 16px;
  background: var(--sheet); box-shadow: inset 0 0 0 1px var(--rule), var(--shadow-1);
  display: grid; grid-template-columns: 1fr 200px; align-items: center;
}
.as-lbl { display: flex; align-items: center; gap: 8px; font-size: 13.5px; color: var(--ink-3); }
.as-title { margin-top: 8px !important; font-size: 32px; font-weight: 600; letter-spacing: -0.03em; line-height: 1.12; }
.as-meta { margin-top: 10px !important; display: flex; align-items: center; font-size: 15px; color: var(--ink-2); }
.as-meta b { color: var(--ink); font-weight: 600; }
.as-btns { margin-top: 22px !important; display: flex; gap: 8px; }
.as-btn, .as-btn-ghost { display: inline-flex; align-items: center; height: 44px; padding: 0 20px; border-radius: 11px; font-size: 15px; font-weight: 600; letter-spacing: -0.012em; }
.as-btn { background: var(--ink); color: var(--on-ink); }
.as-btn-ghost { color: var(--ink-2); padding: 0 14px; }
.as-art { justify-self: end; margin-right: 18px; color: var(--ink); --dd-w: 1.6px; }
.as-art .as-fill { fill: var(--sheet); }
.as-cols { margin-top: 40px; display: grid; grid-template-columns: 1fr 1fr; gap: 56px; }
.as-sec { display: flex; align-items: baseline; justify-content: space-between; padding-bottom: 10px; border-bottom: 1px solid var(--rule-ink); }
.as-sec b { font-size: 15px; font-weight: 600; letter-spacing: -0.01em; }
.as-sec span { font-size: 13.5px; color: var(--ink-3); }
.as-tasks li { display: flex; align-items: center; gap: 12px; height: 50px; border-bottom: 1px solid var(--rule); }
.as-tasks .tt { flex: 1; min-width: 0; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; font-size: 14.5px; }
.as-tasks .when { font-size: 13.5px; color: var(--ink-3); width: 66px; text-align: right; }
.as-tasks li.done .tt { color: var(--ink-3); text-decoration: line-through; text-decoration-color: var(--ink-4); }
.as-check { width: 20px; height: 20px; border-radius: 6px; box-shadow: inset 0 0 0 1.5px var(--ink-4); flex: none; display: grid; place-items: center; }
.as-check.done { background: var(--ink); box-shadow: none; color: var(--on-ink); }
.as-sched li { position: relative; display: grid; grid-template-columns: 54px 1fr auto; gap: 14px; align-items: center; height: 50px; border-bottom: 1px solid var(--rule); }
.as-sched .t { font-size: 13.5px; color: var(--ink-3); }
.as-sched .w { font-size: 14.5px; }
.as-sched .w span { color: var(--ink-3); }
.as-sched .r { font-size: 13.5px; color: var(--ink-3); }
.as-sched li.past .w, .as-sched li.past .t { color: var(--ink-3); }
.as-sched .now { position: absolute; left: 0; right: 0; bottom: -1px; height: 0; border-top: 1.5px solid var(--ink); }
.as-sched .now::before { content: ""; position: absolute; left: 0; top: -4.75px; width: 8px; height: 8px; border-radius: 50%; background: var(--ink); }
.as-sched .now em { position: absolute; right: 0; top: -9px; font-style: normal; font-size: 12px; font-weight: 600; background: var(--paper); padding-left: 8px; }
.as-from { margin-top: 34px !important; display: flex; align-items: center; gap: 10px; height: 48px; padding: 0 16px; border-radius: 12px; background: var(--wash); color: var(--ink-2); font-size: 14px; }
.as-from b { font-weight: 600; color: var(--ink); }
.as-from .as-dot { margin: 0 2px; }
.as-from .go { margin-left: auto; display: inline-flex; align-items: center; gap: 4px; font-weight: 600; color: var(--ink); }

/* Phone: a cropped peek that runs off the right edge; the notes stay out. */
@media (max-width: 860px) {
  .proof-stage { width: calc(100% - var(--gutter)); margin-left: var(--gutter); margin-right: 0; aspect-ratio: 700 / 640; overflow: hidden; contain: paint; border-radius: 12px 0 0 12px; }
  .proof-canvas { width: 700px; height: 640px; scale: tan(atan2(100cqw, 700px)); }
  .proof-shot { left: 1px; top: 1px; height: 638px; border-radius: 14px 0 0 14px; }
  /* Past the rail, straight to the day. */
  .proof-shot .appshot { margin-left: -189px; }
  .proof-notes { display: none; }
}

/* ==========================================================================
   Play: the challenge

   Three questions on cell parts, the way a friend's challenge link looks.
   Tap an answer and the red pen marks it at once; after the third the score
   is ringed in red pen with the pen's one note, and you take your place on
   the scoreboard, highlighted. The board and the card stay the same size
   throughout, so nothing on the page moves while you play.
   ========================================================================== */

.play { padding: clamp(4.5rem, 9vw, 8rem) 0 clamp(4rem, 8vw, 7rem); }
.play-grid {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 560px);
  grid-template-areas: "head card" "board card";
  grid-template-rows: auto 1fr;
  column-gap: clamp(2.5rem, 7vw, 7rem); row-gap: clamp(2.5rem, 4vw, 3.5rem);
  align-items: start;
}
.play-head { grid-area: head; display: flex; flex-direction: column; gap: 1rem; padding-top: 1rem; border-top: 1px solid var(--rule-ink); }
.play-head h2 { font-size: clamp(2.3rem, 5vw, 4.2rem); }
.play-lede { max-width: 36ch; color: var(--ink-2); font-size: clamp(1.05rem, 1.3vw, 1.18rem); line-height: 1.55; }

.at { color: var(--ink-3); font-weight: 400; }
.tag {
  display: inline-flex; align-items: center; height: 22px; padding: 0 7px; border-radius: 6px;
  font-size: 13px; font-weight: 500; letter-spacing: -0.003em; white-space: nowrap;
  background: var(--tag-bg, var(--wash-2)); color: var(--tag-fg, var(--ink-2));
}
.tag.bio { --tag-bg: #E3EDDC; --tag-fg: #305A2D; }
.tag.chem { --tag-bg: #DDE8F2; --tag-fg: #1F4A6B; }
.tag.maths { --tag-bg: #F6E6D3; --tag-fg: #6E3E14; }
.tag.eng { --tag-bg: #F5E1E7; --tag-fg: #712C47; }
.tag.lang { --tag-bg: #F3EDCC; --tag-fg: #625010; }
:root[data-theme="dark"] .tag.bio { --tag-bg: #232F22; --tag-fg: #A6CD9A; }
:root[data-theme="dark"] .tag.chem { --tag-bg: #1D2A36; --tag-fg: #9AC1E0; }
:root[data-theme="dark"] .tag.maths { --tag-bg: #35291C; --tag-fg: #E4B78C; }
:root[data-theme="dark"] .tag.eng { --tag-bg: #35232A; --tag-fg: #E6A8BE; }
:root[data-theme="dark"] .tag.lang { --tag-bg: #322D1A; --tag-fg: #DCC774; }

/* ---- the scoreboard ------------------------------------------------------ */

.cq-boardwrap { grid-area: board; position: relative; width: min(100%, 440px); }
.cq-board-head { display: flex; justify-content: space-between; align-items: baseline; padding-bottom: 10px; border-bottom: 1px solid var(--rule-ink); }
.cq-board-head p { font-size: 15px; font-weight: 600; letter-spacing: -0.01em; }
.cq-board-head span { font-size: 13.5px; color: var(--ink-3); }
.cq-board { list-style: none; position: relative; }
.cq-board li {
  position: relative; z-index: 0;
  display: grid; grid-template-columns: 28px 1fr 52px 46px; align-items: center;
  height: 48px; border-bottom: 1px solid var(--rule); font-size: 15px;
}
.cq-board .rk { color: var(--ink-3); font-size: 14px; }
.cq-board .sc { text-align: right; font-weight: 500; }
.cq-board .tm { text-align: right; color: var(--ink-3); font-size: 14px; }
.cq-board li.is-you { color: var(--hl-ink); }
.cq-board li.is-you b { font-weight: 600; }
/* Your row is the section's one swipe. */
.cq-board li.is-you::before {
  content: ""; position: absolute; z-index: -1;
  left: -12px; right: -10px; top: 7px; bottom: 6px;
  background: var(--hl);
  -webkit-mask: var(--hl-mask) 0 0 / 100% 100% no-repeat; mask: var(--hl-mask) 0 0 / 100% 100% no-repeat;
  mix-blend-mode: var(--hl-blend);
  transform: rotate(-0.6deg);
  animation: nf-swipe 560ms cubic-bezier(0.6, 0, 0.2, 1) var(--swipe-at, 0.5s) both;
}
.cq-board li.is-you .rk, .cq-board li.is-you .tm { color: var(--hl-ink); opacity: 0.78; }
.cq-beat {
  position: absolute; left: calc(100% + 14px); top: 44px;
  font-size: 21px; color: var(--pencil);
  transition: opacity 0.4s var(--ease);
}
.cq-beat svg { width: 40px; height: 18px; margin-top: 8px; }
.play.is-played .cq-beat { opacity: 0; }

/* ---- the card ------------------------------------------------------------ */

.cq { grid-area: card; position: relative; }
.cq-sheets i {
  position: absolute; inset: 0; border-radius: 20px;
  background: var(--sheet); box-shadow: 0 0 0 1px var(--rule-2);
  transition: transform 0.6s var(--ease), opacity 0.4s var(--ease);
}
.cq-sheets i:first-child { transform: rotate(2.2deg) translate(8px, 6px); }
.cq-sheets i:last-child { transform: rotate(-1.4deg) translate(-4px, 10px); }
.cq[data-left="1"] .cq-sheets i:first-child,
.cq[data-left="0"] .cq-sheets i { opacity: 0; transform: none; }
.cq-card {
  position: relative; border-radius: 20px; padding: 24px 28px 24px;
  background: var(--sheet);
  box-shadow: 0 0 0 1px var(--rule-2), 0 2px 4px rgba(22, 22, 21, 0.04), 0 36px 72px -36px rgba(22, 22, 21, 0.24);
}
:root[data-theme="dark"] .cq-card { box-shadow: 0 0 0 1px var(--rule-2), 0 2px 4px rgba(0, 0, 0, 0.3), 0 36px 72px -36px rgba(0, 0, 0, 0.7); }
.cq-top { display: flex; justify-content: space-between; align-items: center; gap: 12px; font-size: 14px; color: var(--ink-2); }
.cq-from { display: flex; align-items: center; gap: 8px; min-width: 0; }
.cq-from b { color: var(--ink); font-weight: 600; white-space: nowrap; }
.cq-by { color: var(--ink-3); white-space: nowrap; }
.cq-clock { display: inline-flex; align-items: center; gap: 6px; color: var(--ink-2); }
.cq-clock .ai { fill: none; stroke: currentColor; stroke-width: 1.6; stroke-linecap: round; stroke-linejoin: round; }

.cq-views { display: grid; margin-top: 16px; }
.cq-view { grid-area: 1 / 1; min-width: 0; }
.js .cq-view.is-off { visibility: hidden; opacity: 0; pointer-events: none; }

/* The paper's progress: the mark's wave, inked as far as you have got. */
.cq-wave { display: block; width: 100%; height: 14px; overflow: visible; }
.cq-wave path { fill: none; stroke-width: 2px; stroke-linecap: round; vector-effect: non-scaling-stroke; }
.cq-wave .track { stroke: var(--rule-2); }
.cq-wave .done { stroke: var(--ink); stroke-dasharray: 1 1.02; stroke-dashoffset: calc(1.02 - var(--done, 0) * 1.02); transition: stroke-dashoffset 0.7s cubic-bezier(0.5, 0, 0.2, 1); }

.cq-count { margin-top: 18px; font-size: 14px; color: var(--ink-3); }
.cq-count b { color: var(--ink); font-weight: 600; }
.cq-q {
  margin-top: 8px; min-height: 2.36em;
  font-size: clamp(1.4rem, 2.1vw, 1.65rem); font-weight: 600; line-height: 1.18; letter-spacing: -0.028em;
  text-wrap: balance;
}
.cq-opts { display: grid; gap: 10px; margin-top: 20px; }
.cq-opt {
  position: relative;
  display: flex; align-items: center; gap: 14px;
  height: 60px; padding: 0 64px 0 14px;
  border-radius: 12px; background: var(--sheet);
  box-shadow: inset 0 0 0 1px var(--rule-2);
  font-size: 17px; letter-spacing: -0.012em; color: var(--ink);
  -webkit-tap-highlight-color: transparent;
  transition: box-shadow 0.18s var(--ease), background-color 0.18s var(--ease), color 0.3s var(--ease), transform 80ms var(--ease);
}
.cq-opt .k {
  display: grid; place-items: center; width: 30px; height: 30px; flex: none; border-radius: 8px;
  box-shadow: inset 0 0 0 1px var(--rule-2);
  font-size: 14px; font-weight: 600; color: var(--ink-2);
  transition: background-color 0.18s var(--ease), color 0.18s var(--ease), box-shadow 0.18s var(--ease);
}
.cq-opt .t { min-width: 0; }
.cq.is-js .cq-opt { cursor: pointer; }
@media (hover: hover) {
  .cq.is-js .cq-opts:not(.is-locked) .cq-opt:hover { background: var(--wash); box-shadow: inset 0 0 0 1px var(--ink-4); }
}
.cq.is-js .cq-opts:not(.is-locked) .cq-opt:active { transform: scale(0.99); }
.cq-opt:focus-visible { outline: 2px solid var(--ink); outline-offset: 2px; border-radius: 12px; }
.cq-opt.is-picked { box-shadow: inset 0 0 0 1.5px var(--ink); }
.cq-opt.is-picked .k { background: var(--ink); color: var(--on-ink); box-shadow: none; }
.cq-opts.is-locked .cq-opt { cursor: default; }
.cq-opts.is-locked .cq-opt:not(.is-picked):not(.is-answer) { color: var(--ink-3); }

/* The red pen: a tick or a cross, drawn by hand, the moment you answer. */
.cq-mark { position: absolute; right: 14px; top: 50%; width: 44px; height: 40px; margin-top: -20px; overflow: visible; pointer-events: none; }
.cq-mark path {
  fill: none; stroke: var(--pen); stroke-width: 2.8px; stroke-linecap: round; stroke-linejoin: round;
  vector-effect: non-scaling-stroke;
  stroke-dasharray: 1 1.02; stroke-dashoffset: 1.02;
  animation: nf-pencil 380ms cubic-bezier(0.5, 0, 0.2, 1) var(--pd, 0s) forwards;
}
.cq-mark path + path { --pd: 0.2s; }
.cq-opt.is-answer:not(.is-picked) .cq-mark path { --pd: 0.36s; }

.cq-hint { margin-top: 18px; font-size: 13.5px; color: var(--ink-3); }

/* A question changes the way the headline does: out on a blur, in from one. */
.cq-body.is-out > :not(.cq-opts) { opacity: 0; filter: blur(8px); transform: translate3d(0, -8px, 0); transition: opacity 0.28s ease-in, filter 0.28s ease-in, transform 0.32s ease-in; }
.cq-body.is-out .cq-opt { opacity: 0; filter: blur(8px); transform: translate3d(0, -6px, 0); transition: opacity 0.26s ease-in calc(var(--i) * 30ms), filter 0.26s ease-in calc(var(--i) * 30ms), transform 0.3s ease-in calc(var(--i) * 30ms); }
.cq-body.is-pre > :not(.cq-opts), .cq-body.is-pre .cq-opt { opacity: 0; filter: blur(10px); transform: translate3d(0, 12px, 0); transition: none; }
.cq-body.is-in > :not(.cq-opts) { transition: opacity 0.6s var(--ease), filter 0.7s var(--ease), transform 0.8s var(--ease-out); }
.cq-body.is-in .cq-opt { transition: box-shadow 0.18s var(--ease), background-color 0.18s var(--ease), color 0.3s var(--ease), opacity 0.6s var(--ease) calc(0.08s + var(--i) * 60ms), filter 0.7s var(--ease) calc(0.08s + var(--i) * 60ms), transform 0.8s var(--ease-out) calc(0.08s + var(--i) * 60ms); }

/* ---- the result ---------------------------------------------------------- */

.cq-result { display: flex; flex-direction: column; }
.cq-result[hidden] { display: none; }
.cq-scorerow { position: relative; display: flex; align-items: center; height: 150px; }
.cq-score { position: relative; padding: 12px 34px 6px 24px; }
.cq-big { display: block; font-family: var(--serif); font-size: 128px; line-height: 0.95; letter-spacing: -0.03em; }
.cq-big .of { color: var(--ink-3); }
.cq-score .ring { position: absolute; left: -4px; top: -6px; width: calc(100% + 10px); height: calc(100% + 12px); transform: rotate(-3deg); overflow: visible; pointer-events: none; }
.cq-score .ring path { fill: none; stroke: var(--pen); stroke-width: 2.6px; stroke-linecap: round; stroke-linejoin: round; vector-effect: non-scaling-stroke; stroke-dasharray: 1 1.02; stroke-dashoffset: 0; }
.cq-pen {
  --dd-w: 1.6px;
  position: relative; flex-direction: column; align-items: flex-start; gap: 2px;
  margin-left: 18px; max-width: 13em;
  font-size: 22px; color: var(--pen); white-space: normal;
  transform: rotate(-4deg);
}
.cq-pen svg { width: 52px; height: 36px; margin-left: 6px; color: var(--pen); }
.cq-verdict { margin-top: 14px; font-size: 1.32rem; font-weight: 600; letter-spacing: -0.024em; line-height: 1.25; }
.cq-verdict b { font-weight: 600; }
.cq-verdict:focus { outline: none; }
.cq-verdict:focus-visible { outline: 2px solid var(--ink); outline-offset: 4px; }
.cq-review { list-style: none; margin-top: 16px; border-top: 1px solid var(--rule-ink); }
/* One line a row, whatever was picked, so the result is never taller than a
   question and the card never grows when it arrives. */
.cq-review li { display: grid; grid-template-columns: 24px minmax(0, 1fr) minmax(0, auto); gap: 10px; align-items: center; height: 36px; border-bottom: 1px solid var(--rule); font-size: 14.5px; }
.cq-review li > span { min-width: 0; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.cq-review .n { color: var(--ink-3); font-size: 13.5px; }
.cq-review .a { color: var(--ink-3); font-size: 13.5px; text-align: right; }
.cq-review .a b { color: var(--ink); font-weight: 500; }
.cq-actions { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; margin-top: 20px; }
.cq-actions .btn-primary { height: 48px; }
.cq-again { height: 48px; background: transparent; color: var(--ink-2); }
.cq-again:hover { background: var(--wash); color: var(--ink); }

/* The result arrives in order: the score, the ring, the pen, the rest. */
.cq-result.is-shown > * { animation: hero-rise 0.8s var(--ease) both; }
.cq-result.is-shown .cq-scorerow { animation-delay: 0.05s; }
.cq-result.is-shown .cq-verdict { animation-delay: 0.5s; }
.cq-result.is-shown .cq-review { animation-delay: 0.62s; }
.cq-result.is-shown .cq-actions { animation-delay: 0.74s; }
.cq-result.is-shown .ring path { animation: nf-pencil 640ms cubic-bezier(0.6, 0, 0.2, 1) 0.45s both; }
.cq-result.is-shown .cq-pen { animation: nf-note 600ms var(--ease) 1.05s both; }

@media (max-width: 1100px) {
  .cq-beat { display: none; }
  .play-grid { grid-template-columns: minmax(0, 1fr) minmax(0, 480px); column-gap: 3rem; }
  .cq-card { padding: 22px 22px 22px; }
}
@media (max-width: 900px) {
  .play-grid { grid-template-columns: minmax(0, 1fr); grid-template-areas: "head" "card" "board"; grid-template-rows: auto; }
  .cq { max-width: 560px; }
  .cq-boardwrap { width: 100%; max-width: 560px; }
}
@media (max-width: 600px) {
  .cq-card { padding: 18px 18px 18px; border-radius: 18px; }
  .cq-sheets i { border-radius: 18px; }
  .cq-by { display: none; }
  .cq-opt { height: 56px; font-size: 16.5px; }
  /* On a phone the card keeps to the question's height with the review in
     it: a smaller score, tighter rows, and the way on at the foot. */
  .cq-big { font-size: 84px; }
  .cq-pen { font-size: 18px; margin-left: 6px; }
  .cq-pen svg { width: 44px; height: 28px; }
  .cq-scorerow { height: 108px; }
  .cq-score { padding: 8px 22px 2px 14px; }
  .cq-verdict { margin-top: 10px; font-size: 1.18rem; }
  .cq-review { margin-top: 10px; }
  .cq-review li { height: 31px; gap: 8px; grid-template-columns: 18px minmax(0, 1fr) minmax(0, auto); font-size: 14px; }
  .cq-review .n, .cq-review .a { font-size: 13px; }
  .cq-actions { margin-top: auto; padding-top: 12px; }
  .cq-actions .btn { flex: 1 1 auto; }
  .cq-actions .btn-primary { flex-basis: 100%; }
  .cq-again { height: 44px; }
}

@media (prefers-reduced-motion: reduce) {
  .headline.is-live .w { filter: none !important; transform: none !important; }
  .cq-body > :not(.cq-opts), .cq-opt { filter: none !important; transform: none !important; }
  .cq-mark path, .cq-score .ring path, .proof-marks path { stroke-dashoffset: 0 !important; animation: none !important; }
  .cq-board li.is-you::before { animation: none !important; }
}

/* ==========================================================================
   Window frames

   A sheet with a hairline and one soft shadow, a quiet bar on top. The
   screenshots inside are still the app's old look and are due a re-shoot.
   ========================================================================== */

.frame {
  margin: 0;
  border-radius: var(--r-xl);
  background: var(--sheet);
  box-shadow: inset 0 0 0 1px var(--rule), var(--shadow-2);
  overflow: hidden;
}
.frame-lg { box-shadow: 0 0 0 1px var(--rule), var(--shadow-3); }
.frame-bar {
  display: flex; align-items: center; gap: 0.7rem;
  height: 36px; padding: 0 0.9rem;
  border-bottom: 1px solid var(--rule);
  background: var(--rail);
}
.frame-dots { display: flex; gap: 6px; }
.frame-dots i { width: 9px; height: 9px; border-radius: 50%; background: var(--rule-2); }
.frame-title { font-size: 0.8rem; color: var(--ink-3); }
.frame-body {
  width: 100%;
  aspect-ratio: 16 / 10; max-height: 360px;
  display: grid; place-content: center; justify-items: center; gap: 0.3rem;
  background: var(--sheet);
  text-align: center;
}
.frame-lg .frame-body { aspect-ratio: 16 / 9; max-height: 520px; }
.frame-body img { display: block; width: 100%; height: 100%; object-fit: cover; object-position: top left; }
.frame .frame-body:has(> img) { display: block; max-height: none; }

/* ==========================================================================
   Sections
   ========================================================================== */

.section { padding: clamp(5rem, 9vw, 8rem) 0; }

/* A section head stands on the exercise-book line. */
.section-head {
  display: flex; flex-direction: column; gap: 1rem;
  padding-top: 1rem; border-top: 1px solid var(--rule-ink);
  margin-bottom: clamp(2.5rem, 5vw, 4rem);
}
.section-head h2 { max-width: 22ch; }
.section-head .section-lede { margin-top: 0.1rem; }

/* ==========================================================================
   How it works

   One Biology note followed from the lecture to the exam. The stage pins for
   the length of the track; js/main.js picks the step from the scroll
   position, swaps the copy, fills the progress and switches the window to
   that step's screen, where CSS plays the step's one move.

   The window is the app as it now looks — paper, or graphite in the dark
   theme — drawn in HTML so each move can happen in it. The note's key lines
   are run over with the highlighter, which is that section's one swipe.
   ========================================================================== */

.loop { position: relative; padding-top: clamp(4rem, 9vw, 7rem); }
.loop-head { display: flex; flex-direction: column; align-items: center; gap: 1.1rem; text-align: center; }
.loop-head h2 { font-size: clamp(2.5rem, 6.4vw, 5.4rem); line-height: 1; letter-spacing: -0.04em; max-width: 14ch; }
.loop-lede { max-width: 42ch; color: var(--ink-2); font-size: clamp(1.05rem, 1.4vw, 1.2rem); line-height: 1.5; }

.loop-track { position: relative; margin-top: clamp(1rem, 3vw, 2rem); }
.loop-stage {
  width: min(var(--container-wide), 100% - var(--gutter) * 2); margin-inline: auto;
  display: grid; grid-template-columns: minmax(0, 0.78fr) minmax(0, 1.22fr);
  gap: clamp(2rem, 5vw, 5rem); align-items: center;
  padding: clamp(2rem, 5vw, 4rem) 0;
}
.loop.js-on .loop-track { height: 560vh; }
.loop.js-on .loop-stage {
  position: sticky; top: 0; height: 100vh; height: 100svh;
  padding: 80px 0 24px;
}

/* Five rules that fill with ink as the story goes; the current word in ink. */
.loop-progress {
  list-style: none; display: grid; grid-template-columns: repeat(5, minmax(0, 1fr)); gap: 8px;
  margin-bottom: clamp(1.5rem, 4vh, 2.5rem);
}
.loop-progress li { display: flex; flex-direction: column; gap: 0.6rem; }
.loop-progress i { position: relative; height: 2px; border-radius: 2px; background: var(--rule-2); overflow: hidden; }
.loop-progress i::after {
  content: ""; position: absolute; inset: 0; background: var(--ink);
  transform-origin: left; transform: scaleX(var(--fill, 0));
}
.loop-progress span { font-size: 0.875rem; font-weight: 500; color: var(--ink-3); transition: color 0.3s var(--ease); }
.loop-progress li.is-on span { color: var(--ink); }
.loop:not(.js-on) .loop-progress { display: none; }

.loop-steps { display: grid; gap: 3rem; }
.loop-step { display: flex; flex-direction: column; gap: 1rem; }
.loop-tool { display: flex; align-items: center; gap: 0.5rem; font-size: 0.94rem; font-weight: 500; color: var(--ink-2); }
.loop-step h3 {
  font-weight: 600;
  font-size: clamp(2rem, 3.8vw, 3.3rem); line-height: 1.04; letter-spacing: -0.035em;
}
.loop-step > p:last-child { max-width: 34ch; color: var(--ink-2); font-size: clamp(1.02rem, 1.25vw, 1.14rem); line-height: 1.55; }

.loop.js-on .loop-steps { gap: 0; }
.loop.js-on .loop-step {
  grid-area: 1 / 1;
  opacity: 0; transform: translateY(18px); filter: blur(6px);
  transition: opacity 0.45s var(--ease), transform 0.6s var(--ease), filter 0.45s var(--ease);
}
.loop.js-on .loop-step.is-active { opacity: 1; transform: none; filter: blur(0); }

.loop-close { padding: clamp(4rem, 9vw, 7rem) 0 clamp(2rem, 4vw, 3rem); text-align: center; }
.loop-close p {
  max-width: 26ch; margin-inline: auto;
  font-weight: 600;
  font-size: clamp(1.7rem, 3.6vw, 2.9rem); line-height: 1.1; letter-spacing: -0.032em;
}

/* ---- the window ---------------------------------------------------------- */

.loop-window {
  container-type: inline-size;
  justify-self: center;
  width: min(100%, calc((100svh - 150px) * 1.42));
  border-radius: var(--r-xl); overflow: hidden;
  background: var(--paper); color: var(--ink);
  box-shadow: 0 0 0 1px var(--rule-2), var(--shadow-3);
}
.lw-bar {
  display: flex; align-items: center; gap: 0.7rem; height: 36px; padding: 0 0.9rem;
  border-bottom: 1px solid var(--rule); background: var(--rail);
}
.lw-title { font-size: 0.8rem; color: var(--ink-3); }
.lw-body { display: grid; grid-template-columns: 50px minmax(0, 1fr); aspect-ratio: 16 / 11; }
.lw-rail {
  display: flex; flex-direction: column; align-items: center; gap: 4px; padding: 10px 0;
  border-right: 1px solid var(--rule); background: var(--rail);
}
.lw-ico {
  position: relative; display: grid; place-items: center; width: 32px; height: 32px; border-radius: 8px;
  color: var(--ink-3); transition: color 0.35s var(--ease), background 0.35s var(--ease);
}
.lw-ico svg { width: 16px; height: 16px; }
.lw-ico.is-on { color: var(--ink); background: var(--rail-on); }

.lw-scenes { position: relative; overflow: hidden; font-size: clamp(8.5px, 2.05cqi, 15px); line-height: 1.5; }
.scene {
  position: absolute; inset: 0; padding: 2.2em 2.6em;
  opacity: 0; transform: translateY(1.2em) scale(0.985); filter: blur(4px);
  transition: opacity 0.45s var(--ease), transform 0.6s var(--ease), filter 0.45s var(--ease);
}
.scene.is-active { opacity: 1; transform: none; filter: blur(0); }

/* 01 · write: the three key lines are run over with the highlighter */
.sc-crumb { font-size: 0.8em; color: var(--ink-3); }
.sc-title { margin-top: 1.2em; font-weight: 600; font-size: 2em; letter-spacing: -0.03em; line-height: 1.1; }
.sc-meta { margin: 0.4em 0 1.3em; font-size: 0.8em; color: var(--ink-3); }
.sc-p { color: var(--ink-2); }
.sc-eq {
  margin: 1em 0; padding: 0.65em 1em; border: 1px solid var(--rule); border-radius: 0.6em;
  background: var(--sheet); text-align: center; font-family: var(--serif); font-style: italic; font-size: 1.1em; color: var(--ink);
}
.sc-h { margin: 1.1em 0 0.6em; font-weight: 600; font-size: 1.12em; color: var(--ink); }
.sc-table {
  display: grid; grid-template-columns: 1.15fr 1.55fr 0.8fr; margin-bottom: 1.1em;
  border-top: 1px solid var(--rule-ink); font-size: 0.9em;
}
.sc-table span { padding: 0.5em 0.2em; border-bottom: 1px solid var(--rule); color: var(--ink-2); }
.scene mark {
  color: inherit; padding: 0 0.12em; margin: 0 -0.12em; border-radius: 0.15em;
  background: linear-gradient(var(--hl), var(--hl)) no-repeat left 60% / 0% 78%;
  transition: background-size 0.6s var(--ease), color 0.4s var(--ease);
}
.scene-write.is-active mark { background-size: 100% 78%; color: var(--hl-ink); transition-delay: calc(0.45s + var(--i) * 0.35s); }

/* 02 · cards: the lines leave the note and land as a deck */
.scene-cards { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1.15fr); gap: 2.2em; align-items: center; }
.sc-kicker { margin-bottom: 1em; font-size: 0.82em; font-weight: 500; color: var(--ink-3); }
.sc-line {
  margin-bottom: 0.7em; padding: 0.65em 0.9em; border-left: 2px solid var(--ink); border-radius: 0 0.4em 0.4em 0;
  background: var(--wash); font-size: 0.92em; line-height: 1.4; color: var(--ink);
}
.sc-make {
  display: inline-flex; align-items: center; gap: 0.5em; margin-top: 0.5em; padding: 0.6em 1em; border-radius: 0.6em;
  background: var(--ink); color: var(--on-ink); font-size: 0.88em; font-weight: 600;
}
.sc-make svg { width: 1.15em; height: 1.15em; }
.scene-cards.is-active .sc-make { animation: sc-press 0.45s var(--ease) 0.35s both; }
@keyframes sc-press { 50% { transform: scale(0.93); } }
.sc-deck { display: flex; flex-direction: column; gap: 0.8em; }
.sc-mini {
  display: flex; flex-direction: column; gap: 0.35em; padding: 1em 1.15em;
  border-radius: 0.8em; background: var(--sheet);
  box-shadow: 0 0 0 1px var(--rule-2), var(--shadow-2);
  opacity: 0; transform: translateX(-3.5em) scale(0.95);
  transition: opacity 0.5s var(--ease), transform 0.7s var(--ease);
}
.scene-cards.is-active .sc-mini { opacity: 1; transform: none; transition-delay: calc(0.75s + var(--i) * 0.18s); }
.sc-mini b { font-size: 0.95em; font-weight: 600; color: var(--ink); }
.sc-mini span { font-size: 0.86em; color: var(--ink-3); }
.sc-added { font-size: 0.82em; color: var(--ink-2); opacity: 0; transition: opacity 0.4s var(--ease); }
.sc-added em { font-style: normal; color: var(--ink); font-weight: 600; }
.scene-cards.is-active .sc-added { opacity: 1; transition-delay: 1.5s; }

/* 03 · review: the card turns over and is rated Good */
.scene-review { display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 1.5em; }
.sc-count { font-size: 0.82em; color: var(--ink-3); }
.sc-flip { position: relative; width: min(100%, 30em); height: 11.5em; perspective: 60em; }
.sc-face {
  position: absolute; inset: 0; display: flex; flex-direction: column; justify-content: center; gap: 0.7em;
  padding: 1.5em 2em; border-radius: 0.9em; background: var(--sheet);
  box-shadow: 0 0 0 1px var(--rule-2), var(--shadow-2);
  font-size: 1.15em; line-height: 1.45; color: var(--ink);
  backface-visibility: hidden; -webkit-backface-visibility: hidden;
  transition: transform 0.8s cubic-bezier(0.6, 0, 0.2, 1);
}
.sc-face span { font-size: 0.66em; font-weight: 500; color: var(--ink-3); }
.sc-back { transform: rotateY(180deg); }
.scene-review.is-active .sc-front { transform: rotateY(-180deg); transition-delay: 0.7s; }
.scene-review.is-active .sc-back { transform: rotateY(0deg); transition-delay: 0.7s; }
.sc-rate { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 0.6em; width: min(100%, 30em); }
.sc-rate span {
  display: flex; flex-direction: column; align-items: center; gap: 0.2em; padding: 0.7em 0.4em;
  border-radius: 0.6em; background: var(--sheet); box-shadow: inset 0 0 0 1px var(--rule-2);
  font-size: 0.78em; color: var(--ink-3); font-variant-numeric: tabular-nums;
  transition: box-shadow 0.4s var(--ease), background 0.4s var(--ease), transform 0.4s var(--ease);
}
.sc-rate b { font-size: 1.2em; font-weight: 600; color: var(--ink); }
.sc-rate .r-again b { color: var(--danger); }
.scene-review.is-active .r-good {
  box-shadow: inset 0 0 0 1.5px var(--ink); background: var(--wash); transform: translateY(-0.25em);
  transition-delay: 1.75s;
}

/* 04 · test: a wrong answer, the right one, and the card it leaves behind */
.scene-test { display: flex; flex-direction: column; gap: 1.15em; }
.sc-exam-head {
  display: flex; gap: 1.2em; padding-bottom: 0.9em; border-bottom: 1px solid var(--rule-ink);
  font-size: 0.82em; color: var(--ink-3); font-variant-numeric: tabular-nums;
}
.sc-clock { margin-left: auto; color: var(--ink); font-weight: 600; }
.sc-q { font-weight: 600; font-size: 1.55em; line-height: 1.2; letter-spacing: -0.02em; }
.sc-opts { list-style: none; display: flex; flex-direction: column; gap: 0.6em; margin: 0; padding: 0; }
.sc-opts li {
  display: flex; align-items: center; gap: 0.9em; padding: 0.75em 1em;
  border-radius: 0.7em; background: var(--sheet); box-shadow: inset 0 0 0 1px var(--rule-2);
  font-size: 0.95em; color: var(--ink-2);
  transition: box-shadow 0.4s var(--ease), background 0.4s var(--ease), color 0.4s var(--ease);
}
.sc-opts i {
  display: grid; place-items: center; width: 1.8em; height: 1.8em; flex: none;
  border-radius: 0.45em; background: var(--wash);
  font-style: normal; font-size: 0.82em; font-weight: 600; color: var(--ink-2);
}
.scene-test.is-active .o-wrong { box-shadow: inset 0 0 0 1px var(--danger); background: var(--danger-soft); color: var(--ink); transition-delay: 0.5s; }
.scene-test.is-active .o-right { box-shadow: inset 0 0 0 1px var(--ok); background: var(--ok-soft); color: var(--ink); transition-delay: 1.05s; }
.sc-toast {
  align-self: flex-end; display: inline-flex; align-items: center; gap: 0.5em; padding: 0.65em 1em;
  border-radius: 0.7em; background: var(--sheet); box-shadow: 0 0 0 1px var(--rule-2), var(--shadow-2);
  font-size: 0.82em; color: var(--ink-2);
  opacity: 0; transform: translateY(0.8em);
  transition: opacity 0.45s var(--ease), transform 0.55s var(--ease);
}
.sc-toast svg { width: 1.15em; height: 1.15em; color: var(--ink); }
.sc-toast em { font-style: normal; color: var(--ink); font-weight: 600; }
.scene-test.is-active .sc-toast { opacity: 1; transform: none; transition-delay: 1.65s; }

/* 05 · plan: revision drops into the days before the exam */
.scene-plan { display: flex; flex-direction: column; gap: 1.1em; }
.sc-week-head { display: flex; align-items: baseline; justify-content: space-between; gap: 1em; padding-bottom: 0.6em; border-bottom: 1px solid var(--rule-ink); }
.sc-week-head span:first-child { font-weight: 600; font-size: 1.5em; letter-spacing: -0.02em; }
.sc-soon { font-size: 0.85em; font-weight: 500; color: var(--ink-2); }
.sc-week { flex: 1; display: grid; grid-template-columns: repeat(5, minmax(0, 1fr)); gap: 0.5em; }
.sc-week > div {
  display: flex; flex-direction: column; gap: 0.5em; padding: 0.7em 0.55em;
  border-radius: 0.7em; background: var(--sheet); box-shadow: inset 0 0 0 1px var(--rule);
}
.sc-week > .day-exam { box-shadow: inset 0 0 0 1px var(--rule-2); }
.sc-week b { display: flex; justify-content: space-between; font-size: 0.78em; font-weight: 500; color: var(--ink-3); font-variant-numeric: tabular-nums; }
.sc-week b em { font-style: normal; color: var(--ink-2); }
.ev {
  display: flex; flex-direction: column; gap: 0.2em; padding: 0.55em 0.6em;
  border-left: 2px solid var(--rule-2); border-radius: 0.4em; background: var(--wash);
  font-size: 0.76em; line-height: 1.25; color: var(--ink-2);
}
.ev small { font-size: 0.88em; color: var(--ink-3); font-variant-numeric: tabular-nums; }
.ev-new {
  border-left-color: var(--ink); background: var(--wash-2); color: var(--ink);
  opacity: 0; transform: translateY(0.6em) scale(0.96);
  transition: opacity 0.45s var(--ease), transform 0.55s var(--ease);
}
.scene-plan.is-active .ev-new { opacity: 1; transform: none; transition-delay: calc(0.5s + var(--i) * 0.22s); }
.ev-exam { border: 1.5px solid var(--ink); background: transparent; color: var(--ink); font-weight: 600; }
.sc-sync { font-size: 0.78em; color: var(--ink-3); }

@media (max-width: 900px) {
  .loop-stage { grid-template-columns: minmax(0, 1fr); gap: 1.25rem; }
  .loop.js-on .loop-stage { align-content: start; padding-top: 80px; }
  .loop-progress { margin-bottom: 1rem; }
  .loop-progress span { font-size: 0.78rem; }
  .loop-step { gap: 0.6rem; }
  .loop-step h3 { font-size: clamp(1.7rem, 7.4vw, 2.5rem); }
  .loop-step > p:last-child { font-size: 0.98rem; }
  .loop-window { width: 100%; }
}
@media (max-width: 900px) and (max-height: 700px) {
  .loop-step > p:last-child { font-size: 0.9rem; }
  .loop-tool { display: none; }
}

/* ==========================================================================
   Everything else

   One grid of sheets at three sizes: the tutor (with a screen) and the focus
   timer large, the rest small with a label, a short title and one line. The
   grade is a result, so the red pen rings it — the only red on the page.
   ========================================================================== */

.bento-section .section-head { align-items: center; text-align: center; border-top: 0; padding-top: 0; }
.bento-section .section-head h2 { font-size: clamp(2.3rem, 5.2vw, 4.2rem); max-width: 18ch; }
.bento {
  display: grid; grid-template-columns: repeat(4, minmax(0, 1fr));
  grid-auto-rows: minmax(14.5rem, auto); gap: 1rem;
}
.tile {
  position: relative; overflow: hidden;
  display: flex; flex-direction: column; gap: 0.55rem; padding: 1.6rem;
  border-radius: var(--r-xl); background: var(--sheet);
  box-shadow: inset 0 0 0 1px var(--rule), var(--shadow-1);
}
.tile h3 { font-size: 1.3rem; font-weight: 600; letter-spacing: -0.025em; line-height: 1.15; }
.tile:not(.tile-dark) h3 { margin-top: auto; }
.tile p { color: var(--ink-2); font-size: 0.97rem; line-height: 1.5; }
.tile .tile-kicker { display: flex; align-items: center; gap: 0.45rem; color: var(--ink-3); font-size: 0.9rem; font-weight: 500; }
.tile-kicker svg { width: 16px; height: 16px; }
.tile, .js-reveal .tile[data-reveal].in { transition: opacity 0.75s var(--ease), transform 0.5s var(--ease), box-shadow 0.5s var(--ease); }
@media (hover: hover) {
  .tile:hover, .js-reveal .tile[data-reveal].in:hover {
    transform: translateY(-3px); transition-delay: 0s;
    box-shadow: inset 0 0 0 1px var(--rule-2), var(--shadow-2);
  }
}

.tile-dark h3 { font-size: clamp(1.6rem, 2.4vw, 2.1rem); line-height: 1.08; letter-spacing: -0.03em; }
.tile-copy { display: flex; flex-direction: column; gap: 0.7rem; max-width: 36ch; }

.tile-tutor { grid-column: span 2; grid-row: span 2; padding: 2rem 0 0 2rem; }
/* Two cells wide, so the seven tiles fill the grid with no gap at four
   columns or at two. Wide, it reads across like the focus tile: the ringed
   grade, then what it is. */
.tile-grades {
  grid-column: span 2;
  display: grid; grid-template-columns: auto minmax(0, 1fr); grid-template-rows: auto 1fr;
  column-gap: clamp(1.75rem, 3.5vw, 3rem); align-items: center;
}
.tile-grades .tile-kicker { grid-column: 1 / -1; align-self: start; }
.tile.tile-grades .tile-figure { margin: 0 0 0 0.25rem; font-size: clamp(4rem, 6.4vw, 6rem); }
.tile.tile-grades > p:last-child { max-width: 24ch; font-size: 1.05rem; }
.tile-tutor .tile-copy { padding-right: 2rem; }
.tile-shot {
  flex: 1; min-height: 16rem; margin-top: 1.6rem;
  border-radius: 12px 0 0 0; overflow: hidden;
  box-shadow: inset 0 0 0 1px var(--rule-2);
}
.tile-shot img { display: block; width: 100%; height: 100%; object-fit: cover; object-position: 60% 0; }

/* The timer: the minutes in the serif, upright, over the wave as a progress line. */
.tile-focus { grid-column: span 2; flex-direction: row; align-items: center; gap: 1.75rem; padding: 2rem; }
.tile-dial { flex: none; display: flex; flex-direction: column; align-items: flex-start; gap: 0.5rem; width: 11rem; margin-left: auto; }
.tile-dial span { font-family: var(--serif); font-size: 3.6rem; line-height: 1; letter-spacing: -0.01em; color: var(--ink); font-variant-numeric: tabular-nums; }
.dd-progress { width: 100%; height: 16px; --dd-w: 2px; }
.dd-progress .dd-track { stroke: var(--rule-2); }
.dd-progress .dd-done { stroke: var(--ink); stroke-dasharray: 1; stroke-dashoffset: 0.28; }
.js-reveal .tile-focus:not(.in) .dd-done { stroke-dashoffset: 1; }
.js-reveal .tile-focus.in .dd-done { animation: dd-fill 2.2s var(--ease) 0.4s both; }
@keyframes dd-fill { from { stroke-dashoffset: 1; } to { stroke-dashoffset: 0.28; } }

.tile .tile-figure {
  margin-top: auto; font-family: var(--serif); font-weight: 400;
  font-size: clamp(3.2rem, 5vw, 4.4rem); line-height: 1; letter-spacing: -0.01em;
  color: var(--ink); font-variant-numeric: tabular-nums;
}
.tile-figure small { font-size: 0.5em; color: var(--ink-3); }
.ring-wrap { position: relative; display: inline-block; padding: 0.06em 0.26em 0.02em 0.2em; }
.ring { position: absolute; top: -6px; left: -4px; width: calc(100% + 10px); height: calc(100% + 12px); overflow: visible; pointer-events: none; transform: rotate(-3deg); }
.ring path { fill: none; stroke: var(--pen); stroke-width: 2.6px; stroke-linecap: round; stroke-linejoin: round; vector-effect: non-scaling-stroke; stroke-dasharray: 1; stroke-dashoffset: 0; }
.js-reveal .tile-grades:not(.in) .ring path { stroke-dashoffset: 1; }
.js-reveal .tile-grades.in .ring path { animation: nf-ink 620ms cubic-bezier(0.6, 0, 0.2, 1) 500ms both; }
@keyframes nf-ink { from { stroke-dashoffset: 1; } to { stroke-dashoffset: 0; } }

@media (max-width: 1000px) {
  .bento { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .tile-tutor { grid-row: auto; }
}
@media (max-width: 600px) {
  .bento { grid-template-columns: minmax(0, 1fr); grid-auto-rows: auto; }
  .tile { min-height: 11rem; }
  .tile-tutor, .tile-focus, .tile-grades { grid-column: auto; }
  .tile-grades { display: flex; align-items: stretch; }
  .tile.tile-grades .tile-figure { margin: auto 0 0; align-self: flex-start; font-size: clamp(3.2rem, 14vw, 4.4rem); }
  .tile.tile-grades > p:last-child { max-width: none; font-size: 0.97rem; }
  .tile-tutor { padding: 1.6rem 0 0 1.6rem; }
  .tile-tutor .tile-copy { padding-right: 1.6rem; }
  .tile-focus { flex-direction: column; align-items: flex-start; padding: 1.6rem; }
  .tile-dial { margin-left: 0; }
}

/* ==========================================================================
   Pricing

   A comparison table: ruled lines, tabular figures, and the recommended
   column carried by a quiet wash rather than a badge.
   ========================================================================== */

.table-scroll { overflow-x: auto; -webkit-overflow-scrolling: touch; }
table.plans { width: 100%; min-width: 640px; border-collapse: collapse; text-align: left; }
table.plans th, table.plans td { padding: 0.9rem 1.1rem; border-bottom: 1px solid var(--rule); vertical-align: middle; }
table.plans thead th { border-bottom: none; padding-bottom: 0.4rem; vertical-align: bottom; }
table.plans tbody th, table.plans tbody td { font-size: 0.97rem; }
table.plans tbody th { font-weight: 400; color: var(--ink-2); width: 30%; }
table.plans tbody td { color: var(--ink); }
table.plans .num { font-variant-numeric: tabular-nums; }

.plan-name { display: block; font-size: 1rem; font-weight: 600; letter-spacing: -0.01em; }
table.plans thead em { display: block; margin-top: 0.2rem; font-style: normal; font-size: 0.82rem; font-weight: 500; color: var(--ink-3); }
.row-price th { font-weight: 400; color: var(--ink-2); font-size: 0.97rem; }
.row-price td { padding-top: 0.3rem; padding-bottom: 1.1rem; border-bottom: 1px solid var(--rule-ink); }
.row-price th { border-bottom: 1px solid var(--rule-ink); }
.row-price b {
  display: block; font-size: 2.1rem; font-weight: 600;
  letter-spacing: -0.035em; line-height: 1; font-variant-numeric: tabular-nums; white-space: nowrap;
}
.row-price span { display: block; margin-top: 0.35rem; font-size: 0.82rem; color: var(--ink-3); }
.row-price b.is-long { font-size: 1.6rem; }
.row-price b.is-longer { font-size: 1.25rem; }

.plans-currency { display: flex; align-items: center; gap: 0.75rem; margin: 1.25rem 0 0.5rem; }
.plans-currency[hidden] { display: none; }
.plans-currency label { font-size: 0.9rem; color: var(--ink-3); }
.plans-currency-select { position: relative; display: inline-flex; }
.plans-currency-select::after {
  content: ""; position: absolute; right: 0.15rem; top: 50%;
  width: 0.4rem; height: 0.4rem; margin-top: -0.3rem;
  border-right: 1.5px solid var(--ink-3); border-bottom: 1.5px solid var(--ink-3);
  transform: rotate(45deg); pointer-events: none;
}
.plans-currency select {
  appearance: none; -webkit-appearance: none;
  padding: 0.35rem 1.4rem 0.35rem 0;
  border: 0; border-bottom: 1px solid var(--rule-2); border-radius: 0;
  background: transparent; color: var(--ink);
  font: 500 0.95rem var(--sans); cursor: pointer;
}
.plans-currency select:hover { border-bottom-color: var(--ink-3); }
.plans-currency select:focus-visible { outline: none; border-bottom-color: var(--ink); }
.plans-currency select option { background: var(--sheet); color: var(--ink); }

/* Yes / no marks, drawn rather than typed so they sit on the baseline. */
.yes::before, .no::before { content: ""; display: block; width: 15px; height: 15px; background: currentColor; }
.yes::before {
  color: var(--ink);
  -webkit-mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 14 14'%3E%3Cpath d='M2.5 7.4l3 3 6-6.8' fill='none' stroke='%23000' stroke-width='1.7' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;
  mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 14 14'%3E%3Cpath d='M2.5 7.4l3 3 6-6.8' fill='none' stroke='%23000' stroke-width='1.7' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / contain no-repeat;
}
.no::before {
  color: var(--ink-4);
  -webkit-mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 14 14'%3E%3Cpath d='M3 7h8' stroke='%23000' stroke-width='1.5' stroke-linecap='round'/%3E%3C/svg%3E") center / contain no-repeat;
  mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 14 14'%3E%3Cpath d='M3 7h8' stroke='%23000' stroke-width='1.5' stroke-linecap='round'/%3E%3C/svg%3E") center / contain no-repeat;
}

table.plans .is-featured { background: var(--wash); }
table.plans thead th.is-featured { border-radius: var(--r-lg) var(--r-lg) 0 0; }
table.plans tfoot .is-featured { border-radius: 0 0 var(--r-lg) var(--r-lg); }
table.plans tfoot td { border-bottom: none; padding-top: 1.1rem; }
table.plans tfoot .btn { width: 100%; }
.table-scroll + .plans-currency + .fine, .table-scroll ~ .fine { margin-top: 1.4rem; max-width: 64ch; }

/* FAQ -------------------------------------------------------------------- */

.faq-wrap { display: grid; grid-template-columns: minmax(0, 0.75fr) minmax(0, 1.25fr); gap: clamp(2rem, 5vw, 5rem); align-items: start; }
.faq-wrap .section-head { margin-bottom: 0; }
.faq { display: flex; flex-direction: column; border-top: 1px solid var(--rule-ink); }
.faq details { border-bottom: 1px solid var(--rule); }
.faq summary {
  list-style: none; cursor: pointer; display: flex; align-items: center; justify-content: space-between; gap: 1rem;
  min-height: 56px; padding: 0.9rem 0; font-weight: 600; font-size: 1.05rem; letter-spacing: -0.01em;
}
.faq summary::-webkit-details-marker { display: none; }
.faq summary::after {
  content: ""; flex: none; width: 12px; height: 12px;
  background: var(--ink-3);
  -webkit-mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 10 10'%3E%3Cpath d='M5 0.5v9M0.5 5h9' stroke='%23000' stroke-width='1.4' stroke-linecap='round'/%3E%3C/svg%3E") center / contain no-repeat;
  mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 10 10'%3E%3Cpath d='M5 0.5v9M0.5 5h9' stroke='%23000' stroke-width='1.4' stroke-linecap='round'/%3E%3C/svg%3E") center / contain no-repeat;
  transition: transform 0.25s var(--ease);
}
.faq details[open] summary::after { transform: rotate(45deg); }
.faq details p { color: var(--ink-2); padding: 0 0 1.3rem; max-width: 62ch; font-size: 1rem; line-height: 1.6; }
@media (max-width: 860px) { .faq-wrap { grid-template-columns: 1fr; } }

/* Footer ----------------------------------------------------------------- */

.site-footer { border-top: 1px solid var(--rule); padding: clamp(2.5rem, 5vw, 4rem) 0 2.5rem; }
.foot { display: grid; grid-template-columns: minmax(0, 2fr) minmax(0, 1fr) minmax(0, 1fr); gap: 2rem; }
.foot-brand { display: flex; flex-direction: column; align-items: flex-start; gap: 0.6rem; }
.foot-brand .brand { font-size: 1.05rem; }
.foot-brand .brand .nf-mark { width: 22px; height: 22px; }
.foot-brand p { font-size: 0.94rem; color: var(--ink-3); max-width: 28ch; }
.foot-col h3 { font-size: 0.9rem; font-weight: 500; color: var(--ink-3); margin-bottom: 0.85rem; }
.foot-col ul { list-style: none; display: flex; flex-direction: column; gap: 0.6rem; }
.foot-col a { color: var(--ink-2); font-size: 0.97rem; transition: color 0.16s; }
.foot-col a:hover { color: var(--ink); }
.foot-copy { grid-column: 1 / -1; margin-top: 1.5rem; padding-top: 1.5rem; border-top: 1px solid var(--rule); font-size: 0.84rem; color: var(--ink-3); }
@media (max-width: 640px) { .foot { grid-template-columns: 1fr 1fr; } .foot-brand { grid-column: 1 / -1; } }

/* ==========================================================================
   Privacy: the statement

   A pinned stage that holds one line at a time, in the serif, and the one
   hard cut on the page to the other polarity: graphite on a paper page,
   paper on a graphite one (.invert takes the other token set, above).
   ========================================================================== */

.invert { background: var(--paper); color: var(--ink); }

.statement { position: relative; height: 380vh; }
.statement-track {
  position: sticky; top: 0; height: 100vh; height: 100svh;
  display: grid; place-items: center; overflow: hidden;
}
.statement-stage {
  width: min(var(--container-wide), 100% - var(--gutter) * 2);
  display: flex; flex-direction: column; align-items: center; gap: clamp(2rem, 5vh, 3.5rem);
  text-align: center;
}
.statement-label { font-size: 0.97rem; font-weight: 500; color: var(--ink-3); }
.statement-lines { position: relative; width: 100%; display: grid; place-items: center; }
.stmt {
  grid-area: 1 / 1;
  font-family: var(--serif); font-style: italic; font-weight: 400;
  font-size: clamp(2.6rem, 7.4vw, 6.4rem);
  line-height: 1.02; letter-spacing: -0.02em;
  max-width: 16ch; text-wrap: balance;
  opacity: 0; will-change: transform, opacity;
}
.stmt .hl { white-space: nowrap; }
.statement-foot { max-width: 56ch; }
.statement-count { display: flex; gap: 0.4rem; }
.statement-count i { width: 22px; height: 2px; border-radius: 2px; background: var(--rule-2); transition: background 0.4s var(--ease); }
.statement-count i.on { background: var(--ink); }

/* ==========================================================================
   Scroll reveals
   ========================================================================== */

.js-reveal [data-reveal] {
  opacity: 0; transform: translateY(22px);
  transition: opacity 0.75s var(--ease), transform 0.75s var(--ease);
  transition-delay: var(--d, 0s);
}
.js-reveal [data-reveal].in { opacity: 1; transform: none; }

@media (prefers-reduced-motion: reduce) {
  .js-reveal [data-reveal] { opacity: 1 !important; transform: none !important; }
  .loop-step, .scene { filter: none !important; }
  .statement { height: auto; }
  .statement-track { position: static; height: auto; padding: clamp(4rem, 9vw, 7rem) 0; }
  .statement-lines { display: flex; flex-direction: column; gap: 1.5rem; }
  .stmt { grid-area: auto; opacity: 1 !important; transform: none !important; }
  .statement-count { display: none; }
  .hl::before, .ring path, .dd-done { animation: none !important; clip-path: none !important; }
  .ring path { stroke-dashoffset: 0 !important; }
  .dd-progress .dd-done { stroke-dashoffset: 0.28 !important; }
}

/* ==========================================================================
   Closing stage
   ========================================================================== */

.cta-final { min-height: 88vh; display: grid; place-items: center; padding: clamp(5rem, 10vw, 8rem) 0; }
.cta-box { display: flex; flex-direction: column; align-items: center; text-align: center; gap: 1.6rem; }
.cta-mark { width: 52px; height: 52px; stroke-width: 2.8; }
.cta-title {
  position: relative;
  font-family: var(--serif); font-style: italic; font-weight: 400;
  font-size: clamp(3rem, 8vw, 6.6rem); line-height: 1; letter-spacing: -0.02em;
  max-width: 13ch;
}
/* A paper plane leaving the headline: something sent, we'll write. */
.cta-plane { position: absolute; right: -0.9em; top: -0.35em; width: 1.1em; height: 0.6em; color: var(--ink); }
.cta-actions { display: flex; flex-wrap: wrap; justify-content: center; gap: 0.6rem; }
@media (max-width: 720px) {
  .cta-plane { right: -0.2em; top: -1.1em; width: 1em; height: 0.54em; }
}

/* ==========================================================================
   Motion preferences
   ========================================================================== */

@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  *, *::before, *::after { animation-duration: 0.001ms !important; animation-iteration-count: 1 !important; transition-duration: 0.001ms !important; }
}

/* ==========================================================================
   Between pages

   Moving between this site and the app is one document swap the browser can
   animate. Into the Reserve screen, the app grows its page out of the button
   that was pressed (web/index.html); everything else cross-fades. Where the
   browser cannot animate the swap, js/main.js draws the same circle here as
   .reserve-veil — the Reserve page's own paper — and leaves when it is full.
   ========================================================================== */

@view-transition { navigation: auto; }
@media (prefers-reduced-motion: reduce) {
  @view-transition { navigation: none; }
}

.reserve-veil {
  position: fixed; inset: 0; z-index: 1000; pointer-events: none;
  background: var(--paper);
  clip-path: circle(0px at 50% 50%);
}

main, .site-footer { position: relative; z-index: 1; }

/* ==========================================================================
   404

   An empty state, so it gets the one doodle: a page, the mark simplified.
   Held on the same left-hand grid as every section head.
   ========================================================================== */

.notfound {
  min-height: 100svh;
  display: grid; align-items: center;
  padding: clamp(7rem, 14vh, 10rem) 0 clamp(4rem, 10vh, 7rem);
}
.nf-stage {
  position: relative;
  display: flex; flex-direction: column; align-items: flex-start;
  gap: clamp(1.25rem, 2.4vw, 1.9rem);
  padding-top: 1rem; border-top: 1px solid var(--rule-ink);
}
.nf-doodle { width: 76px; height: 76px; color: var(--ink); }
.notfound h1 { font-size: clamp(3rem, 7.4vw, 5.8rem); max-width: 13ch; }
.notfound .lede { max-width: 42ch; }
.nf-cta { display: flex; flex-wrap: wrap; gap: 0.6rem; margin-top: 0.3rem; }
.nf-index {
  list-style: none; align-self: stretch;
  display: grid; grid-template-columns: repeat(4, minmax(0, 1fr));
  margin-top: clamp(1rem, 3vw, 2.25rem);
  border-top: 1px solid var(--rule);
}
.nf-index li + li { border-left: 1px solid var(--rule); }
.nf-index a {
  display: flex; align-items: baseline; gap: 0.6rem;
  padding: 1.05rem 1.1rem 1.05rem 0;
  color: var(--ink-2); font-size: 1rem; font-weight: 500;
  transition: color 0.16s var(--ease), background 0.2s var(--ease);
}
.nf-index li + li a { padding-left: 1.1rem; }
.nf-index a:hover { color: var(--ink); background: var(--wash); }
@media (max-width: 720px) {
  .nf-index { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .nf-index li:nth-child(odd) { border-left: 0; }
  .nf-index li:nth-child(n + 3) { border-top: 1px solid var(--rule); }
}
@media (min-width: 721px) and (max-height: 780px) {
  .notfound { padding: 5.5rem 0 3rem; }
  .nf-stage { gap: 1rem; }
  .notfound h1 { font-size: clamp(2.8rem, 5.6vw, 4.4rem); }
  .nf-index { margin-top: 0.75rem; }
  .nf-index a { padding-top: 0.85rem; padding-bottom: 0.85rem; }
}

/* ==========================================================================
   Status

   The 404's stage, reused: a label, a sentence that says how things are, and
   one ruled row per service. The dot only turns amber or red when something
   is actually wrong.
   ========================================================================== */

.status-page { min-height: 100svh; padding: clamp(7rem, 14vh, 10rem) 0 clamp(4rem, 10vh, 7rem); }
.status-stage {
  display: flex; flex-direction: column; align-items: flex-start;
  gap: clamp(1.25rem, 2.4vw, 1.9rem);
  padding-top: 1rem; border-top: 1px solid var(--rule-ink);
}
.status-page h1 { font-size: clamp(2.8rem, 6.4vw, 5rem); max-width: 16ch; }
.status-notice {
  align-self: stretch;
  padding: 0.95rem 1.1rem;
  border-radius: var(--r-md);
  background: var(--sheet); box-shadow: inset 0 0 0 1px var(--rule-2);
  color: var(--ink); font-size: 1rem; line-height: 1.55;
}
.status-list { list-style: none; align-self: stretch; border-top: 1px solid var(--rule); }
.status-row { display: grid; grid-template-columns: auto 1fr auto; align-items: center; gap: 0.9rem; min-height: 56px; border-bottom: 1px solid var(--rule); }
.status-name { font-weight: 500; color: var(--ink); }
.status-detail { font-size: 0.94rem; color: var(--ink-3); font-variant-numeric: tabular-nums; }
.status-dot { width: 9px; height: 9px; border-radius: 50%; background: var(--ink-4); }
.status-row[data-state="up"] .status-dot { background: var(--ok); }
.status-row[data-state="slow"] .status-dot { background: var(--warn); }
.status-row[data-state="down"] .status-dot { background: var(--danger); }
.status-row[data-state="down"] .status-detail { color: var(--danger); }
.status-foot { max-width: 60ch; }
