/* schieldd. One wall of post office boxes seen head on, with a brass rail of readings beside it.
   Built 50 on 50 from the brief's section 4 (the post office, the inks, the two faces, the wax
   seal) and from his CGA screen (the two column split at 58.2 / 1.9 / 39.9, the framed boxes at
   25.1 / 9.0 / 52.8 of the pane's height, the labels cut into the pane's rule, values flush right
   with a unit letter welded on, the double spaced prompted list, the ordered dither).

   Every surface here is a raster drawn by tools/draw.mjs or by public/wall.js. There is no <svg>
   on this site and no CSS rectangle standing in for an object: a box is the brass frame raster,
   nine-sliced, and a key is the brass key raster, nine-sliced. */

@font-face { font-family: Playfair; src: url("/fonts/playfair-900.woff2") format("woff2"); font-weight: 900; font-display: swap; }
@font-face { font-family: Playfair; src: url("/fonts/playfair-700.woff2") format("woff2"); font-weight: 700; font-display: swap; }
@font-face { font-family: Franklin; src: url("/fonts/franklin-400.woff2") format("woff2"); font-weight: 400; font-display: swap; }
@font-face { font-family: Franklin; src: url("/fonts/franklin-600.woff2") format("woff2"); font-weight: 600; font-display: swap; }
@font-face { font-family: Plexmono; src: url("/fonts/plexmono-400.woff2") format("woff2"); font-weight: 400; font-display: swap; }
@font-face { font-family: Plexmono; src: url("/fonts/plexmono-600.woff2") format("woff2"); font-weight: 600; font-display: swap; }

:root {
  /* the inks, one meaning each, mapped from his five onto the brief's five */
  --carbon: #15100B;        /* the field inside every box (his black, 49.17%) */
  --walnut: #3B2A1E;        /* the surround and the gutter (his blue, 11.16%) */
  --brass: #B5893C;         /* the metal, the prompts, the marks (his light grey, 16.77%) */
  --brass-dark: #5E4520;    /* the shaded half of the dither (his dark grey, 14.35%) */
  --brass-lit: #D9AE62;
  --manila: #E8D3A2;        /* every rule and every glyph (his white, 8.55%) */
  --manila-dim: #BFAE86;    /* the same ink, quieter: a label beside its value */
  --frost: #DDE3E6;         /* a window that is LIT, and nothing else */
  --wax: #8E1B1B;           /* the seal, and nothing else: a fill, never a glyph */
  --wax-lit: #B8322B;
  --seat: #2A1F12;

  /* one scale, nothing off it (his order 2026-11-02); the floor is 14, this is a dark theme */
  /* the floor is 16: density comes from spacing, not from small type */
  --t-16: 16px; --t-20: 20px; --t-24: 24px; --t-32: 32px; --t-48: 48px;
  --s-4: 4px; --s-8: 8px; --s-12: 12px; --s-16: 16px; --s-24: 24px; --s-32: 32px; --s-48: 48px;

  /* one container: every block on this page ends on the same right line */
  --page: 1120px;
  --pad: 24px;

  /* his split, measured: 58.2 / 1.9 / 39.9 of the content box */
  --col-pane: 58.2%;
  --col-gap: 1.9%;
  --col-rail: 39.9%;

  --face-display: Playfair, "Playfair Display", Georgia, serif;
  --face-text: Franklin, "Libre Franklin", system-ui, sans-serif;
  --face-data: Plexmono, "IBM Plex Mono", ui-monospace, monospace;
}

* { box-sizing: border-box; }

html { background: var(--walnut); }
body {
  margin: 0;
  background: var(--walnut);
  color: var(--manila);
  font: 400 var(--t-16)/1.6 var(--face-text);
  -webkit-font-smoothing: antialiased;
  font-synthesis: none;
}

::selection { background: var(--brass); color: var(--carbon); }

a { color: var(--manila); }
a:focus-visible, button:focus-visible, input:focus-visible, summary:focus-visible, [tabindex]:focus-visible {
  outline: 3px solid var(--brass-lit);
  outline-offset: 2px;
}

