/* =========================================================================
   Superhuman GTM — design tokens
   Source of truth: DESIGN.md. Do not introduce values that aren't tokens.
   ========================================================================= */

:root {
  /* --- Ground 1: Light. Every reading surface. ------------------------- */
  --bg: oklch(0.952 0.005 250);
  --surface-1: oklch(0.990 0.003 250);
  --surface-2: oklch(0.915 0.007 250);
  --text-primary: oklch(0.205 0.010 250);
  --text-secondary: oklch(0.432 0.012 250);
  --text-muted: oklch(0.520 0.011 250);
  --border: oklch(0.868 0.006 250);
  --border-strong: oklch(0.588 0.010 250);
  --accent: oklch(0.220 0.012 250);
  --accent-hover: oklch(0.300 0.014 250);
  --on-accent: oklch(1 0 0);
  --accent-text: oklch(0.470 0.102 118);
  --emphasis: oklch(0.500 0.108 118);
  --signal-fill: oklch(0.880 0.189 118);
  --on-signal: oklch(0.205 0.010 250);

  /* --- Type ------------------------------------------------------------ */
  --font-display: 'Archivo', ui-sans-serif, system-ui, sans-serif;
  --font-body: 'Source Serif 4', Georgia, serif;
  --font-mono: 'Chivo Mono', ui-monospace, 'SF Mono', Menlo, monospace;

  --fs-display: clamp(2.875rem, 5.5vw, 4.5rem);
  --fs-h1: 2.25rem;
  --fs-h2: 1.75rem;
  --fs-h3: 1.375rem;
  --fs-body: 1.0625rem;
  --fs-small: 0.875rem;
  --fs-caption: 0.8125rem;

  --lh-display: 1.1;
  --lh-heading: 1.25;
  --lh-body: 1.65;

  /* --- Space ------------------------------------------------------------ */
  --sp-1: 4px;   --sp-2: 8px;   --sp-3: 12px;  --sp-4: 16px;
  --sp-6: 24px;  --sp-8: 32px;  --sp-12: 48px; --sp-16: 64px;
  --sp-24: 96px; --sp-32: 128px;

  --radius-sm: 4px;
  --radius-md: 8px;
  --radius-lg: 12px;

  --measure: 68ch;
  --content: 1120px;
  --prose: 720px;

  /* --- Motion ----------------------------------------------------------- */
  --dur-fast: 120ms;
  --dur-base: 220ms;
  --dur-slow: 400ms;
  --ease-out: cubic-bezier(0.2, 0, 0, 1);

  /* --- Z scale ----------------------------------------------------------- */
  --z-sticky: 100;
  --z-nav: 200;

  /* Fixed nav height. Also read by the scroll-flip script in index.html
     (rootMargin) and by the [id] scroll-margin-top rule below — keep all
     three in sync if this changes. */
  --nav-h: 84px;
}

/* Ground 2: Slate. Hero + the one signature block. Not a dark mode.
   Paints its own background so non-<section> children (the footer) can't
   inherit slate's light text onto the page's light canvas. */
.ground-slate {
  background: var(--bg);
  color: var(--text-primary);
  --bg: oklch(0.245 0.008 250);
  --surface-1: oklch(0.292 0.009 250);
  --surface-2: oklch(0.200 0.008 250);
  --text-primary: oklch(0.962 0.004 250);
  --text-secondary: oklch(0.800 0.008 250);
  --text-muted: oklch(0.706 0.010 250);
  --border: oklch(0.365 0.010 250);
  --border-strong: oklch(0.560 0.012 250);
  --accent: oklch(0.962 0.004 250);
  --accent-hover: oklch(0.880 0.005 250);
  --on-accent: oklch(0.245 0.008 250);
  --accent-text: oklch(0.840 0.180 118);
  --emphasis: oklch(0.780 0.168 118);
  --signal-fill: oklch(0.860 0.184 118);
  --on-signal: oklch(0.200 0.008 250);
  --lh-body: 1.70; /* light type on dark reads lighter */
}

