/* ==========================================================================
   sirdominic.scot/commission: private commissions, set in the Haus of Sir's card
   language (thehausofsir.com, 2026-09-23 "title cards"), not a form template.

   One idea per held screen, centred on one axis. Two faces only:
     Haus Heavy  (Libre Franklin 900 narrowed to Franklin Gothic Heavy's widths)
                 for every title, question and choice, in caps with a soft edge
     IBM Plex Mono  for everything read or typed (the Goonbate site's mono)
   Red only in touches: the cue dot on what is chosen, the star separators, the
   rule under a hovered word, an error. Hovers and choices are hard cuts. Nothing
   fades in on scroll. Content never depends on JS.
   ========================================================================== */

@font-face { font-family: 'Haus Heavy'; src: url('../fonts/haus-heavy.woff2') format('woff2'); font-weight: 400 900; font-display: swap; }
@font-face { font-family: 'Haus Heavy Star'; src: url('../fonts/haus-heavy-star.woff2') format('woff2'); font-display: swap; }
@font-face { font-family: 'IBM Plex Mono'; src: url('../fonts/ibm-plex-mono-400.woff2') format('woff2'); font-weight: 400; font-display: swap; }
@font-face { font-family: 'IBM Plex Mono'; src: url('../fonts/ibm-plex-mono-500.woff2') format('woff2'); font-weight: 500; font-display: swap; }

.page-commission {
  --ground: #0c0c0b;                        /* the Haus off-black */
  --ink: #e4e3df;                           /* the Haus soft white */
  --ink-80: rgba(228, 227, 223, .80);       /* 11.9:1 reading copy */
  --ink-60: rgba(228, 227, 223, .60);       /*  7.2:1 secondary */
  --ink-45: rgba(228, 227, 223, .45);       /*  4.6:1 small labels, unchosen words */
  --ink-20: rgba(228, 227, 223, .20);       /* rules */
  --red: #ff2a1f;                           /* touches only */
  --heavy: 'Haus Heavy', 'Franklin Gothic Heavy', 'Libre Franklin', 'Arial Black', sans-serif;
  --mono: 'IBM Plex Mono', ui-monospace, 'SF Mono', Menlo, monospace;
  --gutter: clamp(24px, 5vw, 72px);
  --soft: 0 0 1px rgba(228, 227, 223, .45);  /* the optical-print edge on heavy caps */
  background: var(--ground);
  color: var(--ink);
}
.page-commission ::selection { background: var(--red); color: var(--ink); }

/* the shared header and footer, in this page's two faces so nothing sits on a third */

/* --------------------------------------------------------------------------
   Cards
   -------------------------------------------------------------------------- */
.cm { display: block; }
.card {
  container-type: inline-size;
  display: grid; grid-template-columns: minmax(0, 1fr); place-items: center; text-align: center;   /* a track that can never be pushed wider than the card */
  min-height: 100svh;   /* one card per screen; the pager (main.js) moves a card at a time */
  padding: clamp(4rem, 13svh, 8rem) var(--gutter);
}
.card.open { min-height: calc(100svh - var(--head-h)); padding-top: clamp(2rem, 7svh, 5rem); }
.stack { display: grid; grid-template-columns: minmax(0, 1fr); justify-items: center; gap: clamp(1.1rem, 3svh, 1.9rem); width: 100%; max-width: 62rem; min-width: 0; }

.kicker { display: inline-flex; align-items: center; gap: .8em; font: 500 .72rem/1 var(--mono); letter-spacing: .16em; text-transform: uppercase; color: var(--ink-60); }
.kicker i, .colophon i, .fine i { font-style: normal; color: var(--red); letter-spacing: 0; }

.card-title, .q-title, .statement, .w span, .rung-n, .btn {
  font-family: var(--heavy); font-weight: 400; text-transform: uppercase; letter-spacing: -.01em; text-shadow: var(--soft);
}
.card-title { font-family: 'Haus Heavy Star', var(--heavy); font-size: clamp(2.4rem, 11.4cqi, 9.6rem); line-height: .86; max-width: 100%; }   /* commission.js fits each line to the card */
.card-title > span { display: block; white-space: nowrap; }
.q-title { font-size: clamp(2.1rem, 8.4cqi, 6.2rem); line-height: .9; max-width: 11em; text-wrap: balance; }
.q-title label { cursor: text; }
.statement { font-size: clamp(1.45rem, 4.2cqi, 3rem); line-height: 1.02; max-width: 17em; text-wrap: balance; }
.read { max-width: 38em; font: 400 clamp(.95rem, 1.2vw, 1.05rem)/1.75 var(--mono); color: var(--ink-80); text-wrap: pretty; }
.colophon { font: 500 .7rem/1.9 var(--mono); letter-spacing: .1em; text-transform: uppercase; color: var(--ink-60); text-wrap: balance; }
.colophon i, .fine i { margin: 0 .7em; }
.fine { max-width: 44em; font: 400 .78rem/1.8 var(--mono); color: var(--ink-45); text-wrap: balance; }
.mono-k { font: 500 .66rem/1 var(--mono); letter-spacing: .16em; text-transform: uppercase; color: var(--ink-45); }

