/* Local palette: one-off colors for this page, named by role. Global tokens live in style.css. */
:root {
  --so-letter-body-bg: #e9e2c8;
  --so-trophy-shelf-bg: #b07a4a;
  --so-trophy-shelf-bg-2: #fff8ec;
  --so-panel-bg: #bfe8ff;
  --so-stars-ink: #9a6a0c; /* deep gold: 4.3:1 on the review card (#e0a100 was 2.1:1) */
  --so-tiles-bg: #ffe9a8;
  --so-snap-bg: #ffe896;
  /* Gazette zodiac tiles: one material per sign (.zt-<material>) and its constellation ink */
  --so-zt-moonstone: radial-gradient(circle at 25% 15%, #ffffff 0, transparent 45%), linear-gradient(135deg, #dfe6fb, #c6d3f2 40%, #e9ddfb 70%, #bccff0);
  --so-zt-moonstone-ink: #5a6fb4;
  --so-zt-foil: linear-gradient(115deg, transparent 30%, rgb(255 255 255 / .7) 38%, transparent 46%), linear-gradient(135deg, #f6d873, #fff3c2 22%, #ddb03f 46%, #fbe7a0 64%, #c8942a);
  --so-zt-foil-ink: #9a6a0c;
  --so-zt-wool: repeating-linear-gradient(60deg, rgb(255 255 255 / .28) 0 4px, transparent 4px 8px), repeating-linear-gradient(-60deg, rgb(255 255 255 / .2) 0 4px, transparent 4px 8px), #ef9cc0;
  --so-zt-wool-ink: #a33d6d;
  --so-zt-enamel: radial-gradient(circle at 28% 22%, #ffd6e4 0, transparent 38%), linear-gradient(160deg, #ff7eab, #d93a73);
  --so-zt-enamel-ink: #b0245c;
  --so-zt-brass: radial-gradient(circle at 9px 9px, #7a5410 0 2.5px, transparent 3px), radial-gradient(circle at calc(100% - 9px) 9px, #7a5410 0 2.5px, transparent 3px),
    radial-gradient(circle at 9px calc(100% - 9px), #7a5410 0 2.5px, transparent 3px), radial-gradient(circle at calc(100% - 9px) calc(100% - 9px), #7a5410 0 2.5px, transparent 3px),
    linear-gradient(160deg, #f6d27a, #d9a640 45%, #a87a1f);
  --so-zt-brass-ink: #7a5410;
  --so-zt-seaglass: radial-gradient(circle at 72% 28%, rgb(255 255 255 / .55), transparent 50%), linear-gradient(140deg, #c6f3e7, #88d9ca 55%, #5fc0b4);
  --so-zt-seaglass-ink: #23806f;
  --so-zt-lapis: radial-gradient(circle, #f5d36b 0 1px, transparent 1.6px) 0 0 / 13px 11px, radial-gradient(circle, #f5d36b 0 .8px, transparent 1.3px) 6px 5px / 17px 15px, linear-gradient(150deg, #3554b0, #1f3480);
  --so-zt-lapis-ink: #2a46a0;
  --so-zt-pearl: conic-gradient(from 210deg at 40% 40%, #fdf0ff, #dff2ff, #fff4d8, #ffe2ef, #e6e2ff, #fdf0ff);
  --so-zt-pearl-ink: #8064b4;
  --so-zt-parchment: radial-gradient(circle at 0 0, #e0b13f 0 16px, transparent 17px), radial-gradient(circle at 100% 100%, #e0b13f 0 16px, transparent 17px), linear-gradient(135deg, #f7ecd0, #e9d6a8);
  --so-zt-parchment-ink: #8a5a1c;
  --so-zt-jade: radial-gradient(ellipse at 30% 25%, rgb(255 255 255 / .4), transparent 55%), radial-gradient(ellipse at 85% 80%, #2f8a5c, transparent 55%), linear-gradient(135deg, #95dfb2, #4fae7e);
  --so-zt-jade-ink: #23704a;
  --so-zt-stained: conic-gradient(from 20deg at 30% 62%, var(--sun) 0 70deg, var(--ink) 0 73deg, var(--pink) 0 140deg, var(--ink) 0 143deg, var(--grape) 0 215deg, var(--ink) 0 218deg, var(--sky) 0 290deg, var(--ink) 0 293deg, var(--lime) 0 357deg, var(--ink) 0);
  --so-zt-stained-ink: #6a3fd0;
  --so-zt-velvet: radial-gradient(ellipse at 30% 20%, #6d5ca2 0, transparent 60%), linear-gradient(160deg, #3b2f5c, #1f1736);
  --so-zt-velvet-ink: #3b2f5c;
  --so-zt-porcelain: radial-gradient(circle, transparent 0 7px, #3d6bc4 7px 8.5px, transparent 9px) 0 0 / 22px 22px, radial-gradient(circle, #3d6bc4 0 2px, transparent 2.5px) 11px 11px / 22px 22px, #f2f6ff;
  --so-zt-porcelain-ink: #2f56a8;
  --so-zt-glimshard: linear-gradient(120deg, transparent 34%, rgb(255 255 255 / .6) 40%, transparent 47%), conic-gradient(from 30deg at 62% 40%, #d8f9ff, #8ff0ff 25%, #b391ff 50%, #ff94c2 75%, #d8f9ff);
  --so-zt-glimshard-ink: #5b3fb0;
  --so-zt-marbled: radial-gradient(ellipse 40% 26% at 22% 30%, #9fb0ff, transparent 70%), radial-gradient(ellipse 34% 22% at 78% 72%, #c3b2ff, transparent 70%), repeating-linear-gradient(115deg, #eef0ff 0 6px, #d4dbff 6px 9px);
  --so-zt-marbled-ink: #27306e;
}
/* Social + collections + Gazette pages. Loaded via page({head}) by mail/lookup/collections/gazette routes,
   plus home, login/register, land pages and the error pages in server.js for their page-scoped rules. */

/* Tabs (album pages, mail folders) */
.album-tabs { display: flex; flex-wrap: wrap; gap: 12px; margin: 0 0 16px; }
.head-row + .album-tabs { margin-top: 12px; } /* score tables: the tabs sit under the Play / All games buttons */
.album-tabs a {
  display: inline-flex; align-items: center; min-height: 44px; padding: 6px 16px; border: 2px solid var(--ink); border-radius: 999px; background: var(--card);
  font: 600 .98rem var(--display); color: var(--ink); text-decoration: none; box-shadow: var(--shadow-sm);
}
.album-tabs a[aria-current="page"] { background: var(--pick); }
.album-tabs small { color: var(--muted); font-weight: 600; }
.album-tabs a[aria-current="page"] small { color: var(--ink); } /* --muted on --pick is 3.8:1 */

/* Mail */
.mail-table tr.unread td { font-weight: 800; background: var(--hi-soft); }
.mail-pick { width: 1%; }
.mail-pick label { display: inline-flex; align-items: center; justify-content: center; min-width: 44px; min-height: 44px; } /* whole square is the tap target */
.mail-who { display: flex; align-items: center; gap: 8px; } /* a span inside the td: flex on the td itself breaks the table row */
.mail-who svg { flex: none; border-radius: 50%; background: var(--tint); }
.mail-date { white-space: nowrap; }
.mail-note { margin-top: 12px; } /* the sent folder has no delete row between table and note */
.mail-form { display: grid; gap: 12px; max-width: 640px; }
.letter-head { display: flex; gap: 14px; align-items: center; margin-bottom: 12px; }
.letter-head h1 { margin: 0; }
.letter-head svg { flex: none; }
.ink-seal { display: flex; align-items: center; justify-content: flex-end; gap: 10px; margin: 12px 0; font-style: italic; color: var(--muted); }
.ink-seal svg { flex: none; rotate: -12deg; }
@media (max-width: 560px) { .ink-seal { justify-content: center; } }
.letter-body {
  white-space: pre-wrap; overflow-wrap: anywhere; padding: 16px 18px; margin-bottom: 16px;
  /* one ruled line under each 28px text line: the tile starts at the 16px top padding */
  background: linear-gradient(transparent 27px, var(--so-letter-body-bg) 27px) 0 16px / 100% 28px, var(--parchment);
  border: 2px solid var(--ink); border-radius: var(--r-tile);
  line-height: 28px;
}
@media (max-width: 560px) {
  /* Phones: each letter is a two-line row, [pick] sender . date over the subject */
  .mail-table, .mail-table tbody { display: block; }
  .mail-table thead { display: none; }
  .mail-table tr { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; align-items: center; gap: 2px 10px; padding: 10px 12px; }
  .mail-table.mail-sent tr { grid-template-columns: minmax(0, 1fr) auto; }
  .mail-table tbody tr.unread { background: var(--hi-soft); }
  .mail-table tr + tr { border-top: 1px solid var(--rule); }
  .table.mail-table tr > td { padding: 0; border: 0; background: none; width: auto; }
  .mail-pick { grid-row: span 3; }
  .mail-from { grid-column: 2 / -1; }
  .mail-sent .mail-from { grid-column: 1 / -1; }
  .mail-who svg { width: 28px; height: 28px; }
  .mail-subject { grid-column: 2 / -1; }
  .mail-sent .mail-subject { grid-column: 1 / -1; }
  .mail-date { grid-column: 2 / -1; font-size: var(--fs-xs); color: var(--muted); } /* third line: a right-hand date squeezed long senders into four-line names */
  .mail-sent .mail-date { grid-column: 1 / -1; }
}

/* Profile card + pet scrapbook */
.lookup-head { display: flex; gap: 20px; align-items: center; flex-wrap: wrap; }
.lookup-head h1 { margin: 0; }
.lookup-avatar svg { display: block; border-radius: 50%; box-shadow: var(--shadow-sm); } /* the frame draws its own edge */
.lookup-stats { display: flex; flex-wrap: wrap; gap: 10px; margin: 8px 0 12px; }
.lookup-stats div { background: var(--tint); border: 2px solid var(--ink); border-radius: var(--r-sm); padding: 4px 12px; }
.lookup-stats dt { font: 600 var(--fs-xs) var(--display); color: var(--muted); }
.lookup-stats dd { margin: 0; font-weight: 800; }
/* Phones: profile head is a centered hero; the text column may shrink so long usernames wrap instead of pushing the page wide */
@media (max-width: 560px) {
  .lookup-head { flex-direction: column; text-align: center; gap: 12px; }
  .lookup-head > div { max-width: 100%; min-width: 0; }
  .lookup-head h1 { overflow-wrap: anywhere; }
  .lookup-head h1 :is(.title-tag, .townsfolk) { display: block; width: fit-content; margin: 6px auto 0; white-space: normal; } /* the title pill on its own centered row under the name */
  .lookup-head .lede { margin-inline: auto; }
  .lookup-head .lookup-stats div { text-align: left; }
  .lookup-head .btn-row { justify-content: center; }
}
@media (max-width: 560px) { .lookup-stats { display: grid; grid-template-columns: 1fr 1fr; } } /* 2x2, not 3 + 1 */
.petpage-head { display: flex; gap: 14px; align-items: center; flex-wrap: wrap; }
.petpage-head > svg { flex: none; }
.petpage-head > div { flex: 1 1 180px; min-width: 0; } /* keeps the pet beside its title on phones */
.petpage-head h1 { margin: 0; }
@media (max-width: 560px) {
  .petpage-head { gap: 10px; }
  .petpage-head > svg { width: 64px; height: 64px; }
  .petpage-head h1 { font-size: 1.6rem; }
}
.petpage-head .btn { margin-left: auto; }
.user-html { padding: 0; overflow: hidden; resize: vertical; min-height: 96px; border-end-end-radius: 6px; } /* height is set inline from frameHeight(); drag the corner for more */
.user-html .user-frame { height: 100%; }
.user-frame { display: block; width: 100%; border: 0; background: #fff; } /* style-ok: frames a player-styled profile page, which expects white */

/* HTML editors */
.html-editor { display: grid; gap: 12px; }
.editor-split { display: grid; grid-template-columns: repeat(auto-fit, minmax(280px, 1fr)); gap: 16px; }
.editor-split textarea { font: 500 var(--fs-sm)/1.45 ui-monospace, 'SF Mono', Menlo, monospace; min-height: 420px; resize: vertical; }
.editor-split .user-frame { border: 2px solid var(--ink); border-radius: var(--r-tile); min-height: 420px; }
.editor-preview p { margin: 0 0 4px; font-weight: 700; } /* reads like the textarea's label, so both boxes start level */
@media (max-width: 560px) { .editor-split textarea, .editor-split .user-frame { min-height: 280px; } }
.avatar-picks { align-items: center; }
.avatar-picks .pick { padding: 4px; }

/* Avatars */
.avatar-grid { grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); }
@media (max-width: 560px) { .avatar-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 12px; } } /* 150px min made phones a one-tile column, 30 screens long */
.avatar-tile {
  display: flex; flex-direction: column; align-items: center; gap: 4px; text-align: center; padding: 12px 10px;
  background: var(--card); border: 2px solid var(--ink); border-radius: var(--r-tile); box-shadow: var(--shadow-sm);
}
.avatar-tile small { color: var(--muted); font-size: var(--fs-xs); line-height: 1.3; }
.avatar-tile > :last-child { margin-top: auto; } /* the button or pill sits on the tile's floor */
.avatar-tile.current { background: var(--hi); box-shadow: 0 0 0 3px var(--pink), var(--shadow-sm); }
.avatar-tile .btn-row { display: flex; flex-wrap: wrap; gap: 12px; justify-content: center; }
.locked svg { filter: grayscale(1) brightness(.35) opacity(.45); }
.lock-pill { background: var(--tint-2); }

/* Trophies */
.trophy-shelf {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(140px, 1fr)); align-items: start; gap: 18px 12px; padding: 16px 12px 24px; /* 2 columns on phones; dates sit above the 14px plank */
  background: linear-gradient(transparent calc(100% - 14px), var(--so-trophy-shelf-bg) calc(100% - 14px));
  border: 2px solid var(--ink); border-radius: var(--r-tile); background-color: var(--so-trophy-shelf-bg-2);
}
.trophy-shelf figure { margin: 0; min-width: 0; display: grid; align-content: start; justify-items: center; text-align: center; } /* icons share one top line per row */
.trophy-shelf figcaption { font: 600 var(--fs-sm)/1.2 var(--display); }
.trophy-shelf figcaption small { display: block; color: var(--muted); font: 600 var(--fs-xs) var(--body); }
.item-tile.locked b, .item-tile.locked small { color: var(--muted); }
.item-tile.locked .item-svg { filter: brightness(0) opacity(.25); } /* unearned trophy: its shape as a dark silhouette, the details hidden (same look as fishing.css) */

/* Land pages: neighbors side by side, world map under them on phones */
.land-nav { align-items: center; }
@media (max-width: 560px) {
  .land-nav { display: grid; grid-template-columns: 1fr 1fr; }
  .land-nav .btn { padding-inline: 12px; }
  .land-map { grid-column: 1 / -1; grid-row: 2; }
}

/* Register hints */
.auth-card label small { font-size: var(--fs-sm); font-weight: 600; color: var(--muted); }

/* Error pages (server.js): a pet, what happened, a way back */
.oops h1 { color: var(--ink); }
.oops > svg { display: block; margin: 0 auto 4px; }
.oops p { max-width: 52ch; margin-inline: auto; }
.oops .btn-row { justify-content: center; }

/* Gazette: a cartoon broadsheet. Newsprint card, double-ruled masthead, section tabs, ruled columns. */
.paper {
  --news: #fbf6e6; --news-2: #f1e8cc; --red: #c62d33; /* AA on --news */
  background: radial-gradient(circle, color-mix(in oklab, var(--ink) 7%, transparent) .8px, transparent 1.2px) 0 0 / 6px 6px, var(--news);
  font-size: 1.02rem;
}
.masthead { text-align: center; border-bottom: 5px double var(--ink); padding-bottom: 8px; }
.masthead h1 { font-size: clamp(2.1rem, 7vw, 4rem); margin: 0; letter-spacing: .01em; color: var(--sun); -webkit-text-stroke: 2px var(--ink); paint-order: stroke fill; text-shadow: 4px 4px 0 var(--ink); }
.ears { display: flex; justify-content: space-between; gap: 8px; margin: 0 0 4px; font: 600 var(--fs-sm) var(--display); text-transform: uppercase; letter-spacing: .06em; }
.dateline { margin: 6px 0 0; font-style: italic; border-top: 2px solid var(--ink); padding-top: 6px; }
.paper-tabs { display: flex; gap: 4px; overflow-x: auto; margin: 0 0 18px; border-bottom: 3px solid var(--ink); scrollbar-width: none; }
.paper-tabs a { flex: none; display: inline-flex; align-items: center; min-height: 44px; padding: 8px 14px; font: 600 var(--fs-sm) var(--display); color: var(--ink); text-decoration: none; border: 3px solid transparent; border-bottom: 0; border-radius: 12px 12px 0 0; }
.paper-tabs a:hover { background: var(--news-2); }
.paper-tabs a[aria-current="page"] { background: var(--pick); border-color: var(--ink); }
@media (min-width: 1000px) { .paper-tabs { justify-content: safe center; } } /* desktop: section links centered under the masthead */
/* Phones and small tablets (pick T2, 2026-10-15): six equal buttons, three across and two rows */
@media (max-width: 767px) {
  .paper .paper-tabs { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 12px 8px; overflow: visible; border-bottom: 0; }
  .paper .paper-tabs a { display: flex; align-items: center; justify-content: center; text-align: center; min-height: 44px; padding: 4px; border: 3px solid var(--ink); border-radius: var(--r-sm); white-space: nowrap; }
}
.paper h2 { font-size: 1.3rem; }
.paper section + section { margin-top: 14px; }

/* Front page as a broadsheet (gazette.js front, DECISIONS.md 2026-10-05, tightened 2026-10-15): the lead and its next two
   stories (.front-lead) share the top row with the Gazette photo, so a short lead leaves no hole beside the tall photo; then
   .front-flow sets every box in columns the browser balances; the Funnies and the weather strip run full width. Phones: one
   column, reordered with `order`, with the rest swapped for one-line teasers (.gz-teasers). */
.front { display: grid; grid-template-columns: minmax(0, 1.55fr) minmax(0, 1fr); gap: 0 24px; align-items: start; }
.front > :not(.front-lead, .gz-photo), .front.no-photo > .front-lead { grid-column: 1 / -1; }
.paper .front > .gz-photo { margin: 0; border-left: 2px solid var(--ink); padding-left: 24px; }
.lead-more { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0 32px; margin-top: 16px; border-top: 2px solid var(--ink); padding-top: 14px; }
.paper .lead-more > .story { margin: 0; }
.lead-more > .story + .story { border-left: 2px solid var(--rule); padding-left: 32px; margin-left: -16px; }
.lead-more .story h3 { font-size: 1.1rem; }
.lead-more .story .photo { width: min-content; } /* the caption wraps after its underscore instead of widening the print */
.lead-more .story .photo svg { width: 64px; height: auto; } /* a smaller print, so a long first word still fits beside it */
/* a narrow lead column (tablets) stacks the two stories, so a print never squeezes its story to a word a line */
.front-lead { container-type: inline-size; }
@container (max-width: 520px) {
  .lead-more { grid-template-columns: minmax(0, 1fr); }
  .lead-more > .story + .story { border-left: 0; padding-left: 0; margin-left: 0; border-top: 2px dashed var(--rule); padding-top: 12px; margin-top: 12px; }
}
.front-flow { columns: 2; column-gap: 32px; column-rule: 2px solid var(--rule); margin-top: 24px; border-top: 2px solid var(--ink); padding-top: 14px; }
@media (min-width: 1100px) { .front-flow { columns: 3; column-gap: 40px; } }
.paper .front-flow > * { break-inside: avoid; margin: 0 0 16px; }
.front-flow .town-box :is(li, p) { break-inside: avoid; }
.front-flow :is(h2, h3) { break-after: avoid; }
.front-flow h2 { font-size: 1.1rem; border-bottom: 2px solid var(--ink); padding-bottom: 2px; }
.front-flow .cap-ad h2 { border-bottom: 0; }
.front-flow .story h3 { font-size: 1.1rem; }
.front-flow .my-stars > :last-child { margin-bottom: 0; }
.gz-cottage-pets { display: flex; gap: 8px; margin: 4px 0 6px; }
/* Daily Darlings: the two side by side in a "your stuff" inset. Today's poll: a dashed slip like Twisty Tam's ad. */
.gz-darlings { text-align: center; background: var(--card); border: 2px solid var(--ink); border-radius: var(--r-sm); padding: 8px 12px; }
.gz-darlings h2 a { color: inherit; }
.gz-darlings .potd-pair { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 12px; }
.gz-darlings .potd-pair svg { width: 96px; height: auto; max-width: 100%; }
.gz-darlings .potd-pair p { margin: 4px 0 0; overflow-wrap: anywhere; font-size: var(--fs-sm); }
.gz-poll { background: var(--sun-cream); border: 2px dashed var(--ink); border-radius: var(--r-sm); padding: 8px 12px; }
.paper .front-flow :is(.gz-darlings, .gz-poll) h2 { border-bottom: 0; }
.gz-poll-q { font: 600 1.05rem var(--display); margin: 0 0 8px; }
.gz-poll .link-line { margin: 0; }
/* Phone teasers and the phone-only copies they link to (Town News' weather, Puzzles' gem corner): hidden on desktop */
.gz-teasers, .gz-phone-only { display: none; }
@media (max-width: 767px) {
  .front { display: flex; flex-direction: column; align-items: stretch; gap: 16px; }
  .front-flow, .front-lead, .lead-more { display: contents; }
  .paper .front > *, .paper .front-flow > * { margin: 0; }
  .paper .front > .gz-photo { border-left: 0; padding-left: 0; border-top: 2px solid var(--ink); padding-top: 18px; }
  /* lead, photo, your stuff, the Funnies, then the teasers; the Darlings, the poll slip and Twisty Tam's ad close the page */
  .front .lead-story { order: 0; } .front .gz-photo { order: 1; } .front .gz-stars { order: 2; } .front .gz-col { order: 3; } .front .gz-cottage { order: 4; }
  .front .comic { order: 5; } .front .gz-teasers { order: 6; } .front .gz-darlings { order: 7; } .front .gz-poll { order: 8; } .front .cap-ad { order: 9; }
  .front :is(.story, .town-box, .wx, .hint, .gz-carts) { display: none; }
  .gz-teasers, .gz-phone-only { display: block; }
  .paper .comic { margin: 0; }
  .gz-teasers ul { list-style: none; margin: 0; padding: 0; }
  .gz-teasers li { padding: 6px 0; } /* 12px between two teasers' tap areas, the dashed rule in the middle */
  .gz-teasers :is(a, summary) { display: flex; flex-direction: column; justify-content: center; min-height: 44px; padding: 2px 0; color: var(--ink); text-decoration: none; }
  .gz-teasers summary { cursor: pointer; list-style: none; }
  .gz-teasers summary::-webkit-details-marker { display: none; }
  .gz-teasers details p { margin: 0 0 10px; }
  .gz-teasers li + li { border-top: 1px dashed var(--rule); }
  .gz-teasers small { font: 700 .78rem var(--display); text-transform: uppercase; letter-spacing: .12em; color: var(--red); }
  .gz-teasers span { font: 600 1rem var(--display); text-decoration: underline; text-decoration-color: var(--link); text-decoration-thickness: 2px; text-underline-offset: 3px; }
  .gz-teasers a span::after { content: ' »'; color: var(--link); }
  .gz-teasers summary span::after { content: ' ▾'; color: var(--link); }
  .gz-teasers details[open] summary span::after { content: ' ▴'; }
  .gz-poll { text-align: center; }
  .gz-poll .btn { width: 100%; }
}
/* The Gazette photo: a tilted print, the pet standing in front of the place it was snapped in */
.ph-frame { margin: 0 12px 24px; background: #fff; border: 3px solid var(--ink); padding: 8px; box-shadow: 5px 5px 0 var(--ink); rotate: 1.5deg; } /* style-ok: photo print border */
.shot { height: 250px; background: var(--tint) center 70% / cover no-repeat; border: 2px solid var(--ink); display: flex; align-items: flex-end; justify-content: center; overflow: hidden; }
.shot svg { width: auto; height: 94%; margin-bottom: 1%; filter: drop-shadow(0 4px 0 color-mix(in oklab, var(--ink) 25%, transparent)); }
.gz-photo h3 { font-size: 1.5rem; line-height: 1.12; margin-bottom: 6px; }
.gz-photo .cap { font-size: 1.05rem; margin-bottom: 6px; }
.gz-photo .credit { font: italic 600 .85rem var(--body); color: var(--muted); margin: 0; }
@media (max-width: 767px) { .ph-frame { rotate: -1deg; } .shot { height: 230px; } .gz-photo h3 { font-size: 1.35rem; } }
.kicker { margin: 0 0 2px; font: 700 .78rem var(--display); text-transform: uppercase; letter-spacing: .12em; color: color-mix(in oklab, var(--ink) 65%, transparent); }
.kicker.is-real { color: var(--red); }
.kicker.is-real::before { content: '● '; }
.lead-story h2 { font-size: clamp(1.7rem, 4.6vw, 2.6rem); line-height: 1.08; margin-bottom: 10px; }
.lead-body { display: flow-root; }
.lead-body .photo { float: left; margin: 0 18px 8px 0; }
@media (max-width: 560px) { .lead-body .photo { float: none; display: table; margin: 0 auto 12px; } }
.dropcap::first-letter { float: left; font: 700 2.6em/1 var(--display); margin: 4px 10px 0 0; padding: 4px 10px; background: var(--sun); border: 3px solid var(--ink); border-radius: 10px; box-shadow: 3px 3px 0 var(--ink); }
.photo { margin: 0; display: inline-block; background: #fff; border: 3px solid var(--ink); padding: 6px 6px 2px; box-shadow: 4px 4px 0 var(--ink); rotate: -1.5deg; } /* style-ok: photo print border */
.photo svg { display: block; background: radial-gradient(circle, color-mix(in srgb, #000 7%, transparent) 1px, transparent 1.4px) 0 0 / 5px 5px, var(--news-2); }
.photo figcaption { font: italic 600 .8rem var(--body); text-align: center; }
.story .photo { float: right; margin: 0 0 6px 10px; rotate: 2deg; box-shadow: 3px 3px 0 var(--ink); }
.story { display: flow-root; }
.story h3 { font-size: 1.15rem; margin-bottom: 4px; }
.paper-cols { display: grid; grid-template-columns: repeat(auto-fit, minmax(230px, 1fr)); gap: 18px 24px; margin: 16px 0; border-top: 2px solid var(--ink); padding-top: 14px; }
.paper-cols > section + section { margin-top: 0; border-left: 2px solid var(--rule); padding-left: 20px; }
@media (max-width: 560px) { .paper-cols > section + section { border-left: 0; padding-left: 0; border-top: 2px dashed var(--rule); padding-top: 12px; } }
.crier { list-style: none; padding: 0; margin: 0; }
.crier li + li { border-top: 1px dashed var(--rule); }
.crier li { padding: 6px 0; font-size: var(--fs-sm); }
.my-stars { background: var(--hi); border: 2px solid var(--ink); border-radius: var(--r-sm); padding: 8px 12px; }
/* Twisty Tam's capsule ad (gazette.js capsuleAd): a boxed display ad with a dashed cut line */
.cap-ad { border: 2px dashed var(--ink); border-radius: var(--r-sm); padding: 8px 12px; margin: 12px 0; background: var(--sun-cream); }
.cap-ad h2 { border-bottom: 0; }
.cap-ad p { margin: 0 0 6px; font-size: var(--fs-sm); }
.cap-ad-art { display: flex; gap: 4px; }
.letter-q { background: var(--news-2); border-radius: var(--r-sm); padding: 8px 12px; margin-bottom: 10px; display: flex; gap: 10px; align-items: start; }
.letter-q .star-chart { flex: none; margin-top: 4px; }
.letter-q p { margin: 4px 0; }
.wren-by { display: flex; gap: 8px; align-items: center; }
.wren-by svg { flex: none; }
/* Town news and the pet's weekly column */
.town-box h3 { margin: 8px 0 2px; font-size: var(--fs-sm); }
.town-news .kicker { margin-top: 0; }
/* Town News: the kinds flow through balanced columns, so a one-line kind never holds a whole column */
.paper .town-news { display: block; columns: 3 240px; column-gap: 40px; column-rule: 2px solid var(--rule); }
.paper .town-news > section { break-inside: avoid; margin: 0 0 20px; border-left: 0; padding-left: 0; border-top: 0; padding-top: 0; }
.paper > .wx.gz-phone-only { margin-top: 24px; }
.crier li small { margin-left: 6px; }
.pet-column { border-bottom: 2px solid var(--ink); padding-bottom: 12px; margin-bottom: 14px; }
.column-body { display: flex; gap: 18px; align-items: start; flex-wrap: wrap; }
.column-body > div { flex: 1 1 280px; }
.column-body .snap { flex: none; max-width: 160px; }
.diary { margin: 0 0 8px; padding-left: 20px; }
.signoff { font-style: italic; }
.comic { margin: 20px 0 0; border-top: 3px double var(--ink); padding-top: 12px; }
.comic .strip { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 8px; }
.panel { margin: 0; display: flex; flex-direction: column; justify-content: space-between; min-height: 230px; padding: 8px; border: 3px solid var(--ink); border-radius: 6px; background-color: var(--so-panel-bg); background-size: cover; overflow: hidden; }
.panel-cast { display: flex; justify-content: space-around; align-items: flex-end; }
.panel-cast > svg { width: 42%; height: auto; }
.panel-prop svg { display: block; width: 40px; height: auto; margin-bottom: 8px; }
@media (max-width: 560px) { .comic .strip { grid-template-columns: 1fr; } .panel { min-height: 0; } .panel-cast > svg { width: 30%; } }
.bubble { position: relative; background: var(--card); border: 2px solid var(--ink); border-radius: 16px; padding: 6px 10px; margin: 0 0 14px; font-size: var(--fs-sm); }
.bubble::after { content: ''; position: absolute; bottom: -9px; left: 22%; width: 14px; height: 14px; background: var(--card); border: 2px solid var(--ink); border-top: 0; border-left: 0; transform: rotate(45deg); }
/* Weather strip (art/weather.js): one little scene per land, eight across on desktop, three to a row on phones */
.paper .wx { margin-top: 24px; border-top: 3px double var(--ink); padding-top: 12px; }
.wx-row { list-style: none; padding: 0; margin: 0; display: grid; grid-template-columns: repeat(8, minmax(0, 1fr)); gap: 12px; }
.wx-row li { display: flex; flex-direction: column; gap: 6px; font-size: .86rem; line-height: 1.3; }
.wx-row p { margin: 0; }
.wx-row b { display: block; font: 600 .95rem var(--display); }
.wx-svg { display: block; width: 100%; height: auto; border: 2.5px solid var(--ink); border-radius: 10px; box-shadow: 3px 3px 0 var(--ink); }
@media (max-width: 1099px) { .wx-row { grid-template-columns: repeat(4, minmax(0, 1fr)); } }
@media (max-width: 767px) { .wx-row { grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 12px 8px; } .wx-row li { font-size: .8rem; } }

.paper .table td:last-child { text-align: right; }
.mini-pet svg { width: 28px; height: auto; vertical-align: middle; margin-right: 6px; }
.sports { grid-template-columns: repeat(auto-fit, minmax(min(280px, 100%), 1fr)); } /* min(): at 320 a 280px column is wider than the card */
@media (min-width: 768px) { .sports { grid-template-columns: repeat(2, minmax(0, 1fr)); } } /* two even columns under the Derby */
.sports .table th[scope="row"] { min-width: 7.5em; font: 600 var(--fs-sm) var(--display); }
.sports > section > :is(.table, p) + h2, .sports > section > .table + ul { margin-top: 18px; }
.sports .table :is(th, td) { overflow-wrap: anywhere; } /* a long player name must not push the table past its column */
.sports .derby { grid-column: 1 / -1; border-left: 0; padding-left: 0; }
.sports .derby td:first-child { white-space: nowrap; }
.sports .derby + section { border-left: 0; padding-left: 0; }
.mini-pet { display: inline-block; vertical-align: middle; }
.mini-pet svg { display: block; }
.sports .derby small { margin-left: 4px; }
.sports .table { width: 100%; }
/* Arcade Aces: game names wrap at spaces only (anywhere-wrapping let the table squash them to "Glim/mer/Stack/er"), the
   player's name takes what's left and breaks only when it can't fit, and the score stays on one line. */
.sports .aces th { overflow-wrap: normal; word-break: normal; hyphens: none; }
.sports .aces .num { overflow-wrap: normal; white-space: nowrap; width: 1%; }
@media (max-width: 560px) { .sports .aces th { width: 1%; } .sports .aces :is(th, td) { padding-inline: 8px; } } /* phones: the game column hugs its longest word, so names wrap at spaces and players' names keep the room */
/* Stars by species: zodiac tiles. The material shows round a light newsprint face, the Glimling sits in a medallion,
   and each sign's constellation is inked in its material's color beside the sign's name. */
.stars-grid ul { list-style: none; padding: 0; margin: 0; display: grid; grid-template-columns: repeat(auto-fill, minmax(min(340px, 100%), 1fr)); gap: 12px 16px; }
/* 15 signs never leave one card alone (2026-10-15): three columns of five once three 340px cards fit; in two columns the last
   card spans the row. Container units, since the paper's width depends on the sidebar as well as the window. */
.stars-grid { container-type: inline-size; }
@container (min-width: 1052px) { .stars-grid ul { grid-template-columns: repeat(3, minmax(0, 1fr)); } }
@container (min-width: 696px) and (max-width: 1051.98px) { .stars-grid li:last-child:nth-child(odd) { grid-column: 1 / -1; } }
.zt { display: flex; gap: 10px; align-items: center; padding: 8px; border: 2px solid var(--ink); border-radius: var(--r-sm); box-shadow: 3px 3px 0 var(--ink); background: var(--zt-bg); }
.zt-medal { flex: none; display: grid; place-items: center; width: 72px; height: 72px; border: 2px solid var(--ink); border-radius: 50%; background: radial-gradient(circle, rgb(255 255 255 / .95) 0 45%, rgb(255 255 255 / .55) 70%, rgb(255 255 255 / .2)); }
.zt-medal svg { display: block; width: 64px; height: auto; }
.zt-text { flex: 1; min-width: 0; align-self: stretch; padding: 6px 10px; border-radius: var(--r-sm); background: rgb(255 255 255 / .88); color: var(--ink); }
.zt-text p { margin: 2px 0 0; font-size: var(--fs-sm); }
.zt-text .zt-sign { display: flex; gap: 6px; align-items: center; margin: 0; font-size: 1rem; }
.zt-sign b { display: block; font-family: var(--display); line-height: 1.15; }
.zt-sign small { display: block; font: 600 var(--fs-xs) var(--body); color: var(--muted); text-transform: uppercase; letter-spacing: .06em; }
.zt-stars { flex: none; width: 34px; height: 34px; color: var(--zt-ink); }
.zt-moonstone { --zt-bg: var(--so-zt-moonstone); --zt-ink: var(--so-zt-moonstone-ink); }
.zt-foil { --zt-bg: var(--so-zt-foil); --zt-ink: var(--so-zt-foil-ink); }
.zt-wool { --zt-bg: var(--so-zt-wool); --zt-ink: var(--so-zt-wool-ink); }
.zt-enamel { --zt-bg: var(--so-zt-enamel); --zt-ink: var(--so-zt-enamel-ink); }
.zt-brass { --zt-bg: var(--so-zt-brass); --zt-ink: var(--so-zt-brass-ink); }
.zt-seaglass { --zt-bg: var(--so-zt-seaglass); --zt-ink: var(--so-zt-seaglass-ink); }
.zt-lapis { --zt-bg: var(--so-zt-lapis); --zt-ink: var(--so-zt-lapis-ink); }
.zt-pearl { --zt-bg: var(--so-zt-pearl); --zt-ink: var(--so-zt-pearl-ink); }
.zt-parchment { --zt-bg: var(--so-zt-parchment); --zt-ink: var(--so-zt-parchment-ink); }
.zt-jade { --zt-bg: var(--so-zt-jade); --zt-ink: var(--so-zt-jade-ink); }
.zt-stained { --zt-bg: var(--so-zt-stained); --zt-ink: var(--so-zt-stained-ink); }
.zt-velvet { --zt-bg: var(--so-zt-velvet); --zt-ink: var(--so-zt-velvet-ink); }
.zt-porcelain { --zt-bg: var(--so-zt-porcelain); --zt-ink: var(--so-zt-porcelain-ink); }
.zt-glimshard { --zt-bg: var(--so-zt-glimshard); --zt-ink: var(--so-zt-glimshard-ink); }
.zt-marbled { --zt-bg: var(--so-zt-marbled); --zt-ink: var(--so-zt-marbled-ink); }
/* Small phones: medallion above the face, everything centered, like a tarot card */
@media (max-width: 560px) {
  .zt { flex-direction: column; text-align: center; }
  .zt-text { align-self: stretch; }
  .zt-text .zt-sign { justify-content: center; }
}
.stars { color: var(--so-stars-ink); font-size: 1.3rem; letter-spacing: 2px; }
.review-body { display: flex; gap: 12px; align-items: flex-start; }
.review-body > svg { flex: none; }
.recipe-eq { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; font: 700 1.4rem var(--display); }
.ing { display: inline-flex; flex-direction: column; align-items: center; max-width: 84px; text-align: center; }
.ing small { font: 600 .75rem var(--body); }
.obits { border: 4px double var(--ink); padding: 10px 14px; background: var(--card); }
.obits h2 { text-align: center; }
.obit { display: flex; gap: 10px; align-items: flex-start; font-size: var(--fs-sm); }
.obit svg { flex: none; filter: grayscale(1); }
.obit p { margin: 0; }
/* Lifestyle rows (2026-10-15): the Critic's Table beside the weekly column; the recipe and the stall share a row (with no column
   the review joins them); In Memoriam and Wren's letters each run full width, three across, so neither leaves an empty bottom. */
.life-top { display: grid; grid-template-columns: minmax(0, 2fr) minmax(0, 1fr); gap: 18px 24px; align-items: start; border-bottom: 2px solid var(--ink); padding-bottom: 12px; margin-bottom: 14px; }
.paper .life-top > .pet-column { border-bottom: 0; padding-bottom: 0; margin: 0; }
.paper .life-top > .review { margin: 0; border-left: 2px solid var(--rule); padding-left: 20px; }
/* a paper narrower than 860px (phones, tablets, a small laptop with the pet panel) stacks the review under the column */
.paper { container: gz-paper / inline-size; }
@container gz-paper (max-width: 860px) {
  .life-top { grid-template-columns: minmax(0, 1fr); }
  .paper .life-top > .review { border-left: 0; padding-left: 0; border-top: 2px dashed var(--rule); padding-top: 12px; }
}
@media (min-width: 1000px) {
  .paper-cols:has(> .review + .recipe) { grid-template-columns: minmax(0, 1fr) minmax(0, 1.3fr) minmax(0, 1fr); } /* the recipe's sum fits on one line */
  .paper-cols:has(> .recipe:first-child) { grid-template-columns: minmax(0, 1.6fr) minmax(0, 1fr); }
}
.paper-cols:has(> .obits) { grid-template-columns: minmax(0, 1fr); }
.paper .paper-cols > .wren { border-left: 0; padding-left: 0; }
.obits, .wren { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(240px, 100%), 1fr)); gap: 10px 24px; align-items: start; }
.obits > h2, .wren > h2, .wren > .wren-by { grid-column: 1 / -1; margin: 0; }
.wren .letter-q { margin: 0; }

.puzzle { background: var(--card); border: 3px solid var(--ink); border-radius: var(--r-sm); padding: 12px 16px; box-shadow: 4px 4px 0 var(--ink); }
.puzzle h2 { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; }
/* The quiz and the word search are puzzles on this page now (routes/quiz.js, wordsearch.js; the quiz and grid styles are in daily-plus.css). */
.quiz-by { display: flex; align-items: center; gap: 10px; margin: 0 0 10px; }
.quiz-by svg { flex: none; }
.puzzle .quiz-form .swatch { min-height: 44px; }
.pz-done { display: inline-block; margin: 0 0 8px; padding: 2px 10px; background: var(--hi); border: 2px solid var(--ink); border-radius: 999px; font: 600 var(--fs-sm) var(--display); }
.jumble label { display: grid; gap: 4px; margin-bottom: 12px; }
.tiles { display: flex; flex-wrap: wrap; gap: 4px; }
.tiles b { width: 30px; height: 34px; display: grid; place-items: center; background: var(--so-tiles-bg); border: 2px solid var(--ink); border-radius: 6px; box-shadow: 0 3px 0 var(--ink); font: 700 1.1rem var(--display); }
.tiles b:nth-child(odd) { rotate: -3deg; }
.tiles b:nth-child(3n) { rotate: 4deg; }
.jumble input { text-transform: uppercase; letter-spacing: .1em; max-width: 16ch; }
/* Puzzles side by side keep their full sticker outline (the column rule used to replace the left edge). Desktop: the Jumble's four
   words sit two by two so it is as short as the Emoji Riddle beside it; the quiz and Letter Lagoon share a row (.pz-pair). */
.paper .paper-cols > .puzzle + .puzzle { border-left: 3px solid var(--ink); padding-left: 16px; }
.paper .pz-pair > .puzzle { margin: 0; }
@media (min-width: 768px) {
  .paper-cols:has(> .puzzle .jumble) { grid-template-columns: minmax(0, 1.55fr) minmax(0, 1fr); align-items: start; }
  .jumble { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0 20px; }
  .jumble label { grid-template-rows: auto 1fr auto; } /* a two-line hint pushes the box down; its neighbor's box drops level */
  .jumble > .btn { grid-column: 1 / -1; justify-self: start; }
  .tiles { gap: 3px; } .tiles b { width: 26px; height: 32px; }
  .pz-pair { grid-template-columns: repeat(2, minmax(0, 1fr)); align-items: start; }
  .pz-pair .ws-grid { width: 100%; }
}
.answer { font: 700 1.1rem var(--display); letter-spacing: .1em; color: var(--red); }
.rebus-clue { font-size: clamp(2.4rem, 9vw, 3.4rem); margin: 4px 0; letter-spacing: .1em; }
.rebus-opts { display: flex; flex-wrap: wrap; gap: 12px; }
.spot-pair { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; }
@media (max-width: 560px) { .spot-pair { grid-template-columns: 1fr; } }
.spot-side svg { display: block; width: 100%; height: auto; border: 3px solid var(--ink); border-radius: 8px; }
.spot-hit { cursor: pointer; }
.spot-ring { fill: none; stroke: var(--red); stroke-width: 5; opacity: 0; pointer-events: none; transition: opacity .2s; }
.spot-ring.found, .is-solved .spot-ring { opacity: 1; }
.spot-side.miss { animation: spot-miss .3s; }
@keyframes spot-miss { 25% { translate: -5px 0; } 75% { translate: 5px 0; } }
@media (prefers-reduced-motion: reduce) { .spot-side.miss { animation: none; } }
.spot-count { font: 600 1.05rem var(--display); }

/* an even grid of slips: each row is one height, and an odd last slip spans the row */
.classifieds ul { display: grid; grid-template-columns: minmax(0, 1fr); gap: 12px; list-style: none; margin: 0; padding: 0; }
@media (min-width: 768px) { .classifieds ul { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.classifieds li:last-child:nth-child(odd) { grid-column: 1 / -1; }
.classifieds li { margin: 0; padding: 8px 10px; border: 2px dashed var(--ink); background: var(--card); font-size: var(--fs-sm); }
.classifieds b { font-family: var(--display); letter-spacing: .04em; }
.classifieds a { display: block; }
.paper-ads { align-items: start; } /* the two flyers from src/layout.js flyerCard() keep their own heights */
.back-issues { list-style: none; padding: 0; margin: 0; display: flex; flex-wrap: wrap; gap: 8px; }
.back-issues a { display: inline-block; padding: 4px 12px; color: var(--ink); text-decoration: none; }
.back-issues a:hover { background: var(--hi); color: var(--ink); }
.back-issues a[aria-current="page"] { background: var(--pick); }
/* Back issues at the foot of the paper (the dateline links here) */
.gz-back { margin-top: 24px; border-top: 3px double var(--ink); padding-top: 12px; text-align: center; }
.gz-back h2 { font-size: 1.1rem; margin: 0 0 8px; }
.gz-back .back-issues { justify-content: center; }
@media (max-width: 767px) { .gz-back .pill { display: inline-flex; align-items: center; min-height: 44px; padding: 4px 12px; } .gz-back .back-issues { gap: 12px 8px; } }

/* Poll + POTD */
.poll-form { display: grid; gap: 10px; justify-items: start; }
/* Town Poll page: yesterday's line under the question; before the bell, the four answers as a plain list and the bell (with room
   above it); after it, .poll-reveal = the ballot slips, .poll-town (heading + glow jars), .poll-prize */
.poll-yesterday { font-size: var(--fs-sm); color: var(--muted); margin: 0 0 16px; }
.poll-reveal > h2 { margin: 24px 0 12px; }
/* a read-only numbered list, not buttons: plain rows split by the dashed rule */
.poll-answers { list-style: decimal inside; padding: 0; margin: 0 0 16px; }
.poll-answers li { padding: 8px 4px; }
.poll-answers li + li { border-top: 2px dashed var(--rule); }
.poll-answers li::marker { font-family: var(--display); color: var(--muted); }
.poll-ring { margin: 16px 0 0; }
.poll-town > h2 { margin: 32px 0 12px; }
.poll-prize { margin: 16px 0 0; padding: 10px 14px; background: var(--tint); border: 2px solid var(--ink); border-radius: var(--r-sm); }
.poll-prize.is-won { background: var(--hi-soft); }

/* Ballots: a paper slip per Glimling, 3-up on desktop, stacked on phones. The outline and hard shadow follow the torn bottom edge,
   so they come from drop-shadows on the li, not a border on the paper. */
.poll-slips { list-style: none; margin: 0; padding: 0 4px; display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 240px), 1fr)); gap: 18px 16px; }
.poll-slip { rotate: var(--tilt, 0deg); filter: drop-shadow(2px 0 0 var(--ink)) drop-shadow(-2px 0 0 var(--ink)) drop-shadow(0 -2px 0 var(--ink)) drop-shadow(0 2px 0 var(--ink)) drop-shadow(3px 3px 0 var(--ink)); }
.poll-slip-paper {
  position: relative; padding: 12px 14px 24px; background: var(--parchment);
  /* torn bottom: a row of 16px teeth */
  mask: linear-gradient(black 0 0) top / 100% calc(100% - 8px) no-repeat, conic-gradient(from 135deg at 50% 0, black 90deg, transparent 0) bottom / 16px 8px repeat-x;
}
.poll-slip-head { margin: 0 56px 8px 0; font: 600 1.15rem/1.2 var(--display); display: flex; flex-wrap: wrap; gap: 6px; align-items: center; }
.poll-slip-stamp { position: absolute; top: 6px; right: 8px; padding: 2px; line-height: 0; border: 2px dashed var(--emph); border-radius: 50%; rotate: 10deg; background: var(--card); }
.poll-slip-opts { list-style: none; margin: 0 0 10px; padding: 0; display: grid; gap: 6px; font-size: var(--fs-sm); }
.poll-slip-opts li { display: flex; gap: 8px; align-items: flex-start; color: var(--muted); }
.poll-slip-opts li.on { color: var(--ink); font-weight: 800; }
.poll-slip-opts i { flex: none; position: relative; width: 18px; height: 18px; margin-top: 2px; border: 2px solid var(--ink); background: var(--card); }
.poll-slip-opts li.on i::after { content: ''; position: absolute; left: 4px; top: -6px; width: 8px; height: 18px; border: solid var(--gain); border-width: 0 4px 4px 0; rotate: 40deg; }
/* the quirk's reason, hand-lettered on a ruled line */
.poll-slip-why { margin: 0; padding: 0 2px 4px; font: 500 1rem/1.6 var(--display); color: var(--grape); rotate: -1deg;
  background: repeating-linear-gradient(transparent 0 calc(1.6em - 2px), var(--rule) calc(1.6em - 2px) 1.6em); }
/* phones stack the slips, so each one is kept short: a smaller stamp, a tighter answer list and less paper around it */
@media (max-width: 560px) {
  .poll-slips { gap: 14px; padding: 0 2px; }
  .poll-slip-paper { padding: 10px 12px 20px; }
  .poll-slip-head { margin: 0 40px 6px 0; }
  .poll-slip-stamp { top: 4px; right: 6px; }
  .poll-slip-stamp svg { width: 34px; height: 34px; }
  .poll-slip-opts { gap: 2px; margin-bottom: 6px; line-height: 1.3; }
  .poll-slip-opts i { width: 16px; height: 16px; margin-top: 1px; }
  .poll-slip-opts li.on i::after { left: 3px; top: -6px; height: 16px; }
  .poll-slip-why { line-height: 1.5; background: repeating-linear-gradient(transparent 0 calc(1.5em - 2px), var(--rule) calc(1.5em - 2px) 1.5em); }
}

/* Results: four glow jars. Each fills with glimmer light against the top answer (--f), the real % printed under it; the top
   answer(s) get a sun glow ring, and your Glimlings' faces sit under the jar they voted for. */
.poll-jars { list-style: none; margin: 0; padding: 0; display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 12px; text-align: center; }
.poll-jars > li { display: grid; justify-items: center; align-content: start; gap: 4px; min-width: 0; }
/* the lid sits on the jar's rim, outside its clip */
.poll-jars > li::before { content: ''; grid-row: 1; width: min(70%, 66px); height: 14px; margin-bottom: -24px; z-index: 1; position: relative;
  background: var(--pick); border: var(--line) solid var(--ink); border-radius: var(--r-sm); }
.poll-jar {
  position: relative; display: block; width: 100%; max-width: 96px; height: 120px; margin-top: 12px;
  background: var(--tint); border: var(--line) solid var(--ink); border-radius: var(--r-sm) var(--r-sm) var(--r-card) var(--r-card);
  overflow: hidden; box-shadow: var(--shadow-sm);
}
.poll-jar-light { position: absolute; inset: 0; transform-origin: 50% 100%; scale: 1 var(--f); background: linear-gradient(var(--sun-glow), var(--ui-stat-glow-fill)); }
.poll-jar-glints { position: absolute; left: 0; bottom: 4px; width: 100%; height: 40px; }
/* glass shine: a tilted white oval upper left */
.poll-jar::after { content: ''; position: absolute; left: 12%; top: 10px; width: 10px; height: 32px; border-radius: 50%; background: var(--card); opacity: .8; rotate: 12deg; }
.poll-jars > li.top .poll-jar { box-shadow: 0 0 0 6px var(--sun-soft), 0 0 0 8px var(--sun-glow), var(--shadow-sm); }
.poll-jars > li.top .poll-jar-light { background: linear-gradient(var(--sun-soft), var(--sun)); }
/* a fixed box with strict containment, so the count-up rewriting the number each frame never lays out the rest of the page */
.poll-jars b { display: block; width: 100%; height: 1.4em; margin-top: 8px; font: 600 1.15rem/1.4 var(--display); contain: strict; }
.poll-jar-label { font-size: var(--fs-sm); line-height: 1.25; overflow-wrap: anywhere; hyphens: auto; }
.poll-jars > li.top .poll-jar-label { font-weight: 800; }
.poll-jars .pill { white-space: normal; line-height: 1.15; }
.poll-faces { display: inline-flex; flex-wrap: wrap; justify-content: center; line-height: 0; margin-top: 2px; }
.poll-faces > span + span { margin-left: -8px; }
.poll-voted { margin: 16px 0 0; font-size: var(--fs-sm); }
@media (max-width: 560px) { .poll-jars { gap: 8px; } .poll-jar { height: 104px; } }

/* The reveal, only on the page the bell redirects to (.poll.is-fresh, ?rang=1): one slip per Glimling flutters into the ballot
   box, each ballot unfolds from its top edge, then every jar fills at once while public/poll.js counts its % up, then the prize
   stamps in. About 5 s. Transforms and opacity only, every animation finite; the resting look is the finished page (flying
   slips hidden), so reduced motion or a reload shows that. scaleY, not a 3D flip: rotateX on the drop-shadowed slip cost more. */
.poll { --step: .6s; --bars-at: calc((var(--np, 1) - 1) * var(--step) + 1.75s); }
.poll-fallslip { opacity: 0; }
.poll.is-fresh .poll-fallslip { animation: poll-flutter 1.15s ease-in-out calc(var(--i) * var(--step)) both; }
@keyframes poll-flutter {
  0% { opacity: 1; translate: calc(var(--dx) * var(--U)) calc(-150 * var(--U)); rotate: -28deg; }
  30% { translate: calc(var(--dx) * -.5 * var(--U)) calc(-104 * var(--U)); rotate: 22deg; }
  58% { translate: calc(var(--dx) * .25 * var(--U)) calc(-52 * var(--U)); rotate: -14deg; }
  82% { opacity: 1; translate: 0 0; rotate: 0deg; }
  100% { opacity: 0; translate: 0 calc(26 * var(--U)); }
}
.poll.is-fresh [data-step="ballot"] { transform-origin: 50% 0; animation: poll-unfold .55s var(--ease-out) calc(var(--i) * var(--step) + 1s) both; }
@keyframes poll-unfold { from { opacity: 0; transform: scaleY(.08); } 40% { opacity: 1; } }
.poll.is-fresh :is([data-step="town"], .poll-voted) { animation: poll-fade .4s calc(var(--bars-at) - .3s) both; }
.poll.is-fresh [data-step="bar"] { --count-ms: 900; animation: poll-fade .3s calc(var(--bars-at) - .2s) both; }
.poll.is-fresh [data-step="bar"] .poll-jar-light { animation: poll-fill .9s var(--ease-out) var(--bars-at) both; }
@keyframes poll-fade { from { opacity: 0; } }
@keyframes poll-fill { from { scale: 1 0; } }
.poll.is-fresh [data-step="prize"] { animation: poll-stamp .45s cubic-bezier(.3, 1.6, .5, 1) calc(var(--bars-at) + 1.1s) both; }
@keyframes poll-stamp { from { opacity: 0; scale: 1.5; rotate: -6deg; } }
.reduce-motion .poll.is-fresh :is(.poll-fallslip, [data-step], [data-step] *) { animation: none; }
.potd { text-align: center; }
.potd .lede { margin-inline: auto; } /* the lede's 62ch box sat left of center */
.potd-stage { display: inline-block; max-width: 100%; padding: 20px 24px 0; border-radius: 50% 50% 20px 20px; background: radial-gradient(circle at 50% 30%, var(--sun-cream), var(--land-to)); border: var(--line) solid var(--ink); }
.potd-stage svg { display: block; max-width: 100%; height: auto; }
.potd .btn-row { justify-content: center; }
/* The two Daily Darlings side by side, one above the other when there's no room. */
.potd-pair { width: 100%; display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 260px), 1fr)); gap: 24px; align-items: start; }
.potd-pair h2 { margin: 12px 0 4px; }

/* Photo album: polaroids taped onto a page (services/album.js photoCard) */
.photo-page {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); gap: 18px; padding: 18px;
  background: var(--parchment); border: var(--line) solid var(--ink); border-radius: var(--r-tile); margin-bottom: 14px;
}
.snap { margin: 0; padding: 8px 8px 10px; background: #fff; border: 2px solid var(--ink); box-shadow: var(--shadow-sm); rotate: var(--tilt, 0deg); display: grid; justify-items: center; gap: 6px; text-align: center; position: relative; } /* style-ok: photo print border */
.snap::before { content: ''; position: absolute; top: -9px; left: 50%; width: 46px; height: 16px; translate: -50% 0; rotate: -4deg; background: color-mix(in srgb, var(--so-snap-bg) 80%, transparent); border: 1px solid rgb(0 0 0 / .1); } /* tape */
.snap figcaption { font: 600 var(--fs-sm)/1.25 var(--display); }
.snap figcaption small { display: block; color: var(--muted); font: 600 var(--fs-xs) var(--body); }
.snap-art { display: grid; place-items: end center; overflow: hidden; position: relative; background: linear-gradient(var(--from), var(--to)); border: 1.5px solid var(--ink); }
.snap-art::before { content: ''; position: absolute; inset: 15% 10% 0; border-radius: 50%; background: radial-gradient(circle, rgb(255 250 205 / calc(var(--glow) * .95)) 0 25%, rgb(143 240 255 / calc(var(--glow) * .5)) 50%, transparent 70%); } /* style-ok: color computed from a per-element custom property */
.snap-art svg { position: relative; }

/* Portrait and frames (/avatars) */
.portrait-head { display: flex; gap: 20px; align-items: center; flex-wrap: wrap; }
.portrait-head h1 { margin: 0 0 6px; }
.portrait-head > div:last-child { flex: 1 1 260px; }
.title-pick { margin: 12px 0 4px; flex-wrap: wrap; align-items: end; }
@media (max-width: 560px) { .portrait-head { justify-content: center; text-align: center; } .portrait-head .title-pick { justify-content: center; } } /* portrait, title and Wear it centered on phones */
.avatar-tile .title-tag, .trophy-shelf .title-tag, .item-tile .title-tag { margin: 2px 0 0; white-space: normal; }
.avatar-tile .stat-bar { width: 100%; }

/* Nests (/nest/:username): a 4:3 room, a wall and a floor, every Glimling in it, dimmed by their average glow. Pieces sit by their center
   (public/room.js) and scale with the room: --w is a piece's width at a 720px-wide room, so a layout looks the same on every screen. */
.room {
  position: relative; aspect-ratio: 4 / 3; container-type: inline-size; overflow: hidden; border: var(--line) solid var(--ink); border-radius: var(--r-tile);
  background:
    repeating-linear-gradient(90deg, transparent 0 38px, color-mix(in oklab, var(--wall) 80%, #fff) 38px 40px) top / 100% 62% no-repeat, /* style-ok: room wallpaper art */
    linear-gradient(var(--trim), var(--trim)) 0 62% / 100% 8px no-repeat,
    linear-gradient(var(--wall), var(--wall)) top / 100% 62% no-repeat,
    repeating-linear-gradient(0deg, var(--floor) 0 22px, color-mix(in oklab, var(--floor) 85%, #000) 22px 24px); /* style-ok: room floorboard art */
}
.room::after { content: ''; position: absolute; inset: 0; pointer-events: none; background: rgb(20 10 50 / calc((1 - var(--glow)) * .35)); } /* dim pets, a dim room */ /* style-ok: color computed from a per-element custom property */
.room-piece, .room-emote { position: absolute; translate: -50% -50%; line-height: 0; }
.room-piece { width: max-content; touch-action: none; user-select: none; } /* max-content: else the shrink-to-fit width (room edge minus left) caps the art via style.css's svg max-width, so pieces shrink near the right edge */
.room-piece svg, .room-photo, .room-emote svg { width: calc(var(--w) * 100cqw / 720); height: auto; }
.room[data-edit] .room-piece { cursor: grab; }
.room[data-edit] .room-piece.is-picked { outline: 3px dashed var(--pink); outline-offset: 4px; }
/* Retro sticker motion (src/art/retro.js). It was SMIL, which cost /nest 14-18% main thread. */
.rt-blink { animation: rt-blink 1.2s linear infinite; }
.rt-twinkle, .rt-spin { transform-box: fill-box; transform-origin: center; }
.rt-twinkle { animation: rt-twinkle 1.4s linear infinite; }
.rt-spin { animation: rt-spin 2s linear infinite; }
@keyframes rt-blink { 0%, 33.33% { opacity: 1; } 66.67% { opacity: 0; } }
@keyframes rt-twinkle { 50% { transform: scale(.4); } }
@keyframes rt-spin { 50% { transform: scale(.1, 1); } }
.room[data-edit] .room-piece:focus-visible { outline: 3px solid var(--ink); outline-offset: 4px; box-shadow: 0 0 0 10px var(--sky); }
.room-piece.is-dragging { cursor: grabbing; z-index: 2; filter: drop-shadow(4px 6px 0 rgb(0 0 0 / .25)); }
.room-piece.is-leaving { opacity: .4; }
.room-pet { display: block; position: relative; }
.room-pet::before, .room-pet.glow-stormy::after { content: ''; position: absolute; inset: 10% 5% -5%; border-radius: 50%; background: radial-gradient(circle, rgb(255 250 205 / calc(var(--glow) * .95)) 0 25%, rgb(143 240 255 / calc(var(--glow) * .5)) 50%, transparent 70%); } /* style-ok: color computed from a per-element custom property */
.room-pet svg { position: relative; }
.room-photo { display: block; box-sizing: border-box; padding: 4px 4px 10px; background: #fff; border: 1.5px solid var(--ink); rotate: -3deg; } /* style-ok: photo print border */
.room-photo .snap-art { width: 100% !important; height: auto !important; aspect-ratio: 1; border-width: 1px; } /* style-ok: photoArt sets a fixed inline size; the Nest scales it */
.room-photo .snap-art svg { width: 90%; }
/* Pets standing close share a bubble (lookup.js mingle). Never a piece: hidden while the owner rearranges, back after a save. */
.room-emote { z-index: 1; pointer-events: none; animation: emote-bob 2.4s ease-in-out infinite; }
@keyframes emote-bob { 50% { translate: -50% calc(-50% - 4px); } }
.room.is-dirty .room-emote { display: none; }

/* The owner's tray: Save and Delete on top, then square tabs (CSS-only radios, sticker icon over a tiny label) for stickers, photos,
   critters, things and wallpaper, five to a row. */
.nest-head { margin-bottom: 16px; }
/* The owner's view (lookup.js): a line saying visitors see this room, then Decorate above the room, full width on phones. */
.nest-intro { margin: 8px 0 0; font-weight: 600; }
.nest-decorate { margin: 0 0 12px; justify-content: center; }
.nest-decorate .btn { flex: 1 1 100%; justify-content: center; }
@media (min-width: 768px) { .nest-decorate .btn { flex: 0 1 auto; min-width: 220px; } }
.nest-stage .hint { margin: 12px 0 0; }
.room-unsaved { display: none; font-weight: 700; color: var(--emph); }
.nest-edit:has(.room.is-dirty) .room-unsaved { display: inline; }
.nest-tray { margin-top: 16px; }
.tray-actions { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 12px; margin-bottom: 12px; }
.room-del { display: inline-flex; align-items: center; justify-content: center; gap: 8px; }
.tray-tabs { display: flex; justify-content: center; gap: 12px; max-width: 420px; margin-inline: auto; }
.tray-tab { position: relative; flex: 0 1 calc((100% - 48px) / 5); display: grid; justify-items: center; align-content: center; gap: 3px; aspect-ratio: 1; min-height: 44px; min-width: 0;
  background: var(--card); border: 2px solid var(--ink); border-radius: var(--r-sm); color: var(--ink); cursor: pointer; }
.tray-tab > svg { display: block; width: 28px; height: 28px; }
.tray-tab > span { font: 600 .72rem/1 var(--display); }
.tray-tab input, .wall-swatch input { position: absolute; opacity: 0; pointer-events: none; }
.tray-tab:has(:checked) { background: var(--pick); box-shadow: var(--shadow-sm); }
.tray-tab:has(:focus-visible), .wall-swatch:has(:focus-visible) { outline: 3px solid var(--ink); outline-offset: 2px; box-shadow: 0 0 0 8px var(--sky); }
.tray-tab:has(:checked):has(:focus-visible) { box-shadow: var(--shadow-sm), 0 0 0 8px var(--sky); }
.nest-tray .room-tray { display: none; margin-top: 12px; }
.nest-tray:has([name=tray][value=stickers]:checked) [data-tab=stickers], .nest-tray:has([name=tray][value=photos]:checked) [data-tab=photos],
.nest-tray:has([name=tray][value=critters]:checked) [data-tab=critters], .nest-tray:has([name=tray][value=things]:checked) [data-tab=things],
.nest-tray:has([name=tray][value=walls]:checked) [data-tab=walls] { display: flex; }
.room-tray { flex-wrap: wrap; gap: 12px; }
.tray-piece { display: grid; place-items: center; min-width: 52px; min-height: 52px; padding: 6px; background: var(--card); border: 2px solid var(--ink); border-radius: var(--r-sm); cursor: pointer; line-height: 0; }
.tray-piece:hover { background: var(--hi-soft); }
.tray-piece svg { max-width: 110px; max-height: 56px; width: auto; height: auto; }
.wall-swatch { position: relative; display: grid; justify-items: center; align-content: start; gap: 4px; width: 72px; font: 600 var(--fs-xs) / 1.2 var(--display); text-align: center; cursor: pointer; }
.wall-swatch .wall-chip { width: 56px; height: 44px; border: 2px solid var(--ink); border-radius: var(--r-sm); background: linear-gradient(var(--wall) 0 55%, var(--trim) 55% 68%, var(--floor) 68%); }
.wall-swatch:has(:checked) .wall-chip { outline: 3px solid var(--pink); outline-offset: 2px; }
/* Phones: the tray is a bottom sheet just above the tab bar, one scrolling row of pieces; the page and the feedback bubble make room for it. */
@media (max-width: 767px) {
  :root { --sheet-h: 222px; }
  .nest-edit .nest-head :is(.lookup-avatar, .title-tag, p + p) { display: none; } /* the owner's head is one line so the room shows above the sheet */
  body:has(.nest-tray) { padding-bottom: calc(var(--bar-h) + var(--sheet-h) + env(safe-area-inset-bottom)); }
  body:has(.nest-tray) .fb-bubble { --fb-b: calc(var(--bar-h) + var(--sheet-h) + 12px); }
  .nest-tray {
    position: fixed; z-index: 20; inset: auto 0 calc(var(--bar-h) + env(safe-area-inset-bottom)); height: var(--sheet-h); box-sizing: border-box; margin: 0;
    padding: 10px 12px; background: var(--card); border-top: var(--line) solid var(--ink); box-shadow: 0 -4px 12px color-mix(in srgb, var(--ink) 15%, transparent);
  }
  .nest-tray .room-tray { flex-wrap: nowrap; overflow-x: auto; overscroll-behavior-x: contain; scrollbar-width: none; margin-top: 12px; }
  .room-tray > * { flex: none; }
  .wall-swatch { width: 64px; }
  .wall-swatch .wall-chip { height: 36px; }
  .room-del { min-width: 44px; padding-inline: 12px; }
  .room-del-word { position: absolute; opacity: 0; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); } /* icon only, so Save gets the row */
}
/* Desktop: room on the left, the tray a sticky panel on the right. */
@media (min-width: 1100px) {
  .nest-edit { display: grid; grid-template-columns: minmax(0, 1fr) 320px; gap: 0 20px; align-items: start; }
  .nest-edit .nest-head { grid-column: 1 / -1; }
  .nest-tray { position: sticky; top: 16px; max-height: calc(100vh - 32px); overflow-y: auto; margin: 0; }
}

/* Gazette on phones: clear air under the masthead rule; link rows and link buttons centered */
@media (max-width: 767px) {
  .paper-tabs { margin-top: 16px; }
  .paper .btn-row, .back-issues { justify-content: center; text-align: center; }
  .classifieds a { text-align: center; }
  .paper .link-line, .paper p:has(> a.btn:only-child), .card:has(.back-issues) > p:has(> a.btn) { text-align: center; }
  /* Today's poll card, the puzzles' intro and titles, and the emoji riddle and spot the difference controls sit centered */
  .poll-box, .pz-intro, .stars-grid > h2 { text-align: center; }
  .puzzle h2 { justify-content: center; text-align: center; }
  .puzzle > .pz-done { display: table; margin-inline: auto; }
  .quiz-by { justify-content: center; text-align: center; }
  .puzzle:has(.rebus-clue) { text-align: center; }
  .rebus-opts { display: grid; grid-template-columns: minmax(0, 1fr); }
  .spot-game > .spot-count { text-align: center; }
  .spot-game > .btn { display: flex; margin-inline: auto; }
}

/* Desktop: profile cards put the trophy cabinet and the guestbook side by side (.lookup-cols wraps them in lookup.js) */
@media (min-width: 1100px) {
  .lookup-cols { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1.3fr); gap: 20px; align-items: stretch; }
  .lookup-cols > .card { margin: 0; }
  .mail-form { max-width: 760px; }
}
/* score cells don't break mid-number on a phone (Gazette Arcade Aces) */
.paper .num { text-align: right; white-space: nowrap; font-variant-numeric: tabular-nums; }
/* The midnight night-owl slip: breathing room before the first story */
.paper .gz-owl { margin: 4px 0 20px; }

/* ===== Nest Photos card (#photos, routes/lookup.js photoBoard): a corkboard strip that scrolls sideways; photos hang from pushpins ===== */
:root { --np-cork: #d9a96c; --np-cork-dot: #c48d4f; --np-frame: #c98b52; }
.nest-photos .album-tabs a { gap: 6px; } /* the count sits a space after the name */
.np-cork { display: flex; gap: 24px; overflow-x: auto; scroll-snap-type: x mandatory; padding: 24px 18px 18px; background: var(--np-cork) radial-gradient(var(--np-cork-dot) 1.5px, transparent 1.6px) 0 0 / 14px 14px; border: var(--line) solid var(--ink); border-radius: var(--r-tile); box-shadow: inset 0 0 0 6px var(--np-frame); }
.np-pin { flex: none; width: 170px; scroll-snap-align: start; }
.np-pin .snap { box-sizing: border-box; width: 100%; }
.np-pin .snap::before { width: 16px; height: 16px; top: -8px; border-radius: 50%; rotate: 0deg; border: 2px solid var(--ink); background: var(--pink); } /* a pushpin instead of tape */
.np-pin:nth-child(3n+2) .snap::before { background: var(--sky); }
.np-pin:nth-child(3n) .snap::before { background: var(--sun); }
.np-note { margin: 10px 0 0; font-size: var(--fs-sm); }
@media (max-width: 767px) {
  .np-cork { gap: 16px; padding: 20px 12px 14px; }
  .np-pin { width: 150px; }
  .np-pin .snap-art { width: 126px !important; height: 126px !important; } /* style-ok: photoArt sets a fixed inline size */
  .np-note { text-align: center; }
}
