/* /prints/: the index and every post. Loaded after /site.css and built on its tokens and parts
   (.label, .cap, .rows, .ledger/.m, .more, .btn). Pages are generated by tools/build_prints.py.
   A post is a story: one reading column of about 70 characters, left-aligned on the shell's wrap,
   wide figures breaking out to the right, side notes in the right margin when there is one.
   No accent here beyond what the shell already uses it for. */

.plist .col { max-width: 42rem; }
.post .col { max-width: 40rem; }
/* one label track for the spec sheet, the issue rows and the files, so the column has one left edge for values */
.post { --lab: 8.5rem; }
.crumb { margin: -1rem 0 1.25rem; }
.crumb .more svg { order: -1; }

/* ---------------------------------------------------------------- post head */
.post h1 { margin-top: 0.75rem; font: 700 clamp(2.25rem, 6vw, 3.75rem)/1.02 var(--display); letter-spacing: -0.03em; text-wrap: balance; }
.post .dek { margin-top: 1.25rem; font-size: clamp(1.125rem, 1.6vw, 1.3125rem); color: var(--mid); text-wrap: pretty; }
.post .byline { margin-top: 1.25rem; color: var(--mid); }
.hero-fig { margin-top: 1.75rem; }
.fl.strip { margin-top: 0.75rem; }
.hero-fig.free img { aspect-ratio: auto; object-fit: initial; }   /* a long render, shown whole */
.hero-fig.drawn .plot { display: block; width: 100%; height: auto; padding: 1.25rem 1rem; border: 1px solid var(--line); background: var(--panel); }
.plot .rodl { stroke: var(--mut); stroke-width: 1; stroke-dasharray: 6 4; }
.byline a { white-space: nowrap; }
.hero-fig img, .entry .thumb img { width: 100%; aspect-ratio: 16 / 10; object-fit: cover; border: 1px solid var(--line); background: var(--panel); }

/* ---------------------------------------------------------------- quick facts */
.facts-block { margin-top: 3rem; }
.ledger.nums { margin-top: 2rem; }
.ledger.nums { grid-template-columns: repeat(3, minmax(0, 1fr)); border-top: 1px solid var(--line); padding-top: 1rem; }
.ledger.nums .m dd { font-size: clamp(1.75rem, 5vw, 2.75rem); }
.ledger.nums .m dt { font-size: 0.875rem; }
.spec { margin-top: 1rem; }
.spec > * { padding-block: 0.7rem; }
.rows.spec > * { grid-template-columns: var(--lab) minmax(0, 1fr); }
@media (max-width: 40rem) { .rows.spec > * { grid-template-columns: 1fr; } }
.spec dd { font-size: 0.9375rem; }
.sub-h { margin-top: 2rem; font: 600 1.0625rem/1.4 var(--sans); letter-spacing: 0; }
.sub-h + .cap { margin-top: 0.25rem; }
.sets { margin-top: 0.75rem; border-top: 1px solid var(--line); }
.sets li { display: flex; flex-wrap: wrap; align-items: baseline; gap: 0.25rem 0.6rem; padding-block: 0.6rem; border-bottom: 1px solid var(--line); font-size: 0.9375rem; }
.sets .k { flex: 1 1 13rem; color: var(--ink); }
.sets .was, .sets .now, .sets .to { font: 400 0.875rem/1.5 var(--mono); font-variant-numeric: tabular-nums; white-space: nowrap; }
.sets .was, .sets .to { color: var(--mut); }
.sets .now { color: var(--ink); font-weight: 500; }
/* phones: one row per number, the figure left and what it means beside it */
@media (max-width: 40rem) {
  .ledger.nums { grid-template-columns: 1fr; gap: 0; padding-top: 0; }
  .ledger.nums .m { display: grid; grid-template-columns: 7.5rem minmax(0, 1fr); align-items: baseline; gap: 0 1rem; padding-block: 0.75rem; border-bottom: 1px solid var(--line); }
  .ledger.nums .m dd { font-size: 2rem; }
}