/* Ground 3: Dark mode. System preference. */
@media (prefers-color-scheme: dark) {
  :root {
    --bg: oklch(0.150 0.004 250);
    --surface-1: oklch(0.195 0.005 250);
    --surface-2: oklch(0.235 0.006 250);
    --text-primary: oklch(0.955 0.003 250);
    --text-secondary: oklch(0.752 0.007 250);
    --text-muted: oklch(0.642 0.009 250);
    --border: oklch(0.295 0.006 250);
    --border-strong: oklch(0.510 0.011 250);
    --accent: oklch(0.950 0.003 250);
    --accent-hover: oklch(0.870 0.004 250);
    --on-accent: oklch(0.150 0.004 250);
    --accent-text: oklch(0.820 0.176 118);
    --emphasis: oklch(0.760 0.163 118);
    --signal-fill: oklch(0.880 0.189 118);
    --on-signal: oklch(0.205 0.010 250);
    --lh-body: 1.70;
  }
}

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

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

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

/* Every in-page anchor target lands below the fixed nav rather than under it. */
[id] { scroll-margin-top: var(--nav-h); }

body {
  margin: 0;
  background: var(--bg);
  color: var(--text-primary);
  font-family: var(--font-body);
  font-size: var(--fs-body);
  line-height: var(--lh-body);
  font-optical-sizing: auto; /* Source Serif 4 has an opsz axis — required */
  -webkit-font-smoothing: antialiased;
}

h1, h2, h3 {
  font-family: var(--font-display);
  font-weight: 500;
  line-height: var(--lh-heading);
  text-wrap: balance;
  margin: 0;
}

p { margin: 0; text-wrap: pretty; }

/* UA gives <figure> margin: 1em 40px and <dd> margin-inline-start: 40px. */
figure, figcaption, dl, dd, dt { margin: 0; }
ol, ul { margin: 0; padding: 0; }

a { color: inherit; }

:focus-visible {
  outline: 2px solid var(--accent-text);
  outline-offset: 3px;
  border-radius: var(--radius-sm);
}

.u-skip {
  position: absolute; left: -9999px; top: 0;
  background: var(--accent); color: var(--on-accent);
  padding: var(--sp-3) var(--sp-4); z-index: calc(var(--z-nav) + 1);
  font-family: var(--font-display); font-size: var(--fs-small);
}
.u-skip:focus { left: var(--sp-4); top: var(--sp-4); }

.u-ui { font-family: var(--font-display); }

/* Figures: mono, tabular, rationed to numbers only. */
.u-figure {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-weight: 400;
  letter-spacing: -0.01em;
}

/* The acid mark. Scores, thresholds, state changes. Never decoration. */
.u-mark {
  background: var(--signal-fill);
  color: var(--on-signal);
  padding: 0.1em 0.4em;
  border-radius: var(--radius-sm);
}

.u-shell {
  width: 100%;
  max-width: var(--content);
  margin-inline: auto;
  padding-inline: var(--sp-6);
}
@media (min-width: 700px) { .u-shell { padding-inline: var(--sp-8); } }

section { background: var(--bg); color: var(--text-primary); }

/* =========================================================================
   Nav
   ========================================================================= */

/* Fixed at the page level (not inside the hero), so the CTA stays visible
   on every section. Always opaque — never transparent — because the hero
   holds more content than one viewport, so scrolling within it moves
   headline/CTA/ledger text up into the nav's own band; a transparent nav
   let that content show through and collide with the wordmark. Starts
   solid slate + light text via .ground-slate (that class's own fill,
   unmodified). Once the hero scrolls fully out of view, index.html's
   IntersectionObserver swaps to .is-scrolled: light-ground tokens, solid
   surface, hairline border. Token-driven, so the CTA's outline recolors
   for free. */
.nav {
  position: fixed;
  top: 0; left: 0; right: 0;
  z-index: var(--z-nav);
  height: var(--nav-h);
  display: flex;
  align-items: center;
  border-bottom: 1px solid transparent;
  transition: background-color var(--dur-base) var(--ease-out),
              border-color var(--dur-base) var(--ease-out),
              color var(--dur-base) var(--ease-out);
}
.nav.is-scrolled {
  background: var(--surface-1);
  border-bottom-color: var(--border);
}

.nav__in {
  width: 100%;
  display: flex; align-items: center; justify-content: space-between; gap: var(--sp-4);
}
.nav__mark {
  display: inline-flex;
  align-items: center;
  min-height: 44px; /* WCAG 2.5.8 target size; was 23px */
  font-family: var(--font-display);
  font-size: var(--fs-small);
  font-weight: 500;
  letter-spacing: 0.01em;
  text-decoration: none;
}

