/* Tap-A-Post component layer.
   The recurring pieces the prototypes build over and over: the wax seal, the
   postmark, the perforated stamp, washi tape, parchment cards, radio cards and
   the button set. Screen-specific layout does NOT belong here. */

*, *::before, *::after { box-sizing: border-box; }

html { background: var(--backdrop); transition: background-color var(--dur-theme) ease; }

body {
  margin: 0;
  min-height: 100svh;
  background: var(--backdrop);
  color: var(--ink);
  font-family: var(--font-body);
  font-size: var(--text-body);
  line-height: var(--leading-body);
  -webkit-font-smoothing: antialiased;
}

/* `hidden` is the contract for "not on this page": the questionnaire's
   conditional fields, tab panes, the recorder's takes. Any component that
   sets its own display (.field is flex) silently beats the UA's
   [hidden]{display:none}, and a field the server carefully hid shows anyway
   -- which is exactly how the pet's "what is it, then?" appeared under every
   answer. One rule ends the class of bug. */
[hidden] { display: none !important; }

h1, h2, h3 { font-family: var(--font-display); font-weight: 700; line-height: 1.15; margin: 0; }
h1 { font-size: clamp(2.75rem, 6vw, 5.25rem); }   /* Almendra 44–84px */
h2 { font-size: clamp(1.9375rem, 4vw, 2.875rem); } /* Almendra 31–46px */

a { color: var(--forest); }
a:hover { color: var(--postbox); }

:where(a, button, input, select, textarea, [tabindex]):focus-visible {
  outline: var(--focus-ring);
  outline-offset: var(--focus-offset);
}

/* Every interactive target clears 44px (design handover, accessibility). */
:where(button, .btn, [role="radio"]) { min-height: 44px; }

/* ---- Script accent ------------------------------------------------------ */
.script {
  font-family: var(--font-script);
  font-size: clamp(1.75rem, 4vw, 3.625rem);   /* 17–58px range in prototypes */
  line-height: 1;
}

/* ---- Parchment surfaces ------------------------------------------------- */
.parchment {
  background: var(--parchment-page);
  color: var(--ink);
  view-transition-name: parchment;
}
.letter { background: var(--parchment-letter); }

/* Reading column for legal and copy pages. */
.prose {
  max-width: 68ch;
  margin: 0 auto;
  padding: 140px 24px 80px;
  background: none;
  color: var(--gold-pale);
}
.prose h1 { color: var(--parchment-paper); margin-bottom: 24px; }
.prose a { color: var(--gold-hi); }

/* ---- Wax seal ----------------------------------------------------------- */
/* The tactile brand mark. Same geometry everywhere, only the size changes.
   Melted-blob radius plus drips; the play glyph is embossed by the caller. */
