/*
 * amber-brand — the theme Amber wears for its own landing page.
 *
 * Self-hosted brand webfonts (Fraunces display + Hanken Grotesk body), the
 * amber palette as the design system, warm and calm. Light is the default;
 * dark comes from a prefers-color-scheme block, and a header toggle can pin
 * light or dark per visitor. Only the colour tokens remap between modes —
 * font/spacing tokens are constant, and every literal colour in this file
 * composes from an --amber-* token so both modes hold.
 *
 * Ported from the approved prototype (amber-claude-design/index(1).html); covers
 * @font-face, tokens, base/type, header/footer, hero, the-bet, themes, editor,
 * article, and error pages.
 */

/* ── Brand webfonts (self-hosted, served install-wide at /fonts/) ───────── */
@font-face { font-family:'Fraunces';      src:url('/fonts/Fraunces.woff2') format('woff2-variations');      font-weight:100 900; font-style:normal; font-display:swap; }
@font-face { font-family:'Hanken Grotesk'; src:url('/fonts/HankenGrotesk.woff2') format('woff2-variations'); font-weight:100 900; font-style:normal; font-display:swap; }

/* ── Tokens — light default; dark remaps the colour tokens ─────────────────
   Light defines the base. Dark is applied two ways that share one palette:
   the prefers-color-scheme media block (OS dark, when the visitor hasn't
   chosen — pure CSS, works with JS off) and the explicit
   :root[data-amber-theme="dark"] block set by the header toggle (theme.js),
   which beats the OS. A saved choice is applied to <html> before first paint
   by the inline script in apps/web/src/app.html, so there's no flash. The dark
   values live in both dark blocks — keep them in sync. (--amber-brand is the
   one mode-invariant colour; it never appears in a dark block.) */
:root {
	--amber-bg:#faf7f0; --amber-ink:#2a2622; --amber-ink-muted:#655d4f;
	--amber-accent:#9a6314; --amber-accent-hover:#7c4e0f; --amber-rule:#e4dcc9;
	--amber-surface-sunken:#efe8d6; --amber-selection-bg:rgba(154,99,20,.18);
	--amber-brand:#c6871f; --amber-pine:#2e5a50;
	--amber-font-display:'Fraunces', Georgia, serif;
	--amber-font-body:'Hanken Grotesk', system-ui, -apple-system, 'Segoe UI', sans-serif;
	--amber-font-mono:ui-monospace, SFMono-Regular, Menlo, monospace;
	--amber-ease: cubic-bezier(0.23, 1, 0.32, 1);
	color-scheme: light;
}
/* OS dark — only when the visitor hasn't pinned a choice via the toggle. */
@media (prefers-color-scheme: dark) {
	:root:not([data-amber-theme]) {
		--amber-bg:#1a1714; --amber-ink:#e8e0d2; --amber-ink-muted:#9a8f7d;
		--amber-accent:#d9a441; --amber-accent-hover:#ecbb5e; --amber-rule:#332e27;
		--amber-surface-sunken:#232019; --amber-selection-bg:rgba(217,164,65,.22);
		--amber-pine:#3f7367;
		color-scheme: dark;
	}
}
/* Explicit dark choice (header toggle) — higher specificity than the media
   block's :root, and it carries no media condition, so it wins on any OS. */
:root[data-amber-theme="dark"] {
	--amber-bg:#1a1714; --amber-ink:#e8e0d2; --amber-ink-muted:#9a8f7d;
	--amber-accent:#d9a441; --amber-accent-hover:#ecbb5e; --amber-rule:#332e27;
	--amber-surface-sunken:#232019; --amber-selection-bg:rgba(217,164,65,.22);
	--amber-pine:#3f7367;
	color-scheme: dark;
}

/* ── Base ───────────────────────────────────────────────────────────────── */
*{box-sizing:border-box;}
body{
	margin:0;min-height:100dvh;display:flex;flex-direction:column;
	background:var(--amber-bg);color:var(--amber-ink);
	font-family:var(--amber-font-body);font-size:1.0625rem;line-height:1.6;font-weight:400;
	-webkit-font-smoothing:antialiased;
}
/* Amber owns <main> (between the chrome halves); let it grow so the footer
   sits at the bottom on short pages. Landing sections are full-bleed with
   their own .wrap, so main imposes no measure of its own. */
