/* The companion's one stylesheet, held to two rules.

   A thing is styled for what it is, not for where it sits.
   A selector may reach a component's own parts, so .card-preview .card-image is the preview's image,
   but it never says which page, or which container, the thing happens to be inside.
   Ids are a last resort, and the ones here are the save editor's furniture.
   The only selector naming a page is .page-404 main, since being lost is the whole page's business.

   Relief is raised or sunk, written once under "the construction", and everything with relief names one of them.
   Everything else is flat. A box that wants its own border, shadow or radius is a box that has not been thought about. */

/* ── faces ──────────────────────────────────────────────────────────────────────────────────── */

/* Self-custodied, OFL, licenses beside the files. */
@font-face {
  font-family: "Quicksand";
  src: url("./fonts/quicksand-variable.woff2") format("woff2");
  font-weight: 300 700;
  font-display: swap;
}
@font-face {
  font-family: "M PLUS Rounded 1c";
  src: url("./fonts/mplus-rounded-1c-kana.woff2") format("woff2");
  font-weight: 400;
  font-display: swap;
}
/* Ten digits of Sarasa Mono, so numbers in tables line up; letters fall through to Quicksand. */
@font-face {
  font-family: "Sarasa Digits";
  src: url("./fonts/sarasa-digits.woff2") format("woff2");
  unicode-range: U+0030-0039;
  font-display: swap;
}
/* Quicksand sets 3.1% wider than Arial, so the stand-in is stretched to match:
   the swap from one to the other changes the letters and nothing else. */
@font-face {
  font-family: "Quicksand fallback";
  src: local("Arial"), local("Helvetica"), local("Liberation Sans");
  size-adjust: 103.1%;
}
@font-face {
  font-family: "IM Fell English";
  src: url("./fonts/imfell-400-italic.woff2") format("woff2");
  font-style: italic;
  font-display: swap;
}
@font-face {
  font-family: "Fell Stand-in";
  src: local("Georgia Italic"), local("Georgia-Italic"), local("Georgia");
  font-style: italic;
  size-adjust: 77.67%; ascent-override: 90.53%; descent-override: 36.33%; line-gap-override: 0%;
}
@font-face {
  font-family: "Fell Stand-in";
  src: local("Times New Roman Italic"), local("TimesNewRomanPS-ItalicMT"), local("Times New Roman");
  font-style: italic;
  size-adjust: 86.57%; ascent-override: 90.53%; descent-override: 36.33%; line-gap-override: 0%;
}

/* ── the palette, and the three depths everything is built from ─────────────────────────────── */

:root {
  /* A face's highlight is that face mixed toward white; its shade is the same face taken darker, its drop darker again.
     White has no highlight, so the paper never shows relief. The frame around it does. */
  /* default.html inlines this exact colour as its flash-guard, so no navigation ever paints white;
     a change here must change there in step. */
  --room: #3F5A6E;
  --paper: #FFFFFF;
  --rule: #AFA8A1;

  /* A new page takes another sample of the same walk round the wheel; it does not open a fresh argument. */
  --page-home: #A6DEBE;         --page-home-hi: #BAE5CC;         --page-home-sh: #54BC80;         --page-home-deep: #348E5B;
  --page-dice: #A8D0E8;         --page-dice-hi: #BFDCEE;         --page-dice-sh: #4A9BCC;         --page-dice-deep: #28729E;
  --page-shop: #EFDB9F;         --page-shop-hi: #F3E3B4;         --page-shop-sh: #DFB63A;         --page-shop-deep: #AB871C;
  --page-duelists: #9FD8DB;    --page-duelists-hi: #B9E3E5;    --page-duelists-sh: #3FA9B2;    --page-duelists-deep: #217E88;
  --page-gallery: #B9C0E4;      --page-gallery-hi: #CED3EC;      --page-gallery-sh: #6070BF;      --page-gallery-deep: #384794;
  --page-brain: #C8B4EC;        --page-brain-hi: #D9CBF2;        --page-brain-sh: #8054D0;        --page-brain-deep: #562AA6;
  --page-balance: #F2BCB2;      --page-balance-hi: #F6CFC8;      --page-balance-sh: #D96A57;      --page-balance-deep: #A93E2E;
  --page-editor: #EFDB9F;       --page-editor-hi: #F3E3B4;       --page-editor-sh: #DFB63A;       --page-editor-deep: #AB871C;

  /* the accents, for the small things that carry meaning rather than structure */
  --rose: #F7CBD3;  --rose-deep: #B44A62;
  --link: #7C2B3D;        /* dark enough to read on a panel */
  --peach: #FFDDBE;
  --butter: #FFEDB0;
  --mint: #C5E8D2;  --mint-deep: #3D7C57;
  --sky: #C9E4F2;   --sky-deep: #3F6E8C;
  --cloud: #DDE4E8;
  --purple: #653D7C;      /* deep enough to carry light text */
  --row-lit: #F6F4F1;
  --mono: ui-monospace, "SF Mono", Menlo, Consolas, monospace;

  /* Text is black, and what carries it is white or white barely tinted: a well's floor, the row under the pointer.
     Colour and grey belong to edges, borders and shadows.
     A quieter voice is size, weight or italics, never a colour fading toward the page. */
  --ink: #000000;
  --on-room: #E7ECEF;      /* text with the room behind it rather than a panel */

  /* The type ladder, and there is no rung between these.
     A size is chosen from here or it is a mistake, because sizes an em apart from each other compound. */
  --type-display: 1.6rem;   /* a number that is the whole point of its box */
  --type-head: 1.25rem;     /* a section's name */
  --type-sub: 1.1rem;       /* a heading inside one */
  --type-body: 1rem;
  --type-small: .92rem;     /* tables, captions under a heading, a page's purpose */
  --type-fine: .8rem;       /* a column header, an aside to a line, a password */
  --type-micro: .72rem;     /* a stamp, a state, a mark on something else */

  /* The spacing ladder. Same law as the type one: a gap is chosen from here or it is a mistake.
     Numbered rather than named, because what you want when a thing is too tight is the next rung up. */
  --gap-1: .1rem;   --gap-2: .2rem;   --gap-3: .3rem;   --gap-4: .45rem;
  --gap-5: .6rem;   --gap-6: .9rem;   --gap-7: 1.2rem;  --gap-8: 1.8rem;

  /* The border ladder, thinnest to thickest; a drawn edge takes a rung or it is a mistake. */
  --hairline: 1px;    /* furniture, row rules */
  --pen: 2px;         /* a line that separates: table heads, hr, pill outlines, boxed text */
  --bevel: 3px;       /* the frame at the size of a thing you press */
  --slab: 6px;        /* the thick edge: a card scan's wooden frame, a warning's stripe */
  --frame: 12px;      /* wide enough to read as moulding rather than a keyline */

  --scan: 240px;                            /* a card page's true width */
  --wood-hi: #CEAC88; --wood-sh: #825F3C;   /* the frame a scan sits in */
  /* the cartridge's own two colours, which are not ours to soften */
  --game-paper: #fff; --game-ink: #000;
}


