/* site.css: the Haashiya website. One stylesheet; tokens first, then layout, then components.
   The values come from the app's own src/style.css so the site and the editor feel like one object.
   Spec: site/DESIGN.md (section numbers in comments refer to it). */

/* ---------- fonts (self-hosted; the privacy page promises no third-party requests) ---------- */

/* Newsreader roman: variable, opsz 6–72, wght 400–600, Latin subset. The only preloaded file. */
@font-face {
  font-family: "Newsreader";
  src: url("../fonts/newsreader-roman.woff2") format("woff2");
  font-weight: 400 600; font-style: normal; font-display: swap;
}
/* Italic: margin notes only, so one static weight (opsz dropped to stay in the font budget). */
@font-face {
  font-family: "Newsreader";
  src: url("../fonts/newsreader-italic.woff2") format("woff2");
  font-weight: 400; font-style: italic; font-display: swap;
}
/* Georgia, resized to Newsreader's metrics so the swap doesn't shift the page. */
@font-face {
  font-family: "Newsreader Fallback";
  src: local("Georgia");
  size-adjust: 90%; ascent-override: 73.5%; descent-override: 26.5%; line-gap-override: 0%;
}
/* The two accent scripts are decoration: `optional` means they never cause a late reflow. */
@font-face {
  font-family: "Tiro Devanagari Hindi";
  src: url("../fonts/tiro-dev-sub.woff2") format("woff2");
  font-weight: 400; font-display: optional;
}
@font-face {
  font-family: "Noto Nastaliq Urdu";
  src: url("../fonts/nastaliq-sub.woff2") format("woff2");
  font-weight: 400; font-display: optional;
}

/* ---------- tokens (§2) ---------- */

:root {
  color-scheme: light dark;

  --paper: #fbfaf7; --paper-2: #f4f2ec; --paper-3: #eeebe3;
  --ink: #1d1c1a; --ink-2: #4a4741; --muted: #6f6b63;
  --line: #e7e3da; --line-2: #d9d4c8;
  --accent: #2f5d50; --accent-ink: #fbfaf7; --accent-hover: #264c41;
  --alt: #b9a47a; --alt-ink: #7a6538; --hl: #f1e7cf; --cut: #e9e2f3; --flag: #fbe3a7;
  --ghost: .16; --shadow-c: 29 28 26;
  --shadow-window: 0 1px 0 rgb(var(--shadow-c) / .04), 0 2px 4px rgb(var(--shadow-c) / .04),
    0 12px 24px -6px rgb(var(--shadow-c) / .08), 0 40px 80px -20px rgb(var(--shadow-c) / .18);
  --shadow-card: 0 1px 2px rgb(var(--shadow-c) / .05), 0 8px 24px -12px rgb(var(--shadow-c) / .12);

  --serif: "Newsreader", "Newsreader Fallback", "Iowan Old Style", Charter, Georgia, serif;
  --ui: -apple-system, BlinkMacSystemFont, "Segoe UI", system-ui, sans-serif;
  --mono: ui-monospace, "SF Mono", Menlo, Consolas, monospace;
  --typewriter: "American Typewriter", "Courier Prime", "Courier New", monospace;
  --deva: "Tiro Devanagari Hindi", "Kohinoor Devanagari", "Devanagari Sangam MN", serif;
  --urdu: "Noto Nastaliq Urdu", "Noto Nastaliq", "Geeza Pro", serif;

  --t-display: clamp(2.75rem, 1.4rem + 5.6vw, 6.25rem);
  --t-h2: clamp(2rem, 1.25rem + 3.1vw, 3.75rem);
  --t-h3: clamp(1.375rem, 1.1rem + 1.1vw, 1.875rem);
  --t-lead: clamp(1.1875rem, 1.04rem + .62vw, 1.5rem);
  --t-body: 1.125rem; --t-margin: .9375rem; --t-ui: .9375rem;
  --t-small: .8125rem; --t-label: .75rem; --t-kbd: .8125rem; --t-code: .875rem;

  --s-1: 4px; --s-2: 8px; --s-3: 12px; --s-4: 16px; --s-5: 24px; --s-6: 32px;
  --s-7: 48px; --s-8: 64px; --s-9: 96px; --s-10: 128px; --s-11: 192px;

  --r-sm: 6px; --r-md: 10px; --r-lg: 12px; --r-pill: 999px;
  --ease-out: cubic-bezier(.2, .7, .2, 1); --ease-in-out: cubic-bezier(.65, 0, .35, 1);

  --w-page: 1240px; --w-margin: 180px; --gap: 56px;
  --gutter: 16px; --nav-h: 60px;
  --sec-pad: clamp(96px, 6rem + 6vw, 192px);
  --overlap: clamp(48px, 9vw, 150px);   /* how far the hero window runs into section 2 */
}
@media (min-width: 480px) { :root { --gutter: 24px; } }
@media (min-width: 768px) { :root { --gutter: 40px; } }
@media (min-width: 1200px) { :root { --gutter: 56px; } }

