/* ─── Inter, self-hosted ─────────────────────────────────────────────────── */
/*
   Was a stylesheet <link> to fonts.googleapis.com, which is render-blocking
   and third-party: the browser had to resolve DNS, complete a TLS handshake
   and fetch that CSS before it could paint anything, then go to a SECOND
   origin for the font file. On a throttled mobile connection that was most of
   a 3.0s first paint.

   Only the Latin subsets are shipped. Google served seven — Cyrillic, Greek,
   Vietnamese and so on — which this site has no use for.

   Inter is SIL Open Font License, so self-hosting is expressly permitted.
*/
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 300 600;
  font-display: swap;
  src: url('/assets/fonts/inter-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 300 600;
  font-display: swap;
  src: url('/assets/fonts/inter-latin.woff2') format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}

/* ===========================================================================
   Atlas — website stylesheet
   ---------------------------------------------------------------------------
   The site is a single landing page plus a handful of standalone legal and
   support pages that the app stores require to live at their own URLs.

   Colour tokens are lifted from the app's src/theme/editorial.ts. The palette
   is MONOCHROME: near-black ink on a warm off-white canvas in light, warm
   off-white on OLED black in dark. The app's rule is "no colour accent in UI
   chrome" and this follows it — the only colour anywhere is the Google mark.

   Typography follows cosmos.so: ONE grotesk at every size, no serif, display
   sizes set light with tight negative tracking, body tracked slightly negative.

   BROWSER SUPPORT: last two versions of Safari, Chrome, Firefox and Edge, plus
   iOS Safari and Chrome Android. Modern features carry a fallback immediately
   above them (svh -> vh, color-mix -> flat colour), so an older engine degrades
   rather than breaks.

   Run ./build.sh to deploy — it stamps a content hash onto the asset URLs so
   the year-long immutable cache cannot serve a stale stylesheet.
   =========================================================================== */

/* ─── Reset ──────────────────────────────────────────────────────────────── */

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

html {
  -webkit-text-size-adjust: 100%;
  scroll-behavior: smooth;
}

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

img, svg, picture { display: block; max-width: 100%; }
input, button, textarea, select { font: inherit; color: inherit; }

/* ─── Tokens ─────────────────────────────────────────────────────────────── */

:root {
  --bg: #f8f7f5;
  --bg-elevated: #ffffff;
  --card: #ffffff;
  --card-alt: #f0efed;
  --surface-alt: #eceae5;
  --border: rgba(0, 0, 0, 0.09);
  --border-strong: rgba(0, 0, 0, 0.16);

  --text: #0c0c0c;
  --text-dim: #55554e;
  --text-mute: #6c6b64;

  --accent: #0c0c0c;
  --accent-dim: #444442;
  --accent-soft: rgba(12, 12, 12, 0.06);
  --on-accent: #ffffff;

  /* Landing glass: a raised tint on a flat canvas. */
  --glass: rgba(255, 255, 255, 0.66);
  --glass-hover: rgba(255, 255, 255, 0.92);
  --glass-border: rgba(0, 0, 0, 0.12);

  --r-sm: 12px;
  --r-md: 16px;
  --r-lg: 22px;
  --r-xl: 28px;
  --r-pill: 999px;

  --s-xs: 6px;
  --s-sm: 10px;
  --s-md: 16px;
  --s-lg: 24px;
  --s-xl: 32px;
  --s-xxl: 48px;

  /* One family everywhere. --font-display names an intent, not a second
     typeface: display and body are the same grotesk, separated by size,
     weight and tracking alone. */
  --font-sans: "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto,
    "Helvetica Neue", Arial, sans-serif;
  --font-display: var(--font-sans);

  /* Tracking tightens as type grows — roughly -1% body, -4% display. */
  --track-body: -0.011em;
  --track-lead: -0.021em;
  --track-display: -0.038em;

  --wrap: 1560px;
  --wrap-narrow: 760px;
  --gutter: clamp(20px, 3.6vw, 56px);
  --nav-h: 64px;
}