/* =========================================================================
   Buttons
   ========================================================================= */

.btn {
  display: inline-flex; align-items: center; justify-content: center;
  font-family: var(--font-display);
  font-size: var(--fs-small);
  font-weight: 500;
  line-height: 1;
  min-height: 44px; /* touch target; was 40px */
  padding: var(--sp-3) var(--sp-6);
  border-radius: var(--radius-sm);
  border: 1px solid transparent;
  text-decoration: none;
  cursor: pointer;
  transition: background var(--dur-base) var(--ease-out),
              border-color var(--dur-base) var(--ease-out),
              transform var(--dur-fast) var(--ease-out);
}
.btn--primary { background: var(--accent); color: var(--on-accent); }
.btn--primary:hover { background: var(--accent-hover); }
.btn--secondary { background: transparent; color: var(--text-primary); border-color: var(--border-strong); }
.btn--secondary:hover { border-color: var(--text-primary); }
.btn:active { transform: scale(0.98); }

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

/* =========================================================================
   Hero — slate ground
   ========================================================================= */

.hero {
  background: var(--bg);
  color: var(--text-primary);
  padding-top: var(--nav-h); /* reserve space for the now-fixed .nav */
  padding-bottom: var(--sp-24);
}

.hero__grid {
  display: grid;
  gap: var(--sp-16) var(--sp-12);
  padding-top: var(--sp-16);
  align-items: start;
}
@media (min-width: 1000px) {
  .hero__grid {
    grid-template-columns: 7fr 5fr;
    padding-top: var(--sp-24);
    gap: var(--sp-12);
  }
}

.hero__h {
  font-size: var(--fs-display);
  line-height: var(--lh-display);
  letter-spacing: -0.025em;
  margin-bottom: var(--sp-6);
}
.hero__sub {
  color: var(--text-secondary);
  max-width: 44ch;
  margin-bottom: var(--sp-8);
}
.hero__ctas { display: flex; flex-wrap: wrap; gap: var(--sp-3); }

/* --- The signature: a signal ledger. Typographic, never a dashboard. --- */

.ledger {
  border-top: 1px solid var(--border-strong);
  padding-top: var(--sp-3);
}
.ledger__cap {
  font-family: var(--font-mono);
  font-size: var(--fs-caption);
  color: var(--text-muted);
  display: flex; justify-content: space-between; gap: var(--sp-4);
  padding-bottom: var(--sp-4);
}
.ledger__row {
  display: grid;
  grid-template-columns: auto 1fr auto;
  gap: var(--sp-4);
  align-items: baseline;
  padding-block: var(--sp-3);
  border-top: 1px solid var(--border);
  font-size: var(--fs-small);
}
.ledger__t { font-family: var(--font-mono); font-variant-numeric: tabular-nums; color: var(--text-muted); font-size: var(--fs-caption); }
.ledger__d { font-family: var(--font-mono); font-size: var(--fs-caption); color: var(--text-secondary); }
.ledger__v { font-family: var(--font-mono); font-variant-numeric: tabular-nums; color: var(--text-secondary); font-size: var(--fs-caption); }

/* The ledger holds exactly one acid instance: the score itself. Weights and
   the threshold rule stay neutral so the fired score is the only event. */
.ledger__row--fire { border-top-color: var(--border-strong); }
.ledger__row--fire .ledger__d { color: var(--text-primary); }
.ledger__row--fire .ledger__v { color: var(--on-signal); font-size: var(--fs-small); }

/* Mono, like the rest of the ledger: this is the instrument's own output. */
.ledger__note {
  font-family: var(--font-mono);
  font-size: var(--fs-caption);
  line-height: 1.55;
  color: var(--text-muted);
  padding-top: var(--sp-4);
  max-width: 46ch;
}

/* =========================================================================
   The shift — light ground
   ========================================================================= */

/* .shift uses .sec for padding; only its internals are local. */

.beats { border-top: 1px solid var(--border); }

/* No stepping. The indents were a substitute for numerals, but against a
   full-width rule they left the block with neither a firm left edge nor a
   filled right one. The heading rail now carries the structure, so the
   beats sit flush and the rules span only the column they belong to. */
.beat {
  padding-block: var(--sp-12);
  border-bottom: 1px solid var(--border);
}