/* The column's width is set in rem, so stepping the root size here scales the whole column with the type:
   a line of text stays the same number of characters wide at every window size. */
html { font-size: 16px; }
@media (min-width: 640px)  { html { font-size: 17px; } }
@media (min-width: 1000px) { html { font-size: 18px; } }
@media (min-width: 1500px) { html { font-size: 19px; } }

* { box-sizing: border-box; }

/* navigations cross-fade instead of flashing: the room holds still while the papers swap */
@view-transition { navigation: auto; }
@media (prefers-reduced-motion: reduce) {
  @view-transition { navigation: none; }
}


body {
  margin: 0; background: var(--room); color: var(--ink);
  font-family: "Quicksand", "Quicksand fallback", "M PLUS Rounded 1c", sans-serif;
  line-height: 1.65;
}


/* ── the construction ───────────────────────────────────────────────────────────────────────── */

/* A page wears its own four colours, and a key going somewhere wears the colours of where it goes,
   so the bar across the top is the whole site's palette at once.
   They are declared on the element rather than at :root, because a variable naming another variable resolves where it is written,
   and one written at :root would only ever see :root's. */
.page-home, .to-page-home { --face: var(--page-home); --face-lit: var(--page-home-hi); --face-shade: var(--page-home-sh); --face-drop: var(--page-home-deep); }
.page-dice, .to-page-dice { --face: var(--page-dice); --face-lit: var(--page-dice-hi); --face-shade: var(--page-dice-sh); --face-drop: var(--page-dice-deep); }
.page-shop, .to-page-shop { --face: var(--page-shop); --face-lit: var(--page-shop-hi); --face-shade: var(--page-shop-sh); --face-drop: var(--page-shop-deep); }
.page-duelists, .to-page-duelists { --face: var(--page-duelists); --face-lit: var(--page-duelists-hi); --face-shade: var(--page-duelists-sh); --face-drop: var(--page-duelists-deep); }
.page-gallery, .to-page-gallery { --face: var(--page-gallery); --face-lit: var(--page-gallery-hi); --face-shade: var(--page-gallery-sh); --face-drop: var(--page-gallery-deep); }
.page-brain, .to-page-brain { --face: var(--page-brain); --face-lit: var(--page-brain-hi); --face-shade: var(--page-brain-sh); --face-drop: var(--page-brain-deep); }
.page-balance, .to-page-balance { --face: var(--page-balance); --face-lit: var(--page-balance-hi); --face-shade: var(--page-balance-sh); --face-drop: var(--page-balance-deep); }
.page-editor, .to-page-editor { --face: var(--page-editor); --face-lit: var(--page-editor-hi); --face-shade: var(--page-editor-sh); --face-drop: var(--page-editor-deep); }
/* a page with no colour of its own (the 404) borrows the front page's */
body { --face: var(--page-home); --face-lit: var(--page-home-hi); --face-shade: var(--page-home-sh); --face-drop: var(--page-home-deep); }

/* Raised, at panel size: white paper in a thick frame, standing above a hard drop.
   Only a section directly in the page (or on the editor's #loaded shelf) is one;
   sections nested deeper stay plain paper, free to mean what HTML means by them. */
main > section, #loaded > section, .cardsplainer, .site-contents, .masthead {
  background: var(--paper);
  border: var(--frame) solid; border-color: var(--face-lit) var(--face-shade) var(--face-shade) var(--face-lit);
  box-shadow: 5px 5px 0 var(--face-drop);
}
/* Raised, at key size: small enough to be the coloured face itself rather than paper in a frame. */
button, .door, aside, .pick, .more-pill, summary {
  background: var(--face);
  border: var(--bevel) solid; border-color: var(--face-lit) var(--face-shade) var(--face-shade) var(--face-lit);
  box-shadow: 4px 4px 0 var(--face-drop);
}
/* Sunk: a well cut into the paper, which only a field you type into earns.
   The lip's shadow falls inward, mirroring the drop a raised key throws outward,
   and the floor is tinted, because the bevel alone did not read as depth on white. */
input {
  border: var(--bevel) solid; border-color: var(--face-shade) var(--face-lit) var(--face-lit) var(--face-shade);
  box-shadow: inset 3px 3px 0 color-mix(in srgb, var(--paper) 40%, var(--face));
}
/* Furniture, not controls, so neither construction: a hairline and no relief. */
.stat, .cycle { border: var(--hairline) solid var(--rule); box-shadow: none; }
/* Lit: the face lifted toward white while the pointer is on it. Not a filter:
   a filtered element becomes the containing block for anything fixed inside it,
   so a card preview inside a key would land in the wrong place and under its neighbours.
   Transform does the same, which is why pressing offsets instead. */
button:hover, .door:hover, summary:hover { background: color-mix(in srgb, var(--face) 93%, white); }

/* Pressed: the raised box moves into the spot its drop shadow held, and the shadow goes.
   The label thickens by a shadow of its own letters rather than a heavier font, so pressing never changes its width. */
.door[aria-current="page"], button[aria-checked="true"], button[aria-pressed="true"], details[open] > summary {
  position: relative; left: 4px; top: 4px; box-shadow: none;
  border-color: var(--face-shade) var(--face-lit) var(--face-lit) var(--face-shade); text-shadow: .03em 0 0 currentColor;
}

/* ── surfaces ───────────────────────────────────────────────────────────────────────────────── */

/* --pad is the one number a panel's inside is measured by, so a table breaking out of one can read it
   rather than be told it a second time. */
main > section, #loaded > section, .cardsplainer, .site-contents, .masthead {
  --pad: 1.6rem;
  color: var(--ink);
  padding: var(--gap-7) var(--pad);
  margin: var(--gap-8) 0;
}
.site-contents { --pad: var(--gap-6); padding: var(--gap-6) var(--pad); }
.cardsplainer { --pad: var(--gap-7); padding: var(--gap-7) var(--pad); }