@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --bg: #0a0a0a;
    --bg-elevated: #111110;
    --card: #111110;
    --card-alt: #1c1c1a;
    --surface-alt: #1a1a18;
    --border: rgba(255, 255, 255, 0.11);
    --border-strong: rgba(255, 255, 255, 0.2);

    --text: #f0efeb;
    --text-dim: #a3a29c;
    --text-mute: #85847d;

    --accent: #f0efeb;
    --accent-dim: #cbcac4;
    --accent-soft: rgba(240, 239, 235, 0.08);
    --on-accent: #0a0a0a;

    --glass: rgba(255, 255, 255, 0.06);
    --glass-hover: rgba(255, 255, 255, 0.12);
    --glass-border: rgba(255, 255, 255, 0.16);
  }
}

:root[data-theme="dark"] {
  --bg: #0a0a0a;
  --bg-elevated: #111110;
  --card: #111110;
  --card-alt: #1c1c1a;
  --surface-alt: #1a1a18;
  --border: rgba(255, 255, 255, 0.11);
  --border-strong: rgba(255, 255, 255, 0.2);

  --text: #f0efeb;
  --text-dim: #a3a29c;
  --text-mute: #85847d;

  --accent: #f0efeb;
  --accent-dim: #cbcac4;
  --accent-soft: rgba(240, 239, 235, 0.08);
  --on-accent: #0a0a0a;

  --glass: rgba(255, 255, 255, 0.06);
  --glass-hover: rgba(255, 255, 255, 0.12);
  --glass-border: rgba(255, 255, 255, 0.16);
}

/* ─── Base ───────────────────────────────────────────────────────────────── */

body {
  background: var(--bg);
  color: var(--text);
  font-family: var(--font-sans);
  font-size: 16px;
  line-height: 1.55;
  letter-spacing: var(--track-body);
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
}

h1, h2, h3 {
  font-family: var(--font-display);
  font-weight: 400;
  line-height: 1.05;
  letter-spacing: var(--track-display);
  color: var(--text);
  text-wrap: balance;
}

h1 { font-size: clamp(2.6rem, 5.4vw, 4.6rem); font-weight: 380; }
h2 { font-size: clamp(1.8rem, 3vw, 2.6rem); font-weight: 380; }
h3 {
  font-size: 1.08rem;
  font-weight: 500;
  line-height: 1.3;
  letter-spacing: var(--track-lead);
}

p { text-wrap: pretty; }

a {
  color: var(--text);
  text-decoration-color: var(--border-strong);
  text-underline-offset: 3px;
  transition: text-decoration-color 0.15s ease, color 0.15s ease;
}
a:hover { text-decoration-color: currentColor; }

strong { font-weight: 600; }

:focus-visible {
  outline: 2px solid currentColor;
  outline-offset: 3px;
  border-radius: 3px;
}

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

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

.skip-link {
  position: absolute;
  left: -9999px;
  top: 0;
  background: var(--text);
  color: var(--bg);
  padding: 12px 20px;
  z-index: 300;
}
.skip-link:focus { left: 0; }

/* ─── Layout ─────────────────────────────────────────────────────────────── */

.wrap {
  width: 100%;
  max-width: var(--wrap);
  margin-inline: auto;
  padding-inline: var(--gutter);
}

.wrap-narrow {
  width: 100%;
  max-width: var(--wrap-narrow);
  margin-inline: auto;
  padding-inline: var(--gutter);
}

.section { padding-block: clamp(56px, 7vw, 96px); }
.section--alt {
  background: var(--surface-alt);
  border-block: 1px solid var(--border);
}

.eyebrow, .status {
  display: block;
  font-size: 0.72rem;
  font-weight: 500;
  letter-spacing: 0.09em;
  text-transform: uppercase;
  color: var(--text-mute);
  margin-bottom: var(--s-lg);
}

.lede {
  font-size: clamp(1.02rem, 1.35vw, 1.13rem);
  line-height: 1.5;
  letter-spacing: var(--track-lead);
  color: var(--text-dim);
  max-width: 56ch;
}

.section-head {
  padding-bottom: var(--s-lg);
  border-bottom: 1px solid var(--border);
  margin-bottom: var(--s-xl);
}
.section-head .eyebrow { margin-bottom: var(--s-sm); }
.section-head h2 { max-width: 16ch; }

.mt-lg { margin-top: var(--s-lg); }

/* ─── Nav ────────────────────────────────────────────────────────────────── */
/*
   Two variants. The landing page centres the wordmark with the theme toggle
   alone at the right edge; the support and legal pages keep a compact floating
   pill with links, because those pages need a way back.
*/