.beat__t { color: var(--text-secondary); }
.beat__t b { font-family: var(--font-display); font-weight: 500; color: var(--text-primary); }
.beat__t i { font-style: italic; }

/* The summation. Fills the content column rather than sitting in it. */
.shift__close {
  padding-top: var(--sp-16);
  font-size: var(--fs-h3);
  line-height: 1.45;
  color: var(--text-primary);
}

/* =========================================================================
   Hero load reveal. CSS-only: content is visible by default and the
   animation only enhances it, so a failed render never ships a blank hero.
   ========================================================================= */

@media (prefers-reduced-motion: no-preference) {
  .reveal { animation: rise var(--dur-slow) var(--ease-out) both; }
  .reveal--1 { animation-delay: 60ms; }
  .reveal--2 { animation-delay: 140ms; }
  .reveal--3 { animation-delay: 220ms; }
  .reveal--4 { animation-delay: 320ms; }
}

@keyframes rise {
  from { opacity: 0; transform: translateY(10px); }
  to   { opacity: 1; transform: none; }
}

/* =========================================================================
   Shared section furniture
   ========================================================================= */

.sec { padding-block: var(--sp-24); }

/* Section boundary. Two adjacent light sections with the same padding and
   the same internal texture read as one long block no matter how much air
   sits between them — space alone is not a divider. A rule at the container
   edge is: it's how a technical document separates sections, it repeats
   cleanly, and it costs no colour. Sections that change ground don't need
   one; the colour change is already the boundary. */
.sec--rule { padding-top: 0; }
.sec--rule > .u-shell {
  border-top: 1px solid var(--border-strong);
  padding-top: var(--sp-24);
}

.sec__h {
  font-size: var(--fs-h1);
  letter-spacing: -0.02em;
  max-width: 34ch;
}

/* EXPERIMENTAL — not yet a rule. Direct test against DESIGN.md's "coloured
   rules and borders are banned outright" (rule 1): applied to the three
   headings with no body copy beneath them in the rail (the-shift, why-us,
   how-we-work). border-bottom on the block itself, not text-decoration, so
   wrapped headings ("Why this isn't merely software") get exactly one line
   under the whole box rather than one per row. Revert by removing the
   class from the three <h2> elements and this rule; nothing else depends
   on it. */
.sec__h--mark {
  border-bottom: 12px solid var(--signal-fill);
  padding-bottom: var(--sp-4);
}

.sec__lead {
  color: var(--text-secondary);
  max-width: var(--measure);
  margin-top: var(--sp-6);
}

/* --- Heading rail + content column ---------------------------------------
   The page's structural grammar. Previously the heading sat full-width and
   the content below it reached only ~53% of the container, while the
   hairline rules still spanned 100% — drawing a line across dead space and
   reading as unresolved at large viewports.
   Putting the heading in a left rail gives that space a job and lets the
   rules span only the content column, so nothing is ruled that isn't used.
   The rail sticks while its section scrolls, which keeps the argument's
   subject in view and makes the empty lower rail deliberate. */
.sec__grid { display: grid; gap: var(--sp-8); }

@media (min-width: 1000px) {
  .sec__grid {
    grid-template-columns: minmax(0, 4fr) minmax(0, 7fr);
    gap: var(--sp-16);
    align-items: start;
  }
  /* Static, not sticky: with four sections in a row, sticky-then-release
     on every single one read as a repeated mechanical tic rather than a
     considered choice on any one of them. */
}

/* =========================================================================
   What we build — a definition list, not a card grid.
   Asymmetric columns, full-bleed rules, no icons.
   ========================================================================= */

/* A specification table, not another list of headings. Same spine as every
   other section — the difference is TEXTURE: term and definition side by
   side, body-size rather than heading-size terms, and rows at --sp-4 where
   the argument beats breathe at --sp-12. Reads as reference material next
   to the essay above it, without moving a single margin. */
.parts { border-top: 1px solid var(--border); }

.part {
  padding-block: var(--sp-4);
  border-bottom: 1px solid var(--border);
}
@media (min-width: 620px) {
  .part {
    display: grid;
    grid-template-columns: minmax(0, 2fr) minmax(0, 3fr);
    gap: var(--sp-6);
    align-items: baseline;
  }
}

.part__n {
  font-family: var(--font-display);
  font-weight: 500;
  font-size: var(--fs-body);
  color: var(--text-primary);
}
.part__n i { font-style: italic; }
.part__d { color: var(--text-secondary); }

