/* websterdivision.com — the calm centered layout of v1 with the manual's red,
   hatch and notice box. The homepage, the 404 and HQ's section pages use this.
   Colors, type sizes and spacing come from /tokens.css; the parts every page
   shares (page base, logo, hatch, ticks, eyebrow, rule, footer) from /base.css. */

:root {
  /* A figure's largest width: the rink at 60% of the window height, in its
     212:97 drawing frame (rink.js FRAME_W x FRAME_H: the rink plus room for
     the dimension lines), plus the figure's 16px padding each side. */
  --figure-max: calc(60svh * 212 / 97 + 32px);
}

/* ---- Top bar: red mark left, hatch strip right ---- */
.top {
  position: relative;
  z-index: 1;
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: calc(var(--space-6) + env(safe-area-inset-top)) clamp(var(--gutter), 4vw, var(--space-12)) 0;
}

/* Inline SVG diagrams (Fig. 404) color their parts with these, since SVG
   fill and stroke attributes can't take var(): f- for fill, s- for stroke. */
.f-ice { fill: var(--ice); }
.f-red { fill: var(--red); }
.f-steel { fill: var(--steel); }
.f-night { fill: var(--night); }
.s-ice { stroke: var(--ice); }
.s-red { stroke: var(--red); }

/* ---- Hero ---- */
.hero {
  position: relative;
  z-index: 1;
  flex: 1;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  text-align: center;
  padding: var(--space-12) var(--gutter);
}

.eyebrow {
  margin: 0 0 var(--space-5);
}

.wordmark {
  margin: 0;
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  column-gap: 0.3em; /* tuned: the word space, in em so it scales with the wordmark */
  font-weight: 400;
  font-size: var(--text-display);
  line-height: var(--leading-none);
  text-transform: uppercase;
}

.rule {
  margin: var(--space-8) 0 var(--space-12);
}

/* ---- Client demo box ---- */
.notice {
  width: min(100%, var(--width-xs));
  margin-right: var(--space-3); /* room for the offset shadow so it stays centered visually */
  padding: var(--space-6) var(--space-6) var(--space-6);
  background: var(--surface-paper);
  color: var(--ink-on-paper);
  text-align: left;
  box-shadow: 10px 10px 0 var(--accent);
}

.notice-head {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  margin-bottom: var(--space-3);
}

.notice-icon {
  width: 28px;
  height: 26px;
  flex: 0 0 auto;
  color: var(--accent-text);
}

.notice h2 {
  margin: 0;
  font-weight: 700;
  font-size: var(--text-heading);
  letter-spacing: var(--track-entry);
  text-transform: uppercase;
  color: var(--accent-text);
}

.notice p {
  margin: 0 0 var(--space-5);
  font-size: var(--text-label);
  line-height: var(--leading-body);
}

.cta {
  display: inline-flex;
  align-items: center;
  gap: var(--space-3);
  padding: var(--space-3) var(--space-5);
  background: var(--accent);
  color: var(--on-accent);
  font-weight: 700;
  font-size: var(--text-label);
  letter-spacing: var(--track-caps);
  text-transform: uppercase;
  text-decoration: none;
  transition: background var(--dur-fade), transform var(--dur-fast);
}

.cta:hover,
.cta:focus-visible {
  background: var(--surface);
}

.cta:active {
  transform: translate(2px, 2px);
}

/* ---- Entrance ---- */
.hero > * {
  opacity: 0;
  transform: translateY(12px);
  animation: rise 0.9s var(--ease-out) forwards;
}
.hero > :nth-child(2) { animation-delay: 0.1s; }
.hero > :nth-child(3) { animation-delay: 0.25s; }
.hero > :nth-child(4) { animation-delay: 0.4s; }

@keyframes rise {
  to {
    opacity: 1;
    transform: none;
  }
}

@media (prefers-reduced-motion: reduce) {
  .hero > * {
    animation: none;
    opacity: 1;
    transform: none;
  }
}