/* Dark values, twice: once for the OS setting, once for a future explicit toggle (data-theme). */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --paper: #1b1a18; --paper-2: #22201d; --paper-3: #2a2824;
    --ink: #e9e5dc; --ink-2: #c4beb2; --muted: #9a9488;
    --line: #34312c; --line-2: #45413a;
    --accent: #8cc4b2; --accent-ink: #132a24; --accent-hover: #a3d3c3;
    --alt: #b39f72; --alt-ink: #cdb98a; --hl: #3a3224; --cut: #342d3d; --flag: #5a4716;
    --ghost: .22; --shadow-c: 0 0 0;
    --shadow-window: 0 1px 0 rgb(var(--shadow-c) / .3), 0 2px 4px rgb(var(--shadow-c) / .3),
      0 12px 24px -6px rgb(var(--shadow-c) / .4), 0 40px 80px -20px rgb(var(--shadow-c) / .55),
      inset 0 0 0 1px rgb(255 255 255 / .04);
  }
}
:root[data-theme="dark"] {
  --paper: #1b1a18; --paper-2: #22201d; --paper-3: #2a2824;
  --ink: #e9e5dc; --ink-2: #c4beb2; --muted: #9a9488;
  --line: #34312c; --line-2: #45413a;
  --accent: #8cc4b2; --accent-ink: #132a24; --accent-hover: #a3d3c3;
  --alt: #b39f72; --alt-ink: #cdb98a; --hl: #3a3224; --cut: #342d3d; --flag: #5a4716;
  --ghost: .22; --shadow-c: 0 0 0;
  --shadow-window: 0 1px 0 rgb(var(--shadow-c) / .3), 0 2px 4px rgb(var(--shadow-c) / .3),
    0 12px 24px -6px rgb(var(--shadow-c) / .4), 0 40px 80px -20px rgb(var(--shadow-c) / .55),
    inset 0 0 0 1px rgb(255 255 255 / .04);
}

/* ---------- base ---------- */

*, *::before, *::after { box-sizing: border-box; }
html { -webkit-text-size-adjust: 100%; text-size-adjust: 100%; scroll-padding-top: calc(var(--nav-h) + 24px); }
@media (prefers-reduced-motion: no-preference) { html { scroll-behavior: smooth; } }
body {
  margin: 0; background: var(--paper); color: var(--ink);
  font: 400 var(--t-body)/1.65 var(--serif);
  font-optical-sizing: auto; font-variant-numeric: oldstyle-nums;
  -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale;
  text-rendering: optimizeLegibility;
  overflow-x: clip;
}
::selection { background: var(--hl); color: var(--ink); }
h1, h2, h3, p, ul, ol, figure, blockquote, dl, dd { margin: 0; }
h1, h2, h3 { font-weight: 500; text-wrap: balance; color: var(--ink); }
p, li { text-wrap: pretty; }
img, video, svg, iframe { display: block; max-width: 100%; }
button, input, select { font: inherit; color: inherit; }
button { cursor: pointer; }
[hidden] { display: none !important; }

q { quotes: "‘" "’" "“" "”"; }   /* British: single quotes outside */
a { color: var(--accent); text-decoration: underline 1px; text-underline-offset: 3px;
    text-decoration-color: color-mix(in srgb, var(--accent) 40%, transparent);
    transition: text-decoration-color .15s; }
a:hover { text-decoration-color: var(--accent); }

/* One focus style for everything; never removed (§2.7). */
:focus-visible { outline: 2px solid var(--accent); outline-offset: 3px; border-radius: inherit; }

.vh { position: absolute !important; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); white-space: nowrap; }

.skip { position: absolute; left: var(--gutter); top: 8px; z-index: 100; padding: 10px 16px;
        background: var(--accent); color: var(--accent-ink); border-radius: var(--r-sm);
        font: 500 var(--t-ui)/1.4 var(--ui); text-decoration: none; transform: translateY(-200%); }
.skip:focus { transform: none; }

/* Desktop-only line break in headlines. */
@media (max-width: 719px) { br.d { display: none; } }

/* ---------- layout: page, margin column, the margin line (§2.5) ---------- */

.wrap { width: 100%; max-width: calc(var(--w-page) + 2 * var(--gutter)); margin-inline: auto; padding-inline: var(--gutter); }

.grid { display: block; }
.margin { margin-bottom: var(--s-5); }
@media (min-width: 1024px) {
  .grid { display: grid; grid-template-columns: var(--w-margin) minmax(0, 1fr); column-gap: var(--gap); }
  .margin { position: sticky; top: 96px; align-self: start; margin: 0; padding-top: .55em; }
}

/* The single vertical rule: centred in the gutter between margin column and main column. */
.page { position: relative; }
@media (min-width: 1024px) {
  .page::before {
    content: ""; position: absolute; top: 0; bottom: 0; z-index: 1; width: 1px; background: var(--line);
    left: calc(max(var(--gutter), (100% - var(--w-page)) / 2) + var(--w-margin) + var(--gap) / 2);
    pointer-events: none;
  }
  /* Home: the hero slides up under the translucent nav (so its paper fade has no seam);
     the margin line still starts below the nav. */
  .page.home::before { top: var(--nav-h); }
}

.col { min-width: 0; }

/* Margin column text: label (number + name) and an italic note, like a reader's annotation. */
.label { font: 600 var(--t-label)/1.2 var(--ui); letter-spacing: .08em; text-transform: uppercase;
         color: var(--muted); font-variant-numeric: lining-nums tabular-nums; }
.label .num { color: var(--ink); margin-right: .5em; }
.note { font: italic 400 var(--t-margin)/1.45 var(--serif); color: var(--muted); margin-top: var(--s-2); }
@media (max-width: 1023px) {
  /* Collapsed margin: "§ 1  THE IDEA · after a demo by Jason Fried" on one line. */
  .margin { display: flex; flex-wrap: wrap; align-items: baseline; column-gap: .5em; row-gap: 2px; }
  .margin .note { margin: 0; }
  .margin .label + .note::before { content: "·"; font-style: normal; margin-right: .5em; color: var(--line-2); }
}

/* ---------- type ---------- */

.display { font-size: var(--t-display); line-height: 1; letter-spacing: -.022em; font-variation-settings: "opsz" 72; }
.h2, .sec h2 { font-size: var(--t-h2); line-height: 1.06; letter-spacing: -.016em; }
.h3 { font-size: var(--t-h3); line-height: 1.18; letter-spacing: -.008em; }
.lead { font-size: var(--t-lead); line-height: 1.5; color: var(--ink-2); max-width: 32em; }
.eyebrow { font: 600 var(--t-label)/1.2 var(--ui); letter-spacing: .08em; text-transform: uppercase; color: var(--muted); }
.small, figcaption, .meta { font: 400 var(--t-small)/1.45 var(--ui); color: var(--muted); }
.prose { max-width: 34em; }
.prose p + p { margin-top: 1em; }
.text { max-width: 40rem; }