.wrap { max-width: 52rem; margin: 0 auto; padding: 0 var(--gap-7) 4rem; }
main { color: var(--on-room); }
footer { text-align: center; padding: var(--gap-8) var(--gap-7); }
/* The mark sits on a small paper card of its own, so the ordinary link colours stay readable against it. */
.makers-mark {
  display: inline-block; margin: 0; padding: var(--gap-4) var(--gap-7);
  background: var(--paper); color: var(--ink);
  border: var(--frame) solid; border-color: var(--face-lit) var(--face-shade) var(--face-shade) var(--face-lit);
  box-shadow: 5px 5px 0 var(--face-drop);
  font-family: "IM Fell English", "Fell Stand-in", serif; font-style: italic; font-size: var(--type-body);
}

.masthead { padding: var(--gap-8) var(--gap-7) var(--gap-7); text-align: center; }
.masthead h1 { margin: 0; font-size: var(--type-display); letter-spacing: .02em; }
.masthead p { margin: var(--gap-4) 0 0; font-size: var(--type-small); }

/* ── things you press, type in, and go to ───────────────────────────────────────────────────── */

/* A form control inherits neither the page's font nor its colour. */
button, input { font: inherit; color: var(--ink); border-radius: 0; }
button { line-height: 1.45; padding: var(--gap-3) var(--gap-6); cursor: pointer; }
/* Only a lasting choice moves.
   A button that shifted while held would slide out from under the pointer, and the release would land on nothing. */
button:active { border-color: var(--face-shade) var(--face-lit) var(--face-lit) var(--face-shade); }
input { background: color-mix(in srgb, var(--paper) 74%, var(--face)); padding: var(--gap-4) var(--gap-6); outline: none; }
.filter { width: 100%; margin: var(--gap-4) 0 var(--gap-5); }
input::placeholder { color: var(--ink); opacity: 1; }
input:focus-visible { outline: 3px solid var(--sky-deep); outline-offset: 1px; }

.site-map { display: flex; gap: var(--gap-4); justify-content: center; flex-wrap: wrap; margin-top: var(--gap-6); font-size: var(--type-small); }
.site-map-group { display: contents; }
/* a sprite on a coloured key can vanish into it; four white shadows draw it a 1px outline */
.site-map .emoji, .site-contents .emoji, aside .emoji {
  filter: drop-shadow(-1px -1px 0 rgba(255, 255, 255, .85)) drop-shadow(1px -1px 0 rgba(255, 255, 255, .85))
          drop-shadow(-1px 1px 0 rgba(255, 255, 255, .85)) drop-shadow(1px 1px 0 rgba(255, 255, 255, .85)); }
/* A door is a key you go through: to another page, to a place on this one. */
.door {
  display: inline-block; text-decoration: none; color: var(--ink);
  padding: var(--gap-2) var(--gap-5); margin: var(--gap-2) var(--gap-1);
  /* the metric-matched fallback holds a line's width but not its height, so a key states its own line box */
  line-height: 1.45;
}
/* Laid out in cells rather than flowed, so the row count comes from the panel's width and not the letters':
   the webfont arriving cannot add a row and shift the page under a reader. */
.site-contents {
  font-size: var(--type-small); margin-bottom: var(--gap-7);
  display: grid; grid-template-columns: repeat(auto-fill, minmax(11rem, 1fr)); gap: var(--gap-3);
}
.site-contents .door { margin: 0; text-align: center; }
.site-contents .contents-name { grid-column: 1 / -1; margin: 0; }

/* ── type ───────────────────────────────────────────────────────────────────────────────────── */

h2 { margin: 0 0 var(--gap-3); font-size: var(--type-head); }
h2 .dot { font-size: var(--type-body); margin-right: var(--gap-4); }
h3 { font-size: var(--type-sub); margin: var(--gap-7) 0 var(--gap-4); }
.purpose { font-size: var(--type-small); margin: 0 0 var(--gap-6); }
.purpose p, aside p { margin: 0; }  /* pandoc hands both a paragraph; the box owns its own spacing */
.footnote { font-size: var(--type-small); font-weight: 400; }
.back { color: var(--link); text-decoration: none; font-weight: 600; }
/* A link that leaves the site stays text rather than being dressed as a control.
   nyuu.page is still us, so it is written in our own accent; everywhere else is plainly elsewhere. */
a[href^="http"] { color: var(--link); text-underline-offset: .18em; }
a[href*="nyuu.page"] { color: var(--ink); text-decoration-color: var(--link); text-decoration-thickness: var(--pen); }
a[href^="http"]:hover { color: var(--ink); }
/* A reading is spoken over the name it belongs to, so it is the one size measured against its host
   rather than off the ladder: it has to shrink when the name it sits above does. */
rt { font-size: .62em; letter-spacing: .03em; }
.reading { display: block; font-size: .62em; letter-spacing: .03em; }
code { font-family: var(--mono); font-size: var(--type-fine); }
.official-name { font-size: var(--type-fine); }
.official-name::before { content: "og: "; letter-spacing: .04em; }
.symbol { font-size: var(--type-head); }
hr { border: none; border-top: var(--pen) solid var(--rule); margin: var(--gap-7) 0 var(--gap-1); }
.lab-lede { margin: var(--gap-3) 0 var(--gap-4); }

/* inline-block keeps a wrapped passage one box, where an inline span would break into strips. */
.gametext {
  display: inline-block; background: var(--game-paper); border: var(--hairline) solid var(--game-ink);
  padding: .04em .4em; font-size: var(--type-small);
}
/* an arrow never wraps away from what it joins */
.arrow { color: var(--face-drop); font-weight: 700; white-space: nowrap; }

/* ── tables ─────────────────────────────────────────────────────────────────────────────────── */

table { border-collapse: collapse; width: 100%; margin: var(--gap-5) 0; font-size: var(--type-small); }
th {
  text-align: left; font-size: var(--type-fine); text-transform: uppercase; letter-spacing: .06em;
  font-weight: 600; padding: var(--gap-3) var(--gap-5);
  border-bottom: var(--pen) solid var(--ink);
}
td { padding: var(--gap-4) var(--gap-5); border-top: var(--hairline) solid var(--rule); }
tr:hover td { background: var(--row-lit); }
.numeric { text-align: right; font-variant-numeric: tabular-nums;
           font-family: "Sarasa Digits", Quicksand, "Quicksand fallback", sans-serif; }
.password { font-family: var(--mono); font-size: var(--type-fine); white-space: nowrap; }

/* A wide table scrolls inside its panel rather than widening the page,
   so a mark in the corner has to say that there are columns out past the right edge. */