main{flex:1 0 auto;}
::selection{background:var(--amber-selection-bg);}
a{color:var(--amber-accent);text-decoration:none;}
a:hover{color:var(--amber-accent-hover);}
:focus-visible{outline:2px solid var(--amber-accent);outline-offset:3px;border-radius:4px;}

/* One shared measure for the whole page — every scrolled surface (header,
   hero, bet, themes, editor, footer, article) sits in this same centred
   column so the page reads at one consistent, desktop-first width top to
   bottom. Per-section content stays left-aligned at this column's left
   edge; only text lines cap their own measure for readability. */
.wrap{max-width:1200px;margin:0 auto;padding:0 32px;}

/* ── Type ───────────────────────────────────────────────────────────────── */
.display{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 144,'SOFT' 30,'WONK' 0;
	font-weight:600;letter-spacing:-0.015em;line-height:1.04;margin:0;
	color:var(--amber-ink);text-wrap:balance;
}
h2.display{font-variation-settings:'opsz' 72,'SOFT' 30,'WONK' 0;letter-spacing:-0.01em;line-height:1.1;}
.eyebrow{
	font-family:var(--amber-font-mono);font-size:.8rem;letter-spacing:.16em;
	text-transform:uppercase;color:var(--amber-accent);margin:0 0 18px;font-weight:500;
}
.lede{font-size:1.0625rem;line-height:1.6;color:var(--amber-ink-muted);margin:0;}

/* ── Wordmark ───────────────────────────────────────────────────────────── */
.wm{display:inline-flex;align-items:center;gap:.42em;line-height:1;}
.gem--wm{height:1.12em;width:auto;margin-top:.02em;flex:none;display:block;}
.wm__txt{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 144,'SOFT' 40,'WONK' 0;
	font-weight:560;letter-spacing:-0.01em;color:var(--amber-ink);
}

/* ── Header ─────────────────────────────────────────────────────────────── */
.site-head{position:sticky;top:0;z-index:50;
	background:color-mix(in srgb,var(--amber-bg) 86%,transparent);
	backdrop-filter:blur(10px);border-bottom:1px solid transparent;}
.site-head__in{display:flex;align-items:center;justify-content:space-between;height:72px;}
.site-head .wm__txt{font-size:1.45rem;}
.site-head__end{display:flex;align-items:center;gap:18px;}
.nav{display:flex;align-items:center;gap:26px;}
.nav a{color:var(--amber-ink-muted);font-size:.95rem;font-weight:500;transition:color .2s ease;}
.nav a:hover{color:var(--amber-ink);}
@media (max-width:620px){.nav a.nav__txt{display:none;}}

/* Light/dark toggle — a quiet icon button. Hidden until theme.js reveals it,
   so no-JS visitors never see a dead control (the palette still auto-follows
   their OS). theme.js sets data-resolved to the active mode; CSS shows the
   icon for the mode you'd switch TO (moon in light, sun in dark). */
.theme-toggle{
	display:inline-flex;align-items:center;justify-content:center;
	width:38px;height:38px;padding:0;border-radius:9px;
	background:transparent;border:1px solid var(--amber-rule);
	color:var(--amber-ink-muted);cursor:pointer;
	transition:color .2s ease,border-color .2s ease;
}
.theme-toggle:hover{color:var(--amber-ink);border-color:var(--amber-accent);}
.theme-toggle .ic{display:block;width:20px;height:20px;}
.theme-toggle .ic-sun{display:none;}
.theme-toggle[data-resolved="dark"] .ic-moon{display:none;}
.theme-toggle[data-resolved="dark"] .ic-sun{display:block;}

/* ── Footer ─────────────────────────────────────────────────────────────── */
.site-foot{border-top:1px solid var(--amber-rule);padding:56px 0 64px;}
.site-foot__top{display:flex;justify-content:space-between;align-items:flex-end;gap:30px;flex-wrap:wrap;}
.site-foot .wm__txt{font-size:1.4rem;}
.foot-tag{font-size:.92rem;color:var(--amber-ink-muted);margin:14px 0 0;}
.foot-links{display:flex;gap:24px;flex-wrap:wrap;}
.foot-links a{color:var(--amber-ink-muted);font-size:.95rem;font-weight:500;}
.foot-links a:hover{color:var(--amber-ink);}