.skip {
  position: absolute; left: -9999px; top: var(--s-8);
  background: var(--manila); color: var(--carbon);
  padding: var(--s-12) var(--s-16); font: 600 var(--t-16)/1 var(--face-text);
  z-index: 20;
}
.skip:focus { left: var(--s-16); }

.page {
  max-width: var(--page);
  margin: 0 auto;
  padding: var(--s-32) var(--pad) var(--s-48);
}

/* ------------------------------------------------------------------ the brass plaque
   The masthead above the wall, which is where the brief puts the lettering and the links.
   It is the plaque raster, nine-sliced, never a bar and never a <header> element. */
.plaque {
  background: var(--img-brushed) 0 0 repeat;
  display: grid;
  grid-template-columns: 1fr auto;
  align-items: center;
  gap: var(--s-24);
  border-style: solid;
  border-width: 14px;
  border-image: var(--img-plaque) 56 / 14px / 0 stretch;
  padding: var(--s-16) var(--s-24);
  margin-bottom: var(--s-24);
}
.plaque > div { min-width: 0; }
.plaque__name {
  margin: 0;
  font: 900 var(--t-48)/1.0 var(--face-display);
  letter-spacing: -0.015em;
  color: var(--carbon);
}
.plaque__ticker {
  font: 600 var(--t-16)/1 var(--face-data);
  color: var(--carbon);
  letter-spacing: 0.04em;
}
.plaque__line {
  margin: var(--s-4) 0 0;
  font: 400 var(--t-16)/1.4 var(--face-text);
  color: var(--carbon);
}
.plaque__links { display: flex; align-items: center; gap: var(--s-12); }

/* ------------------------------------------------------------------ keys (every button)
   The brass key raster, nine-sliced, three real states. A dead key is a DIFFERENT SURFACE,
   never the live surface at a lower opacity. */
.key {
  background: var(--img-brushed) 0 0 repeat;
  display: inline-flex; align-items: center; justify-content: center; gap: var(--s-8);
  min-height: 48px;
  padding: 0 var(--s-24);
  border: 0;
  border-style: solid;
  border-width: 10px;
  border-image: var(--img-key) 40 / 10px / 0 stretch;
  color: var(--carbon);
  font: 600 var(--t-16)/1 var(--face-text);
  text-decoration: none;
  white-space: nowrap;
  cursor: pointer;
  transition: transform 0.08s ease-out, filter 0.18s ease-out;
}
.key:hover { filter: brightness(1.1); }
.key:active { border-image: var(--img-key-press) 40 / 10px / 0 stretch; background-color: #7A5C28; transform: translateY(1px); }
.key[aria-disabled="true"], .key:disabled {
  background: var(--img-field) 0 0 repeat;
  border-image: var(--img-key-dead) 40 / 10px / 0 stretch;
  color: var(--manila-dim);
  cursor: not-allowed;
  pointer-events: none;
}
.key--small { min-height: 48px; min-width: 48px; padding: 0 var(--s-12); }
.key__mark { width: 20px; height: 20px; display: block; object-fit: contain; }
.key--mark-dex .key__mark { width: 22px; height: 22px; }
.key--wide { width: 100%; }

/* ------------------------------------------------------------------ the split: his two columns */
.split {
  display: grid;
  grid-template-columns: var(--col-pane) var(--col-rail);
  gap: var(--col-gap);
  align-items: stretch;
}

/* ------------------------------------------------------------------ a framed box
   Every box on this site is the brass frame raster, nine-sliced. The inner padding is set on
   the BOX, never on the text: 24 px sides, 16 px top and bottom, over the 8 px frame. */
.box {
  background: var(--img-field) 0 0 repeat;
  border-style: solid;
  border-width: 8px;
  border-image: var(--img-frame) 32 / 8px / 0 stretch;
  padding: var(--s-16) var(--s-24);
  min-width: 0;
}
.box__head {
  display: flex; align-items: baseline; justify-content: space-between; gap: var(--s-12);
  margin: 0 0 var(--s-12);
  padding-bottom: var(--s-8);
  font: 600 var(--t-16)/1.2 var(--face-text);
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--manila-dim);
  position: relative;
}
.box__head::after {
  content: ""; position: absolute; left: 0; right: 0; bottom: 0; height: 1px;
  background: var(--brass-dark);
}