/* the line icon above each question: a primary stroke and a thinner one that draws in red when that card is done */
.ico { width: 28px; height: 28px; fill: none; stroke: var(--ink-60); stroke-linecap: round; stroke-linejoin: round; overflow: visible; }
.ico-p { stroke-width: 1.5; }
.ico-s { stroke-width: 1.1; stroke: var(--ink-45); }
.q.is-done .ico-s { stroke: var(--red); }
@media (prefers-reduced-motion: no-preference) {
  .q.is-done .ico-s path { stroke-dasharray: 1; stroke-dashoffset: 1; animation: draw .5s cubic-bezier(.6, 0, .2, 1) forwards; }
}
@keyframes draw { to { stroke-dashoffset: 0; } }

/* --------------------------------------------------------------------------
   The Haus button: heavy caps on a hairline, led by a red cue dot.
   Hover is a hard cut: the rule turns red and the arrow steps 4px on.
   -------------------------------------------------------------------------- */
.btn {
  display: inline-flex; align-items: center; gap: .7em; cursor: pointer;
  font-size: clamp(1.05rem, 1.7vw, 1.3rem); line-height: 1; letter-spacing: .03em;
  color: var(--ink); text-decoration: none; background: none; border: 0; border-bottom: 2px solid var(--ink); border-radius: 0;
  padding: .55em 0 .6em; min-height: 44px;
}
.btn::before { content: ""; width: .52em; height: .52em; border-radius: 50%; background: var(--red); flex: none; transform: translateY(-.04em); }
.btn-arrow { width: 1.3em; height: .78em; flex: none; fill: none; stroke: currentColor; stroke-width: 2.4; stroke-linecap: round; stroke-linejoin: round; overflow: visible; }
.btn-arrow--down { transform: rotate(90deg); }
.btn:hover, .btn:focus-visible { border-bottom-color: var(--red); outline: none; }
.btn:focus-visible { outline: 2px solid var(--ink); outline-offset: 6px; }
.btn:hover .btn-arrow, .btn:focus-visible .btn-arrow { transform: translateX(4px); color: var(--red); }
.btn:hover .btn-arrow--down, .btn:focus-visible .btn-arrow--down { transform: rotate(90deg) translateX(4px); }
.btn--toggle[aria-expanded="true"] .btn-arrow--down { transform: rotate(-90deg); }
.btn--send { font-size: clamp(1.4rem, 2.6vw, 2rem); margin-top: .4rem; }
.cm-form.sending .btn--send { cursor: wait; }
.cm-form.sending .btn--send .lbl { animation: blink .5s steps(1, end) infinite; }
@keyframes blink { 50% { visibility: hidden; } }
.link { min-height: 44px; padding: 0 .2em; border: 0; background: none; cursor: pointer; font: 500 .74rem/1 var(--mono); letter-spacing: .12em; text-transform: uppercase; color: var(--ink-60); }
.link:hover, .link:focus-visible { background: var(--ink); color: var(--ground); outline: none; }

/* --------------------------------------------------------------------------
   Words to choose. Unchosen sit back at 45%. Hover: full ink and the red rule.
   Chosen: full ink, led by the red cue dot (the Haus "current page" mark).
   -------------------------------------------------------------------------- */