/* ---- Fig. 1, the rink panel, below the demo box ---- */
.stage {
  width: min(100%, var(--width-2xl));
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  justify-items: center;
  gap: var(--space-16);
}

.figure {
  position: relative;
  justify-self: center;
  width: 100%;
  /* Big, but never taller than ~60% of the window (short laptop screens). */
  max-width: var(--figure-max);
  margin: 0;
  padding: var(--space-4) var(--space-4) var(--space-3);
  text-align: left;
  background: var(--surface); /* solid plate: the field never shows through the game */
}

#rink {
  grid-area: rink;
  display: block;
  width: 100%;
  aspect-ratio: 212 / 97;
  touch-action: none;
  cursor: crosshair;
}

#rink.aiming {
  cursor: grabbing;
}

.figure figcaption {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: var(--space-1) var(--space-4);
  margin-top: var(--space-3);
  font-size: var(--text-label);
  letter-spacing: var(--track-label);
  text-transform: uppercase;
  color: var(--ink-muted);
}

/* Fig. 1's controls: a column left of the rink that mirrors the scoreboard on
   its right (same width, head, rule, rows and status line). Modes are numbered
   rows; the one in use is Ice and bold with its number red and a red
   underline, the others Steel. During a run the Shootout row's name becomes
   the clock (red for the last ten seconds). Row 04 is a redacted slot for the
   next mode. */
.ctrl-col {
  grid-area: ctrl;
  display: flex;
  flex-direction: column;
  min-width: 0;
  padding-right: var(--space-6);
  border-right: 1px solid var(--line);
}
/* Ten rows spread down the column exactly as the board's ten places are
   (.board-rows): every row is 28px, the board's row height, so the lines on
   both sides of the rink meet. */
.ctrl-rows {
  flex: 1;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  padding-top: var(--space-1);
}
.ctrl-rows > * {
  height: var(--fig-row);
}
.mode-btn,
.ctrl-row {
  display: grid;
  grid-template-columns: 30px minmax(0, 1fr) auto;
  align-items: center;
  width: 100%;
  padding: var(--space-1) 0;
  border: 0;
  border-bottom: 1px solid var(--line-faint);
  background: none;
  font: inherit;
  font-size: var(--text-label);
  letter-spacing: var(--track-entry);
  text-align: left;
  text-transform: uppercase;
  font-variant-numeric: tabular-nums;
  color: var(--ink-muted);
}
.mode-btn {
  grid-template-columns: 30px minmax(0, 1fr);
  cursor: pointer;
  transition: color var(--dur-fade);
}
.mode-btn .n {
  font-size: var(--text-label);
  font-weight: 700;
}
.mode-btn .name {
  justify-self: start;
}
.mode-btn[aria-pressed='true'] {
  color: var(--ink);
  font-weight: 700;
}
.mode-btn[aria-pressed='true'] .n {
  color: var(--accent-text);
}
.mode-btn[aria-pressed='true'] .name {
  text-decoration: underline;
  text-decoration-color: var(--accent);
  text-decoration-thickness: 2px;
  text-underline-offset: 5px;
}
.mode-btn:not(:disabled):hover,
.mode-btn:focus-visible,
.reset-btn:hover,
.reset-btn:focus-visible {
  color: var(--ink);
}
.mode-btn.late .name {
  color: var(--accent-text);
}
.mode-btn.soon {
  cursor: default;
}
.mode-btn.soon > * {
  opacity: var(--fade-disabled);
}
.redact {
  display: block;
  width: 72px;
  height: 0.8em;
  background: var(--ink);
}
/* The Tally heading: set like the column head, sitting on its rule. */
.ctrl-sub {
  display: flex;
  justify-content: space-between;
  align-items: flex-end;
  padding-bottom: var(--space-2);
  border-bottom: 1px solid var(--line-strong);
  font-size: var(--text-micro);
  font-weight: 400;
  letter-spacing: var(--track-caps);
  text-transform: uppercase;
  color: var(--ink-muted);
}
.ctrl-row {
  grid-template-columns: minmax(0, 1fr) auto;
}
.ctrl-row:last-child {
  border-bottom: 0;
}
.ctrl-row b {
  color: var(--ink);
  font-weight: 700;
}
.reset-btn {
  /* Invisible padding makes the click target 24px tall (WCAG 2.2) with no change in looks. */
  margin: calc(var(--space-2) * -1) 0;
  padding: var(--space-2) 0;
  border: 0;
  background: none;
  font: inherit;
  letter-spacing: inherit;
  text-transform: inherit;
  color: var(--ink-muted);
  cursor: pointer;
  transition: color var(--dur-fade);
}
/* The rink figure. */
.rink-wrap {
  position: relative;
  width: 100%;
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  justify-items: center;
}