.nav {
  position: fixed;
  top: 14px;
  left: 0;
  right: 0;
  z-index: 100;
  display: flex;
  justify-content: center;
  padding-inline: var(--s-md);
  pointer-events: none;
}

.nav__inner {
  pointer-events: auto;
  display: flex;
  align-items: center;
  gap: var(--s-xl);
  max-width: 100%;
  padding: 7px 8px 7px 20px;
  border-radius: var(--r-pill);
  border: 1px solid var(--border-strong);
  /* Flat colour first for engines without color-mix (Safari < 16.2); they get
     an opaque pill rather than a translucent one, which is correct. */
  background: var(--bg);
  background: color-mix(in srgb, var(--bg) 76%, transparent);
  -webkit-backdrop-filter: saturate(180%) blur(20px);
  backdrop-filter: saturate(180%) blur(20px);
  box-shadow: 0 4px 24px rgba(0, 0, 0, 0.07);
}
:root[data-theme="dark"] .nav__inner { box-shadow: 0 4px 24px rgba(0, 0, 0, 0.45); }
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .nav__inner { box-shadow: 0 4px 24px rgba(0, 0, 0, 0.45); }
}

/* Landing: a compact pill that shrinks to its contents rather than spanning
   the page. The two side cells are given the SAME fixed width as the toggle —
   not flex:1, which collapses to zero in a shrink-to-fit box — so the wordmark
   is dead centre rather than approximately centred. */
.nav--landing { top: 10px; padding-inline: var(--gutter); }
.nav--landing .nav__inner {
  width: auto;
  max-width: 100%;
  justify-content: center;
  gap: var(--s-md);
  padding: 5px 10px;
  border-color: var(--glass-border);
  background: var(--glass);
}
.nav--landing .nav__side { flex: 0 0 26px; width: 26px; }
.nav--landing .nav__brand .wordmark { height: 15px; }
.nav--landing .icon-btn { width: 26px; height: 26px; }
.nav--landing .icon-btn svg { width: 15px; height: 15px; }
.nav__side { flex: 1 1 0; display: flex; align-items: center; }
.nav__side--end { justify-content: flex-end; }

.nav__brand { display: inline-flex; align-items: center; flex-shrink: 0; }

/* One wordmark asset (black on transparent), inverted in dark rather than
   shipped twice — exact brand fidelity, and it tracks the toggle instantly. */
.wordmark { width: auto; }
:root[data-theme="dark"] .wordmark { filter: invert(1); }
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .wordmark { filter: invert(1); }
}

.nav__brand .wordmark { height: 18px; }



.nav__actions { display: flex; align-items: center; gap: 2px; margin-left: auto; }

.icon-btn {
  width: 32px;
  height: 32px;
  display: grid;
  place-items: center;
  border: none;
  background: transparent;
  color: var(--text-mute);
  cursor: pointer;
  border-radius: var(--r-pill);
  transition: color 0.15s ease, background 0.15s ease;
}
.icon-btn:hover { color: var(--text); background: var(--accent-soft); }
.icon-btn svg { width: 16px; height: 16px; }

.icon-sun { display: none; }
:root[data-theme="dark"] .icon-sun { display: block; }
:root[data-theme="dark"] .icon-moon { display: none; }
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .icon-sun { display: block; }
  :root:not([data-theme="light"]) .icon-moon { display: none; }
}


/* Pages other than the landing start below the fixed pill. */
/* Reserves room for the fixed nav. The standalone documents have no nav —
   they open in their own window and carry only the footer — so they get a
   plain top margin instead of a nav-sized hole. */
body:not(.landing):not(.doc) { padding-top: calc(var(--nav-h) + 14px); }

/* The documents now carry the same fixed pill nav as the landing page, so they
   need the same shorter nav height AND room reserved for it — otherwise the
   first heading sits underneath the bar. */
body.doc {
  --nav-h: 48px;
  padding-top: calc(var(--nav-h) + 28px);
}

@media (max-width: 820px) {
  .nav__inner { width: 100%; justify-content: space-between; gap: var(--s-sm); }
}

/* ─── Landing stage ──────────────────────────────────────────────────────── */