.table-scroll { overflow-x: auto; }
.table-frame { position: relative; }
.more-pill {
  position: absolute; top: .4rem; right: .5rem; z-index: 1;
  --face: var(--butter); --face-lit: #FFF6D8; --face-shade: #D9B33C; --face-drop: #A88722;
  padding: var(--gap-1) var(--gap-5); font-size: var(--type-fine); font-weight: 700;
  opacity: 0; transition: opacity .18s; pointer-events: none;
}
.more-right .more-pill { opacity: 1; }

/* ── drawers ────────────────────────────────────────────────────────────────────────────────── */

/* A drawer's handle is a key, and opening is a lasting choice, so an open handle sits pressed.
   The contents lie on the panel below it rather than on a surface of their own,
   which is one fewer background for every colour on the site to work against. */
details { margin: var(--gap-6) 0; }
summary { display: inline-block; padding: var(--gap-3) var(--gap-6); cursor: pointer; font-weight: 600; }
/* display: inline-block discards the native marker, so the handle carries its own. */
summary::before { content: "▸ "; }
details[open] > summary::before { content: "▾ "; }
/* The rich entry rows are a list, and a list wants one left edge.
   content-visibility is forbidden here: like filter and transform above, it makes the entry the containing
   block for the fixed-position card previews inside it, imprisoning them in the box they must escape. */
.entry summary { display: block; }
details[open] > summary { margin-bottom: var(--gap-5); }
/* A closed drawer is closed.
   Browsers otherwise search inside one and throw it open on a find,
   so asking a page for a card name flings apart every drawer that happens to list it. */
details:not([open]) > *:not(summary) { display: none; }

.entry summary::-webkit-details-marker { display: none; }
.pill-line { margin-left: var(--gap-3); }
.entry ul { margin: var(--gap-4) 0 var(--gap-3); padding-left: var(--gap-7); font-size: var(--type-small); }
.entry li { margin: var(--gap-3) 0; }

/* ── pills and stamps ────────────────────────────────────────────────────────────────────────── */

/* A pill names something and goes nowhere: an alignment, a type, an attack, an add-on.
   Its outline is the whole of its colour, so the word inside stays black on white. */
.pill {
  display: inline-block; padding: var(--gap-1) var(--gap-5); border-radius: 999px;
  font-size: var(--type-fine); margin: var(--gap-1) var(--gap-2) var(--gap-1) 0;
  background: var(--paper); border: var(--pen) solid;
}
/* A pill shrunk to a stamp on something else, saying what state it is in rather than what it is.
   Not spelled "mark": pandoc reads that class as a request for a <mark> element and drops the rest. */
.pill-mark {
  font-size: var(--type-micro); font-weight: 700; letter-spacing: .05em;
  padding: var(--gap-1) var(--gap-5); margin: 0; vertical-align: middle;
}

.pill-rose { border-color: var(--rose); } .pill-peach { border-color: var(--peach); }
.pill-butter { border-color: var(--butter); } .pill-mint { border-color: var(--mint); } .pill-sky { border-color: var(--sky); }
.pill-cloud { border-color: var(--cloud); }
.pill-purple { border-color: var(--purple); font-weight: 600; }
.pill-black { border-color: var(--ink); }
.pill-white { border-color: var(--rule); }

/* The state of a stamp is how much ink it carries: filled is deckable from the start,
   ringed unlocks after the credits, and a greyed-out letter means that cartridge has not got the card at all. */
.stamps { display: inline-flex; gap: .15em; vertical-align: middle; white-space: nowrap; }
.stamp {
  display: inline-flex; align-items: center; justify-content: center;
  width: 1.5em; height: 1.5em; border-radius: 50%;
  font-size: var(--type-micro); font-weight: 700;
}
.stamp-start.stamp-yugi { background: var(--rose); }
.stamp-start.stamp-kaiba { background: var(--sky); }
.stamp-start.stamp-jonouchi { background: var(--mint); }
/* A ring has no fill to carry it, so its colour is the whole mark.
   Plain rose reads lighter than its two siblings, L* 62 against 53 and 58, so the ring takes a rose darkened to match. */
.stamp-later.stamp-yugi { box-shadow: inset 0 0 0 1.5px var(--rose-deep); }
.stamp-later.stamp-kaiba { box-shadow: inset 0 0 0 1.5px var(--sky-deep); }
.stamp-later.stamp-jonouchi { box-shadow: inset 0 0 0 1.5px var(--mint-deep); }
.stamp-none { color: var(--rule); }

/* ── small boxes inside panels ──────────────────────────────────────────────────────────────── */

/* An aside is a box laid flat inside a panel, opening with a mark that says what sort of aside it is.
   It wears one colour on every page, because a page's own colours mean where you are, and an aside is
   not a place; peach is the accent sitting furthest from the pages that carry asides. */
aside {
  padding: var(--gap-6) var(--gap-6); margin: var(--gap-6) 0; font-size: var(--type-small); box-shadow: none;
  --face: var(--peach); --face-lit: #FFEEDE; --face-shade: #D89340; --face-drop: #A96C22;
}
.stat-row { display: flex; gap: var(--gap-6); flex-wrap: wrap; margin: var(--gap-6) 0; }
/* the basis fits a four-digit stat and its label */
.stat { flex: 1 1 130px; padding: var(--gap-6) var(--gap-6); text-align: center; }
.stat-number { font-size: var(--type-display); font-weight: 700; }
.stat-label { font-size: var(--type-fine); }
.cycle { font-size: var(--type-body); text-align: center; padding: var(--gap-5); }
.beats { color: var(--link); font-weight: 700; }
.cycle-part { border-top: var(--hairline) dashed var(--rule); margin-top: var(--gap-5); padding-top: var(--gap-5); }
p[id^="equip-"] { border-top: var(--hairline) dashed var(--rule); padding-top: var(--gap-6); margin-top: var(--gap-6); }
.rules ol, .rules ul { padding-left: var(--gap-7); }  /* the fence is the wrapper; the list is what indents */
.rules li { margin: var(--gap-5) 0; }
.side-list { display: block; background: var(--game-paper); border: var(--pen) solid var(--rule); --pad: var(--gap-5); padding: var(--gap-4) var(--pad); margin: var(--gap-3) 0; font-size: var(--type-small); }

/* ── card previews ──────────────────────────────────────────────────────────────────────────── */

/* Built by site.hs, and by companion.js for the rows it renders live: a class change here means both. */
/* Inline, not inline-block: an atomic box that wraps takes the whole line with it,
   pushing whatever followed the name, an id or a stamp, onto a line of its own. */