/* ---------------------------------------------------------------- what went wrong
   The summary is the whole post in one glance: symptom, then the fix, each a link to its entry. */
.post h2 { margin-top: 3rem; font: 650 1.5rem/1.2 var(--display); letter-spacing: -0.015em; }
.post h2 + p, .post h2 + .cap { margin-top: 0.85rem; }
.post .col > p + p, .issue dd p + p { margin-top: 0.95rem; }
.post p, .post li { text-wrap: pretty; }
.post code { font: 450 0.875em/1 var(--mono); }
.ilog ol { margin-top: 1rem; border-top: 1px solid var(--line); }
.ilog li { border-bottom: 1px solid var(--line); }
.ilog a { display: grid; grid-template-columns: 2.25rem minmax(0, 1fr); gap: 0 0.5rem; padding-block: 0.7rem; text-decoration: none; }
.ilog a:hover .sym { color: var(--signal); text-decoration: underline; }
.ilog .n { grid-row: span 2; font: 500 0.8125rem/1.6 var(--mono); color: var(--mut); padding-top: 0.1rem; }
.ilog .sym { color: var(--ink); font-weight: 500; }
.ilog .fx { color: var(--mid); font-size: 0.9375rem; }
.ilog .fx::before { content: "Fix: "; color: var(--mut); }

/* one entry per problem: label, symptom as the title, then Problem / Cause / Fix / Result */
.issue { margin-top: 3rem; padding-top: 1.25rem; border-top: 1px solid var(--line); scroll-margin-top: calc(var(--head) + 2.25rem + 1rem); }
.issue h3 { margin-top: 0.4rem; font: 700 1.5rem/1.2 var(--display); letter-spacing: -0.015em; }
.pcf { display: grid; gap: 0.9rem; margin-top: 1.25rem; }
.pcf > div { display: grid; grid-template-columns: var(--lab) minmax(0, 1fr); gap: 0.25rem var(--gap); }
.pcf dt { font: 500 0.75rem/1.9 var(--mono); letter-spacing: 0.12em; text-transform: uppercase; color: var(--mut); }
.pcf .pb dd, .pcf .cs dd { color: var(--mid); }
.pcf .fx dd { color: var(--ink); }
.pcf .rs dd { color: var(--ink); font-weight: 500; }
@media (max-width: 40rem) { .pcf > div { grid-template-columns: 1fr; } }