/*
   The landing is exactly one screen. `height` rather than `min-height` on both
   so nothing can push the document past the viewport and produce a scrollbar
   on a page with only one section. The short-viewport case below reopens
   scrolling, because clipping content is worse than a scrollbar.
*/
.landing {
  /* Scoped: the landing bar is shorter than the one on the other pages, so the
     space the stage reserves for it shrinks to match. */
  --nav-h: 48px;
}

.stage {
  position: relative;
  min-height: 100vh;
  min-height: 100svh;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  padding: calc(var(--nav-h) + 32px) var(--gutter) var(--s-xl);
}

.stage__inner { position: relative; }

.stage__inner {
  flex: 1 1 auto;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  text-align: center;
  /* Gap grows with viewport height so a tall screen spreads the group out
     instead of clustering it in the middle with dead space above and below. */
  gap: clamp(var(--s-lg), 5.4vh, 70px);
  /* Lifted above true centre so the composition sits high and the footer has
     room underneath. Smaller than before: the group itself is taller now. */
  padding-bottom: clamp(32px, 6vh, 84px);
}

/* Title and its status line are a tight pair; the parent's larger gap then
   separates the whole block from the compose card. */
.stage__head {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: clamp(10px, 1.6vh, 20px);
}

/* One line, always. The vw term is sized so 24 characters of Inter at this
   weight clear the gutters at every width, so nowrap can never push the page
   into a horizontal scroll. The vh term is what stops a short, wide window
   from picking a size that fills the width but overflows the height lock. */
.stage__title {
  font-size: clamp(1.5rem, min(7.6vw, 13vh), 8rem);
  white-space: nowrap;
  margin-bottom: 0;
}

/* ─── Compose card ───────────────────────────────────────────────────────── */

.compose {
  width: 100%;
  max-width: 820px;
  padding: clamp(var(--s-lg), 2.6vh, 34px);
  border-radius: var(--r-xl);
  border: 1px solid var(--glass-border);
  background: var(--bg-elevated);
  background: color-mix(in srgb, var(--bg-elevated) 88%, transparent);
  -webkit-backdrop-filter: saturate(180%) blur(24px);
  backdrop-filter: saturate(180%) blur(24px);
  box-shadow: 0 18px 48px rgba(0, 0, 0, 0.14);
  text-align: left;
}

.compose__input {
  width: 100%;
  border: none;
  background: transparent;
  padding: var(--s-xs) 2px var(--s-lg);
  font-size: clamp(1rem, 1.5vw, 1.3rem);
  letter-spacing: var(--track-lead);
  color: var(--text);
}
.compose__input::placeholder { color: var(--text-mute); }
.compose__input:focus { outline: none; }

.compose__row {
  display: flex;
  align-items: center;
  justify-content: flex-end;
  gap: var(--s-sm);
}


/* The Google mark keeps its own colours; Apple's is monochrome and follows the
   theme. Provider marks are the one licensed exception to the palette. */

.compose__send {
  flex-shrink: 0;
  width: 40px;
  height: 40px;
  display: grid;
  place-items: center;
  border: none;
  border-radius: 50%;
  background: var(--accent);
  color: var(--on-accent);
  cursor: pointer;
  transition: background 0.15s ease, transform 0.12s ease;
}
.compose__send:hover { background: var(--accent-dim); }
.compose__send:active { transform: scale(0.94); }
.compose__send[disabled] { opacity: 0.5; cursor: default; }
.compose__send svg { width: 18px; height: 18px; }

/* Collapsed while empty: otherwise its reserved height plus a flex gap sits
   between the message bar and the chips, pushing the chips down against the
   socials instead of centring them between the two. */
.compose__msg:empty { display: none; }

.compose__msg {
  min-height: 1.3em;
  font-size: 0.88rem;
  color: var(--text-dim);
  text-align: center;
}

/* ─── Key features ───────────────────────────────────────────────────────── */
/*
   Static chips, not buttons. They were <button>s that expanded a note; nothing
   presses now, so nothing carries a pressed affordance — no hover lift, no
   pointer cursor, no border that reads as a control edge.

   Laid out as one row rather than three stacked full-width pills, which is
   what made them dominate the page.
*/

.keys {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  gap: 8px;
  list-style: none;
  padding: 0;
  margin: 0;
}