/* Fig. 1 holds the rink between two matching columns, each the rink's height:
   the controls on the left, the scoreboard on the right. Being symmetrical,
   the rink sits in the middle of the page on its own. The figure grows by both
   columns (2 x 188px) so the rink keeps the size it had with one; it may run
   wider than the 1200px stage (a grid item wider than its track overflows
   both sides equally), never closer than 24px to the window's edges. At
   1100px and narrower both columns go under the rink, side by side; on phones, stacked. */
.figure.rink-fig {
  width: min(100vw - 48px, var(--figure-max) + 376px, 1388px); /* tuned: the rink plus its two columns, capped */
  max-width: none;
}
.rink-body {
  /* One row height for both columns, so the controls and the scoreboard
     line up row for row. */
  --fig-row: 28px;
  display: grid;
  grid-template-columns: 164px minmax(0, 1fr) 164px;
  grid-template-areas: 'ctrl rink board';
  gap: var(--space-6);
  align-items: stretch;
}
.board-col {
  grid-area: board;
  display: flex;
  flex-direction: column;
  min-width: 0;
  padding-left: var(--space-6);
  border-left: 1px solid var(--line);
}
.board-head {
  display: flex;
  justify-content: space-between;
  padding-bottom: var(--space-3);
  border-bottom: 1px solid var(--line-strong);
  font-size: var(--text-micro);
  font-weight: 400;
  letter-spacing: var(--track-caps);
  text-transform: uppercase;
  color: var(--ink-muted);
}
.board-rows {
  flex: 1;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  margin: 0;
  padding: var(--space-1) 0 0;
  list-style: none;
}
.board-rows li {
  height: var(--fig-row);
  display: grid;
  grid-template-columns: 30px minmax(0, 1fr) auto;
  align-items: center;
  padding: var(--space-1) 0;
  border-bottom: 1px solid var(--line-faint);
  font-size: var(--text-label);
  letter-spacing: var(--track-entry);
  text-transform: uppercase;
  font-variant-numeric: tabular-nums;
}
.board-rows li:last-child {
  border-bottom: 0;
}
.board-rows .n {
  font-size: var(--text-label);
  font-weight: 700;
  color: var(--accent-text);
}
.board-rows .g {
  text-align: right;
}
.board-rows li.empty {
  color: var(--ink-muted);
}
.board-rows li.empty > * {
  opacity: var(--fade-disabled);
}
.board-rows li.mine .name,
.board-rows li.entry .name,
.board-rows li.entry .g {
  color: var(--accent-text);
  font-weight: 700;
}
/* The initials slot: three letters typed straight into the row. */
.board-rows input {
  width: 4.5ch;
  margin: calc(var(--space-half) * -1 - 1px) 0; /* cancels the padding and underline: the row keeps its height */
  padding: var(--space-half) 0;
  border: 0;
  border-bottom: 1px solid var(--accent);
  background: none;
  font: inherit;
  font-weight: 700;
  letter-spacing: inherit;
  text-transform: uppercase;
  color: var(--accent-text);
  caret-color: var(--accent);
  outline: none;
}
/* The visitor's initials glitch: while they're typed, a faint signal fault
   that never quite settles, and a tear on every key (scoreboard.js); once
   saved, the name keeps glitching in bursts until the page is reloaded (a
   letter also scrambles now and then, scoreboard.js). */