.words { display: flex; flex-wrap: wrap; justify-content: center; gap: .15em 1.05em; font-size: clamp(1.2rem, 2.7cqi, 1.9rem); line-height: 1; }
.w { position: relative; cursor: pointer; }
.w input, .rung input, .cur input, .adult input { position: absolute; opacity: 0; width: 1px; height: 1px; pointer-events: none; }
.w span { position: relative; display: inline-block; white-space: nowrap; padding: .38em 0 .32em; color: var(--ink-45); border-bottom: 2px solid transparent; }
.w span::before { content: ""; position: absolute; left: -.62em; top: 50%; width: .36em; height: .36em; margin-top: -.2em; border-radius: 50%; background: var(--red); visibility: hidden; }
.w:hover span { color: var(--ink); border-bottom-color: var(--red); }
.w input:checked + span { color: var(--ink); }
.w input:checked + span::before { visibility: visible; }
.w input:focus-visible + span { outline: 2px solid var(--ink); outline-offset: 4px; }
/* starred rows: the red star between words, never at a line start */
.words--starred { gap: .15em 0; align-items: center; }
.words--starred .w { display: inline-flex; align-items: center; }
.words--starred .w + .w::before { content: "\2605"; display: inline-block; color: var(--red); font: 400 .34em/1 var(--mono); margin: 0 3.2em 0 2.4em; }
.words--xl { font-size: clamp(1.9rem, 5.4cqi, 4.2rem); flex-wrap: nowrap; }
.words--xl .w span { padding: .2em 0 .14em; }
.words--s { font-size: clamp(1.05rem, 2cqi, 1.4rem); gap: .1em 1.5em; }

/* direction: three groups, each a centred row */
.themes { display: grid; gap: clamp(1.4rem, 3.5svh, 2.2rem); width: 100%; margin-top: .4rem; }
.theme-group { display: grid; gap: .7rem; justify-items: center; }

/* the work: shaping details open once a form is chosen */
.read--swap span { display: none; }
.read--swap span[data-v=""] { display: inline; }
.read--swap.has span { display: none; }
.read--swap.has span.on { display: inline; }
.spec { display: none; width: 100%; max-width: 46rem; border-top: 1px solid var(--ink-20); }
.cm-form.has-format .spec { display: grid; }
.spec-row { display: grid; gap: .5rem; justify-items: center; padding: 1.1rem 0 1.2rem; border-bottom: 1px solid var(--ink-20); }
.spec .fine { padding-top: 1rem; justify-self: center; text-align: center; }
.spec-row--timing { width: 100%; max-width: 46rem; border-bottom: 0; padding-bottom: 0; margin-top: .6rem; }

/* fields: mono on a hairline, labels small and tracked */
.field { display: grid; gap: .5rem; width: 100%; text-align: left; }
.field--narrow { max-width: 24rem; }
.field > label { font: 500 .66rem/1 var(--mono); letter-spacing: .16em; text-transform: uppercase; color: var(--ink-60); }
.field input, .field textarea {
  width: 100%; min-width: 0; padding: .45rem 0 .55rem; border: 0; border-bottom: 1px solid var(--ink-20); border-radius: 0;
  background: transparent; color: var(--ink); outline: none; caret-color: var(--red); color-scheme: dark;
  font: 400 1.02rem/1.5 var(--mono);
}
.field textarea { resize: vertical; min-height: 5rem; }
.field input:hover, .field textarea:hover { border-bottom-color: var(--ink-45); }
.field input:focus, .field textarea:focus { border-bottom-color: var(--ink); }
.fields { display: grid; grid-template-columns: 1fr 1fr; gap: 1.6rem 2.4rem; width: 100%; max-width: 46rem; margin-top: .6rem; }
.fields[hidden], .page-commission [hidden] { display: none !important; }
.field--wide { grid-column: 1 / -1; }
.fields--two { max-width: 40rem; }

/* the idea: a ruled sheet in the reading face */
.sheet { width: 100%; max-width: 46rem; margin-top: .6rem; text-align: left; }
.sheet textarea {
  --lh: 34px;
  display: block; width: 100%; min-height: calc(var(--lh) * 7); resize: vertical; padding: 0; border: 0; outline: none;
  font: 400 1.08rem/var(--lh) var(--mono); color: var(--ink); caret-color: var(--red);
  --rule: var(--ink-20);
  background: linear-gradient(to top, var(--rule) 1px, transparent 1px) 0 0 / 100% var(--lh) repeat-y; background-attachment: local;
}
.sheet textarea::placeholder { color: var(--ink-45); }
.sheet textarea:focus { --rule: var(--ink-45); }
.sheet-foot { display: flex; align-items: baseline; gap: 1rem; margin-top: .8rem; }
.count { margin-left: auto; font: 500 .66rem/1 var(--mono); letter-spacing: .14em; text-transform: uppercase; color: var(--ink-45); font-variant-numeric: tabular-nums; }