.key {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: clamp(8px, 1.1vh, 12px) clamp(16px, 1.5vw, 22px);
  border-radius: var(--r-pill);
  border: 1px solid var(--glass-border);
  background: var(--glass);
  -webkit-backdrop-filter: saturate(180%) blur(18px);
  backdrop-filter: saturate(180%) blur(18px);
  color: var(--text-dim);
  font-size: clamp(0.88rem, 1vw, 1rem);
  font-weight: 500;
  letter-spacing: var(--track-lead);
  white-space: nowrap;
  cursor: default;
}
.key svg { width: 15px; height: 15px; flex-shrink: 0; color: var(--text-mute); }

/* ─── Landing footer ─────────────────────────────────────────────────────── */

/* One row, pinned to the outer edges: credit hard left, legal links hard
   right. Stacks and centres on narrow screens, where the two would collide. */
.site-foot {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--s-md);
  padding: var(--s-xl) var(--gutter) var(--s-xl);
  font-size: 0.82rem;
  color: var(--text-mute);
  border-top: 1px solid var(--border);
}

/* No longer inside the footer, so it can no longer inherit the muted colour —
   set it here or it reads as loud as the headline. */
.stage__status,
.chapter__more {
  font-size: 0.72rem;
  font-weight: 500;
  letter-spacing: 0.09em;
  text-transform: uppercase;
  color: var(--text-mute);
}

.socials {
  display: flex;
  align-items: center;
  justify-content: center;
  flex-wrap: wrap;
  gap: 6px;
  font-size: clamp(0.82rem, 0.95vw, 0.95rem);
}
.socials a {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding-inline: 6px;
  color: var(--text-dim);
  text-decoration: none;
  font-weight: 500;
}
.socials a:hover { color: var(--text); }
.socials a svg { flex-shrink: 0; }
.socials > span { color: var(--border-strong); }

/* Icons only. The label is still in the DOM (visually-hidden) so the link has
   an accessible name. */
.socials a { padding-inline: 10px; }
.socials a svg { width: 18px; height: 18px; }

.stage__links { display: flex; flex-wrap: wrap; justify-content: flex-end; gap: 8px; }
.stage__links a { color: var(--text-dim); text-decoration: none; }
.stage__links a:hover { color: var(--text); text-decoration: underline; text-underline-offset: 3px; }

.stage__credit a { color: var(--text-dim); text-decoration: none; }
.stage__credit a:hover { color: var(--text); text-decoration: underline; }

@media (max-width: 620px) {
  .stage { padding-top: calc(var(--nav-h) + 20px); }
  /* Credit and links collide well before this width — stack and centre. */
  .site-foot { flex-direction: column; gap: 8px; text-align: center; }
  .stage__links { justify-content: center; }
  .stage__inner { gap: var(--s-md); padding-bottom: var(--s-xl); }
  .compose { padding: var(--s-md); }
}

/* ─── Buttons (support + legal pages) ────────────────────────────────────── */

.btn {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: 12px 22px;
  border-radius: var(--r-pill);
  border: 1px solid transparent;
  font-size: 0.95rem;
  font-weight: 500;
  letter-spacing: var(--track-lead);
  text-decoration: none;
  cursor: pointer;
  transition: background 0.15s ease, border-color 0.15s ease;
}
.btn svg { width: 16px; height: 16px; flex-shrink: 0; }

.btn--primary { background: var(--accent); color: var(--on-accent); }
.btn--primary:hover { background: var(--accent-dim); }

.btn--ghost { color: var(--text); border-color: var(--border-strong); }
.btn--ghost:hover { background: var(--accent-soft); }

.btn-row { display: flex; flex-wrap: wrap; gap: var(--s-sm); margin-top: var(--s-xl); }

/* ─── Definition list (support page) ─────────────────────────────────────── */

.list {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: clamp(28px, 3.5vw, 52px) clamp(32px, 5vw, 88px);
}

.list__item { padding-top: var(--s-md); border-top: 1px solid var(--border-strong); }

.list__term {
  display: block;
  font-size: 1.24rem;
  font-weight: 500;
  line-height: 1.25;
  letter-spacing: var(--track-lead);
  margin-bottom: 8px;
}

.list__desc { font-size: 0.96rem; color: var(--text-dim); max-width: 46ch; }

@media (max-width: 760px) {
  .list { grid-template-columns: 1fr; gap: var(--s-lg); }
}