/* ---------- nav (§3 Nav) ---------- */

.nav-sentinel { position: absolute; top: 0; left: 0; height: 8px; width: 1px; }
.nav { position: sticky; top: 0; z-index: 50; height: var(--nav-h);
       background: color-mix(in srgb, var(--paper) 85%, transparent);
       -webkit-backdrop-filter: blur(12px) saturate(1.2); backdrop-filter: blur(12px) saturate(1.2);
       border-bottom: 1px solid transparent; transition: border-color .2s; }
.nav.scrolled { border-bottom-color: var(--line); }
.nav .wrap { height: 100%; display: flex; align-items: center; justify-content: space-between; gap: var(--s-5); }
.brand { display: inline-flex; align-items: center; gap: 8px; color: var(--ink); text-decoration: none;
         font: 500 1.3125rem/1 var(--serif); letter-spacing: -.01em; font-variation-settings: "opsz" 36; }
.brand img { width: 22px; height: 22px; }
.nav-links { display: flex; align-items: center; gap: var(--s-5); list-style: none; padding: 0; margin: 0;
             font: 500 var(--t-ui)/1.4 var(--ui); }
.nav-links a:not(.btn) { color: var(--ink-2); text-decoration: none; }
.nav-links a:not(.btn):hover { color: var(--ink); }
@media (max-width: 767px) { .nav-links li:not(:last-child) { display: none; } }

/* ---------- buttons, kbd (§2.7) ---------- */

.btn { display: inline-flex; align-items: center; justify-content: center; gap: 8px;
       padding: 12px 20px; border-radius: var(--r-sm); border: 0;
       font: 500 var(--t-ui)/1.4 var(--ui); text-decoration: none; white-space: nowrap;
       transition: background-color .15s, border-color .15s, color .15s; }
.btn:active { transform: translateY(1px); }
.btn svg { width: 16px; height: 16px; flex: none; }
.btn-primary { background: var(--accent); color: var(--accent-ink); }
.btn-primary:hover { background: var(--accent-hover); }
.btn-secondary { background: transparent; color: var(--ink); box-shadow: inset 0 0 0 1px var(--line-2); }
.btn-secondary:hover { background: var(--paper-2); }
.btn-sm { padding: 8px 14px; }
.btn-text { background: none; border: 0; padding: 4px 6px; border-radius: var(--r-sm);
            font: 500 var(--t-small)/1.2 var(--ui); color: var(--accent); }
.btn-text:hover { color: var(--accent-hover); text-decoration: underline 1px; text-underline-offset: 3px; }

kbd { display: inline-block; min-width: 1.6em; text-align: center; padding: 1px 6px;
      font: 500 var(--t-kbd)/1.35 var(--ui); color: var(--ink); background: var(--paper);
      border: 1px solid var(--line-2); border-bottom-width: 2px; border-radius: 5px;
      font-variant-numeric: lining-nums; }
kbd + kbd { margin-left: 2px; }

/* ---------- sections and bands (§3) ---------- */

.sec { position: relative; padding-block: var(--sec-pad); background: var(--paper); }
.band-2 { background: var(--paper-2); }
.sec h2 + .lead, .sec h2 + .prose { margin-top: var(--s-5); }

/* ---------- hero (§3.1) ---------- */

.hero { padding-top: calc(var(--nav-h) + clamp(48px, 8vw, 128px)); margin-top: calc(-1 * var(--nav-h)); padding-bottom: 0;
        background: radial-gradient(60% 50% at 70% 0%, var(--paper-2), var(--paper) 70%); }
.hero .eyebrow { margin-bottom: var(--s-5); }
/* The hero line must hold its longest alternate ("for the second-guessers.") without wrapping,
   or the tour would push the whole page down a line. At ≥720px the H1 is therefore capped to
   its column width (8.7cqi ≈ column ÷ 11.5); the spec's clamp stays the upper bound. Below 720px
   the headline wraps freely and the longest option is skipped on phones (marks.js). */
.hero .display { text-wrap: wrap; }   /* balance would re-break the line as the word changes */
@media (min-width: 720px) {
  .hero .col { container-type: inline-size; }
  .hero .display { font-size: min(var(--t-display), 8.7cqi); }
}
.hero .lead { margin-top: var(--s-6); }
.hero-ctas { display: flex; flex-wrap: wrap; gap: var(--s-3); margin-top: var(--s-6); }
.hero .meta { margin-top: var(--s-4); font-variant-numeric: lining-nums; }
.hero .meta a { color: inherit; text-decoration-color: color-mix(in srgb, var(--muted) 50%, transparent); }
.hero .meta a:hover { color: var(--ink); }
@media (max-width: 479px) {
  .hero-ctas { flex-direction: column; }
  .hero-ctas .btn { width: 100%; }
}

/* The marginal gloss: the word in its two scripts, then its meaning. */
.gloss { margin: 0; }
.gloss .deva { display: block; font: 400 1.75rem/1.2 var(--deva); color: var(--ink); }
.gloss .urdu { display: block; font: 400 1.25rem/2 var(--urdu); color: var(--muted); direction: rtl; text-align: left; margin-top: -.15em; }
.gloss .def { display: block; font: italic 400 var(--t-margin)/1.45 var(--serif); color: var(--muted); margin-top: var(--s-2); }
.gloss .def b { font-weight: 400; color: var(--ink-2); }
.gloss .short { display: none; }
@media (min-width: 1024px) { .hero .margin { padding-top: 2.6rem; } }
@media (max-width: 1023px) {
  .hero .margin { display: block; margin-bottom: var(--s-4); }
  .gloss { display: flex; align-items: baseline; gap: .5em; }
  .gloss .deva { display: inline; font-size: 1.25rem; }
  .gloss .urdu, .gloss .def { display: none; }
  .gloss .short { display: inline; font: italic 400 var(--t-margin)/1.45 var(--serif); color: var(--muted); }
  .gloss .short::before { content: "·"; font-style: normal; margin-right: .5em; color: var(--line-2); }
}