/* ── Hero ─────────────────────────────────────────────────────────────────
   The signature moment: the jewel is the hero; everything around it is quiet.
   The gem is a crisp raster anchor; its glow is a CSS radial-gradient on the
   wrapping span's ::after (::before/::after don't render on replaced <img>
   elements). The halo is laid out statically here; Task 9 animates its
   opacity (a gentle breathe). The headline stays the typographic moment. */
.hero{padding:88px 0 96px;position:relative;overflow:hidden;}
.hero__glow{
	position:absolute;inset:-120px auto auto -160px;width:620px;height:620px;
	pointer-events:none;z-index:0;
	background:radial-gradient(circle at center,
		color-mix(in srgb,var(--amber-brand) 20%,transparent),transparent 62%);
}
/* The hero fills the shared column; its h1/subhead keep their own ch-measures
   and stay left-aligned, so the hero anchors at the same left edge as every
   section below it. */
.hero__in{position:relative;z-index:1;}

/* Headline + subhead come from {{{html}}} (rendered index.md): <h1> + <p>. */
.hero__text h1{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 144,'SOFT' 30,'WONK' 0;
	font-weight:600;letter-spacing:-0.015em;line-height:1.04;
	color:var(--amber-ink);text-wrap:balance;
	font-size:clamp(2.6rem,6.2vw,4.4rem);margin:0 0 22px;max-width:14ch;
}
.hero__text p{
	font-size:1.2rem;line-height:1.6;color:var(--amber-ink-muted);
	max-width:48ch;margin:0 0 34px;
}

/* The real gem + its CSS halo. Image stays sharp (the gradient lives on the
   wrapper, not the gem); the gem's own drop-shadow composes from the brand
   token. */
.gem--hero-wrap{position:relative;display:inline-block;margin:0 0 28px;}
.gem--hero{
	display:block;width:clamp(84px,12vw,132px);height:auto;
	filter:drop-shadow(0 10px 30px color-mix(in srgb,var(--amber-brand) 28%,transparent));
	position:relative;z-index:1;
}
.gem--hero-wrap::after{
	content:"";position:absolute;inset:-55% -55% -42% -55%;z-index:0;pointer-events:none;
	background:radial-gradient(circle at 50% 52%,
		color-mix(in srgb,var(--amber-brand) 34%,transparent),transparent 62%);
}

/* install block */
.install{margin:0 0 30px;max-width:30rem;}
.code{
	font-family:var(--amber-font-mono);font-size:.86rem;line-height:1.85;
	background:var(--amber-surface-sunken);border:1px solid var(--amber-rule);
	border-radius:12px;padding:18px 20px;margin:0;color:var(--amber-ink);
	overflow-x:auto;
}
.code .ln{display:block;white-space:pre;}
.code .pr{
	color:var(--amber-accent);opacity:.85; /* bumped from .75 so the prompt clears legibility on sunken in light mode too */
	-webkit-user-select:none;user-select:none;margin-right:.6em;
}
.install__cap{font-size:.88rem;color:var(--amber-ink-muted);margin:12px 2px 0;}
.kbd{
	font-family:var(--amber-font-mono);background:var(--amber-surface-sunken);
	border:1px solid var(--amber-rule);border-radius:5px;padding:1px 6px;
	font-size:.86em;color:var(--amber-ink);
}

/* buttons — primary is ALWAYS ink-on-amber (both modes); the hover deepens the
   amber and keeps the ink label so it never flips to white-on-light in dark. */