/* scope: a ladder that reads down, centred; each rung left-aligned inside */
.cur { display: inline-flex; gap: .2rem; }
.cur label { cursor: pointer; }
.cur span { display: grid; place-items: center; width: 40px; height: 36px; font: 500 .95rem/1 var(--mono); color: var(--ink-45); }
.cur span:hover { color: var(--ink); }
.cur input:checked + span { background: var(--ink); color: var(--ground); }
.cur input:focus-visible + span { outline: 2px solid var(--ink); outline-offset: 2px; }
.ladder { width: 100%; max-width: 40rem; border-top: 1px solid var(--ink-20); text-align: left; }
.rung { position: relative; display: grid; grid-template-columns: 1.4rem minmax(0, 1fr) auto; align-items: center; gap: .6rem; min-height: 60px; padding: .55rem 0; border-bottom: 1px solid var(--ink-20); cursor: pointer; }
.rung::before { content: ""; width: .42rem; height: .42rem; border-radius: 50%; background: var(--red); visibility: hidden; justify-self: center; }
.rung-n { font-size: clamp(1.1rem, 2cqi, 1.45rem); line-height: 1.05; color: var(--ink-45); }
.rung-r { font: 400 .86rem/1 var(--mono); color: var(--ink-45); font-variant-numeric: tabular-nums; white-space: nowrap; }
.rung:hover .rung-n { color: var(--ink); }
.rung:hover { box-shadow: inset 0 -2px 0 var(--red); }
.rung:has(input:checked)::before { visibility: visible; }
.rung:has(input:checked) .rung-n { color: var(--ink); }
.rung:has(input:checked) .rung-r { color: var(--ink-80); }
.rung:has(input:focus-visible) { outline: 2px solid var(--ink); outline-offset: 2px; }
.reveal { display: none !important; }
.reveal.on { display: grid !important; }

/* errors: plain and red, only when needed */
.err { display: none; font: 400 .86rem/1.4 var(--mono); color: var(--red); text-align: left; }
.is-bad .err, .err.is-bad { display: block; }
.field.is-bad input { border-bottom-color: var(--red); }
.field.is-bad > label { color: var(--red); }
.sheet.is-bad textarea { --rule: rgba(255, 42, 31, .6); }
.adult + .err { text-align: center; margin-top: -.6rem; }
.cm-form .hp { position: absolute; left: -9999px; width: 1px; height: 1px; opacity: 0; }

/* --------------------------------------------------------------------------
   The close: the eye in its ring, the line, the confirmation, the button.
   The answer replaces it in the same grid cell, so the page does not move.
   -------------------------------------------------------------------------- */