/* The hero window sits on the seam: its lower quarter runs into the next section. */
.hero .hero-win { margin-top: var(--s-8); position: relative; z-index: 2; margin-bottom: calc(-1 * var(--overlap)); }
.hero + .sec { padding-top: calc(var(--sec-pad) + var(--overlap)); }

/* Load sequence (§3.1). Only when JS is on and motion is welcome; otherwise everything just shows. */
@keyframes rise { from { opacity: 0; transform: translateY(var(--rise, 8px)); } to { opacity: 1; transform: none; } }
@media (prefers-reduced-motion: no-preference) {
  .js .hero .seq { animation: rise 520ms var(--ease-out) both; }
  .js .hero .seq:nth-of-type(1) { animation-delay: 0ms; }
  .js .hero .s2 { animation-delay: 70ms; }
  .js .hero .s3 { animation-delay: 140ms; }
  .js .hero .s4 { animation-delay: 210ms; }
  .js .hero .s5 { animation-delay: 240ms; }
  .js .hero .hero-win { --rise: 16px; animation: rise 700ms var(--ease-out) 280ms both; }
}

/* ---------- window frame (§2.6) ---------- */

.win { margin: 0; max-width: 1000px; }
.win-frame { position: relative; border-radius: var(--r-lg); border: 1px solid var(--line); background: var(--paper);
             box-shadow: var(--shadow-window); overflow: hidden; isolation: isolate; }
.win-bar { position: relative; height: 36px; display: flex; align-items: center; justify-content: center;
           background: var(--paper-3); border-bottom: 1px solid var(--line); }