/* ─── FAQ ────────────────────────────────────────────────────────────────── */

.faq-group {
  font-size: 0.72rem;
  font-weight: 500;
  letter-spacing: 0.09em;
  text-transform: uppercase;
  color: var(--text-mute);
  margin-bottom: var(--s-sm);
}
.faq + .faq-group { margin-top: var(--s-xl); }

.faq { border-top: 1px solid var(--border); }
.faq details { border-bottom: 1px solid var(--border); }

.faq summary {
  cursor: pointer;
  list-style: none;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--s-md);
  font-size: 1.02rem;
  font-weight: 500;
  letter-spacing: var(--track-lead);
  padding-block: var(--s-lg);
}
.faq summary::-webkit-details-marker { display: none; }
.faq summary::after {
  content: "";
  width: 9px;
  height: 9px;
  flex-shrink: 0;
  border-right: 1.5px solid var(--text-mute);
  border-bottom: 1.5px solid var(--text-mute);
  transform: rotate(45deg) translateY(-2px);
  transition: transform 0.18s ease;
}
.faq details[open] summary::after { transform: rotate(-135deg) translateY(-2px); }
.faq details > p {
  color: var(--text-dim);
  font-size: 0.96rem;
  padding-bottom: var(--s-md);
  max-width: 82ch;
}

/* ─── Prose (legal pages) ────────────────────────────────────────────────── */

.page-head {
  padding-top: clamp(32px, 4vw, 56px);
  padding-bottom: clamp(32px, 4vw, 48px);
}
.page-head + .section { border-top: 1px solid var(--border); }
.page-head h1 { font-size: clamp(2.2rem, 4.4vw, 3.2rem); margin-bottom: var(--s-md); }
.page-head .meta { font-size: 0.88rem; color: var(--text-mute); }

.prose { padding-block: clamp(32px, 4vw, 52px); }
.prose h2 {
  font-size: clamp(1.35rem, 2.3vw, 1.75rem);
  margin-top: var(--s-xxl);
  margin-bottom: var(--s-md);
  scroll-margin-top: calc(var(--nav-h) + 24px);
}
.prose h2:first-child { margin-top: 0; }
.prose h3 { margin-top: var(--s-xl); margin-bottom: var(--s-sm); }
.prose p, .prose ul, .prose ol { color: var(--text-dim); margin-bottom: var(--s-md); }
.prose ul, .prose ol { padding-left: 1.3em; }
.prose li { margin-bottom: 6px; }
.prose li::marker { color: var(--text-mute); }
.prose a, .prose strong { color: var(--text); }

.prose table {
  width: 100%;
  border-collapse: collapse;
  margin-bottom: var(--s-lg);
  font-size: 0.92rem;
}
.prose th, .prose td {
  text-align: left;
  padding: 10px 12px 10px 0;
  border-bottom: 1px solid var(--border);
  vertical-align: top;
  color: var(--text-dim);
}
.prose th { color: var(--text); font-weight: 600; }

.table-scroll { overflow-x: auto; -webkit-overflow-scrolling: touch; }

.callout {
  border-left: 2px solid var(--text);
  padding: 2px 0 2px var(--s-lg);
  margin-bottom: var(--s-lg);
}
.callout p:last-child { margin-bottom: 0; }
.callout strong { display: block; margin-bottom: 5px; color: var(--text); }

.toc {
  border-top: 1px solid var(--border);
  border-bottom: 1px solid var(--border);
  padding-block: var(--s-lg);
  margin-bottom: var(--s-xl);
}
.toc p {
  font-size: 0.72rem;
  letter-spacing: 0.09em;
  text-transform: uppercase;
  color: var(--text-mute);
  margin-bottom: var(--s-sm);
}
.toc ol { margin: 0; padding-left: 1.2em; columns: 2; column-gap: var(--s-xl); font-size: 0.94rem; }
@media (max-width: 620px) { .toc ol { columns: 1; } }
.toc li { margin-bottom: 4px; break-inside: avoid; }
.toc a { color: var(--text-dim); }