.card-preview { position: relative; }
/* a card name is an inline span under a dotted rule; the default ring is easy to lose there */
.card-preview:focus-visible, summary:focus-visible, .side:focus-visible {
  outline: 3px solid var(--rose-deep); outline-offset: 2px;
}
/* The weld between a mark and its name's first word; CardLinks says why it is markup rather than CSS.
   The cell selector is the stylesheet's one where-it-sits exception:
   a weld in a table would raise the column's width floor, so cells unweld. */
.wedded { white-space: nowrap; }
td .wedded { white-space: normal; }
.card-name { border-bottom: var(--pen) dotted var(--rose-deep); cursor: help; }
/* an Egyptian god wears its alignment's purple, which the hub's cycles taught the reader */
.god-card .card-name { color: var(--purple); font-weight: 600; }
/* The image is a popover:
   it opens into the top layer, where no scroller, stacking context, or transformed ancestor can clip or misplace it.
   The script measures out its place beside the hovered line and reports it in the custom properties. */
.card-preview .card-image {
  inset: auto;
  top: var(--card-top);
  left: var(--card-left);
  height: var(--card-height);
  width: auto;   /* the height decides; width follows the scans' own ratio */
  margin: 0;
  padding: 0;   /* the browser pads popovers by default, which puts white air inside the wood frame */
  image-rendering: pixelated;
  border: var(--slab) solid; border-color: var(--wood-hi) var(--wood-sh) var(--wood-sh) var(--wood-hi);
  box-shadow: 6px 6px 0 rgb(0 0 0 / .35);
}
.summary-preview {
  display: inline-block;
  cursor: zoom-in; background: var(--game-paper); border: var(--pen) solid var(--rule);
  padding: .05em .45em .05em .3em;
}
.summary-preview .card-name { border-bottom: none; font-weight: 700; }

/* A marker's drawing lives here rather than inline, so the recoloured view can name a different one.
   The mark before a name is the card's kind; a mark with no kind is the official record's, worn upright. */
.glyph-card { background-image: url(./images/art/monster-card.svg); }
.glyph-of-monster { background-image: url(./images/art/monster-card.svg); }
.glyph-of-effect { background-image: url(./images/art/effect-card.svg); }
.glyph-of-magic { background-image: url(./images/art/magic-card.svg); }

/* ── emoji ──────────────────────────────────────────────────────────────────────────────────── */

/* The glyph stays in the span, so copy, search and screen readers still meet real text;
   text-indent shoves it out of view and the asset paints in its place. */
.emoji {
  display: inline-block; width: 1.2em; height: 1.2em; overflow: hidden; text-indent: 200%;
  white-space: nowrap; background-repeat: no-repeat; background-position: center;
  background-size: contain; vertical-align: -0.2em;
}
.emoji.pixelated { image-rendering: pixelated; }
.hanafuda { margin-right: .1em; }
/* The marker lies at an angle and stands upright while its card name is hovered or focused.
   The class is on the mark itself: a transform does nothing to a plain inline box, and the wrapper around it is one. */
.hanafuda-leaning { transform: rotate(7deg); }
@media (prefers-reduced-motion: no-preference) {
  .hanafuda-leaning { transition: transform .18s ease; }
  .card-preview:hover .hanafuda-leaning,
  .card-preview:has(.card-image:popover-open) .hanafuda-leaning,
  .card-preview:focus-visible .hanafuda-leaning { transform: rotate(0); }
}

/* ── fusion widgets ─────────────────────────────────────────────────────────────────────────── */