.win-dots { position: absolute; left: 14px; top: 50%; translate: 0 -50%; display: flex; gap: 8px; }
.win-dots i { width: 12px; height: 12px; border-radius: 50%; background: var(--line-2); transition: background-color .2s; }
.win-frame:hover .win-dots i:nth-child(1) { background: #ec6a5e; }
.win-frame:hover .win-dots i:nth-child(2) { background: #f4bf4f; }
.win-frame:hover .win-dots i:nth-child(3) { background: #61c554; }
.win-title { font: 400 var(--t-small)/1 var(--ui); color: color-mix(in srgb, var(--muted) 85%, var(--ink)); /* --muted alone is 4.45:1 on --paper-3 */ white-space: nowrap; overflow: hidden; text-overflow: ellipsis; max-width: 60%; }
.win-media { position: relative; background: var(--paper); }
.win-media video, .win-media img, .win-media iframe { display: block; width: 100%; height: auto; aspect-ratio: 1280 / 800; background: var(--paper); border: 0; }
.win figcaption { margin-top: var(--s-4); max-width: 40rem; }
@media (max-width: 599px) {
  .win-bar { height: 28px; }
  .win-dots { left: 10px; gap: 6px; }
  .win-dots i { width: 9px; height: 9px; }
  .win-title { display: none; }
}
/* The clips are light-theme footage: never inverted; a hairline keeps them from glaring at the edge. */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .win-media::after { content: ""; position: absolute; inset: 0; box-shadow: inset 0 0 0 1px var(--line); pointer-events: none; }
}
:root[data-theme="dark"] .win-media::after { content: ""; position: absolute; inset: 0; box-shadow: inset 0 0 0 1px var(--line); pointer-events: none; }

/* Play/pause control in each clip's corner (§4.6). Shown on hover/focus; always on touch. */
.vctl { position: absolute; right: 12px; bottom: 12px; z-index: 2; width: 32px; height: 32px; padding: 0;
        display: grid; place-items: center; border-radius: 50%; border: 1px solid var(--line); color: var(--ink);
        background: color-mix(in srgb, var(--paper) 85%, transparent);
        -webkit-backdrop-filter: blur(8px); backdrop-filter: blur(8px);
        opacity: 0; transition: opacity .2s; }
.vctl::after { content: ""; position: absolute; inset: -6px; } /* 44px touch target */
.vctl svg { width: 12px; height: 12px; }
.win-frame:hover .vctl, .vctl:focus-visible, .vctl.show { opacity: 1; }
@media (hover: none) { .vctl { opacity: 1; } }
.vctl .i-play { display: none; }
.vctl.paused .i-play { display: block; }
.vctl.paused .i-pause { display: none; }

/* ---------- alternates: the S1 component (§4.1) ---------- */

/* Static look matches the app: wavy gold underline, dots for how many versions. */
.alt { position: relative; border-radius: 4px; cursor: pointer; transition: background-color 150ms;
       -webkit-tap-highlight-color: transparent; }
.display .alt { white-space: nowrap; }
.alt:hover, .alt:focus-visible, .alt.on { background: var(--hl); }
.alt:focus-visible { outline-offset: 2px; }
.alt-w { position: relative; display: inline-block; vertical-align: bottom;
         /* clip sideways only: the outgoing word must not show past the box, the wave below must */
         clip-path: inset(-.5em -.02em -.5em -.02em); }
.alt-w.tween { transition: width 260ms var(--ease-out); }
.alt-t, .alt.static { text-decoration: underline wavy var(--alt); text-decoration-thickness: max(1px, .035em);
         text-underline-offset: .14em; text-decoration-skip-ink: none; }
.alt-t { display: inline-block; white-space: nowrap; }
.alt-t.out { position: absolute; left: 0; top: 0; }
.alt-t.ghosted { opacity: var(--ghost); }
.alt-t.cut { opacity: .22; background: var(--cut); border-radius: 2px; }   /* an AI cut, as the app's trim */
.display .alt-t, .display .alt.static { text-decoration-thickness: max(2px, .03em); text-underline-offset: .12em; }

.dots { display: inline-flex; align-items: center; height: .14em; gap: .08em; margin-left: .06em; vertical-align: .62em; line-height: 0; }  /* fixed height: the ✦ (a fallback font) must not grow the line */
.dots i { width: .14em; height: .14em; border-radius: 50%; background: var(--muted); opacity: .55; transition: background-color .2s, opacity .2s; }
.dots i.cur { background: var(--accent); opacity: 1; }
/* The ✦ sits out of flow (left of the dots, in room made by .ai) so it can't move the baseline. */
.dots { position: relative; }
.dots.ai, .display .dots.ai { margin-left: .5em; }
.dots .star { position: absolute; right: calc(100% + .07em); top: 50%; translate: 0 -50%; width: .3em; height: .3em; fill: var(--alt-ink); }
/* Body-size specimens: dots need a floor so they stay visible. */
.spec .dots i { width: max(.14em, 4px); height: max(.14em, 4px); }
.spec .dots { gap: max(.08em, 2px); vertical-align: .55em; }
.spec .dots .star { width: max(.3em, 7px); height: max(.3em, 7px); }
.spec .dots.ai { margin-left: max(.42em, 10px); }
.display .dots { vertical-align: .58em; margin-left: .04em; }

/* Swap motion, driven by marks.js via classes. */
@keyframes alt-out { to { opacity: 0; transform: translateY(-.18em); } }
@keyframes alt-in { from { opacity: 0; transform: translateY(.18em); } }
.alt-t.out { animation: alt-out 160ms var(--ease-in-out) forwards; }
.alt-t.in { animation: alt-in 220ms var(--ease-out) 120ms both; }

/* ---------- S2: the ghosting sentence (§4.2) ---------- */

.ghostable { transition: opacity 300ms var(--ease-out); cursor: default; }
.ghostable.ghosting { transition: opacity 900ms var(--ease-in-out); }
.ghostable.ghost { opacity: var(--ghost); cursor: pointer; }
.ghostable.ghost:hover { opacity: .45; }
.ghost-btn { margin-left: .35em; vertical-align: .1em; font-size: .8em; padding: 2px 6px; opacity: 1; transition: opacity 300ms; }
.ghost-btn.pre { opacity: 0; }

/* ---------- specimen cards (S1b, S4) ---------- */

.spec { background: var(--paper); border: 1px solid var(--line); border-radius: var(--r-md);
        box-shadow: var(--shadow-card); padding: 40px 48px; max-width: 1000px; }
.spec-text { font: 400 1.375rem/1.7 var(--serif); color: var(--ink); max-width: 34em; }
@media (max-width: 599px) { .spec { padding: 24px 20px; } .spec-text { font-size: 1.1875rem; } }
.spec + figcaption, .spec-cap { margin-top: var(--s-4); }

/* S4: highlights sweep in as a growing background (§4.4). */
.slop-card { display: grid; gap: var(--s-5); }
@media (min-width: 768px) { .slop-card { grid-template-columns: minmax(0, 1fr) 180px; column-gap: var(--s-7); } }
/* --fc is registered so the highlight colour can fade out when a flag becomes an alternate. */
@property --fc { syntax: "<color>"; inherits: false; initial-value: transparent; }
.flag { --fc: var(--flag); border-radius: 2px; cursor: pointer;
        background-image: linear-gradient(var(--fc), var(--fc)); background-repeat: no-repeat;
        background-size: 0% 100%; transition: background-size 420ms var(--ease-out), --fc 200ms linear, background-color 150ms; }
.flag.lit { background-size: 100% 100%; }
.flag.alt { --fc: transparent; background-size: 100% 100%; }
.slop sup.n { font: 600 .55em/0 var(--ui); color: var(--alt-ink); margin-left: .1em; opacity: 0; transition: opacity .2s; font-variant-numeric: lining-nums; }
.flag.lit + sup.n, .flag.alt + sup.n { opacity: 1; }
html:not(.js) .flag { background-size: 100% 100%; }
html:not(.js) .slop sup.n { opacity: 1; }
.rules { list-style: none; padding: 0; margin: 0; font: italic 400 var(--t-small)/1.45 var(--serif); color: var(--muted); counter-reset: r; }
.rules li { counter-increment: r; opacity: 0; transition: opacity 300ms var(--ease-out); }
.rules li.on, html:not(.js) .rules li { opacity: 1; }
.rules li::before { content: counter(r); font: 600 .75rem/1 var(--ui); font-style: normal; color: var(--alt-ink); margin-right: .45em; font-variant-numeric: lining-nums; }
@media (min-width: 768px) {
  .rules { border-left: 1px solid var(--line); padding-left: var(--s-5); display: grid; align-content: start; gap: var(--s-3); padding-top: .35em; }
}
@media (max-width: 767px) {
  .rules { display: flex; flex-wrap: wrap; column-gap: .6em; row-gap: 2px; }
  .rules li + li::after { content: none; }
  .rules li:not(:last-child)::after { content: "·"; font-style: normal; margin-left: .6em; color: var(--line-2); }
}
.slop-foot { grid-column: 1 / -1; display: flex; justify-content: flex-end; margin: -8px -6px -20px 0; }

/* Feature shortcut line. */
.keys { margin-top: var(--s-5); font: 400 var(--t-small)/2 var(--ui); color: var(--muted); }
.keys kbd { color: var(--ink); }

/* ---------- features (§3.3) ---------- */

.features-intro { padding-bottom: 0; }
.feat { padding-top: clamp(96px, 10vw, 160px); }
.feat h3 { font-size: var(--t-h2); line-height: 1.06; letter-spacing: -.016em; }
.feat h3 + .prose { margin-top: var(--s-5); }
.feat .media { margin-top: var(--s-7); }
.feat .lead-spec { margin-top: var(--s-7); }
.feat .lead-spec + .prose { margin-top: var(--s-7); }
.feat .margin .label .num { margin-right: 0; }
#features { padding-bottom: var(--sec-pad); }

/* ---------- try it (§3.4) ---------- */

.chips { display: flex; flex-wrap: wrap; gap: var(--s-2) var(--s-3); margin-top: var(--s-6); padding: 0; list-style: none;
         font: 400 var(--t-small)/1.4 var(--ui); color: var(--ink-2); }
.chips li { display: inline-flex; align-items: center; gap: 6px; padding: 6px 10px 6px 6px; border: 1px solid var(--line);
            border-radius: var(--r-sm); background: var(--paper); }
.demo { margin-top: var(--s-8); }
.demo .win-media { min-height: 560px; }
@media (min-width: 1024px) { .demo .win-media { aspect-ratio: 1280 / 860; min-height: 0; } }
/* Poster, veil and iframe stack in the same box, which gets its height from the rules above. */
.demo .win-media > * { position: absolute; inset: 0; }
.demo .win-media img { width: 100%; height: 100%; aspect-ratio: auto; object-fit: cover; object-position: top left; }
.demo .win-media iframe { width: 100%; height: 100%; aspect-ratio: auto; opacity: 0; transition: opacity 300ms; }
.demo .win-media iframe.ready { opacity: 1; }
.veil { display: grid; place-content: center; justify-items: center; text-align: center; padding: var(--s-5);
        background: color-mix(in srgb, var(--paper) 55%, transparent); transition: opacity 200ms; z-index: 1; }
/* The button and its note sit on a small sheet of paper so the note stays legible over the poster. */
.veil-card { display: grid; justify-items: center; gap: var(--s-3); padding: 24px 28px 18px; border-radius: var(--r-md);
             background: var(--paper); border: 1px solid var(--line); box-shadow: var(--shadow-card); }
.veil .small { max-width: 24em; }
.veil.gone { opacity: 0; pointer-events: none; }
.demo-tools { position: absolute; right: 8px; top: 50%; translate: 0 -50%; display: flex; gap: 2px; }
.demo-tools[hidden] { display: none; }
.demo-tools .btn-text { color: var(--ink-2); text-decoration: none; }
.demo-tools .btn-text:hover { color: var(--ink); }
.loadbar { position: absolute; left: 0; bottom: -1px; height: 2px; width: 100%; background: var(--accent);
           transform-origin: left; transform: scaleX(0); opacity: 0; transition: opacity 300ms; }
.loadbar.run { opacity: 1; animation: load 2.4s var(--ease-out) forwards; }
@keyframes load { to { transform: scaleX(.85); } }
.loadbar.done { transform: scaleX(1); opacity: 0; animation: none; transition: opacity 300ms, transform 200ms; }
.demo-note { margin-top: var(--s-4); max-width: 40rem; }
@media (max-width: 767px) { .demo .win-media { min-height: 420px; } }

/* ---------- principles (§3.5) ---------- */

.rules-grid { display: grid; gap: var(--s-7); margin-top: var(--s-8); list-style: none; padding: 0; }
@media (min-width: 768px) { .rules-grid { grid-template-columns: 1fr 1fr; column-gap: var(--s-7); row-gap: 56px; } }
.rules-grid > li { border-top: 1px solid var(--line); padding-top: var(--s-5); min-width: 0; }
.rules-grid .n { font: 600 var(--t-label)/1.2 var(--ui); letter-spacing: .08em; color: var(--accent); font-variant-numeric: lining-nums tabular-nums; }
.rules-grid h3 { margin-top: var(--s-3); }
.rules-grid p { margin-top: var(--s-3); color: var(--ink-2); }
.code { margin-top: var(--s-5); background: var(--paper-2); border: 1px solid var(--line); border-radius: var(--r-sm);
        padding: 16px 20px; font: 400 var(--t-code)/1.6 var(--mono); color: var(--ink); overflow-x: auto; white-space: pre; tab-size: 2; }
.code .tok-alt { color: var(--alt-ink); }
.code .tok-ghost { color: var(--muted); }
.code + figcaption { margin-top: var(--s-3); }

/* ---------- look & sound: S3 key strip (§4.3) ---------- */

.keys-card { margin-top: var(--s-7); max-width: 42rem; background: var(--paper); border: 1px solid var(--line);
             border-radius: var(--r-md); padding: 24px; box-shadow: var(--shadow-card); }
.kc-top { display: flex; flex-wrap: wrap; align-items: center; gap: var(--s-3); }
.seg { display: inline-flex; padding: 3px; gap: 2px; border-radius: var(--r-pill); background: var(--paper-2); border: 1px solid var(--line); }
.seg label { position: relative; }
.seg input { position: absolute; opacity: 0; inset: 0; margin: 0; cursor: pointer; }
.seg span { display: block; padding: 6px 14px; border-radius: var(--r-pill); font: 500 var(--t-small)/1.4 var(--ui); color: var(--ink-2); transition: background-color .15s, color .15s, box-shadow .15s; }
.seg input:checked + span { background: var(--paper); color: var(--ink); box-shadow: var(--shadow-card), 0 0 0 1px var(--line); }
.seg input:focus-visible + span { outline: 2px solid var(--accent); outline-offset: 2px; }
.music { display: inline-flex; gap: var(--s-2); transition: opacity 200ms; }
.music.pre { opacity: 0; }
.music select { font: 500 var(--t-small)/1.4 var(--ui); padding: 6px 28px 6px 10px; border-radius: var(--r-sm);
                border: 1px solid var(--line-2); background: var(--paper); color: var(--ink); min-height: 34px; }
.kc-hint { margin-top: var(--s-5); min-height: 1.45em; transition: opacity .3s; }
.kc-field { display: block; width: 100%; margin-top: var(--s-2); padding: 6px 0 10px; border: 0; border-bottom: 1px solid var(--line);
            border-radius: 0; background: transparent; color: var(--ink); caret-color: var(--accent);
            font: 400 var(--t-lead)/1.5 var(--serif); transition: opacity 300ms; }
.kc-field::placeholder { color: var(--muted); opacity: 1; }
.kc-field:focus { outline: none; border-bottom-color: var(--accent); }
.kc-field:focus-visible { outline: none; }
.kc-field.tw { font-family: var(--typewriter); font-size: calc(var(--t-lead) * .9); }
.kc-field.cr { opacity: 0; }
.kc-bottom { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: var(--s-4); margin-top: var(--s-5); }
.caps { display: flex; flex-wrap: wrap; gap: 4px; }
.cap { min-width: 44px; height: 44px; padding: 0 8px; display: grid; place-items: center;
       background: var(--paper-3); color: var(--ink); border: 1px solid var(--line-2); border-bottom-width: 2px; border-radius: 6px;
       font: 500 var(--t-kbd)/1 var(--ui); transition: transform 90ms, border-bottom-width 90ms; }
.cap.down { transform: translateY(1px); border-bottom-width: 1px; }
.vol { display: inline-flex; align-items: center; gap: 8px; color: var(--muted); }
.vol svg { width: 16px; height: 16px; }
.vol input { width: 100px; accent-color: var(--accent); }

/* A clip that follows a card or text inside a section's column. */
.col > .win.media { margin-top: var(--s-7); }

/* ---------- in & out (§3.7) ---------- */

.halves { display: grid; gap: var(--s-9); margin-top: var(--s-8); }
@media (min-width: 1024px) { .halves { grid-template-columns: 1fr 1fr; gap: var(--s-7); } }
.halves h3 + p { margin-top: var(--s-3); }
.halves p { color: var(--ink-2); }
.halves .win { margin-top: var(--s-6); }
.filechips { display: flex; flex-wrap: wrap; gap: var(--s-2); margin-top: var(--s-5); padding: 0; list-style: none; }
.filechips li { font: 400 var(--t-small)/1.4 var(--ui); color: var(--ink-2); border: 1px solid var(--line); border-radius: var(--r-sm); padding: 4px 8px; font-variant-numeric: lining-nums; }
.inflow { margin-top: var(--s-6); max-width: 360px; color: var(--line-2); }
.inflow svg { width: 100%; height: auto; overflow: visible; }
.inflow .t { font: 500 11px var(--ui); fill: var(--ink-2); }
.inflow .box { fill: var(--paper); stroke: var(--line-2); }
.inflow .bar { fill: var(--paper-3); }
.inflow .ln { fill: var(--line-2); }
.inflow .alt-ln { stroke: var(--alt); fill: none; }

/* ---------- privacy band (§3.8) ---------- */

.trio { display: grid; gap: var(--s-6); margin-top: var(--s-7); }
@media (min-width: 768px) { .trio { grid-template-columns: repeat(3, 1fr); gap: var(--s-7); } }
.trio p { color: var(--ink-2); }
.trio b { color: var(--ink); font-weight: 600; }
.more { margin-top: var(--s-7); font: 500 var(--t-ui)/1.4 var(--ui); }

/* ---------- download (§3.9) ---------- */

.cards { display: grid; gap: var(--s-5); margin-top: var(--s-8); max-width: 1000px; }
@media (min-width: 768px) { .cards { grid-template-columns: 1fr 1fr; } }
.card { display: flex; flex-direction: column; align-items: flex-start; gap: var(--s-3);
        background: var(--paper-2); border-radius: var(--r-md); padding: 32px; box-shadow: var(--shadow-card); border: 1px solid var(--line); }
.card .meta { font-variant-numeric: lining-nums; }
@media (min-width: 768px) { .card .meta { min-height: 2.9em; } }   /* buttons line up across cards */
.card .btn { margin-top: var(--s-3); }
.card .small { color: var(--ink-2); }
.card b { font-weight: 600; }
.win-first .card-win { order: -1; }
.after { margin-top: var(--s-6); display: grid; gap: var(--s-2); font: 400 var(--t-small)/1.6 var(--ui); color: var(--muted); max-width: 46rem; }
.after b { color: var(--ink); font-weight: 600; }
.after kbd { font-size: .75rem; }
.after .links { display: flex; flex-wrap: wrap; gap: var(--s-2) var(--s-5); }
.version { font-variant-numeric: lining-nums; }

/* ---------- FAQ (§3.10) ---------- */

.faq { margin-top: var(--s-8); max-width: 44rem; border-bottom: 1px solid var(--line); }
.faq details { border-top: 1px solid var(--line); }
.faq summary { list-style: none; position: relative; cursor: pointer; padding: 20px 40px 20px 0;
               font: 500 1.25rem/1.3 var(--serif); letter-spacing: -.005em; color: var(--ink); border-radius: var(--r-sm); }
.faq summary::-webkit-details-marker { display: none; }
.faq summary::before, .faq summary::after { content: ""; position: absolute; right: 6px; top: 50%; width: 12px; height: 1.5px;
                                            background: var(--muted); transition: transform 200ms var(--ease-out); }
.faq summary::after { transform: rotate(90deg); }
.faq details[open] summary::before { transform: rotate(45deg); }
.faq details[open] summary::after { transform: rotate(135deg); }
.faq summary:hover::before, .faq summary:hover::after { background: var(--ink); }
.faq .a { padding-bottom: 24px; color: var(--ink-2); max-width: 36em; }
.faq [lang="hi"] { font-family: var(--deva); }

/* ---------- footer (§3 Footer) ---------- */

.foot { position: relative; z-index: 2; background: var(--paper); border-top: 1px solid var(--line); padding: 64px 0 48px;
        font: 400 var(--t-small)/1.6 var(--ui); color: var(--muted); }
.foot .row1 { display: flex; align-items: center; gap: var(--s-4); }
.foot .brand, .foot .brand:hover { font-size: 1.375rem; color: var(--ink); }
.foot .brand img { width: 28px; height: 28px; align-self: center; }
.foot .deva { font: 400 1.375rem/1 var(--deva); color: var(--muted); }
.foot nav ul { display: flex; flex-wrap: wrap; gap: var(--s-2) var(--s-5); list-style: none; padding: 0; margin: var(--s-6) 0 0; }
.foot a { color: var(--muted); text-decoration: none; }
.foot a:hover { color: var(--ink); }
.foot .row3 { display: flex; flex-wrap: wrap; gap: var(--s-1) var(--s-5); margin-top: var(--s-5); }
.foot .row3 a { text-decoration: underline 1px; text-underline-offset: 3px; text-decoration-color: var(--line-2); }

/* ---------- inner pages: privacy, changelog (§5, §6) ---------- */

.page-head { padding-top: clamp(48px, 8vw, 128px); }
.page-head h1 { font-size: var(--t-h2); line-height: 1.06; letter-spacing: -.016em; }
.page-head .lead { margin-top: var(--s-5); }
.book { max-width: 36em; }
.book h2 { font-size: var(--t-h3); line-height: 1.18; letter-spacing: -.008em; margin-top: var(--s-8); }
.book h2 + * { margin-top: var(--s-4); }
.book p + p, .book p + ul, .book ul + p { margin-top: 1em; }
.book ul { padding-left: 1.2em; }
.book li + li { margin-top: .4em; }
.book li::marker { color: var(--muted); }
.book .updated { font-style: italic; color: var(--muted); margin-top: var(--s-4); }
.book .intro { margin-top: var(--s-7); }
.toc { list-style: none; padding: 0; margin: var(--s-4) 0 0; font: 400 var(--t-small)/1.4 var(--ui); display: grid; gap: var(--s-2); }
.toc a { color: var(--muted); text-decoration: none; transition: color .15s; }
.toc a:hover, .toc a.cur { color: var(--ink); }
@media (max-width: 1023px) { .toc-wrap { display: none; } }
.inner-sec { padding-top: var(--s-8); padding-bottom: var(--sec-pad); }

/* Changelog: one grid row per release. */
.rel { padding-top: var(--s-8); }
.rel + .rel { margin-top: var(--s-8); border-top: 1px solid var(--line); }
@media (min-width: 1024px) { .rel + .rel { border-top: 0; } .rel + .rel .col { border-top: 1px solid var(--line); padding-top: var(--s-8); } .rel + .rel { padding-top: 0; } .rel + .rel .margin { padding-top: calc(var(--s-8) + .3em); } }
.rel .ver { font: 500 var(--t-h3)/1.18 var(--serif); letter-spacing: -.008em; color: var(--ink);
            font-variant-numeric: lining-nums tabular-nums; text-decoration: none; display: inline-flex; align-items: baseline; gap: .3em; }
.rel .ver .hash { font: 400 .7em/1 var(--ui); color: var(--muted); opacity: 0; transition: opacity .15s; }
.rel .ver:hover .hash, .rel .ver:focus-visible .hash { opacity: 1; }
.rel .latest { margin-top: var(--s-1); }
@media (max-width: 1023px) { .rel .margin { display: flex; align-items: baseline; gap: var(--s-3); } .rel .latest { margin: 0; } }
.notes { max-width: 36em; color: var(--ink); }
.notes p + p, .notes p + ul, .notes ul + p { margin-top: 1em; }
.notes strong { font-weight: 600; }
.notes ul { padding-left: 1.2em; margin-top: .6em; }
.notes li + li { margin-top: .4em; }
.notes li::marker { color: var(--muted); }
.notes code { font: 400 .85em var(--mono); background: var(--paper-2); padding: 1px 5px; border-radius: 4px; }
.notes h3 { font-size: 1.25rem; margin-top: var(--s-6); }
.notes h3 + * { margin-top: var(--s-3); }
.all-rel { margin-top: var(--s-9); font: 500 var(--t-ui)/1.4 var(--ui); }

/* 404 (§7). */
.nf { min-height: calc(100svh - var(--nav-h) - 220px); display: grid; place-content: center; text-align: center; padding: var(--s-9) var(--gutter); }
.nf .deva { font: 400 4rem/1.2 var(--deva); color: var(--muted); }
.nf h1 { margin-top: var(--s-5); font-size: var(--t-h2); line-height: 1.06; letter-spacing: -.016em; }
.nf p { margin-top: var(--s-5); color: var(--ink-2); font-size: var(--t-lead); }

/* ---------- scroll reveals (§4.7): H2 + first paragraph, once ---------- */

@media (prefers-reduced-motion: no-preference) {
  .js .rv { opacity: 0; transform: translateY(12px); transition: opacity 560ms var(--ease-out), transform 560ms var(--ease-out); }
  .js .rv + .rv { transition-delay: 60ms; }
  .js .rv.in { opacity: 1; transform: none; }
}

/* ---------- reduced motion: everything instant ---------- */

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after { animation-duration: 1ms !important; animation-delay: 0ms !important; transition-duration: 1ms !important; transition-delay: 0ms !important; }
  .cap.down { transform: none; border-bottom-width: 2px; }
  .vctl { opacity: 1; }
}

/* Body-size alternates (S1b, S4): the new words simply fade in where they land. */
@keyframes alt-fade { from { opacity: 0; } }
.alt-t.inline { display: inline; white-space: normal; }
.alt-t.inline.fade { animation: alt-fade 220ms var(--ease-out); }
.alt-t.inline.ghosted.fade { animation: none; }
.rel .ver-h { font: inherit; margin: 0; }
@media (max-width: 479px) { .kc-field.tw { font-size: 1rem; } }

/* The app icon is a dark tile: on dark paper it needs a hairline to keep its edge. */
@media (prefers-color-scheme: dark) { :root:not([data-theme="light"]) .brand img { border-radius: 22%; box-shadow: 0 0 0 1px var(--line-2); } }
:root[data-theme="dark"] .brand img { border-radius: 22%; box-shadow: 0 0 0 1px var(--line-2); }