.crt-in .board-rows input {
  animation: crt-entry 2.4s steps(1, end) infinite;
}
.crt-in .board-rows input.key {
  animation: crt-key 0.2s linear both;
}
.crt-in .board-rows li.mine .name {
  animation: crt-mine 3.4s steps(1, end) infinite;
}
.board-status {
  /* Room for three lines, the longest message ("25 goals · 1st · type your
     initials, Enter"): both columns' foot lines must stay the same height,
     or the rows above them drift out of line across the rink. */
  min-height: 4.35em;
  margin: var(--space-3) 0 0;
  font-size: var(--text-micro);
  line-height: var(--leading-body);
  letter-spacing: var(--track-caps);
  text-transform: uppercase;
  color: var(--ink-muted);
}
/* The controls' foot line keeps the line breaks in its text (rink.js). */
#mode-note {
  white-space: pre-line;
}
.board-status.red {
  color: var(--accent-text);
  font-weight: 700;
}

/* Fig. 1's two columns as CRT pictures with no set around them (the effect
   from the shelved scoreboard console, private/shelved/scoreboard-console/,
   minus its screen, bezel, glare and vignette, which boxed a column in and
   broke the mirror). Everything here darkens rather than lightens, so on the
   Night page it only shows where it crosses the text: soft scanlines
   (.crt-fx). (A dark band rolling down was tried: over the empty rows it
   showed as a box.) The text glows in its own
   color (Steel glows Steel, red glows red) and flickers now and then, each
   column on its own rhythm. crt.js powers them on (a bright line opening out)
   when they first scroll into view, and jolts one, with a red and white
   split: the board when the top ten changes, the controls when the mode does.
   Between those, each has small faults at random (see below). */
.crt {
  position: relative;
  /* Phosphor glow, in each text's own color (currentColor resolves where it's used). */
  --glow: 0 0 1px color-mix(in srgb, currentColor 45%, transparent), 0 0 6px color-mix(in srgb, currentColor 22%, transparent);
}
.crt-fx {
  position: absolute;
  inset: 0;
  z-index: 1;
  overflow: hidden;
  pointer-events: none;
  /* A soft line every 3px that shades the letters rather than cutting them.
     It's Night, blended with "darken" (each pixel keeps the darker of the
     two), so on the page it changes nothing and only the text, and its glow,
     gets lines. (Plain black lines darkened the page a level between the
     letters too, and each column showed as a slightly darker rectangle.) */
  background: repeating-linear-gradient(to bottom, transparent 0, color-mix(in srgb, var(--surface) 24%, transparent) 1px, transparent 2px, transparent 3px); /* tuned: scanline darkness, set by eye */
  mix-blend-mode: darken;
}
/* Over each column's content, not its rule beside the rink. */
.ctrl-col .crt-fx {
  right: 22px;
}
.board-col .crt-fx {
  left: 22px;
}
.crt-in {
  flex: 1;
  display: flex;
  flex-direction: column;
  min-height: 0;
  transform-origin: center;
  animation: crt-flicker 5s infinite;
}
/* Phosphor glow in each piece of text's own color. */
.crt-in * {
  text-shadow: var(--glow);
}
/* The two columns flicker out of step, as two separate screens would. */
.ctrl-col .crt-in {
  animation-delay: -2.3s;
}
/* Dark until it first comes into view, then it powers on. */
.crt.off .crt-in {
  opacity: 0;
  animation: none;
}
.crt.boot .crt-in {
  animation: crt-on 0.9s var(--ease-out) both, crt-flicker 5s 0.9s infinite;
}
.crt.zap .crt-in {
  animation: crt-zap 0.5s linear both;
}
/* The split, on the text itself (its glow is set there). */
.crt.zap .crt-in * {
  animation: crt-split 0.5s linear both;
}
/* Random faults (crt.js): a line tears sideways (--tear, 2-4px either way)
   with a faint split; a line's signal drops out for an instant; or the
   vertical hold slips and the whole picture hops. Each starts with a hard
   jump and eases back, like the jolt, only smaller. */