.side { border-bottom: var(--pen) dotted var(--mint-deep); cursor: pointer; }
.tap-note { color: #2F6144; font-size: var(--type-micro); }
/* The chip rides the middle of its line, level with the words beside it. */
.entry > summary .summary-preview { max-width: calc(100% - 1.6em); vertical-align: middle; }
/* A recipe is one box holding its two pools. Below 880px they stack in one column;
   at 880px, the width where arithmetic says the widest row fits a half, they sit side by side.
   The screen decides that, never the cards.
   Rows never wrap, and the number columns hug their digits so the name column takes the slack. */
.recipe { margin: var(--gap-6) 0; border: var(--hairline) solid var(--rule);
          --pad: var(--gap-5); padding: var(--gap-4) var(--pad); font-size: var(--type-small); }
.recipe .ingredient { min-width: 0; }
.ingredient td { padding: var(--gap-1) var(--gap-4); }
.ingredient th { padding: var(--gap-3) var(--gap-4); }
.ingredient td.numeric, .ingredient th.numeric { width: 1%; padding-left: var(--gap-2); padding-right: var(--gap-2); }
.pool-title { margin: 0 0 var(--gap-3); font-size: var(--type-fine);
              text-transform: uppercase; letter-spacing: .06em; font-weight: 600; }
@media (min-width: 880px) {
  /* The pools dissolve into one shared grid: titles on the first row, tables on the second,
     so a title wrapping to two lines can never push its own table below its neighbour's. */
  .recipe { display: grid; grid-template-columns: 1fr 1fr; gap: var(--gap-3) var(--gap-7); }
  .recipe .ingredient { display: contents; }
  .recipe .ingredient > * { min-width: 0; }
  .recipe .ingredient:first-child > * { grid-column: 1; }
  .recipe .ingredient:last-child > * { grid-column: 2; }
  .recipe .pool-title { grid-row: 1; margin: 0; align-self: end; }
  .recipe .table-scroll, .recipe .table-frame { grid-row: 2; align-self: start; }
}
/* A card you can pick up: rose while it is only offered, mint once it is held and can be put back. */
.pick {
  display: inline-block; margin: var(--gap-1); padding: var(--gap-2) var(--gap-5); cursor: pointer; font-size: var(--type-fine);
  --face: var(--rose); --face-lit: #FCE4E8; --face-shade: #D9758C; --face-drop: #AC4A61;
}
.held { --face: var(--mint); --face-lit: #E2F3E9; --face-shade: #4FA274; --face-drop: #357853; }
.held::after { content: " ✕"; color: var(--mint-deep); font-size: var(--type-micro); }
.tray { margin: var(--gap-3) 0; }

/* ── the gallery ────────────────────────────────────────────────────────────────────────────── */

.gallery { display: grid; grid-template-columns: repeat(auto-fill, var(--scan)); justify-content: center; gap: var(--gap-7) var(--gap-6); margin: var(--gap-7) 0; }
body.page-gallery { overflow-x: clip; }  /* 50vw includes half the scrollbar; clip forgives it */
/* Negative margins let the wall span the whole window from inside the prose column. */
@media (min-width: 701px) {
  .gallery { margin-left: calc(50% - 50vw); margin-right: calc(50% - 50vw); padding: 0 var(--gap-7); }
}
.gallery figure { margin: 0; position: relative; }
/* Find-in-page cannot read a name painted into a scan, so each tile repeats it in transparent text
   laid over the printed one, and a search highlights the card where the reader is already looking.
   20px stands our lettering at the height of the game's. */
.tile-name {
  position: absolute; top: 2.7%; left: 4.5%; width: 90%; z-index: 1;
  color: transparent; font-size: 20px; line-height: 1.15; pointer-events: none;
}
/* clipped to nothing, but not also transparent: a browser's search skips text that is both */
.tile-aliases {
  position: absolute; width: 1px; height: 1px; overflow: hidden;
  clip-path: inset(50%); white-space: nowrap;
}
.gallery .card-image {
  display: block; width: var(--scan); aspect-ratio: 160 / 144; image-rendering: pixelated;
  border: var(--slab) solid; border-color: var(--wood-hi) var(--wood-sh) var(--wood-sh) var(--wood-hi);
  box-shadow: 6px 6px 0 rgb(0 0 0 / .3);
}
.gallery figcaption {
  text-align: center; color: var(--on-room); font-size: var(--type-fine); margin-top: var(--gap-4);
  letter-spacing: .1em; font-variant-numeric: tabular-nums;
}

/* ── the page for addresses with nothing buried at them ─────────────────────────────────────── */

.page-404 main { text-align: center; }
/* the art's own display height */
.lost-card { display: block; height: 300px; margin: var(--gap-8) auto var(--gap-4); }

/* ── on a phone ─────────────────────────────────────────────────────────────────────────────── */

@media (max-width: 700px) {
  /* a framed table runs out to the edges of whatever panel holds it */
  .table-frame { margin-inline: calc(-1 * var(--pad, 0px)); }
  /* a phone gets a bottom sheet rather than an anchored balloon */
  .card-preview .card-image {
    inset: auto auto max(12px, env(safe-area-inset-bottom)) 50%;
    margin: 0; transform: translateX(-50%); width: min(var(--scan), 88vw);
    height: auto;
  }
  .gallery { grid-template-columns: 1fr; }
  .gallery .card-image { width: min(var(--scan), 92vw); margin: 0 auto; }
}

/* ── the save editor's workbench ────────────────────────────────────────────────────────────── */

.key-row { display: flex; gap: var(--gap-4); flex-wrap: wrap; }
.row { display: flex; gap: var(--gap-4); align-items: center; flex-wrap: wrap; margin: var(--gap-5) 0; }
.row input[list] { flex: 1 1 10rem; min-width: 0; width: auto; }
.field { display: flex; gap: var(--gap-5); align-items: center; flex-wrap: wrap; margin: var(--gap-5) 0; }
/* one width for every label, so the editor's controls line up in a column */
.field .label { min-width: 11rem; }

#drop { border: var(--bevel) dashed var(--face-shade); padding: var(--gap-7); text-align: center; }
#drop p { margin: 0 0 var(--gap-4); }
#drop input { max-width: 100%; }
#drop.over { background: var(--face-lit); }

/* The save panel's rendered height, reserved so its section holds still while the module arrives.
   Measured from the rendered panel; one button-row taller below 368px, where its row wraps. */
#save-mount { min-height: 10.82rem; }
@media (max-width: 368px) { #save-mount { min-height: 13.69rem; } }

/* the deck reads down its columns, the way it is ordered */
ol.deck { list-style: none; padding: 0; margin: var(--gap-5) 0 0; display: grid; gap: var(--gap-3);
          grid-template-rows: repeat(10, auto); grid-auto-flow: column;
          grid-auto-columns: minmax(13rem, 1fr); overflow-x: auto; }
@media (max-width: 46rem) { ol.deck { grid-template-rows: repeat(20, auto); } }
ol.deck li { display: flex; gap: var(--gap-3); align-items: center; padding: var(--gap-1) var(--gap-3) var(--gap-1) var(--gap-3);
             border: var(--pen) solid var(--rule); }
/* touch-action: none hands the gesture to the drag; only the grip pays that price, so a finger
   anywhere else on the row still scrolls the page */
ol.deck .grip { cursor: grab; touch-action: none; user-select: none; opacity: .55; }
ol.deck li.dragging { opacity: .45; }
.dragging .grip { cursor: grabbing; }
ol.deck li.dropbefore { border-color: var(--face-drop); }
ol.deck .id, ol.deck .cost { font-variant-numeric: tabular-nums; font-size: var(--type-fine); }
ol.deck .name { flex: 1; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
ol.deck button, .key-row button { padding: var(--gap-1) var(--gap-4); }

.warn { margin: var(--gap-4) 0; padding: var(--gap-4) var(--gap-5);
        border: var(--bevel) solid var(--face-shade); border-left-width: var(--slab); background: var(--face-lit); }
.warn.refusal { border-color: var(--rose-deep); background: var(--rose); }
ul.plain { margin: var(--gap-4) 0; padding-left: var(--gap-7); }
/* wide enough for 9999 and the browser's spinner beside it */
.record-count { width: 5.5rem; }
#loaded[hidden], #refusals[hidden], #spentList[hidden] { display: none; }
#pile { display: flex; gap: var(--gap-4); align-items: center; flex-wrap: wrap; margin: var(--gap-5) 0; }
#pile input { width: 5.5rem; }  /* the record-count width, for the same four digits */
#touchedPiles { margin-top: var(--gap-5); }

/* ── the opponents' shelves ─────────────────────────────────────────────────────────────────── */

.duelist-cols { display: flex; gap: var(--gap-8); flex-wrap: wrap; }
/* the basis fits the longest line the data can deal: "2× Dragoness, the Enchanted Knight" at 298px */
.deck-half { flex: 1 1 17.5rem; min-width: 0; }
/* a deck line never wraps; too narrow for the longest one and it scrolls sideways, as the wide tables do */
.deck-lines { white-space: nowrap; }
.drops-half { flex: 2 1 20rem; min-width: 0; }
ul.deck-lines { list-style: none; margin: var(--gap-4) 0; padding: 0; font-size: var(--type-small); }
table.sortable td { padding: var(--gap-1) var(--gap-5); white-space: nowrap; }
table.sortable th { cursor: pointer; }
table.sortable th[aria-sort='ascending']::after { content: ' ▴'; }
table.sortable th[aria-sort='descending']::after { content: ' ▾'; }
/* the meter draws a row's odds against the pool's best, so the bar is relative and the number beside it absolute */
.meter { display: inline-block; width: 3.5rem; height: .5em; margin-left: var(--gap-4);
         background: var(--face-lit); border: var(--hairline) solid var(--face-shade); vertical-align: baseline; }
.meter span { display: block; height: 100%; background: var(--face-drop); }


/* ── Dungeon Dice Monsters: what this companion adds, in the ladders above ─────────────────── */

/* the pages that carry tile rows want more room than a column of prose */
.page-shop .wrap, .page-duelists .wrap, .page-dice .wrap, .page-gallery .wrap { max-width: 70rem; }

/* the four levels' colours, used for a tile's stripe and named once in a legend */
:root { --level-1: var(--mint-deep); --level-2: var(--sky-deep); --level-3: #B0741C; --level-4: var(--rose-deep); }
.legend { font-size: var(--type-small); display: flex; flex-wrap: wrap; align-items: center; gap: var(--gap-2) var(--gap-4); }
.swatch { display: inline-block; width: 1em; height: 1em; border-radius: 2px; vertical-align: -.15em; }
.swatch.level-1 { background: var(--level-1); } .swatch.level-2 { background: var(--level-2); } .swatch.level-3 { background: var(--level-3); } .swatch.level-4 { background: var(--level-4); }

/* a die's six faces as a row of pills, each in its crest's colour; a count follows the crest (Atk2) */
span.faces { display: inline-flex; flex-wrap: wrap; gap: 3px; vertical-align: middle; }
.crest { display: inline-block; padding: 1px 6px; border-radius: 4px; border: var(--hairline) solid; font: 600 var(--type-micro)/1.5 var(--mono); color: var(--ink); white-space: nowrap; }
.crest.sum { background: var(--cloud); border-color: var(--rule); color: #444; }
.crest.mov { background: var(--sky); border-color: var(--sky-deep); }
.crest.atk { background: var(--rose); border-color: var(--rose-deep); }
.crest.def { background: var(--butter); border-color: #B0741C; }
.crest.mag { background: #E9DCF5; border-color: var(--purple); }
.crest.tra { background: var(--mint); border-color: var(--mint-deep); }

/* the Japanese name on its own quiet line */
.jp { display: block; font-size: var(--type-fine); word-break: keep-all; }
.jp .reading { color: #555; }   /* a Japanese name breaks only where a <wbr> lets it: after ・ or ： */

/* the dice table: names and abilities wrap at the places marked for it; numbers and pills never break */
/* fixed columns, so a long name is pressed to wrap at its marks instead of widening the table */
table.dice { table-layout: fixed; width: 100%; min-width: 64rem; }   /* a phone keeps the desktop's columns and scrolls the frame, as the shelf does */
table.dice th:nth-child(2) { width: 13.5rem; } table.dice th:nth-child(3) { width: 17rem; } table.dice th:nth-child(4) { width: 15rem; }
table.dice td { vertical-align: top; }
/* dm4's sortable tables keep every cell on one line; here the name and the ability are prose and wrap */
table.dice td.name, table.dice td.ability { white-space: normal; }
table.dice td.stats { white-space: normal; }   /* six hearts and the two gauges may take two lines; each piece stays whole */
table.dice td.faces { white-space: nowrap; }
table.dice td.faces span.faces { flex-wrap: nowrap; }
table.dice .kind { display: block; font-size: var(--type-fine); }
table.dice td.ability { font-size: var(--type-fine); }
td.ability .crest { font-size: var(--type-micro); vertical-align: .05em; }
/* a cost stands in a little box of its own, the way the game draws it: the number, a times sign, the crest */
.cost { display: inline-block; white-space: nowrap; border: var(--hairline) solid var(--rule); background: var(--paper); padding: 0 var(--gap-3); margin-left: var(--gap-2); font-family: var(--mono); font-size: var(--type-fine); }
td.stats .hearts, td.stats .gauge { white-space: nowrap; margin-right: var(--gap-4); }

/* a tile: an outlined box holding the portrait, a stripe in the level's colour, the name, and the page's own line (price, or odds) */
.tiles { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: var(--gap-3); }
.tile { display: flex; flex-direction: column; align-items: center; width: 6.6rem; padding: var(--gap-2) var(--gap-2) var(--gap-3); border: var(--hairline) solid var(--rule); background: var(--paper);
  text-align: center; font-size: var(--type-fine); line-height: 1.2; position: relative; }
.tile .portrait { width: 65px; height: 56px; image-rendering: pixelated; display: block; }
.tile .stripe { display: block; width: 65px; height: 4px; margin-bottom: var(--gap-2); }
.tile.level-1 .stripe { background: var(--level-1); } .tile.level-2 .stripe { background: var(--level-2); } .tile.level-3 .stripe { background: var(--level-3); } .tile.level-4 .stripe { background: var(--level-4); }
.tile .name { display: block; height: 2.6em; overflow: hidden; }   /* two lines, and room under the second for its dotted rule */
/* what Grandpa charges and what he pays, one row each across the tile so a 50,000 has room: the shop's butter for buying, money-green for selling */
.tile .prices { display: flex; flex-direction: column; gap: 2px; width: 100%; margin-top: var(--gap-1); font-size: var(--type-fine); line-height: 1.3; font-variant-numeric: tabular-nums; }
/* the page's own face rather than the monospace stack: a phone's monospace is wider than a desktop's, and this one travels with the site.
   If a row still cannot hold both, the label wraps above the price instead of poking out of the tile. */
.tile .prices > span { display: flex; flex-wrap: wrap; justify-content: space-between; align-items: baseline; gap: 0 4px; padding: 1px 4px; border: var(--hairline) solid; border-radius: 3px; white-space: nowrap; }
.tile .prices > span > :last-child { margin-left: auto; }
.tile .prices small { font: 600 var(--type-micro)/1.2 "Quicksand", "Quicksand fallback", "M PLUS Rounded 1c", sans-serif; letter-spacing: .06em; text-transform: uppercase; color: var(--face-drop); }
.tile .buy { background: var(--butter); border-color: #B0741C; }
.tile .sell { background: var(--mint); border-color: var(--mint-deep); }
.tile .twice { position: absolute; top: var(--gap-2); left: var(--gap-2); background: var(--butter); border: var(--hairline) solid #B0741C; font-size: var(--type-micro); padding: 0 3px; line-height: 1.3; }
/* the odds under a die: a bar as wide as the portrait on one scale for every duelist (full at 20% a win), and the number */
.odds { display: block; width: 65px; position: relative; padding-top: 7px; margin-top: var(--gap-1); font-family: var(--mono); font-size: var(--type-fine); }
.odds::before { content: ""; position: absolute; top: 0; left: 0; right: 0; height: 5px; background: var(--cloud); }
.odds i { position: absolute; top: 0; left: 0; height: 5px; background: var(--face-drop); }
.odds b { font-weight: normal; }
.face { width: 32px; height: 32px; image-rendering: pixelated; vertical-align: middle; border: var(--hairline) solid var(--rule); }

/* the shelf as a ladder: a rail of rungs on the left, each rung's dice as a band of tiles on the right */
.ladder { display: grid; grid-template-columns: 8rem 1fr; gap: 0; }
/* a phone keeps the ladder's shape and scrolls it sideways, rather than stacking one tile a row */
.shelf-scroll { overflow-x: auto; }
@media (max-width: 700px) {
  .ladder { min-width: 42rem; }
  .table-toggle > p { display: contents; }               /* pandoc wraps the label and buttons in a paragraph */
  .table-toggle span { flex-basis: 100%; }             /* the label takes its own line; the two buttons stay together */
}
.rail { padding: var(--gap-4) var(--gap-4) var(--gap-4) 0; border-right: var(--pen) solid var(--face-shade); border-bottom: var(--pen) solid var(--face-shade); }
.rail b { display: block; font-size: var(--type-small); }
.rail b .points { color: var(--face-drop); }
.rail small { display: block; font-size: var(--type-fine); }
.band { padding: var(--gap-4) 0 var(--gap-4) var(--gap-4); border-bottom: var(--pen) solid var(--face-shade); align-content: flex-start; }
/* rungs a once-through run does not reach are downplayed, as the proof of concept did */
.rail.beyond { color: #666; }
.rail.beyond b .points { color: #666; }
.band.beyond .tile { filter: saturate(.45); opacity: .75; }
.beyond-note { color: var(--face-drop); }

/* a duelist is a card: their face and names, then the two parts of their list as boxed tile rows, then the cups */
.duelist { margin-top: var(--gap-6); padding: var(--gap-4) var(--gap-5) var(--gap-5); border: var(--pen) solid var(--face-shade); background: color-mix(in srgb, var(--face) 14%, var(--paper)); }
.duelist h3 { display: flex; align-items: center; flex-wrap: wrap; gap: var(--gap-3) var(--gap-4); margin: 0 0 var(--gap-4); font-size: var(--type-sub); }
.duelist h3 .jp { font-weight: normal; }
.duelist h3 small { font-weight: normal; font-size: var(--type-fine); flex-basis: 100%; }
.duelist .group { border: var(--hairline) solid var(--face-shade); background: var(--paper); padding: var(--gap-3) var(--gap-4) var(--gap-4); margin-top: var(--gap-3); }
.duelist h4 { font-size: var(--type-micro); text-transform: uppercase; letter-spacing: .08em; margin: 0 0 var(--gap-3); }
.duelist .meet { margin-top: var(--gap-4); }
.cups { list-style: none; margin: 0; padding: 0; display: grid; grid-template-columns: repeat(6, 1fr); gap: var(--gap-2); font-size: var(--type-micro); }
.cup { border: var(--hairline) solid var(--rule); padding: var(--gap-1) var(--gap-3); background: var(--paper); line-height: 1.2; }
.cup.sure { background: var(--face); border-color: var(--face-drop); }
.cup.maybe { background: color-mix(in srgb, var(--face) 45%, var(--paper)); }
.cup.never { color: #777; }
.cup small { display: block; }
@media (max-width: 640px) { .cups { grid-template-columns: repeat(3, 1fr); } .ladder { grid-template-columns: 6rem 1fr; } }

/* which cartridge's numbers: the shape of dm4's art toggle */
.table-toggle { display: flex; flex-wrap: wrap; align-items: center; gap: var(--gap-3); margin: var(--gap-4) 0 var(--gap-6); font-size: var(--type-small); }

/* the card that opens beside a hovered name: the card page in dm4's wooden frame, the description as its alt text */
#card-tip { inset: auto; top: var(--tip-top); left: var(--tip-left); width: var(--tip-width, 240px); margin: 0; padding: 0; background: var(--paper);
  border: var(--slab) solid; border-color: var(--wood-hi) var(--wood-sh) var(--wood-sh) var(--wood-hi); box-shadow: 6px 6px 0 rgb(0 0 0 / .35); }
#card-tip img { display: block; width: 100%; height: auto; image-rendering: pixelated; }
/* the faces under the picture: a paper strip of the table's pills, never wider than the frame */
#card-tip .tip-faces { display: flex; flex-wrap: wrap; justify-content: center; gap: 3px; padding: 5px 4px 4px; }
#card-tip .tip-faces .crest { padding: 1px 4px; }

/* the who-has-it answer */
.answer h3 { display: flex; align-items: center; gap: var(--gap-4); font-size: var(--type-sub); }
.answer h3 img { width: 240px; height: 160px; image-rendering: pixelated; border: var(--pen) solid var(--rule); }
.answer ul { list-style: none; padding: 0; }
.answer li { display: flex; align-items: center; gap: var(--gap-3); padding: var(--gap-2) 0; border-bottom: var(--hairline) solid var(--rule); }
.answer li .jp { display: inline; }

/* the gallery: the card pages at their true size */
.gallery { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: var(--gap-5); }
.gallery li { width: 240px; font-size: var(--type-fine); text-align: center; }
.gallery img { display: block; width: 240px; height: 160px; image-rendering: pixelated; border: var(--pen) solid var(--rule); margin-bottom: var(--gap-2); }

/* how a duelist plays, and what they say: a sentence, then a fold-out of the eight lines */
.duelist .play { margin-top: var(--gap-4); }
.duelist .play p { margin: 0; }
.duelist .lines { margin: var(--gap-4) 0 0; }
.duelist .lines summary { font-size: var(--type-small); }
.duelist .lines h4 { margin-top: var(--gap-4); }
.duelist .lines dl { margin: 0; display: grid; grid-template-columns: max-content 1fr; gap: var(--gap-2) var(--gap-4); font-size: var(--type-small); }
.duelist .lines dt { color: var(--face-drop); }
.duelist .lines dd { margin: 0; min-width: 0; }
@media (max-width: 700px) {
  .duelist .lines dl { grid-template-columns: 1fr; gap: var(--gap-1); }   /* a phone: when above, the line below it */
  .duelist .lines dd { margin-bottom: var(--gap-3); }
}
.duelist .lines dd .jp { display: block; color: var(--face-drop); font-size: var(--type-fine); }
.duelist .lines q { quotes: "“" "”"; }