.seal {
  --seal-size: 92px;
  position: relative;
  width: var(--seal-size);
  height: var(--seal-size);
  border: none;
  padding: 0;
  cursor: pointer;
  display: grid;
  place-items: center;
  color: var(--parchment-paper);
  background: var(--seal-face);
  border-radius: var(--seal-blob);
  box-shadow:
    inset 0 2px 6px rgba(255, 255, 255, 0.35),
    inset 0 -4px 10px rgba(90, 60, 8, 0.45),
    0 6px 18px -6px rgba(31, 36, 48, 0.5);
  transition: filter 150ms ease, transform 150ms ease;
}
.seal:hover { filter: brightness(1.06); }
.seal:active { transform: scale(0.97); }
.seal--red { background: radial-gradient(circle at 34% 28%, #D9564A, var(--postbox) 52%, var(--postbox-shadow)); }
.seal--sm { --seal-size: 56px; }
.seal--lg { --seal-size: 132px; }

/* Wax drips: two blobs bleeding off the bottom edge. */
.seal::before,
.seal::after {
  content: "";
  position: absolute;
  bottom: -6px;
  width: 14px;
  height: 16px;
  background: inherit;
  border-radius: 50% 50% 60% 40% / 40% 40% 60% 60%;
  z-index: -1;
}
.seal::before { left: 26%; }
.seal::after { right: 22%; height: 12px; width: 11px; }

/* ---- Postmark ----------------------------------------------------------- */
/* Circular ink stamp that chapter headings overlap. multiply so it reads as
   ink soaked into the paper rather than a sticker sitting on top. */
.postmark {
  width: 104px;
  height: 104px;
  border: 2.5px solid var(--theme-ink);
  border-radius: 50%;
  color: var(--theme-ink);
  display: grid;
  place-items: center;
  text-align: center;
  font-family: var(--font-body);
  font-size: 0.6875rem;
  font-weight: 700;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  mix-blend-mode: multiply;
  transform: rotate(-6deg);
}
.postmark--right { transform: rotate(5deg); }

/* ---- Perforated stamp --------------------------------------------------- */
.stamp {
  width: 44px;
  height: 53px;
  display: grid;
  place-items: center;
  background: var(--parchment-input);
  color: var(--ink-muted);
  transform: rotate(-2.5deg);
  transition: transform 200ms ease;
  /* Scalloped edge is an SVG path on the element in markup; this is the plate. */
}
.stamp:hover { transform: rotate(0deg) scale(1.08); }
.stamp[aria-current="true"] { background: var(--gold-pale); color: var(--ink); }

/* ---- Washi tape chrome -------------------------------------------------- */
.washi {
  position: fixed;
  left: 0;
  right: 0;
  height: 9px;
  z-index: 40;
  background: repeating-linear-gradient(45deg,
    var(--washi-red) 0 10px,
    var(--parchment-paper) 10px 20px,
    var(--navy) 20px 30px,
    var(--parchment-paper) 30px 40px);
}
.washi--top { top: 0; }
.washi--bottom { bottom: 0; }

/* ---- Site chrome -------------------------------------------------------- */
.site-head {
  position: fixed;
  top: 9px;                       /* clears the washi strip */
  left: 0;
  right: 0;
  z-index: 30;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: calc(var(--unit) * 2);
  padding: calc(var(--unit) * 1.5) calc(var(--unit) * 3);
}
.wordmark {
  display: inline-flex;
  align-items: center;
  gap: var(--unit);
  padding: 8px 18px;
  border-radius: var(--radius-pill);
  background: var(--parchment-paper);
  color: var(--ink);
  text-decoration: none;
  font-family: var(--font-display);
  font-size: 1.0625rem;
  font-weight: 700;
}
.wordmark:hover { color: var(--ink); }
.wordmark__tag {
  font-family: var(--font-body);
  font-size: 0.625rem;
  font-weight: 600;
  letter-spacing: 0.18em;
  color: var(--ink-faint);
}
.site-head__cta { padding: 10px 22px; font-size: 0.9375rem; }

.site-foot {
  padding: calc(var(--unit) * 6) calc(var(--unit) * 3) calc(var(--unit) * 5);
  text-align: center;
  color: var(--gold-pale);
}
.site-foot nav { display: flex; gap: calc(var(--unit) * 3); justify-content: center; font-size: 0.875rem; }
.site-foot a { color: var(--gold-pale); }
.site-foot a:hover { color: #fff; }

@media (max-width: 560px) {
  .wordmark__tag { display: none; }
  .site-head { padding-inline: calc(var(--unit) * 2); }
}

/* ---- Getting the header out of the way on a phone -----------------------
   `.site-head` is fixed and has no background of its own, so on a wide screen
   the wordmark and the CTA sit in the margin. On a phone there is no margin:
   they land on the words, and a real handset test found the storybook hard to
   read underneath them.

   So below 700px it tucks away while you read down and comes back the moment
   you scroll up, or at the top of the page. static/js/site.js decides when;
   this is only what it looks like. Never above 700px -- there it is not in
   the way, and a header that vanished on a desktop would be a header nobody
   could find. */
@media (max-width: 700px) {
  .site-head, .sb-head { transition: transform 220ms ease, opacity 220ms ease; }
  .site-head.is-tucked, .sb-head.is-tucked {
    /* -160% clears the pill's own shadow as well as its box. */
    transform: translateY(-160%);
    opacity: 0;
    /* Gone means gone: it must not eat a tap aimed at the page beneath it. */
    pointer-events: none;
  }
  /* Asked for less motion: still gets out of the way, without the slide. */
  .site-head.no-motion, .sb-head.no-motion { transition: none; }
}

/* ---- Buttons ------------------------------------------------------------ */
/* Buttons name their outcome — never "Submit" or "OK". */
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: calc(var(--unit) * 1.25);
  padding: 14px 28px;
  border: none;
  border-radius: var(--radius-pill);
  font-family: var(--font-body);
  font-size: 1rem;
  font-weight: 600;
  cursor: pointer;
  /* Deliberately NOT transitioning background-color: when the value comes from
     a themed custom property, Chrome pins the pre-change colour and the button
     never picks up the new accent. Hover feedback is filter/border instead, so
     nothing is lost. */
  transition: filter 150ms ease, border-color 150ms ease, transform 100ms ease;
}
.btn--primary { background: var(--accent); color: var(--parchment-paper); }
.btn--primary:hover { filter: brightness(0.93); }
.btn--primary:active { transform: scale(0.98); }
.btn--quiet {
  background: transparent;
  color: var(--ink);
  border: 1.5px solid rgba(42, 36, 22, 0.35);
}
.btn--quiet:hover { border-color: var(--ink); }

/* ---- Radio cards -------------------------------------------------------- */
.radio-card {
  display: flex;
  align-items: center;
  gap: calc(var(--unit) * 2);
  padding: calc(var(--unit) * 2);
  background: var(--parchment-input);
  border: 2px solid rgba(42, 36, 22, 0.18);
  border-radius: var(--radius-input);
  cursor: pointer;
  transition: border-color 150ms ease, background-color 150ms ease;
}
/* TWO MARKUPS, ONE LOOK. The shop and the design gallery build these from
   `<div role="radio" aria-checked>` (ported straight from the prototype); the
   questionnaire builds them from a real `<label>` wrapping a real
   `<input type="radio">`, and marks the chosen one with `.is-on`. Only the
   first was ever styled, so on every questionnaire page the card highlighted
   and the wax dot inside it stayed grey -- the gold dot the founder kept
   looking for.

   `:has(input:checked)` as well as `.is-on`, so the dot is right the instant
   a radio is pressed, without waiting for the class-toggling script. */
.radio-card[aria-checked="true"],
.radio-card.is-on,
.radio-card:has(input:checked) {
  border-color: var(--gold);
  background: rgba(201, 162, 39, 0.13);
}
.radio-card[aria-disabled="true"] { opacity: 0.55; cursor: not-allowed; }

/* The 22px wax-blob dot standing in for a radio control. */
.radio-card__dot {
  flex: none;
  width: 22px;
  height: 22px;
  border-radius: var(--seal-blob);
  background: rgba(42, 36, 22, 0.18);
}
.radio-card[aria-checked="true"] .radio-card__dot,
.radio-card.is-on .radio-card__dot,
.radio-card:has(input:checked) .radio-card__dot { background: var(--seal-face); }

/* ---- Fields ------------------------------------------------------------- */
.field { display: flex; flex-direction: column; gap: var(--unit); }
.field__label { font-weight: 600; }
.field__hint { font-size: 0.875rem; color: var(--ink-muted); font-style: italic; }
.field__input {
  min-height: 46px;
  padding: 12px 14px;
  background: var(--parchment-input);
  border: 1.5px solid rgba(42, 36, 22, 0.25);
  border-radius: var(--radius-input);
  font-family: var(--font-body);
  font-size: 1.0625rem;
  color: var(--ink);
}
.field__input[aria-invalid="true"] { border-color: var(--ink-error); border-width: 2px; }

/* Postie's error bank renders here. Inline, never modal. */
.field__error {
  color: var(--ink-error);
  font-size: 0.9375rem;
  font-weight: 600;
}

/* Counter appears at 80% of max (questionnaire spec). */
.field__counter { font-size: 0.8125rem; color: var(--ink-faint); font-variant-numeric: tabular-nums; }

/* ---- Cut-here slip ------------------------------------------------------ */
.slip {
  border: 1.5px dashed rgba(42, 36, 22, 0.4);
  border-radius: var(--radius-input);
  padding: calc(var(--unit) * 3);
  background: var(--parchment-input);
}

/* ---- Placeholder slots -------------------------------------------------- */
/* Marks where commissioned illustration and real QR codes go. The handoff
   flags these as the only two things that are NOT final design intent. */
.slot {
  display: grid;
  place-items: center;
  border: 1.5px dashed rgba(35, 48, 91, 0.35);
  border-radius: 14px;
  background: repeating-linear-gradient(45deg,
    rgba(35, 48, 91, 0.1) 0 10px,
    rgba(35, 48, 91, 0.04) 10px 20px);
  font-family: var(--font-mono);
  font-size: 0.625rem;
  color: var(--navy);
  min-height: 132px;
}

/* ---- Empty merge slot --------------------------------------------------- */
/* Live preview shows "(their name)" in soft grey italics — never {child_name}. */
.merge-empty { color: var(--ink-faint); font-style: italic; }

/* ---- Screen-reader only ------------------------------------------------- */
.sr-only {
  position: absolute;
  width: 1px;
  height: 1px;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
}

/* ---- Payment pages ------------------------------------------------------ */
.pay { max-width: 640px; margin: 0 auto; padding: 130px 24px 80px; }
.pay__card { border-radius: var(--radius-cta); padding: 36px 32px; box-shadow: 0 20px 46px -26px rgba(0,0,0,.6); }
.pay__kicker { font-family: var(--font-mono); font-size: .8125rem; letter-spacing: .1em; color: var(--ink-muted); margin: 0 0 6px; }
.pay__lede { color: var(--ink-muted); margin: 10px 0 26px; }
.pay__lines { list-style: none; margin: 0 0 6px; padding: 0; }
.pay__lines li { display: flex; justify-content: space-between; gap: 16px; align-items: baseline;
  padding: 13px 0; border-bottom: 1px solid rgba(42,36,22,.14); }
.pay__lines em { font-style: normal; color: var(--ink-muted); }
.pay__total { display: flex; justify-content: space-between; align-items: baseline;
  padding: 16px 0 4px; font-family: var(--font-display); }
.pay__total b { font-size: 1.625rem; }
.pay__discount { display: flex; justify-content: space-between; align-items: baseline;
  padding: 13px 0; margin: 0; border-bottom: 1px solid rgba(42,36,22,.14); }
.pay__cta { width: 100%; margin-top: 22px; font-size: 1.0625rem; }
.pay__note { font-size: .9375rem; color: var(--ink-muted); margin-top: 16px; }
.pay__note--warn { color: var(--ink-error); font-weight: 600; }
.pay__stamp { display: inline-block; font-family: var(--font-display); font-size: 1.75rem; font-weight: 700;
  color: var(--ink-error); border: 3px solid var(--ink-error); border-radius: 8px; padding: 4px 16px; margin-bottom: 14px; }

/* Fulfilment timeline: Your voice, Printing, Sealing, Posted, Tap!
   The state rules below are written as `.timeline li.x`, not `.x`. `.timeline
   li` is (0,1,1) and would otherwise out-specify a lone class — which is why
   the "done" green had silently never applied. */
.timeline { list-style: none; display: flex; justify-content: center; gap: 6px;
  margin: 26px 0; padding: 0; counter-reset: stop; flex-wrap: wrap; }
.timeline li { flex: 1 1 90px; font-size: .875rem; color: var(--ink-faint);
  border-top: 3px solid rgba(42,36,22,.18); padding-top: 10px; }
.timeline li.timeline__done { color: var(--forest); font-weight: 600; border-top-color: var(--forest); }
.timeline li.timeline__done::before { content: "\2713\00a0"; }

/* A stop the BUYER still has to do. Distinct from merely un-ticked: those are
   ours to finish and need no attention, this one stalls the order until it is
   done. Colour alone never carries it — the bullet and the weight change too,
   so it still reads as urgent without colour vision. */
.timeline li.timeline__todo { color: var(--ink-error); font-weight: 700; border-top-color: var(--ink-error); }
.timeline li.timeline__todo::before { content: "\25cf\00a0"; }

/* The one panel on the site allowed to shout. Used when an order cannot be
   fulfilled until the buyer acts — today that means a missing recording. */
.pay__urgent {
  margin: 24px 0 6px; padding: 22px 22px 18px;
  border: 2px solid var(--ink-error); border-radius: var(--radius-cta);
  background: color-mix(in srgb, var(--ink-error) 6%, var(--parchment-input));
}
.pay__urgent__kicker {
  font-size: .75rem; letter-spacing: .14em; font-weight: 700;
  color: var(--ink-error); margin-bottom: 6px;
}
.pay__urgent h2 { font-size: 1.3rem; margin-bottom: 8px; text-wrap: balance; }
.pay__urgent p { color: var(--ink-muted); max-width: 52ch; }
.pay__urgent__cta { margin: 16px 0 12px; }
.pay__urgent__calm { font-size: .9375rem; color: var(--ink-faint); }

/* ---- Order Builder ------------------------------------------------------ */
.shop {
  max-width: 1160px; margin: 0 auto; padding: 122px 24px 80px;
  display: grid; grid-template-columns: minmax(0, 1fr) 360px; gap: 26px; align-items: start;
}
.shop__paper { position: relative; border-radius: var(--radius-cta); padding: 40px 36px 34px;
  box-shadow: 0 20px 46px -26px rgba(0,0,0,.6); }
.shop__paper > h1 { font-size: clamp(2.25rem, 3.6vw, 3rem); }

/* Rotated season postmark, top-right of the paper. */
.shop__badge {
  position: absolute; top: 22px; right: 26px; width: 92px; height: 92px;
  border: 2.5px solid var(--theme-ink); border-radius: 50%; color: var(--theme-ink);
  display: grid; place-content: center; text-align: center; gap: 2px;
  transform: rotate(-7deg); mix-blend-mode: multiply; pointer-events: none;
}
.shop__glyph { font-size: 1.375rem; line-height: 1; }
.shop__season { font-size: .5625rem; font-weight: 700; letter-spacing: .14em; }

.shop__scriptline { font-size: clamp(1.125rem, 2.4vw, 1.75rem); color: var(--gold-pale); }

.step { margin-top: 32px; }
.step__n { font-size: .6875rem; font-weight: 700; letter-spacing: .18em;
  text-transform: uppercase; color: var(--ink-faint); margin: 0 0 14px; }

.shop__cat { display: grid; gap: 10px; }
.radio-card--off { opacity: .55; cursor: not-allowed; }
.radio-card__body { flex: 1; display: flex; flex-direction: column; gap: 2px; }
.radio-card__blurb { font-size: .9375rem; color: var(--ink-muted); }
.radio-card__price { text-align: right; display: flex; flex-direction: column; gap: 2px; white-space: nowrap; }
.radio-card__price em { font-style: normal; font-size: .6875rem; letter-spacing: .1em;
  text-transform: uppercase; color: var(--ink-faint); }

.opt { margin-bottom: 22px; }
.opt__q { font-weight: 600; margin: 0 0 10px; }
.opt__pair { display: grid; gap: 10px; grid-template-columns: repeat(auto-fit, minmax(230px, 1fr)); }
.opt__note { font-size: .9375rem; color: var(--ink-muted); font-style: italic; margin-top: 14px; }
.opt__check { display: flex; gap: 12px; align-items: flex-start; cursor: pointer;
  background: var(--parchment-input); border: 2px solid rgba(42,36,22,.18);
  border-radius: var(--radius-input); padding: 14px 16px; }
.opt__check input { margin-top: 4px; width: 20px; height: 20px; accent-color: var(--gold); }
.opt__check em { display: block; font-style: normal; font-size: .9375rem; color: var(--ink-muted); }

.qty { display: flex; align-items: center; gap: 12px; margin-top: 18px; }
.qty__btn { width: 44px; height: 44px; border-radius: 50%; border: 1.5px solid rgba(42,36,22,.35);
  background: var(--parchment-input); font-size: 1.25rem; cursor: pointer; color: var(--ink); }
.qty__btn:hover { border-color: var(--ink); }
.qty__n { min-width: 2ch; text-align: center; font-family: var(--font-display);
  font-size: 1.25rem; font-variant-numeric: tabular-nums; }

.shop__cta { width: 100%; margin-top: 30px; font-size: 1.0625rem; }
.shop__reassure { font-size: .9375rem; color: var(--ink-muted); text-align: center; margin-top: 12px; }

/* The slip rides along on desktop and drops under the paper on mobile. */
.shop__rail { position: sticky; top: 96px; }
.slip__head { font-family: var(--font-display); font-size: 1.25rem; margin: 0 0 14px; }
.slip__lines { list-style: none; margin: 0; padding: 0; }
.slip__lines li, .slip__bd li { display: flex; justify-content: space-between; gap: 14px;
  align-items: baseline; padding: 9px 0; border-bottom: 1px solid rgba(42,36,22,.13); font-size: .9375rem; }
.slip__lines b, .slip__bd b { white-space: nowrap; }
.slip__total { display: flex; justify-content: space-between; align-items: baseline;
  padding-top: 15px; font-family: var(--font-display); margin: 0; }
.slip__total b { font-size: 1.625rem; }
.slip__sub { font-size: .8125rem; color: var(--ink-muted); margin: 2px 0 0; min-height: 1em; }
.slip__bd { margin-top: 16px; }
.slip__bd summary { cursor: pointer; font-size: .9375rem; color: var(--forest); padding: 6px 0; }
.slip__bd ul { list-style: none; margin: 8px 0 0; padding: 0; }
/* What's in the price: a list of things, not a column of figures. The
   space-between rule above is for label/amount pairs and would stretch a
   lone line across the slip, so these opt out of it. */
.slip__inc li { display: grid; grid-template-columns: 15px 1fr; gap: 11px;
  justify-content: start; align-items: start; }
/* A stamp, not a tick.
   The same perforated silhouette the storybook's navigation rail uses,
   drawn at bullet size with a wax dot where the illustration would be, so
   the site speaks one postal language instead of borrowing a checkmark
   from a form. Inline as a data URI: no extra request, and it obeys the
   tap page's rule that nothing is fetched from anywhere but us.

   It replaces a tick that rendered as "¹3" — the CSS escape went through
   a Python string on its way into this file, and \271 is a valid octal
   escape there. */
.slip__inc li::before {
  content: ""; width: 15px; height: 17.5px; margin-top: 2px;
  background: url("data:image/svg+xml,%3Csvg%20xmlns%3D%22http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%22%20viewBox%3D%220%200%2024%2028%22%3E%3Cpath%20d%3D%22M%200%200%20L%202.7%200%20A%201.3%201.3%200%200%200%205.3%200%20L%2010.7%200%20A%201.3%201.3%200%200%200%2013.3%200%20L%2018.7%200%20A%201.3%201.3%200%200%200%2021.3%200%20L%2024%200%20L%2024%202.2%20A%201.3%201.3%200%200%200%2024%204.8%20L%2024%209.2%20A%201.3%201.3%200%200%200%2024%2011.8%20L%2024%2016.2%20A%201.3%201.3%200%200%200%2024%2018.8%20L%2024%2023.2%20A%201.3%201.3%200%200%200%2024%2025.8%20L%2024%2028%20L%2021.3%2028%20A%201.3%201.3%200%200%200%2018.7%2028%20L%2013.3%2028%20A%201.3%201.3%200%200%200%2010.7%2028%20L%205.3%2028%20A%201.3%201.3%200%200%200%202.7%2028%20L%200%2028%20L%200%2025.8%20A%201.3%201.3%200%200%200%200%2023.2%20L%200%2018.8%20A%201.3%201.3%200%200%200%200%2016.2%20L%200%2011.8%20A%201.3%201.3%200%200%200%200%209.2%20L%200%204.8%20A%201.3%201.3%200%200%200%200%202.2%20Z%22%20fill%3D%22%23F7F1E3%22%20stroke%3D%22rgba%2894%2C74%2C14%2C.35%29%22%20stroke-width%3D%22.5%22%2F%3E%3Crect%20x%3D%223.2%22%20y%3D%223.6%22%20width%3D%2217.6%22%20height%3D%2220.8%22%20fill%3D%22none%22%20stroke%3D%22rgba%2894%2C74%2C14%2C.4%29%22%20stroke-width%3D%22.7%22%2F%3E%3Ccircle%20cx%3D%2212.0%22%20cy%3D%2213.6%22%20r%3D%224.1%22%20fill%3D%22%23C9A227%22%2F%3E%3Ccircle%20cx%3D%2211.0%22%20cy%3D%2212.4%22%20r%3D%221.5%22%20fill%3D%22%23E7CF74%22%20opacity%3D%22.85%22%2F%3E%3C%2Fsvg%3E") center/contain no-repeat;
}
.slip__inc span { line-height: 1.55; }
.slip__note { font-size: .8125rem; color: var(--ink-muted); margin-top: 10px; line-height: 1.5; }

@media (max-width: 900px) {
  .shop { grid-template-columns: minmax(0, 1fr); }
  .shop__rail { position: static; }
  .shop__paper { padding: 32px 22px 28px; }
  .shop__badge { width: 72px; height: 72px; top: 16px; right: 16px; }
  .shop__paper > h1 { padding-right: 76px; }
}

/* "Keep this link" — with no accounts, the URL IS the credential, so it is
   presented as an object to keep rather than a footnote. */
.pay__keep { background: var(--parchment-input); border: 1.5px dashed rgba(42,36,22,.35);
  border-radius: var(--radius-input); padding: 16px 18px; margin-top: 26px; }
.pay__keep code { display: block; font-size: .9375rem; word-break: break-all;
  color: var(--ink); background: none; padding: 0; }
.track { display: grid; gap: 18px; margin-top: 22px; max-width: 420px; }

/* ---- Legal pages -------------------------------------------------------- */
/* Six documents, one template (templates/legal/document.html). Long-form
   reading on a dark ground, so the measure is tight and the rows are a
   definition list rather than a table: a policy read on a phone must not
   scroll sideways. */
.legal__stamp {
  font-size: .8125rem; letter-spacing: .04em;
  color: var(--gold-pale); opacity: .7; margin: -12px 0 28px;
}
.legal__intro { font-size: 1.0625rem; line-height: 1.7; margin: 0 0 32px; }
.legal__section { margin: 0 0 30px; }
.legal__section h2 {
  font-size: 1.125rem; color: var(--parchment-paper);
  margin: 0 0 10px; line-height: 1.3;
}
.legal__section p { line-height: 1.7; margin: 0 0 12px; }
.legal__list { line-height: 1.7; padding-left: 22px; margin: 0 0 12px; }
.legal__list li { margin: 0 0 8px; }
.legal__rows { margin: 0 0 14px; }
.legal__rows dt {
  font-weight: 600; color: var(--parchment-paper);
  margin: 12px 0 2px; line-height: 1.5;
}
.legal__rows dd { margin: 0; line-height: 1.7; }
/* An unresolved fact is shown, not hidden: a policy missing something the law
   requires is exactly what the founder must be able to see from the page. */
.legal__flag {
  border-left: 3px solid var(--gold-hi);
  background: rgba(255, 253, 246, .06);
  padding: 12px 16px; margin: 0 0 28px; line-height: 1.6;
}
.legal__more { margin-top: 48px; border-top: 1px solid rgba(247, 238, 216, .18); }
.legal__more h2 { font-size: 1rem; margin: 24px 0 10px; color: var(--parchment-paper); }

/* ---- Pre-contract disclosures ------------------------------------------- */
/* The block that sits immediately above a payment button. Deliberately plain:
   it is the one thing on that screen a buyer must actually read, so it is not
   dressed to be skimmed past, and not so loud that it reads as a warning
   about us. See legal/precontract.py. */
.precontract {
  border: 1px solid rgba(42, 36, 22, .18);
  border-radius: 10px;
  padding: 16px 18px;
  margin: 26px 0 18px;
  text-align: left;
}
.precontract__h {
  font-size: .75rem; letter-spacing: .16em; text-transform: uppercase;
  margin: 0 0 10px; color: rgba(42, 36, 22, .62); font-weight: 700;
}
.precontract__list { list-style: none; margin: 0; padding: 0; }
.precontract__list li {
  padding: 9px 0; line-height: 1.55; font-size: .9375rem;
  border-top: 1px solid rgba(42, 36, 22, .1);
}
.precontract__list li:first-child { border-top: none; padding-top: 0; }
.precontract__list strong { display: block; margin-bottom: 2px; }
.precontract__links { display: block; margin-top: 4px; font-size: .8125rem; }

/* ---- Christmas posting notice ------------------------------------------- */
/* Sitewide in November and December only. "shut" is the one that matters: the
   delivery policy promises the site will SAY the window has gone rather than
   quietly take an order it cannot deliver, so it is the loud one. */
.xmas-notice {
  margin: 0; padding: 10px 20px; text-align: center;
  font-size: .9375rem; line-height: 1.5;
  background: var(--gold-deep, #b8860b); color: #1F2430;
}
.xmas-notice a { color: inherit; text-decoration: underline; }
.xmas-notice--shut { background: var(--brand-red, #C0392B); color: #F7EED8; }