.crt-tear {
  animation: crt-tear-move 0.22s linear both;
}
.crt-tear * {
  animation: crt-tear-split 0.22s linear both;
}
.crt-drop {
  animation: crt-drop 0.16s linear both;
}
.crt.vhold .crt-in {
  animation: crt-vhold 0.24s linear both;
}
@keyframes crt-flicker {
  0%, 47%, 49%, 100% { opacity: 1; }
  48% { opacity: 0.93; }
  82% { opacity: 0.97; }
}
@keyframes crt-on {
  0% { transform: scale(0.5, 0.006); filter: brightness(4); opacity: 0.2; }
  35% { transform: scale(1, 0.006); filter: brightness(3); opacity: 1; }
  70% { transform: scale(1, 1.03); filter: brightness(1.6); }
  100% { transform: none; filter: none; }
}
/* A loss of sync, then the lock: two hard jumps (the picture tears
   sideways, skews, slips down as the vertical hold goes, flares; the text
   splits red and white, flipping sides), held with no in-between frames, then
   one smooth glide back into place, ending exactly on the normal picture so
   nothing snaps. (A version that jittered back and forth as it settled felt
   too jiggly.) The split is two shadows each way, so it narrows back into
   the glow rather than cutting off. */
@keyframes crt-zap {
  0% { transform: translate(3px, 0) skewX(-3deg); filter: brightness(1.6); animation-timing-function: steps(1, end); }
  9% { transform: translate(-2px, 2px) skewX(1.2deg) scaleY(0.99); filter: brightness(1.3); animation-timing-function: steps(1, end); }
  18% { transform: translate(1px, 0.5px); filter: brightness(1.15); animation-timing-function: var(--ease-out); }
  100% { transform: none; filter: none; }
}
@keyframes crt-split {
  0% { text-shadow: -2.5px 0 0 color-mix(in srgb, var(--accent) 65%, transparent), 2.5px 0 0 color-mix(in srgb, var(--ink) 40%, transparent); animation-timing-function: steps(1, end); }
  9% { text-shadow: 2px 0 0 color-mix(in srgb, var(--accent) 60%, transparent), -2px 0 0 color-mix(in srgb, var(--ink) 35%, transparent); animation-timing-function: steps(1, end); }
  18% { text-shadow: -1.2px 0 0 color-mix(in srgb, var(--accent) 45%, transparent), 1px 0 0 color-mix(in srgb, var(--ink) 28%, transparent); animation-timing-function: var(--ease-out); }
  100% { text-shadow: var(--glow); }
}
@keyframes crt-tear-move {
  0% { transform: translateX(var(--tear, 3px)); animation-timing-function: steps(1, end); }
  35% { transform: translateX(calc(var(--tear, 3px) * -0.35)); animation-timing-function: var(--ease-out); }
  100% { transform: none; }
}
@keyframes crt-tear-split {
  0% { text-shadow: -1.5px 0 0 color-mix(in srgb, var(--accent) 50%, transparent), 1.5px 0 0 color-mix(in srgb, var(--ink) 30%, transparent); animation-timing-function: steps(1, end); }
  35% { text-shadow: 1px 0 0 color-mix(in srgb, var(--accent) 35%, transparent), -1px 0 0 color-mix(in srgb, var(--ink) 20%, transparent); animation-timing-function: var(--ease-out); }
  100% { text-shadow: var(--glow); }
}
@keyframes crt-drop {
  0% { opacity: 0.35; animation-timing-function: steps(1, end); }
  30% { opacity: 0.85; animation-timing-function: steps(1, end); }
  55% { opacity: 0.3; animation-timing-function: ease-out; }
  100% { opacity: 1; }
}
@keyframes crt-vhold {
  0% { transform: translateY(2px); filter: brightness(1.1); animation-timing-function: steps(1, end); }
  30% { transform: translateY(-1px); animation-timing-function: var(--ease-out); }
  100% { transform: none; filter: none; }
}
@keyframes crt-entry {
  0%, 33%, 72%, 100% { transform: none; text-shadow: var(--glow); }
  30% { text-shadow: -1.5px 0 0 color-mix(in srgb, var(--ink) 45%, transparent), 1.5px 0 0 color-mix(in srgb, var(--accent) 60%, transparent); }
  68% { transform: translateX(1px); text-shadow: 1px 0 0 color-mix(in srgb, var(--ink) 40%, transparent), -1px 0 0 color-mix(in srgb, var(--accent) 50%, transparent); }
}
@keyframes crt-key {
  0% { transform: translateX(-3px); text-shadow: 2.5px 0 0 color-mix(in srgb, var(--ink) 55%, transparent), -2.5px 0 0 color-mix(in srgb, var(--accent) 70%, transparent);
    animation-timing-function: steps(1, end); }
  30% { transform: translateX(1px); text-shadow: -1px 0 0 color-mix(in srgb, var(--ink) 35%, transparent), 1px 0 0 color-mix(in srgb, var(--accent) 50%, transparent);
    animation-timing-function: var(--ease-out); }
  100% { transform: none; text-shadow: var(--glow); }
}
@keyframes crt-mine {
  0%, 16%, 19%, 60%, 100% { transform: none; text-shadow: var(--glow); }
  14% { transform: translateX(1.5px); text-shadow: -1.5px 0 0 color-mix(in srgb, var(--ink) 50%, transparent), 1.5px 0 0 color-mix(in srgb, var(--accent) 65%, transparent); }
  17% { transform: translateX(-1px); text-shadow: 1px 0 0 color-mix(in srgb, var(--ink) 40%, transparent), -1px 0 0 color-mix(in srgb, var(--accent) 50%, transparent); }
  57% { transform: translateX(-1px); text-shadow: 1.5px 0 0 color-mix(in srgb, var(--ink) 45%, transparent), -1.5px 0 0 color-mix(in srgb, var(--accent) 60%, transparent); }
}
/* Fig. 1 at 1100px and narrower: both columns go under the rink, side by
   side, each with a rule above it instead of beside it. (After the columns'
   own rules, so these win.) */