.steps { list-style: none; padding: 0; counter-reset: step; display: grid; gap: var(--s-md); }
.steps li {
  counter-increment: step;
  display: grid;
  grid-template-columns: 1.6rem 1fr;
  gap: var(--s-md);
  align-items: baseline;
}
.steps li::before {
  content: counter(step);
  font-size: 0.8rem;
  font-weight: 500;
  color: var(--text-mute);
  border-bottom: 1px solid var(--border-strong);
  padding-bottom: 2px;
}
.steps strong { display: block; margin-bottom: 2px; }
.steps p { margin-bottom: 0; color: var(--text-dim); font-size: 0.95rem; }

/* ─── Footer (support + legal pages) ─────────────────────────────────────── */







/* ─── Scroll cue ─────────────────────────────────────────────────────────── */

.cue {
  position: absolute;
  left: 50%;
  bottom: var(--s-lg);
  transform: translateX(-50%);
  display: inline-flex;
  flex-direction: column;
  align-items: center;
  gap: 4px;
  padding: 6px 10px;
  color: var(--text-mute);
  text-decoration: none;
  font-size: 0.68rem;
  font-weight: 500;
  letter-spacing: 0.09em;
  text-transform: uppercase;
}
.cue:hover { color: var(--text); }
.cue svg { width: 15px; height: 15px; animation: cue-bob 2.4s ease-in-out infinite; }

@keyframes cue-bob {
  0%, 100% { transform: translateY(0); opacity: 0.55; }
  50%      { transform: translateY(4px); opacity: 1; }
}

/* ─── Chapter (the section below the hero) ───────────────────────────────── */

/* Sized to sit on one screen, carousel included: the band is a column that
   distributes title / features / marquee across the viewport. */
.chapter {
  min-height: 100vh;
  min-height: 100svh;
  display: flex;
  flex-direction: column;
  /* space-between rather than center: pushes the tiles down off the heading
     and drops the carousel to the foot of the section, so the band actually
     uses its full height instead of clustering in the middle. */
  justify-content: space-between;
  gap: clamp(18px, 3vh, 40px);
  padding: clamp(52px, 13.5vh, 160px) 0 clamp(28px, 5vh, 64px);
  position: relative;
  /* Contains the marquee's 100vw breakout. */
  overflow: hidden;
}

.chapter__title {
  /* The vh term keeps a short, wide window from picking a size that fits the
     width but pushes the carousel out of a section that clips its overflow. */
  font-size: clamp(1.7rem, min(4.2vw, 7.5vh), 3.6rem);
  letter-spacing: var(--track-display);
  text-align: center;
  padding-inline: var(--gutter);
  margin: 0;
  text-wrap: balance;
}

/* Features sit side by side, unnumbered, so the whole section fits a screen. */
/* A sibling of the tiles and the carousel, not wrapped with either, so the
   section's space-between hands it an equal gap on each side and it lands
   midway between the two. */
.chapter__more { margin: 0; text-align: center; }

.feats {
  list-style: none;
  margin: 0 auto;
  padding-inline: var(--gutter);
  max-width: var(--wrap);
  width: 100%;
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  /* No gap: the columns butt up against their shared rule, and each column's
     own padding provides the breathing room instead. */
  gap: 0;
}

/* No card chrome: the only separation between columns is a hairline rule. */
.feat {
  display: flex;
  flex-direction: column;
  padding-inline: clamp(16px, 1.7vw, 30px);
}

.feat + .feat { border-left: 1px solid var(--border); }
.feat:first-child { padding-inline-start: 0; }
.feat:last-child { padding-inline-end: 0; }

.feat h3 {
  font-size: clamp(1rem, 1.35vw, 1.18rem);
  margin: 0 0 10px;
  letter-spacing: var(--track-lead);
}

.feat p {
  margin: 0;
  color: var(--text-dim);
  font-size: clamp(0.86rem, 0.95vw, 0.95rem);
  line-height: 1.6;
}

@media (max-width: 900px) {
  .feats { grid-template-columns: repeat(2, 1fr); row-gap: clamp(24px, 3vh, 40px); }
  /* Two per row: the rule belongs between the pair, not at the row start. */
  .feat:nth-child(odd) { padding-inline-start: 0; border-left: 0; }
  .feat:nth-child(even) { padding-inline-end: 0; border-left: 1px solid var(--border); }
}
@media (max-width: 560px) {
  .feats { grid-template-columns: 1fr; gap: 0; }
  /* Single column: the separator turns horizontal. */
  .feat { padding-inline: 0; padding-block: clamp(18px, 2.4vh, 26px); }
  .feat + .feat { border-left: 0; border-top: 1px solid var(--border); }
  .feat:first-child { padding-block-start: 0; }
  .feat:last-child { padding-block-end: 0; }
  /* Four stacked features plus the carousel no longer fit a phone screen —
     let the section grow rather than squashing the text. */
  .chapter { min-height: 0; }
}