/* ------------------------------------------------------------------ the pane
   His left pane: a square raster inside a rule, with a label cut into the rule at the top and
   another at the foot. The foot rule is also the pot bar: it fills with brass as the pot fills. */
.pane {
  position: relative;
  margin: var(--s-16) 0;
  background: var(--img-field) 0 0 repeat;
  border-style: solid;
  border-width: 8px;
  border-image: var(--img-frame) 32 / 8px / 0 stretch;
  padding: var(--s-16);
  display: flex;
  flex-direction: column;
  gap: var(--s-12);
}
.pane__label {
  position: absolute;
  left: 50%;
  transform: translateX(-50%);
  margin: 0;
  background: var(--walnut);
  padding: var(--s-12) var(--s-24);
  white-space: nowrap;
  font: 600 var(--t-16)/1.2 var(--face-data);
  letter-spacing: 0.06em;
  color: var(--manila);
  z-index: 2;
}
.pane__label--top { top: -22px; }
.pane__label--foot { bottom: -22px; }
.pane__label b { color: var(--brass-lit); font-weight: 600; }
.pane__label i { font-style: normal; color: var(--brass-lit); }  /* his > and < brackets, lit so they clear 4.5 on walnut */

.pane__view {
  position: relative;
  flex: 1 1 auto;
  min-height: 420px;
  background: var(--img-field) 0 0 repeat;
}
.pane__view > canvas { position: absolute; inset: 0; display: block; width: 100%; height: 100%; }

/* the pot bar: his foot rule, filling from the left */
.pane__pot {
  position: absolute;
  left: 8px; right: 8px; bottom: 4px;
  height: 4px;
  background: var(--seat);
}
.pane__pot i { display: block; height: 100%; width: 0; background: var(--brass); transition: width 0.28s ease-out; }

/* the postmark struck over the wall: the live reading sits in its flat middle disc */
.postmark {
  position: absolute;
  left: var(--s-32);
  top: 56px;
  z-index: 2;
  width: 32%;
  max-width: 244px;
  aspect-ratio: 1 / 1;
  background: var(--img-postmark) center / contain no-repeat;
  display: grid;
  place-items: center;
  pointer-events: none;
}
.postmark__read {
  width: 46%;
  margin: 0;
  text-align: center;
  display: grid;
  gap: 2px;
}
.postmark__read span { font: 600 var(--t-16)/1.1 var(--face-data); color: var(--brass-lit); }
.postmark__read strong { font: 900 var(--t-32)/1.0 var(--face-display); color: var(--manila); }
.postmark__read small { font: 400 var(--t-16)/1.1 var(--face-data); color: var(--manila-dim); }

/* ------------------------------------------------------------------ the rail
   His three boxes, at his shares of the pane's height: 25.1, 9.0 and 52.8 per cent, the last
   split in two by one gap so the money and the doors are not one list. */
.rail {
  display: grid;
  grid-template-rows: auto auto auto minmax(min-content, 1fr);
  gap: var(--col-gap);
  min-width: 0;
}
.rail > .box { display: flex; flex-direction: column; min-width: 0; }