@media (max-width: 1100px) {
  .figure.rink-fig {
    width: 100%;
    max-width: var(--figure-max);
  }
  .rink-body {
    grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
    grid-template-areas: 'rink rink' 'ctrl board';
    gap: var(--space-4) var(--space-6);
  }
  .ctrl-col,
  .board-col {
    padding: var(--space-4) 0 0;
    border: 0;
    border-top: 1px solid var(--line);
  }
  .rink-body .crt-fx {
    inset: 14px 0 0 0;
  }
}
@media (prefers-reduced-motion: reduce) {
  .crt-in,
  .crt.boot .crt-in,
  .crt.zap .crt-in,
  .crt.zap .crt-in *,
  .crt.vhold .crt-in,
  .crt-tear,
  .crt-tear *,
  .crt-drop,
  .crt-in .board-rows input,
  .crt-in .board-rows li.mine .name {
    animation: none !important;
  }
}
@media (max-width: 760px) {
  .rink-body {
    grid-template-columns: minmax(0, 1fr);
    grid-template-areas: 'rink' 'ctrl' 'board';
    gap: var(--space-4);
  }
  .board-rows,
  .ctrl-rows {
    flex: none;
  }
  /* Stacked, nothing to line up with: drop the spacer rows. */
  .ctrl-gap {
    display: none;
  }
  .ctrl-sub {
    margin-top: var(--space-5);
  }
}

.index-fig {
  max-width: var(--width-md);
}

/* Table 1: the index of works, set like a parts list. */
.index {
  width: 100%;
  border-collapse: collapse;
  font-size: var(--text-label); /* the entries are content: text size */
  text-align: left;
}