/* ---------------------------------------------------------------- figures */
.fig { margin-top: 1.75rem; }
.fig img, .fig .ph { border: 1px solid var(--line); background: var(--panel); }
.fig.wide { width: min(56rem, calc(100vw - 2 * var(--pad))); }
.fig.native img { width: auto; max-width: 100%; }
/* a portrait phone photo stays inside one screen */
.fig.col img, .fig.native img { max-height: min(70svh, 36rem); width: auto; max-width: 100%; }
.fig .plot { width: 100%; height: auto; border: 1px solid var(--line); background: var(--panel); padding: 2%; }
.plot path { fill: none; vector-effect: non-scaling-stroke; }
.plot .pl { stroke: var(--mut); stroke-width: 1; }
.plot .car { stroke: var(--mid); stroke-width: 0.75; }
.plot path.sup { fill: var(--ink); stroke: none; }
.plot .seam circle { fill: var(--ink); }
.plot .gap { stroke: var(--mid); stroke-width: 1; }
.plot path.loose { fill: var(--ink); stroke: var(--ink); stroke-width: 1; }
/* panels side by side, each with its own label; "stack" keeps them one above the other at every width */
.panels { display: grid; gap: 0.75rem var(--gap); }
@media (min-width: 40rem) { .panels:not(.stack) { grid-template-columns: repeat(auto-fit, minmax(0, 1fr)); } }
.panels.row { grid-template-columns: repeat(auto-fit, minmax(0, 1fr)); }
.fig.tall img { display: block; width: auto; max-width: 100%; max-height: min(36rem, 80svh); margin-inline: auto; }   /* portraits: a screen tall, never a column wide */   /* two portraits that read side by side even on a phone */
.panel { display: grid; gap: 0.4rem; min-width: 0; }
.panel img { width: 100%; height: auto; max-height: none; }
/* a short silent loop from the printer's camera; the poster stands in for it when motion is off */
.fig video { display: block; width: 100%; height: auto; border: 1px solid var(--line); background: var(--panel); }
.fig.native video { width: auto; max-width: 100%; max-height: min(70svh, 36rem); }
/* a clip with a phone cut: one of the two plays, the other is display:none and never fetched past its poster */
.fig video.narrow { display: none; }
@media (max-width: 40rem) { .fig video.wide { display: none; } .fig video.narrow { display: block; } }
.plabel, .edge { font: 500 0.6875rem/1.4 var(--mono); letter-spacing: 0.1em; text-transform: uppercase; color: var(--mut); }
.edge { text-align: center; }
.issue .fig + .fig { margin-top: 1.25rem; }
/* a photo still to take: drafts only, the build refuses it in a published post */
.ph { display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 0.75rem; aspect-ratio: 16 / 10; padding: 1.5rem; border-style: dashed !important; text-align: center; color: var(--mid); font-size: 0.9375rem; }

/* ---------------------------------------------------------------- draft marks (local preview only) */
.draft { display: inline-block; padding: 0.15em 0.5em; border: 1px solid var(--line); font: 500 0.6875rem/1.5 var(--mono); letter-spacing: 0.1em; text-transform: uppercase; color: var(--mut); vertical-align: 0.1em; white-space: nowrap; }
.draft-note { margin-bottom: 1.5rem; padding: 0.75rem 0.9rem; border: 1px dashed var(--line); font-size: 0.875rem; color: var(--mid); }

/* ---------------------------------------------------------------- files */
.getfile { margin-top: 3rem; padding-block: 1.25rem; border-block: 1px solid var(--line); }
.getfile h2 { margin-top: 0; }
.files { margin-block: 1rem; border-top: 1px solid var(--line); }
.files li { display: grid; column-gap: var(--gap); grid-template-columns: var(--lab) minmax(0, 1fr) auto auto; align-items: baseline; row-gap: 0.25rem; padding-block: 0.6rem; border-bottom: 1px solid var(--line); }
.files .what { font: 500 0.75rem/1.7 var(--mono); letter-spacing: 0.1em; text-transform: uppercase; color: var(--mut); }
.files a, .files .name { font: 450 0.875rem/1.5 var(--mono); overflow-wrap: anywhere; }
/* tap targets: the hit box reaches 44 px without moving the text */
.files a, .credits .ct, .inspo .ct { display: inline-block; padding-block: 0.7rem; margin-block: -0.7rem; }
.files .name { color: var(--mid); }
.files .size { font: 400 0.75rem/1.5 var(--mono); color: var(--mut); white-space: nowrap; }
@media (max-width: 40rem) {
  .files li { grid-template-columns: minmax(0, 1fr) auto; }
  .files .what, .files a, .files .name { grid-column: 1 / -1; }
}

.back { margin-top: 2rem; }
.back .more svg { order: -1; }
.pager { display: grid; grid-template-columns: repeat(auto-fit, minmax(14rem, 1fr)); gap: 1rem var(--gap); margin-top: 3rem; }
.pager a { display: grid; gap: 0.25rem; padding-top: 1rem; border-top: 1px solid var(--line); text-decoration: none; }
.pager a.ol { text-align: right; }
.pager .t { font: 600 1.0625rem/1.35 var(--sans); }
.pager a:hover .t { text-decoration: underline; }