/* a label and its value: the ONE way a number is printed on this site */
.row {
  display: flex; align-items: baseline; justify-content: space-between; gap: var(--s-12);
  padding: 6px 0;
  position: relative;
  min-width: 0;
}
.row + .row::before {
  content: ""; position: absolute; left: 0; right: 0; top: 0; height: 1px;
  background: #241B10;
}
.row__name { font: 400 var(--t-16)/1.3 var(--face-text); color: var(--manila-dim); min-width: 0; }
.row__value {
  font: 600 var(--t-16)/1.2 var(--face-data);
  color: var(--manila);
  white-space: nowrap;
  font-variant-numeric: tabular-nums;
}
/* his unit letter, welded on to the value */
.row__value u { text-decoration: none; color: var(--brass); }
.row--live .row__name::before {
  content: "\2192\00a0" / "";                        /* his marker arrow on the live row */
  color: var(--brass-lit);
}
.row--live .row__name { color: var(--manila); }

/* the two value line of his status box */
.pair { display: flex; align-items: baseline; justify-content: space-between; gap: var(--s-12); }
.pair span { font: 600 var(--t-16)/1.2 var(--face-data); color: var(--manila); font-variant-numeric: tabular-nums; }
.pair span u { text-decoration: none; color: var(--brass); }
.note-centre {
  margin: var(--s-4) 0 0;
  text-align: center;
  font: 400 var(--t-16)/1.3 var(--face-text);
  color: var(--manila-dim);
}

/* ------------------------------------------------------------------ the prompted list
   His command rail: one blue prompt per line, double spaced, with one centred statement that
   carries no prompt because it is not a verb. */