.close { min-height: 100svh; }
.close-ask, .close-done { grid-area: 1 / 1; }
.close-done { visibility: hidden; align-content: center; }
.cm-form.done .close-ask { visibility: hidden; }
.cm-form.done .close-done { visibility: visible; }
.cm-form.done .q { opacity: .35; pointer-events: none; }
.seal { --seal: clamp(150px, 18vw, 200px); position: relative; width: var(--seal); aspect-ratio: 1; display: grid; place-items: center; margin-bottom: .4rem; }
.seal img { width: 44%; height: auto; }
.circular-text { position: absolute; inset: 0; font: 500 calc(var(--seal) * .074)/1 var(--mono); text-transform: uppercase; color: var(--ink-80); border-radius: 50%; }
.circular-text span { position: absolute; inset: 0; text-align: center; }
@media (prefers-reduced-motion: no-preference) {
  .circular-text { animation: tick 60s steps(60, end) infinite; }
  .seal:hover .circular-text { animation-duration: 15s; }
}
@keyframes tick { to { transform: rotate(360deg); } }
/* tick boxes: a square that fills soft white with a drawn tick (Add personal direction, Discord, 18+) */
.tickbox { display: inline-flex; align-items: center; gap: .85rem; min-height: 44px; cursor: pointer; font: 400 1.02rem/1.4 var(--mono); color: var(--ink); text-align: left; }
.tickbox input { position: absolute; opacity: 0; width: 1px; height: 1px; pointer-events: none; }
.tickbox-box { width: 22px; height: 22px; flex: none; box-shadow: inset 0 0 0 1.5px var(--ink-45); }
.tickbox:hover .tickbox-box { box-shadow: inset 0 0 0 1.5px var(--ink); }
.tickbox-box { position: relative; }
.tickbox input:checked + .tickbox-box { background: var(--ink); box-shadow: none; }
.tickbox-box::after { content: ""; position: absolute; inset: 0; visibility: hidden; background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 18'%3E%3Cpath d='M3 9.6c2.3 1.9 4.1 3.9 5.6 6C11.5 10.5 15.6 5.6 21 2.2' fill='none' stroke='%230c0c0b' stroke-width='3.2' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") center / 70% no-repeat; }
.tickbox input:checked + .tickbox-box::after { visibility: visible; }
@media (prefers-reduced-motion: no-preference) {
  .tickbox input:checked + .tickbox-box::after { animation: tick-draw .26s cubic-bezier(.6, 0, .2, 1) both; }
  .tickbox input:checked + .tickbox-box { animation: tick-pop .3s cubic-bezier(.16, .84, .24, 1); }
}
@keyframes tick-draw { from { clip-path: inset(0 100% 0 0); } to { clip-path: inset(0 0 0 0); } }
@keyframes tick-pop { 0% { transform: scale(.82); } 100% { transform: none; } }
.tickbox input:focus-visible + .tickbox-box { outline: 2px solid var(--ink); outline-offset: 3px; }
.tickbox--s { font-size: .9rem; color: var(--ink-80); }
.tickbox--s .tickbox-box { width: 18px; height: 18px; }
.adult.is-bad .tickbox-box { box-shadow: inset 0 0 0 1.5px var(--red); }
.send-msg { min-height: 1.4em; max-width: 40em; font: 400 .9rem/1.6 var(--mono); color: var(--red); text-wrap: balance; }
.send-msg .miss { color: var(--ink); text-decoration: underline 1px var(--red); text-underline-offset: .25em; }
.send-msg .miss:hover, .send-msg .miss:focus-visible { background: var(--ink); color: var(--ground); text-decoration: none; outline: none; }
.done-eye { width: clamp(110px, 12vw, 150px); height: auto; }
.close-done b { color: var(--ink); font-weight: 500; }
@media (prefers-reduced-motion: no-preference) { .cm-form.done .done-eye { animation: stamp .5s cubic-bezier(.16, .84, .24, 1) both; } }
@keyframes stamp { from { transform: scale(1.8) rotate(-12deg); } to { transform: none; } }

/* arrival, once, on the loader's cut: the opening card's lines ease up in order */
@media (prefers-reduced-motion: no-preference) {
  html.loaded .open .stack > *, html.loaded .tipx > * { animation: rise .8s cubic-bezier(.16, .84, .24, 1) both; }
  html.loaded .open .stack > :nth-child(1), html.loaded .tipx > :nth-child(1) { animation-delay: .05s; }
  html.loaded .open .stack > :nth-child(2), html.loaded .tipx > :nth-child(2) { animation-delay: .15s; }
  html.loaded .open .stack > :nth-child(3) { animation-delay: .3s; }
  html.loaded .open .stack > :nth-child(n+4) { animation-delay: .42s; }
  @keyframes rise { from { opacity: 0; transform: translateY(14px); } to { opacity: 1; transform: none; } }
}
@keyframes cut-in { from { visibility: hidden; } to { visibility: visible; } }

/* --------------------------------------------------------------------------
   Phones: the same cards, just narrower. Fields stack; words wrap centred.
   -------------------------------------------------------------------------- */
@media (max-width: 640px) {
  .card { min-height: 100svh; padding-block: clamp(3rem, 9svh, 4.5rem); }   /* one card per screen, snapped */
  .card.open { min-height: calc(100svh - var(--head-h)); }
  .fields { grid-template-columns: 1fr; }
  .words--xl { flex-direction: column; align-items: center; font-size: clamp(1.9rem, 10cqi, 2.8rem); }
  .words--starred .w + .w::before { display: none; }
  .rung { grid-template-columns: 1.2rem minmax(0, 1fr); }
  .rung-r { grid-column: 2; padding-bottom: .15rem; }
  .colophon i { display: block; height: 0; overflow: hidden; }
  }


/* React Bits, ported: ClickSpark (one fixed canvas, red sparks where you choose), DecryptedText
   (a chosen word scrambles and resolves), CountUp (the ranges count to new values) */
.spark-canvas { position: fixed; inset: 0; width: 100vw; height: 100vh; pointer-events: none; z-index: 900; }
.rate-note { font: 500 .7rem/1.6 var(--mono); letter-spacing: .12em; text-transform: uppercase; color: var(--ink-60); }
.rate-note b { color: var(--red); font-weight: 500; }
.rung-r { min-width: 9.5em; text-align: right; }

/* phones (any way up) and tablets: fingertip-sized choices and readable labels */
@media (max-width: 700px), (pointer: coarse) {
  .words .w span { padding: .62em 0 .56em; min-height: 44px; display: inline-flex; align-items: center; }
  .words { column-gap: 1.2em; }
  .kicker { font-size: .78rem; }
  .mono-k, .field > label, .count, .seg-k { font-size: .74rem; }
  .fine { font-size: .84rem; }
  .rung { min-height: 64px; }
  .cur span { width: 48px; height: 44px; }
  .tickbox { min-height: 48px; }
}