/* ---------------------------------------------------------------- index */
.plist h1 { margin-top: 0.75rem; font: 800 clamp(3rem, 10vw, 7rem)/0.9 var(--display); letter-spacing: -0.045em; }
.plist .lede { margin-top: 1.25rem; max-width: 52ch; }
.totals { margin-top: clamp(2rem, 5vh, 3rem); }
/* the header: a fixed-shape dark panel (no layout shift), the still underneath, the canvas fades in over it
   once header.js is printing. Dark in both themes: it is a picture of a print bed. */
.hdr { position: relative; margin-top: clamp(2rem, 5vh, 3rem); aspect-ratio: 21 / 9; overflow: hidden; border: 1px solid var(--line); background: #0c0d12; }
.hdr img, .hdr canvas { position: absolute; inset: 0; display: block; width: 100%; height: 100%; object-fit: cover; }
.hdr canvas { opacity: 0; transition: opacity 0.5s; }
.hdr.live canvas { opacity: 1; }
@media (max-width: 40rem) { .hdr { aspect-ratio: 16 / 9; } }
@media (prefers-reduced-motion: reduce) { .hdr canvas { transition: none; } }
.entries-list { margin-top: clamp(2rem, 5vh, 3.5rem); border-top: 1px solid var(--line); }
.entry { display: grid; grid-template-columns: repeat(12, minmax(0, 1fr)); gap: 1rem var(--gap); padding-block: clamp(1.25rem, 3vh, 2rem); border-bottom: 1px solid var(--line); }
.entry > * { grid-column: 1 / -1; min-width: 0; }
.entry .txt { display: grid; gap: 0.6rem; align-content: start; }
.entry h2 { font: 700 clamp(1.5rem, 3vw, 2.25rem)/1.1 var(--display); letter-spacing: -0.025em; text-wrap: balance; }
.entry h2 a { text-decoration: none; }
.entry h2 a:hover { text-decoration: underline; text-decoration-thickness: 2px; }
.entry .dek { max-width: 52ch; color: var(--mid); text-wrap: pretty; }
/* units are case-sensitive (MM is megametres), so this line is not uppercased like the other labels.
   The dot rides on the item before it, so a wrapped line never starts with one. */
.fl { display: flex; flex-wrap: wrap; gap: 0.25rem 0.6em; font: 500 0.8125rem/1.6 var(--mono); letter-spacing: 0.02em; color: var(--mut); font-variant-numeric: tabular-nums; }
.fl li { white-space: nowrap; }
.fl li:not(:last-child)::after { content: "·"; padding-left: 0.6em; }
@media (min-width: 53.75rem) {
  .entry .thumb { grid-column: 1 / 5; }
  .entry .txt { grid-column: 5 / -1; }
}

/* ---------------------------------------------------------------- the story
   18 px Plex on a 40rem column is ~70 characters a line. Chapter heads are small: they mark a turn
   in the story, they are not sections of a report. */
.story { margin-top: 2.25rem; }
.story > p { font-size: 1.125rem; line-height: 1.7; }
.story > p + p { margin-top: 1.1rem; }
.story > h2 { margin-top: 2.75rem; font: 650 1.375rem/1.25 var(--display); letter-spacing: -0.01em; }
.story > h2 + p { margin-top: 0.75rem; }
.story > .fig { margin-top: 1.75rem; }
.story > .fig + p { margin-top: 1.75rem; }
/* Side notes: the measured detail behind a paragraph, for whoever wants it. Same treatment at every
   width (top hairline, mono label). From 72rem the note and its paragraph share one grid row, so the
   note sits level with the text it explains and anything after starts below both. */
.withnote { margin-top: 1.1rem; }
.withnote .pt > p { font-size: 1.125rem; line-height: 1.7; }
.withnote .pt > p + p { margin-top: 1.1rem; }
.sn { margin-top: 1rem; padding-top: 0.6rem; border-top: 1px solid var(--line); font-size: 0.9375rem; line-height: 1.6; color: var(--mid); }
.sn .label { margin-bottom: 0.3rem; }
.sn p + p { margin-top: 0.5rem; }
@media (min-width: 72rem) {
  .withnote { display: grid; grid-template-columns: 40rem 15rem; column-gap: 3.5rem; width: calc(40rem + 18.5rem); align-items: start; }
  .withnote .sn { margin-top: 0.35rem; font-size: 0.875rem; }
}
.story > .withnote + p, .story > p + .withnote, .story > .withnote + .withnote { margin-top: 1.1rem; }
.story > h2 + .withnote { margin-top: 0.75rem; }

/* The short version, after the story: one line for each thing that went wrong and what fixed it. */
.recap { margin-top: 3rem; padding-top: 1.25rem; border-top: 1px solid var(--line); }
.recap h2 { margin-top: 0; font-size: 1.125rem; }
.recap ol { margin-top: 0.75rem; counter-reset: rc; }
.recap li { counter-increment: rc; display: grid; grid-template-columns: 2rem minmax(0, 1fr); gap: 0.1rem 0.5rem; padding-block: 0.55rem; border-bottom: 1px solid var(--line); font-size: 0.9375rem; }
.recap li::before { content: counter(rc, decimal-leading-zero); grid-row: span 2; font: 500 0.8125rem/1.7 var(--mono); color: var(--mut); }
.recap .pb { color: var(--ink); }
.recap .fx { color: var(--mid); }
.recap .fx::before { content: "Fix: "; color: var(--mut); }
.recap a { display: contents; text-decoration: none; color: inherit; }
.recap a:hover .pb { color: var(--signal); text-decoration: underline; }
.facts-note { margin-top: 1rem; }
.story > h2 { scroll-margin-top: calc(var(--head) + 3.25rem); }
.recap { scroll-margin-top: calc(var(--head) + 3.25rem); }

/* ---------------------------------------------------------------- credits
   Built on (in a post) and Inspirations (on the index): the same row, a link to the original, then
   designer · site · licence in mono, then one line in the story voice. */
.credits { margin-top: 3rem; padding-top: 1.25rem; border-top: 1px solid var(--line); }
.credits h2 { margin-top: 0; font-size: 1.125rem; }
.credits ul { margin-top: 0.75rem; }
.credits li, .inspo li { display: grid; gap: 0.15rem; padding-block: 0.6rem; border-bottom: 1px solid var(--line); }
.ct { font-weight: 600; text-underline-offset: 0.2em; }
.cm { font: 400 0.75rem/1.6 var(--mono); color: var(--mut); }
.cm a { color: inherit; }
.cw { font-size: 0.9375rem; color: var(--mid); text-wrap: pretty; }
/* on the entries' own grid: heading in the image track, rows in the text track */
.inspo { display: grid; grid-template-columns: repeat(12, minmax(0, 1fr)); gap: 1rem var(--gap); margin-top: clamp(2.5rem, 6vh, 4rem); }
.inspo > * { grid-column: 1 / -1; min-width: 0; }
.inspo h2 { font: 650 1.375rem/1.25 var(--display); letter-spacing: -0.01em; }
.inspo .cap { margin-top: 0.4rem; max-width: 62ch; }
.inspo > ul { border-top: 1px solid var(--line); }
@media (min-width: 53.75rem) { .inspo .ih { grid-column: 1 / 5; } .inspo > ul { grid-column: 5 / -1; } }
.ct svg { display: inline; margin-left: 0.25em; width: 0.85em; height: 0.85em; vertical-align: -0.05em; fill: none; stroke: currentColor; stroke-width: 1.8; stroke-linecap: round; stroke-linejoin: round; }
.recap li:last-child { border-bottom: 0; }

@media print {
  .crumb, .pager, .draft-note { display: none; }
  .fig.wide { width: 100%; }
}