.prompted { list-style: none; margin: 0; padding: 0; display: grid; align-content: start; }
.prompted li { margin: 0; }
.prompted a, .prompted span.prompted__flat {
  display: flex; align-items: center; gap: var(--s-8);
  min-height: 44px;
  flex: none;
  padding: 0 var(--s-8);
  text-decoration: none;
  font: 400 var(--t-16)/1.2 var(--face-text);
  color: var(--manila);
  transition: background 0.12s ease-out, color 0.12s ease-out;
}
.prompted a::before {
  content: ">" / "";
  font: 600 var(--t-16)/1 var(--face-data);
  color: var(--brass);
  flex: none;
}
.prompted a:hover { background: #241B10; }
.prompted a[aria-current="page"] {
  background: var(--manila);
  color: var(--carbon);
  font-weight: 600;
}
.prompted a[aria-current="page"]::before { content: "\2192" / ""; color: var(--carbon); }
.prompted__flat { justify-content: center; color: var(--manila-dim); letter-spacing: 0.12em; text-transform: uppercase; font-size: var(--t-16); }

/* ------------------------------------------------------------------ the journal, full width */
.journal { margin-top: var(--s-24); }
.journal__scroll { overflow-x: auto; }
.jrow {
  display: grid;
  grid-template-columns: 56px 1fr 1fr 1fr minmax(120px, 1.2fr);
  gap: var(--s-16);
  align-items: baseline;
  padding: var(--s-12) var(--s-8);
  position: relative;
  min-width: 640px;
}
.jrow + .jrow::before {
  content: ""; position: absolute; left: 0; right: 0; top: 0; height: 1px; background: #241B10;
}
.jrow--head { color: var(--manila-dim); font: 600 var(--t-16)/1.2 var(--face-text); letter-spacing: 0.1em; text-transform: uppercase; }
.jrow--head::after { content: ""; position: absolute; left: 0; right: 0; bottom: 0; height: 1px; background: var(--brass-dark); }
.jrow b { font: 600 var(--t-16)/1.2 var(--face-data); color: var(--manila); font-variant-numeric: tabular-nums; }
.jrow b u { text-decoration: none; color: var(--brass); }
.jrow a { font: 400 var(--t-16)/1.3 var(--face-data); color: var(--brass-lit); word-break: break-all; }
.empty {
  margin: 0; padding: var(--s-24) var(--s-8);
  font: 400 var(--t-16)/1.6 var(--face-text); color: var(--manila-dim);
}

/* ------------------------------------------------------------------ the contract */
.ca {
  display: block;
  margin: 0 0 var(--s-12);
  padding: var(--s-12) var(--s-16);
  background: #0E0A06;
  font: 400 var(--t-16)/1.5 var(--face-data);
  color: var(--manila);
  word-break: break-all;
  overflow-wrap: anywhere;
  min-width: 0;
  user-select: all;
}
.ca--empty { color: var(--manila-dim); user-select: none; }
.ca-actions { display: flex; gap: var(--s-8); flex-wrap: wrap; margin-top: auto; }
.said { font: 400 var(--t-16)/1.4 var(--face-text); color: var(--brass-lit); margin: var(--s-8) 0 0; min-height: 20px; }

/* ------------------------------------------------------------------ forms */
.field { display: grid; gap: var(--s-8); margin-bottom: var(--s-16); }
.field label { font: 600 var(--t-16)/1.2 var(--face-text); letter-spacing: 0.08em; text-transform: uppercase; color: var(--manila-dim); }
.field input, .field textarea {
  width: 100%;
  min-height: 48px;
  padding: var(--s-12) var(--s-16);
  background: #0E0A06;
  border: 1px solid var(--brass-dark);
  color: var(--manila);
  font: 400 var(--t-16)/1.5 var(--face-data);
  overflow-wrap: anywhere;
}
.field input::placeholder { color: #7A6B4E; }
.field input:focus { border-color: var(--brass); }
.hint { margin: 0; font: 400 var(--t-16)/1.5 var(--face-text); color: var(--manila-dim); }
.verdict { margin: var(--s-8) 0 0; font: 400 var(--t-16)/1.5 var(--face-text); min-height: 22px; }
.verdict--ok { color: var(--brass-lit); }
.verdict--no { color: #E8857C; }                 /* wax is a fill, never a glyph: this is its lit relative */

/* ------------------------------------------------------------------ prose blocks */
.prose { max-width: 62ch; }
.prose h2 { margin: var(--s-32) 0 var(--s-12); font: 700 var(--t-24)/1.2 var(--face-display); color: var(--manila); }
.prose h3 { margin: var(--s-24) 0 var(--s-8); font: 600 var(--t-16)/1.3 var(--face-text); letter-spacing: 0.06em; text-transform: uppercase; color: var(--manila-dim); }
.prose p { margin: 0 0 var(--s-12); font: 400 var(--t-16)/1.65 var(--face-text); }
.prose ul { margin: 0 0 var(--s-12); padding-left: var(--s-24); }
.prose li { margin: 0 0 var(--s-8); font: 400 var(--t-16)/1.65 var(--face-text); }
code, .prose code { font: 400 var(--t-16)/1.5 var(--face-data); color: var(--brass-lit); }

/* the four steps: one raster per step, its words under it, every card the same height */
.steps { display: grid; grid-template-columns: repeat(4, 1fr); gap: var(--s-16); margin-top: var(--s-16); }
.step { display: grid; grid-template-rows: auto auto 1fr; gap: var(--s-8); }
.step__plate { width: 100%; aspect-ratio: 2 / 1; background-size: cover; background-position: center; }
.step h3 { margin: 0; font: 600 var(--t-16)/1.3 var(--face-text); color: var(--manila); letter-spacing: 0; text-transform: none; }
.step p { margin: 0; font: 400 var(--t-16)/1.55 var(--face-text); color: var(--manila-dim); }

/* ------------------------------------------------------------------ the seal, the signature act */
.sealing { display: grid; place-items: center; gap: var(--s-16); padding: var(--s-24) 0; }
.sealing__disc {
  width: 160px; height: 160px;
  background: var(--img-seal) center / contain no-repeat;
  transition: transform 0.28s cubic-bezier(.2,.9,.3,1.3);
}
.sealing--struck .sealing__disc { background-image: var(--img-seal-stamped); transform: scale(1.04); }
.sealing__say { font: 600 var(--t-16)/1.3 var(--face-text); color: var(--manila); text-align: center; }

/* ------------------------------------------------------------------ widths
   Measured at 1920 / 1440 / 1280 / 1024 / 768 / 390 by tools/review.mjs. */
@media (max-width: 1023px) {
  .split { grid-template-columns: 1fr; gap: var(--s-24); }
  .rail { grid-template-rows: auto auto auto auto; gap: var(--s-24); }
  .steps { grid-template-columns: repeat(2, 1fr); }
  .postmark { width: 42%; }
}
@media (max-width: 680px) {
  :root { --pad: 16px; }
  .plaque { grid-template-columns: 1fr; gap: var(--s-12); padding: var(--s-12) var(--s-24); }
  .plaque__name { font-size: var(--t-32); }
  .plaque__line { font-size: var(--t-16); }
  .plaque__links { gap: var(--s-8); flex-wrap: nowrap; }
  .plaque__links .key { flex: 1 1 auto; min-width: 0; padding: 0 var(--s-16); white-space: normal; }
  .plaque__links .key--small { flex: 0 0 48px; padding: 0; }
  .pane__view { min-height: 380px; }
  .steps { grid-template-columns: 1fr; }
  .postmark { position: static; width: 208px; max-width: 72%; margin: 0 auto var(--s-12); }
  .postmark__read { width: 52%; }
  .postmark__read strong { font-size: var(--t-24); }
  .jrow { grid-template-columns: 44px 1fr 1fr; min-width: 0; }
  .jrow > :nth-child(4), .jrow > :nth-child(5) { grid-column: 1 / -1; }
}

@media (prefers-reduced-motion: reduce) {
  * { transition-duration: 0.001s !important; animation: none !important; }
}

/* ------------------------------------------------------------------ the inner panes
   The wall pane holds a raster edge to edge; the other panes hold reading and controls, so
   they carry the same inner padding every box on this site carries. */
.pane__view--pad { padding: var(--s-24); display: flex; flex-direction: column; }
.pane__view--pad > .hint--after:last-child { margin-top: auto; padding-top: var(--s-16); }
.pane__view--tall { padding-top: var(--s-48); padding-bottom: var(--s-48); }
.pane__view--pad canvas { width: 100%; height: auto; display: block; }
.hint--after { margin-top: var(--s-12); }
.hint--middle { text-align: center; max-width: 46ch; margin: var(--s-16) auto 0; }
.ca-actions--top { margin-top: var(--s-16); }
.ca-actions--middle { justify-content: center; margin-top: var(--s-24); }
.ca--top { margin-top: var(--s-16); }
.rows--top { margin-top: var(--s-16); }
.steps--two { grid-template-columns: repeat(2, 1fr); }
.subhead {
  margin: var(--s-24) 0 var(--s-8);
  font: 600 var(--t-16)/1.2 var(--face-text);
  letter-spacing: 0.1em; text-transform: uppercase; color: var(--manila-dim);
}
.sealing__disc--lost { background-image: var(--img-envelope-open); }
.docs { margin-top: var(--s-24); }
@media (max-width: 680px) { .steps--two { grid-template-columns: 1fr; } }

/* ------------------------------------------------------------------ filling the pane
   The pane is as tall as the rail beside it, so a short page would leave a band of nothing at
   its foot. The content of a form pane is a column that fills the pane and pushes its closing
   block to the bottom, and the steps spread instead of stacking at the top. */
.pane__view--pad > div:not(.steps) { display: flex; flex-direction: column; flex: 1 1 auto; min-height: 0; }
.pane__view--pad .ca-actions--top { margin-top: auto; }
.steps--two { flex: 1 1 auto; align-content: stretch; grid-auto-rows: 1fr; }
.sealing { flex: 0 0 auto; }

/* A display rule outweighs the `hidden` attribute, so the closed half of a page keeps taking up
   room: `#opened` was adding 500 px of nothing under the shut door. Say it once, for the page. */
[hidden] { display: none !important; }

/* Under about 420 px the primary key cannot hold its label AND a full em of padding beside two
   mark keys, and the padding is the rule: it takes a row of its own and the marks sit under it. */
@media (max-width: 420px) {
  .plaque__links { flex-wrap: wrap; }
  .plaque__links .key:first-child { flex: 1 0 100%; }
}