/* ─── Scroll reveal ──────────────────────────────────────────────────────── */

/* GSAP ScrollTrigger owns the reveal and the hero exit — see main.js. There is
   deliberately NO hidden start state here: the start values are set by GSAP at
   runtime, so if it fails to load the content renders plainly rather than
   staying invisible. GSAP's matchMedia handles reduced motion for those; the
   two looping CSS animations still need switching off by hand. */
.stage__inner, .reveal { will-change: opacity, transform; }

@media (prefers-reduced-motion: reduce) {
  .marquee__track { animation: none; }
  .cue svg { animation: none; }
}

/* ─── Trip-types marquee ─────────────────────────────────────────────────── */

.marquee {
  /* Breaks out of the chapter's narrow column to run edge to edge. */
  position: relative;
  left: 50%;
  right: 50%;
  margin-left: -50vw;
  margin-right: -50vw;
  width: 100vw;
  overflow: hidden;
  /* Fade the ends so tiles enter and leave rather than being sliced off. */
  -webkit-mask-image: linear-gradient(to right, transparent, #000 7%, #000 93%, transparent);
  mask-image: linear-gradient(to right, transparent, #000 7%, #000 93%, transparent);
}

.marquee__track {
  display: flex;
  width: max-content;
  animation: marquee 70s linear infinite;
}

.marquee__set {
  display: flex;
  gap: 12px;
  padding-right: 12px;
}

/* Deliberately no :hover pause — the strip runs continuously. */

@keyframes marquee {
  from { transform: translateX(0); }
  to   { transform: translateX(-50%); }
}

.trip {
  position: relative;
  margin: 0;
  flex: 0 0 auto;
  width: clamp(150px, 17vw, 230px);
  aspect-ratio: 1 / 1;
  border-radius: var(--r-lg, 18px);
  overflow: hidden;
  background: var(--surface-alt);
}

.trip img {
  width: 100%;
  /* The height attribute is a presentational hint that outranks aspect-ratio,
     so it has to be overridden explicitly or the tile renders stretched. */
  height: 100%;
  object-fit: cover;
  display: block;
}

.trip figcaption {
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  padding: 22px 12px 10px;
  font-size: 0.76rem;
  font-weight: 500;
  letter-spacing: var(--track-lead);
  color: #fff;
  background: linear-gradient(to top, rgba(0, 0, 0, 0.62), transparent);
}

/* ─── Reach (support + partnerships) ─────────────────────────────────────── */

/* Not a full screen like the bands above it: two addresses do not need one,
   and a third 100vh section would just be scrolling for its own sake. */
.reach {
  padding: clamp(64px, 11vh, 128px) var(--gutter) clamp(64px, 11vh, 128px);
  border-top: 1px solid var(--border);
}

.reach__title {
  font-size: clamp(1.5rem, min(3.4vw, 6vh), 2.6rem);
  letter-spacing: var(--track-display);
  text-align: center;
  margin: 0 0 clamp(32px, 5vh, 56px);
}

/* Reuses .feats/.feat so the dividing rules and stacking behaviour stay
   identical to the section above — only the column count differs. */
.feats--pair {
  grid-template-columns: repeat(2, 1fr);
  max-width: 900px;
}

.feat__mail {
  display: inline-block;
  margin-top: 14px;
  color: var(--text);
  font-size: clamp(0.88rem, 1vw, 0.98rem);
  font-weight: 500;
  text-decoration: none;
  border-bottom: 1px solid var(--border-strong);
  padding-bottom: 2px;
  align-self: flex-start;
  word-break: break-word;
}
.feat__mail:hover { border-bottom-color: var(--text); }

/* This block is declared after the breakpoints above, so at equal specificity
   it would otherwise win and hold the pair at two columns on a phone. */
@media (max-width: 560px) {
  .feats--pair { grid-template-columns: 1fr; }
}