.index th {
  padding: 0 var(--space-1) var(--space-3);
  border-bottom: 1px solid var(--line-strong);
  font-weight: 400;
  font-size: var(--text-micro);
  letter-spacing: var(--track-caps);
  text-transform: uppercase;
  color: var(--ink-muted);
}

.index td {
  padding: var(--space-3) var(--space-1);
  border-bottom: 1px solid var(--line);
  letter-spacing: var(--track-entry);
  text-transform: uppercase;
}

.index tr:last-child td {
  border-bottom: 0;
}

.index td:first-child,
.index .status {
  white-space: nowrap;
}

.index td:first-child {
  width: 22%;
  font-weight: 700;
  color: var(--accent-text);
}

.index .status {
  width: 30%;
  font-size: var(--text-label);
  letter-spacing: var(--track-caps);
  color: var(--ink-muted);
}

.index .status.live {
  color: var(--ink);
  font-weight: 700;
}

.index .status.restricted {
  color: var(--accent-text);
  font-weight: 700;
}

/* A redaction bar: solid, with nothing underneath to select or read. */
.redacted {
  display: inline-block;
  width: 9.5em;
  max-width: 100%;
  height: 0.95em;
  vertical-align: -0.1em;
  background: var(--ink);
}

@media (max-width: 900px) {
  .stage {
    gap: var(--space-12);
  }
}

@media (max-width: 520px) {
  .index {
    font-size: var(--text-label);
  }

  .index td,
  .index th {
    padding-left: var(--space-half);
    padding-right: var(--space-half);
  }

  .index td:first-child {
    width: auto;
    padding-right: var(--space-3);
  }

  .index .status {
    width: auto;
    font-size: var(--text-micro);
    letter-spacing: var(--track-label);
  }

  .redacted {
    width: 6em;
  }
}

/* ---- Contact panel (contact.js): the demo box's style, as a modal ---- */
.contact-panel {
  width: min(100% - 2 * var(--gutter), var(--width-xs));
  max-width: none;
  padding: 0 var(--space-3) var(--space-3) 0; /* room for the box's red offset shadow */
  border: 0;
  background: transparent;
  color: var(--ink-on-paper);
  overflow: visible;
}

.contact-panel::backdrop {
  background: var(--scrim);
}

.contact-panel[open] {
  animation: rise 0.35s var(--ease-out);
}

.contact-box {
  position: relative;
  width: 100%;
  margin: 0;
  padding-right: var(--space-12);
  outline: none; /* focused on open so no button starts highlighted */
}

.contact-close {
  position: absolute;
  top: 10px;
  right: 10px;
  width: 36px;
  height: 36px;
  padding: 0;
  border: 0;
  background: none;
  color: var(--ink-on-paper);
  font: inherit;
  font-size: var(--text-large);
  line-height: var(--leading-none);
  cursor: pointer;
}

.contact-close:hover,
.contact-close:focus-visible {
  color: var(--accent-text);
}

.notice .contact-address {
  margin: 0 calc(var(--space-8) * -1) var(--space-5) 0;
  padding: var(--space-3) var(--space-4);
  border: var(--stroke-heavy) solid var(--ink-on-paper);
  font-weight: 700;
  font-size: var(--text-heading);
  letter-spacing: var(--track-tight);
  overflow-wrap: anywhere;
  user-select: all;
}
/* Phones: one step down, so the whole address fits on one line. */
@media (max-width: 520px) {
  .notice .contact-address {
    font-size: var(--text-label);
  }
}

.contact-actions {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--space-4) var(--space-6);
}

.contact-copy {
  border: 0;
  font-family: inherit;
  cursor: pointer;
}

.contact-open {
  font-weight: 700;
  font-size: var(--text-label);
  letter-spacing: var(--track-caps);
  text-transform: uppercase;
  color: var(--ink-on-paper);
  text-decoration: none;
  border-bottom: var(--rule) solid var(--accent);
  padding: var(--space-1) 0;
}