.build__callout {
  margin-top: var(--sp-12);
  font-size: var(--fs-h3);
  line-height: 1.45;
}
.build__callout b { font-family: var(--font-display); font-weight: 500; }

/* =========================================================================
   Why this isn't merely software — recessed band, two columns.
   ========================================================================= */

/* The page's mid-point pause. Sits on exactly the same rail and content
   column as every other section — an earlier version centred it in its own
   narrower column, which broke the spine and made the whole band read as
   thrown in rather than emphasised. The ground and the type scale do the
   differentiating; the margins do not move.
   This is the third slate block, against DESIGN.md's earlier limit of two.
   The limit existed to stop slate becoming wallpaper; at three, spaced
   across the page's start, middle and end, it reads as punctuation. */
.why { padding-block: var(--sp-32); }

.why__lede {
  font-size: var(--fs-h2);
  line-height: 1.4;
  color: var(--text-primary);
}
.why__body {
  margin-top: var(--sp-6);
  color: var(--text-secondary);
}

/* =========================================================================
   How we work — the page's one numbered sequence. Numerals earned here.
   ========================================================================= */

.phases {
  counter-reset: phase;
  list-style: none;
  border-top: 1px solid var(--border);
}

.phase {
  counter-increment: phase;
  display: grid;
  gap: var(--sp-2);
  padding-block: var(--sp-12);
  border-bottom: 1px solid var(--border);
}
.phase::before {
  content: counter(phase, decimal-leading-zero);
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: var(--fs-caption);
  color: var(--text-muted);
}
@media (min-width: 800px) {
  .phase { grid-template-columns: auto minmax(0, 1fr); gap: var(--sp-12); }
  .phase::before { padding-top: 0.35em; }
}

.phase__t { color: var(--text-secondary); }
.phase__t b { font-family: var(--font-display); font-weight: 500; color: var(--text-primary); }

/* =========================================================================
   Close + footer — the second and last slate block. Bookends the hero.
   ========================================================================= */

.close { padding-block: var(--sp-24); }
.close__h { font-size: var(--fs-h1); letter-spacing: -0.02em; max-width: 22ch; }
.close__sub {
  margin-top: var(--sp-6);
  color: var(--text-secondary);
  max-width: 54ch;
}
.close__cta { margin-top: var(--sp-8); display: flex; }

/* --- Booking calendar -----------------------------------------------------
   Deliberately seamless: no border, no surface, no radius, no shadow, so it
   reads as the CTA expanding rather than as a separate panel appearing.
   The 0fr -> 1fr grid-row transition animates to the content's natural
   height without hard-coding one.
   Note: `.cal { display: grid }` outranks the UA's `[hidden] { display:none }`
   (equal specificity, author sheet wins), so the [hidden] case is explicit. */
.cal {
  display: grid;
  grid-template-rows: 0fr;
  transition: grid-template-rows var(--dur-slow) var(--ease-out);
  margin-top: 0;
}
.cal[hidden] { display: none; }
.cal.is-open { grid-template-rows: 1fr; margin-top: var(--sp-8); }

.cal__inner { overflow: hidden; min-height: 0; }

.cal__frame {
  display: block;
  width: 100%;
  border: 0;
  /* Fallback height for when the provider's resize script is blocked or
     fails; form_embed.js overrides this with the real content height. */
  min-height: 720px;
  border-radius: var(--radius-md);
}

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

.footer { padding-bottom: var(--sp-16); }
.footer__rule { border-top: 1px solid var(--border); padding-top: var(--sp-8); }
.footer__mark {
  font-family: var(--font-display);
  font-size: var(--fs-small);
  font-weight: 500;
}
.footer__line {
  margin-top: var(--sp-2);
  color: var(--text-secondary);
  font-size: var(--fs-small);
  max-width: 46ch;
}
.footer__meta {
  margin-top: var(--sp-8);
  display: flex;
  flex-wrap: wrap;
  gap: var(--sp-2) var(--sp-6);
  justify-content: space-between;
  font-family: var(--font-display);
  font-size: var(--fs-caption);
  color: var(--text-muted);
}
.footer__meta a { text-decoration-color: var(--border-strong); text-underline-offset: 3px; }
.footer__meta a:hover { text-decoration-color: currentColor; }