.cta-row{display:flex;gap:14px;align-items:center;flex-wrap:wrap;margin-bottom:22px;}
.btn{
	font-family:var(--amber-font-body);font-size:1.0625rem;font-weight:600;
	border-radius:11px;padding:13px 26px;display:inline-flex;align-items:center;gap:.5em;
	border:1px solid transparent;cursor:pointer;
	transition:transform .15s var(--amber-ease),background .2s ease,color .2s ease,border-color .2s ease;
}
.btn:hover{transform:translateY(-1px);}
.btn:active{transform:scale(.97);}
.btn--primary{background:var(--amber-brand);color:#2a2622;} /* ink label on amber — never white; #2a2622 is a fixed dark ink in BOTH modes (do not tokenize) */
.btn--primary:hover{background:#bf831d;color:#2a2622;} /* deeper amber, ink label — AA in both modes (4.63:1) */
/* The global :focus-visible ring is var(--amber-accent) (amber) — on the amber
   primary bg that's ~1.4:1, below WCAG 1.4.11's 3:1 non-text threshold. Swap to
   the ink colour: #2a2622 on #c6871f ≈ 4.9:1, legible in both modes (the amber
   bg is mode-invariant). Width/offset/border-radius inherit from the global rule. */
.btn--primary:focus-visible{outline-color:#2a2622;}
.btn--ghost{color:var(--amber-accent);border-color:var(--amber-rule);background:transparent;}
.btn--ghost:hover{border-color:var(--amber-accent);}
.micro{font-size:.88rem;color:var(--amber-ink-muted);margin:0;letter-spacing:.01em;}

/* ── Section rhythm ─────────────────────────────────────────────────────────
   Mid-page beats share a vertical cadence and a hairline rule between them.
   The hero (no .beat class) is untouched. .reveal/.rise scroll-state lives in
   Task 9 — deliberately unstyled here so all content is visible at rest. */
/* Scoped to the landing sections so a positioning context isn't forced onto
   <section> elements an author might use in article-page content. */
.hero,.bet,.themes,.editor{position:relative;}
.beat{padding:104px 0;}
.beat--rule{border-top:1px solid var(--amber-rule);}

/* ── ② The bet ──────────────────────────────────────────────────────────────
   A calm claim with a large, faint gem drifting off the right edge — an
   ambient brand mark, not a focal one. The earlier hero task hid .gem--bet;
   that rule is removed and the gem now renders here at low opacity. */
.bet{position:relative;overflow:hidden;}
.gem--bet{
	position:absolute;right:-90px;top:50%;transform:translateY(-50%);
	width:340px;height:auto;opacity:.10;pointer-events:none;z-index:0;
}
.bet__in{position:relative;z-index:1;}
.bet h2{font-size:clamp(2rem,4.4vw,3rem);margin:0 0 26px;max-width:16ch;}
.bet p{font-size:1.2rem;line-height:1.65;color:var(--amber-ink-muted);margin:0;max-width:50ch;}
.bet p strong{color:var(--amber-ink);font-weight:500;} /* emphasis: ink on muted body */

/* ── ③ Theme windows ────────────────────────────────────────────────────────
   Two browser-chrome mockups showing the SAME content under two themes:
   amber-default (warm serif) and amber-editorial (sans magazine). The visible
   difference is the proof of "one space, any look" — not a generic card grid. */
.themes h2{font-size:clamp(2rem,4.4vw,3rem);margin:0 0 16px;}
.themes .lede{max-width:52ch;margin-bottom:54px;font-size:1.15rem;}
.window-grid{display:grid;grid-template-columns:1fr 1fr;gap:30px;align-items:start;}
@media (max-width:780px){.window-grid{grid-template-columns:1fr;gap:26px;}}

.win{
	border-radius:14px;overflow:hidden;border:1px solid var(--amber-rule);
	background:var(--amber-surface-sunken);
	box-shadow:0 24px 60px -28px rgba(0,0,0,.5),0 2px 0 rgba(255,255,255,.02) inset; /* elevation, not palette */
}
.win__chrome{
	display:flex;align-items:center;gap:14px;padding:11px 14px;
	border-bottom:1px solid var(--amber-rule);
	background:color-mix(in srgb,var(--amber-bg) 50%,var(--amber-surface-sunken));
}
.win__dots{display:flex;gap:7px;}
.win__dots i{width:11px;height:11px;border-radius:50%;display:block;background:var(--amber-rule);}
.win__dots i:nth-child(1){background:#d98b6a;} /* traffic-light metaphor — constant in both modes */
.win__dots i:nth-child(2){background:#d9b85f;}
.win__dots i:nth-child(3){background:#7fae8a;}
.win__url{
	flex:1;font-family:var(--amber-font-mono);font-size:.78rem;color:var(--amber-ink-muted);
	background:var(--amber-bg);border:1px solid var(--amber-rule);border-radius:7px;
	padding:5px 12px;text-align:center;
}
.win__body{padding:34px 30px 36px;min-height:248px;background:var(--amber-bg);}
.win__tag{
	font-size:.72rem;font-family:var(--amber-font-mono);letter-spacing:.04em;
	color:var(--amber-ink-muted);margin-top:14px;display:block;
}

/* theme: amber-default (warm serif) */
.t-default .pg-title{
	font-family:var(--amber-font-display);font-variation-settings:'opsz' 80,'SOFT' 30;
	font-weight:600;font-size:1.9rem;letter-spacing:-0.01em;margin:0 0 12px;color:var(--amber-ink);
}
.t-default .pg-prose{font-size:1rem;line-height:1.6;color:var(--amber-ink-muted);margin:0 0 22px;max-width:34ch;}
.t-default .pg-nav{display:flex;gap:18px;font-size:.95rem;}
.t-default .pg-nav a{color:var(--amber-accent);}

/* theme: amber-editorial (sans magazine) */
.t-editorial .pg-kicker{
	font-family:var(--amber-font-body);font-size:.72rem;font-weight:700;
	letter-spacing:.18em;text-transform:uppercase;color:var(--amber-accent);margin:0 0 14px;
}
.t-editorial .pg-title{
	font-family:var(--amber-font-body);font-weight:800;font-size:2rem;
	line-height:1.05;letter-spacing:-0.02em;margin:0 0 14px;color:var(--amber-ink);
}
.t-editorial .pg-prose{
	font-size:.98rem;line-height:1.55;color:var(--amber-ink-muted);
	margin:0 0 22px;max-width:32ch;padding-top:16px;border-top:1px solid var(--amber-rule);
}
.t-editorial .pg-nav{display:flex;gap:22px;font-size:.74rem;font-weight:700;letter-spacing:.1em;text-transform:uppercase;}
.t-editorial .pg-nav a{color:var(--amber-ink);}

/* ── ④ Editor demo (static) ─────────────────────────────────────────────────
   A real-looking editor window with a markdown document already in it. STATIC
   in this task: the prototype's typing setup (max-width:0/overflow/border-right
   on .ed-line, the blinking caret) is deliberately NOT ported — that's Task 9.
   Here the full document text is visible and the caret is a quiet static bar. */
.editor h2{font-size:clamp(2rem,4.4vw,3rem);margin:0 0 16px;}
.editor .lede{max-width:50ch;margin-bottom:50px;font-size:1.15rem;}
.ed-win{width:100%;}
.ed-toolbar{
	display:flex;align-items:center;gap:6px;padding:9px 14px;
	border-bottom:1px solid var(--amber-rule);
	background:color-mix(in srgb,var(--amber-bg) 50%,var(--amber-surface-sunken));
}
.ed-tool{
	font-family:var(--amber-font-body);font-size:.8rem;font-weight:600;color:var(--amber-ink-muted);
	padding:5px 9px;border-radius:7px;border:1px solid transparent;background:transparent;line-height:1;
}
.ed-tool.is-i{font-style:italic;}
.ed-tool.is-b{font-weight:800;}
.ed-sep{width:1px;height:18px;background:var(--amber-rule);margin:0 4px;}
.ed-toolbar .spacer{flex:1;}
.ed-dot{width:7px;height:7px;border-radius:50%;background:var(--amber-pine);opacity:.7;}
.ed-saved{font-family:var(--amber-font-mono);font-size:.72rem;color:var(--amber-ink-muted);}
.ed-doc{padding:40px 42px 56px;background:var(--amber-bg);min-height:320px;}
.ed-row{display:flex;align-items:baseline;}
/* Static: full text visible — typing setup (max-width:0/overflow/border-right) is Task 9. */
.ed-line{font-family:var(--amber-font-mono);white-space:nowrap;}
.ed-line.l1{font-size:1.25rem;font-weight:600;color:var(--amber-ink);line-height:2;}
.ed-line.l2{font-size:1rem;color:var(--amber-ink-muted);line-height:2;}
.ed-caret{
	display:inline-block;width:2px;height:1.05em;background:var(--amber-accent);
	margin-left:1px;transform:translateY(2px);visibility:visible; /* static bar; blink is Task 9 */
}

/* ── Motion ──────────────────────────────────────────────────────────────────
   CSS-only motion for the landing page. The governing idea: every motion is a
   well-made object settling, never a product-launch reveal — calm, restrained,
   mostly unnoticed.

   Accessibility architecture: ALL motion lives inside
   @media (prefers-reduced-motion: no-preference). The default (and reduced-
   motion) state — set by Tasks 7/8 above — is the fully-visible static page:
   .rise/.reveal at full opacity, .ed-line as nowrap visible mono text, the gem
   halo a static gradient, .ed-caret a quiet visible bar. No opacity:0 /
   max-width:0 / visibility:hidden start-state exists OUTSIDE this block, so if
   an animation never runs (older browser, reduced-motion) content is never
   stuck invisible. Reduced-motion users simply never enter the block — no
   separate reduce-reset is needed.

   Keyframes are defined outside the media query: they are inert without a
   referencing animation, and every animation that references them lives inside
   no-preference. Only transform/opacity (and max-width for the typewriter clip)
   animate; entrances use --amber-ease. No bounce, neon, parallax, or spin. */

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

/* Gem inner-glow breathe — opacity-only (transform on ::after is reserved for
   Task 10's pointer JS). Long period, low amplitude: always on screen, so it
   must never nag. */
@keyframes gemBreathe{0%,100%{opacity:.7;}50%{opacity:1;}}

/* Editor typing demo — a calm ~13s loop demonstrating that the editor types
   markdown to disk. steps() gives the typewriter feel; max-width clips the line
   (clipping, not layout thrash). */
@keyframes type1{
	0%{max-width:0;border-right-color:transparent;}
	6%{max-width:0;border-right-color:var(--amber-accent);animation-timing-function:steps(10,end);}
	17%{max-width:10ch;border-right-color:var(--amber-accent);}
	20%{border-right-color:transparent;}
	100%{max-width:10ch;border-right-color:transparent;}
}
@keyframes type2{
	0%{max-width:0;border-right-color:transparent;}
	22%{max-width:0;border-right-color:var(--amber-accent);animation-timing-function:steps(36,end);}
	42%{max-width:36ch;border-right-color:var(--amber-accent);}
	44%{border-right-color:transparent;}
	100%{max-width:36ch;border-right-color:transparent;}
}
@keyframes caretShow{
	0%,43%{visibility:hidden;}
	44%,90%{visibility:visible;}
	91%,100%{visibility:hidden;}
}
@keyframes caretBlink{0%,49%{opacity:1;}50%,100%{opacity:0;}}
@keyframes edFade{0%{opacity:0;}5%{opacity:1;}90%{opacity:1;}97%,100%{opacity:0;}}

/* Smooth in-page anchor scrolling — gated behind no-preference so reduced-motion
   users get instant jumps (WCAG 2.3.3). A second no-preference at-rule is valid
   CSS; kept separate from the entrance-motion block below for clarity. */
@media (prefers-reduced-motion: no-preference) {
	html{scroll-behavior:smooth;}
}

@media (prefers-reduced-motion: no-preference) {
	/* 1 · Hero load stagger — plays once on load. Tight stagger (90ms), 14px
	   travel, strong ease-out. Settled, not flashy. */
	.rise{opacity:0;animation:rise .7s var(--amber-ease) forwards;
		animation-delay:calc(var(--i,0)*90ms + 120ms);}

	/* 2 · Gem inner-glow breathe — barely there. */
	.gem--hero-wrap::after{animation:gemBreathe 7s ease-in-out infinite;}

	/* 3 · Scroll-driven section reveals — only where scroll timelines exist;
	   other browsers show content statically (Task 10 adds a JS fallback). The
	   reveal is inherently reversible and never parallaxes. (The rise keyframe's
	   from{translateY(14px)} overrides the 24px below under the scroll timeline —
	   approved prototype behaviour.) */
	@supports (animation-timeline: view()){
		.reveal{opacity:0;transform:translateY(24px);
			animation:rise linear both;animation-timeline:view();animation-range:entry 8% cover 32%;}
	}

	/* 4 · Editor typing demo — the hidden start-state (clip + invisible caret)
	   lives ONLY here, so reduced-motion users keep Task 8's full static text. */
	.ed-line{max-width:0;overflow:hidden;border-right:2px solid transparent;}
	.ed-doc{animation:edFade 13s ease-in-out infinite;}
	.ed-line.l1{animation:type1 13s infinite;}
	.ed-line.l2{animation:type2 13s infinite;}
	.ed-caret{visibility:hidden;animation:caretShow 13s infinite,caretBlink 1.1s steps(1,end) infinite;}
}

/* ── Enhancement hooks (theme.js) ──────────────────────────────────────────────
   Optional progressive enhancement layered by theme.js (which the layout loads
   as a deferred module when present). The page is complete without it; these
   hooks are no-ops until the script sets their custom property / class.

   (a) Pointer-glow transform on the hero halo. Defaults to translate(0,0) — a
   no-op without JS. The breathe animation (above) animates opacity only, so the
   transform channel is free; this rule MERGES with the base ::after (background/
   inset/z-index) and the breathe ::after (animation) — no property overlaps.
   Harmless under reduced-motion: the JS never sets the vars then. */
.gem--hero-wrap::after{
	transform:translate(var(--gem-glow-x,0),var(--gem-glow-y,0));
	transition:transform .25s var(--amber-ease);
}

/* (b) Reveal fallback for browsers lacking animation-timeline: view(). Scoped
   under html.js-reveal so the hidden start-state exists ONLY when JS is present
   AND driving it — no-JS (no class) keeps .reveal fully visible. theme.js only
   adds the class when motion is allowed, so reduced-motion never sees opacity:0. */
@supports not (animation-timeline: view()){
	html.js-reveal .reveal{opacity:0;transform:translateY(24px);transition:opacity .7s ease, transform .7s var(--amber-ease);}
	html.js-reveal .reveal.is-in{opacity:1;transform:none;}
}

/* ── Article (non-home content pages, e.g. the colophon) ──────────────────────
   Non-landing pages render as a single <article> inside .wrap (chrome.html's
   <main>). The column is left-aligned at the SAME left edge as the header
   wordmark and the landing sections — one family — but caps its line length at
   a comfortable reading measure rather than the full page width. Headings take
   the Fraunces display face, prose the Hanken body face; every colour composes
   from an --amber-* token so light and dark both hold. (Before this the article
   had no theme styles at all: UA-default Times headings, edge-to-edge text.) */
.article-wrap{padding-top:72px;padding-bottom:104px;}
article{max-width:70ch;}

.article-header{margin:0 0 44px;}
.article-title{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 96,'SOFT' 30,'WONK' 0;
	font-weight:600;font-size:clamp(2.4rem,5vw,3.4rem);line-height:1.06;
	letter-spacing:-0.015em;color:var(--amber-ink);text-wrap:balance;margin:0;
}
.article-date{
	font-family:var(--amber-font-mono);font-size:.8rem;letter-spacing:.04em;
	color:var(--amber-ink-muted);margin:14px 0 0;
}

.article-body{font-size:1.0625rem;line-height:1.7;color:var(--amber-ink);}
.article-body > :first-child{margin-top:0;}
.article-body p{margin:0 0 1.3em;}
.article-body h2{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 60,'SOFT' 30,'WONK' 0;
	font-weight:600;font-size:1.7rem;line-height:1.18;letter-spacing:-0.01em;
	color:var(--amber-ink);margin:2em 0 .55em;
}
.article-body h3{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 40,'SOFT' 30,'WONK' 0;
	font-weight:600;font-size:1.28rem;line-height:1.25;color:var(--amber-ink);margin:1.8em 0 .5em;
}
.article-body a{
	color:var(--amber-accent);text-decoration:underline;
	text-underline-offset:2px;text-decoration-thickness:1px;
}
.article-body a:hover{color:var(--amber-accent-hover);}
.article-body strong{color:var(--amber-ink);font-weight:600;}
.article-body ul,.article-body ol{margin:0 0 1.3em;padding-left:1.4em;}
.article-body li{margin:0 0 .45em;}
.article-body li::marker{color:var(--amber-accent);}
.article-body blockquote{
	margin:1.7em 0;padding:4px 0 4px 22px;border-left:2px solid var(--amber-accent);
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 32,'SOFT' 40,'WONK' 0;
	font-weight:500;font-size:1.25rem;line-height:1.45;color:var(--amber-ink);
}
.article-body blockquote p{margin:0;color:inherit;}
.article-body code{
	font-family:var(--amber-font-mono);font-size:.88em;
	background:var(--amber-surface-sunken);border:1px solid var(--amber-rule);
	border-radius:5px;padding:1px 6px;color:var(--amber-ink);
}
.article-body pre{
	font-family:var(--amber-font-mono);font-size:.86rem;line-height:1.7;
	background:var(--amber-surface-sunken);border:1px solid var(--amber-rule);
	border-radius:12px;padding:18px 20px;margin:0 0 1.4em;overflow-x:auto;color:var(--amber-ink);
}
.article-body pre code{background:none;border:0;padding:0;font-size:1em;}
.article-body hr{border:0;border-top:1px solid var(--amber-rule);margin:2.4em 0;}

/* ── Draft banner (non-home pages flagged draft: true) ────────────────────────
   A calm dev-only notice sitting above the article, aligned to the article's
   reading measure rather than the full page width. A full accent-tinted border
   over a faint accent wash signals "notice" without alarm (no side-stripe); a
   small leading dot reads as a status mark. Body face, muted ink, normal case —
   read as a sentence, not shouted in caps. Both colours compose from tokens, so
   light and dark hold; the muted-on-wash pairing matches .foot-tag. */
.draft-banner{
	max-width:70ch;margin:0 0 40px;
	display:flex;align-items:center;gap:.65em;
	padding:12px 18px;border-radius:11px;
	border:1px solid color-mix(in srgb,var(--amber-accent) 38%,var(--amber-rule));
	background:color-mix(in srgb,var(--amber-accent) 7%,var(--amber-bg));
	color:var(--amber-ink-muted);
	font-family:var(--amber-font-body);font-size:.92rem;line-height:1.55;
}
.draft-banner::before{
	content:"";flex:none;width:7px;height:7px;border-radius:50%;
	background:var(--amber-accent);
}

/* ── Auto-index (a page's index_html listing, after the article body) ─────────
   A ruled list of child pages: the title in the Fraunces display face (echoing
   .article-title / .article-body h3), an optional date in mono pushed to the
   right edge (matching .article-date). Full hairline rules above the first row
   and between rows — no side accents. Rendered inside <article>, so it inherits
   the 70ch measure. flex-wrap lets a long title and its date degrade onto two
   lines; a dateless row leaves the title alone at the left. */
.amber-auto-index{list-style:none;margin:52px 0 0;padding:0;}
.amber-auto-index-item{
	display:flex;flex-wrap:wrap;align-items:baseline;gap:.25em 1.2em;
	padding:15px 0;border-bottom:1px solid var(--amber-rule);
}
.amber-auto-index-item:first-child{border-top:1px solid var(--amber-rule);}
.amber-auto-index-link{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 40,'SOFT' 30,'WONK' 0;
	font-weight:560;font-size:1.2rem;letter-spacing:-0.01em;
	color:var(--amber-ink);transition:color .2s ease;
}
.amber-auto-index-link:hover{color:var(--amber-accent);}
.amber-auto-index-date{
	margin-left:auto;font-family:var(--amber-font-mono);
	font-size:.78rem;letter-spacing:.04em;color:var(--amber-ink-muted);
	white-space:nowrap;
}

/* ── Error page ──────────────────────────────────────────────────────────────
   Rendered by +error.svelte inside the layout-owned <main> (which has no .wrap),
   so .error-page supplies its own measure + horizontal padding, mirroring .wrap.
   Calm and centred: a large amber numeral, a Fraunces title, a quiet line, a
   link home. Every colour composes from an --amber-* token, so light and dark
   both hold. Structure modelled on amber-editorial's error block; values are all
   amber-brand tokens (editorial's --amber-text-… / -ui scale doesn't exist here). */
.error-page{
	max-width:1080px;margin:0 auto;padding:96px 32px 104px;text-align:center;
}
.error-code{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 144,'SOFT' 30,'WONK' 0;
	font-weight:600;font-size:clamp(4.5rem,16vw,8rem);line-height:1;
	letter-spacing:-0.02em;color:var(--amber-accent);margin:0 0 .1em;
}
.error-title{
	font-family:var(--amber-font-display);font-optical-sizing:auto;
	font-variation-settings:'opsz' 72,'SOFT' 30,'WONK' 0;
	font-weight:600;font-size:clamp(2rem,5vw,3rem);line-height:1.1;
	letter-spacing:-0.015em;color:var(--amber-ink);text-wrap:balance;margin:0 0 18px;
}
/* The descriptive line only (404 branch). Scoped with :not([class]) so it can't
   override .error-code / .error-back, which are also <p> but carry classes. */
.error-page p:not([class]){font-size:1.15rem;line-height:1.6;color:var(--amber-ink-muted);margin:0 auto;max-width:42ch;}
.error-back{margin-top:30px;}
.error-back a{color:var(--amber-accent);font-weight:600;}
.error-back a:hover{color:var(--amber-accent-hover);}

@media (prefers-reduced-motion: no-preference){
	.error-page{animation:rise .6s var(--amber-ease) both;}
}