.contact-open:hover,
.contact-open:focus-visible {
  color: var(--accent-text);
}

/* Announced to screen readers only; sighted users see the button change. */
.notice .contact-status {
  position: absolute;
  width: 1px;
  height: 1px;
  margin: 0;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
}

/* ---- Print: a black-on-white manual sheet ---- */
.title-block {
  display: none;
}

@media print {
  @page {
    margin: 14mm;
  }

  /* (The print colors themselves are in base.css, for every page.) */
  body {
    display: block;
    min-height: 0;
  }

  #field,
  #glitch,
  #board,
  .ctrl-col,
  .contact-link,
  .contact-panel,
  .contact-panel[open] {
    display: none;
  }

  /* The logo's white strokes become black (assets/logo-print.svg); red stays red. */
  .mark {
    content: url('/assets/logo-print.svg');
    width: 15mm;
  }

  /* Inline diagrams (Fig. 404) are drawn in screen colors: remap them.
     The rink canvas redraws itself in print colors (rink.js). */
  svg .s-ice {
    stroke: var(--print-ink);
  }
  svg .f-ice {
    fill: var(--print-ink);
  }
  svg .f-night {
    fill: var(--print-paper);
  }
  svg .f-steel {
    fill: var(--ink-muted);
  }

  .top {
    padding: 0;
  }

  .hatch {
    background: repeating-linear-gradient(135deg, transparent 0 7px, var(--print-ink) 7px 9px);
  }

  /* Sizes and gaps kept tight so Table 1 fits on the same sheet. */
  .hero {
    padding: 4mm 0 0;
  }

  .hero > * {
    animation: none;
    opacity: 1;
    transform: none;
  }

  .wordmark {
    font-size: 34pt;
  }

  .rule {
    margin: 4mm 0 6mm;
  }

  .stage {
    gap: 5mm;
  }

  .figure {
    max-width: none;
    background: none;
    break-inside: avoid;
  }

  .tick {
    border-color: var(--print-ink);
  }

  /* The demo box: the button becomes the address to write to. */
  .notice {
    border: var(--stroke-heavy) solid var(--print-ink);
    box-shadow: 6px 6px 0 var(--accent);
    break-inside: avoid;
  }

  .notice .cta {
    padding: 0;
    background: none;
    color: var(--accent-text);
  }

  .notice .cta[data-contact]::after {
    content: 'contact@websterdivision.com';
    color: var(--print-ink);
    text-transform: none;
    letter-spacing: var(--track-tight);
  }

  .redacted {
    background: var(--print-ink);
  }

  .index-fig {
    max-width: 120mm;
  }

  .rink-body {
    grid-template-columns: minmax(0, 1fr);
    grid-template-areas: 'rink';
  }

  .rink-wrap > .figure {
    width: 100%;
    max-width: 125mm;
  }

  .figure figcaption {
    font-size: 7.5pt;
    color: var(--ink-muted);
  }

  .index th,
  .index td {
    border-color: var(--print-rule);
  }

  .index th {
    padding: 0 1mm 1.6mm;
  }

  .index td {
    padding: 1.2mm 1mm;
  }

  .title-block {
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    margin-top: 10mm;
    border: var(--stroke-heavy) solid var(--print-ink);
    break-inside: avoid;
    font-size: 8pt;
    letter-spacing: var(--track-label);
    text-transform: uppercase;
  }

  .title-block div {
    padding: 2mm 3mm;
    border-right: 1px solid var(--print-ink);
    border-bottom: 1px solid var(--print-ink);
  }

  .title-block div:nth-child(3n) {
    border-right: 0;
  }

  .title-block div:nth-child(n + 4) {
    border-bottom: 0;
  }

  .title-block span {
    display: block;
    margin-bottom: 1mm;
    font-size: 6.5pt;
    color: var(--ink-muted);
  }

  .title-block b {
    color: var(--print-ink);
  }
}
