/**
 * chat.css — Chat surface layout (desktop + mobile).
 *
 * Extracted from index.html in b.840 (was <style id="surface-layout-chat">,
 * lines 43743-43958 in the b.839 single-file build). Content is byte-identical
 * to the inline block it replaced.
 *
 * Owns: .ce-stage, .ce-thread, .ce-inputbar, .ce-input-row, .ce-input-meta,
 *       .ce-input-tools, .ce-textarea, .ce-send-btn
 *
 * Loaded LAST in <head> (after mobile-landing.css) so it wins cascade order
 * over earlier inline rules. Chat is DESKTOP-ONLY as of b.843; mobile chat
 * code was deleted because mobile-landing.css overlay takes over the full
 * viewport at <=1024px and no chat element is ever visible on mobile.
 *
 * NOTE: a separate file `chat-surface.css` (at the project root) is dead
 * weight from a b.805 experiment that was never wired up. Safe to delete
 * manually — sandbox can't delete files. User can drop it from Finder.
 */

/* ─────────────────────────────────────────────────────────────────
   CHAT SURFACE LAYOUT
   Owns: .ce-stage, .ce-thread, .ce-inputbar, .ce-input-row,
         .ce-input-meta, .ce-input-tools, .ce-textarea, .ce-send-btn
   ───────────────────────────────────────────────────────────────── */

/* ═══════════════ DESKTOP CHAT (>=1025px) ═══════════════ */
@media (min-width: 1025px) {

  /* .ce-stage — chat container fills .main as flex column. */
  body.chat-engine-active #chatEngine.ce-stage {
    position: absolute;
    inset: 0;
    z-index: 6;
    background: transparent;
    max-width: none;
    margin: 0;
    padding: 18px 22px 8px;
    overflow: auto;
    display: flex;
    flex-direction: column;
  }

  /* .ce-thread — message scroll area; absolutely positioned between
     top padding and the position:fixed input cluster below. */
  body.chat-engine-active #chatEngine > .ce-thread {
    position: absolute;
    top: 18px;
    left: 22px;
    right: 22px;
    bottom: 130px;
    overflow-y: auto;
    display: flex;
    flex-direction: column;
    gap: 18px;
    padding: 8px 4px;
  }

  /* .ce-inputbar — meta row (mode + brain + right actions). Fixed
     to viewport bottom; IIFE near </body> sets `bottom` dynamically
     to (8 + measured_input_row_height + 8) for exact 8px gap. */
  body.chat-engine-active #chatEngine > .ce-inputbar {
    position: fixed;
    left: 22px;
    right: 22px;
    bottom: 64px; /* JS overrides with measured value */
    z-index: 10;
    display: flex;
    flex-direction: column;
    gap: 5px;
  }

  /* .ce-input-meta — single row inside the meta bar. Zero padding so
     Chat pill aligns with bar's left edge, Books/History aligns with
     bar's right edge. */
  body.chat-engine-active #chatEngine .ce-input-meta {
    display: flex;
    flex-direction: row;
    align-items: center;
    flex-wrap: wrap;
    gap: 10px;
    padding: 0;
    grid-template-columns: none;
    grid-template-rows: none;
  }

  body.chat-engine-active #chatEngine .ce-input-meta > .ce-mode-selector,
  body.chat-engine-active #chatEngine .ce-input-meta > #ceModelGroup,
  body.chat-engine-active #chatEngine .ce-input-meta > .ce-pill-row,
  body.chat-engine-active #chatEngine .ce-input-meta > .ce-input-meta-center,
  body.chat-engine-active #chatEngine .ce-input-meta > .ce-meta-actions {
    display: inline-flex;
    grid-column: auto;
    grid-row: auto;
    width: auto;
  }

  /* Right cluster (Books / History / + New chat) pushed to right edge. */
  body.chat-engine-active #chatEngine .ce-input-meta > .ce-meta-actions {
    margin-left: auto;
  }

  /* Mobile-only triggers stay hidden on desktop. */
  body.chat-engine-active #chatEngine .ce-mobile-model-trigger,
  body.chat-engine-active #chatEngine .ce-mobile-tools-trigger,
  body.chat-engine-active #chatEngine .ce-mobile-tools-close {
    display: none;
  }

  /* .ce-input-row — input pill (tools + textarea + send) fixed at
     viewport bottom, full width minus 22px gutter. align-self:center
     on children avoids the b.792 flex-end stacking bug. */
  body.chat-engine-active #chatEngine > .ce-input-row {
    position: fixed;
    left: 22px;
    right: 22px;
    bottom: 8px;
    z-index: 10;
    display: flex;
    flex-direction: row;
    align-items: center;
    flex-wrap: nowrap;
    gap: 10px;
  }

  body.chat-engine-active #chatEngine > .ce-input-row > .ce-input-tools {
    position: relative;
    display: flex;
    flex-direction: row;
    align-items: center;
    align-self: center;
    flex: 0 0 auto;
    width: auto;
    height: auto;
    top: auto;
    bottom: auto;
    left: auto;
    right: auto;
    gap: 6px;
    padding: 4px 0;
    background: transparent;
    z-index: auto;
    margin: 0;
  }

  body.chat-engine-active #chatEngine > .ce-input-row > .ce-input-tools > .ce-tool-btn,
  body.chat-engine-active #chatEngine > .ce-input-row > .ce-input-tools > #ceFileBtn,
  body.chat-engine-active #chatEngine > .ce-input-row > .ce-input-tools > #ceWebBtn,
  body.chat-engine-active #chatEngine > .ce-input-row > .ce-input-tools > #ceSettingsBtn,
  body.chat-engine-active #chatEngine > .ce-input-row > .ce-input-tools > #ceVoiceModeBtn,
  body.chat-engine-active #chatEngine > .ce-input-row > .ce-input-tools > #ceSkillBtn {
    position: relative;
    display: inline-flex;
    align-self: center;
    bottom: auto;
    top: auto;
    left: auto;
    right: auto;
    animation: none;
    flex: 0 0 auto;
  }

  body.chat-engine-active #chatEngine > .ce-input-row > .ce-textarea,
  body.chat-engine-active #chatEngine > .ce-input-row > #cePrompt {
    flex: 1 1 auto;
    min-width: 0;
    width: auto;
    align-self: center;
  }

  body.chat-engine-active #chatEngine > .ce-input-row > .ce-send-btn {
    flex: 0 0 auto;
    flex-direction: row;
    align-self: center;
  }

  body.chat-engine-active #chatEngine .ce-input-tools.mobile-tools-open::before {
    display: none;
  }
}

/* MOBILE CHAT — DELETED in b.843. Chat is desktop-only now;
   mobile is owned entirely by styles/mobile-landing.css. */


/* ════════════════════════════════════════════════════════════════════
   LIVE DEBATE / COACH / DM / VOICE-CALL / SHARE — extracted in b.845.
   These are all Chat Engine sub-features (debate is a chat mode, coach
   is a chat mode, voice-call is a chat mode, share is the SoJ share
   modal used to share chat artifacts). 4,714 lines total moved from
   index.html top inline <style> (was lines 29315-34028 in b.844).
   ════════════════════════════════════════════════════════════════════ */

    /* ============================================================
   LIVE DEBATE — 3/4-column live UI (b.287)
   Each For / Against / Neutral / User column highlights as that
   speaker becomes active, with text streaming into the panel body.
   Recipe matches the standard parallel-debate grid so Live and
   Standard share one design language.
   ============================================================ */
    .ld-judge-banner {
      margin: 0 0 14px;
      padding: 12px 16px;
      border-radius: 14px;
      background:
        radial-gradient(60% 60% at 0% 0%, rgba(200, 170, 255, .16) 0%, transparent 70%),
        rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .22);
      -webkit-backdrop-filter: blur(18px) saturate(1.3);
      backdrop-filter: blur(18px) saturate(1.3);
    }

    .ld-judge-banner-head {
      display: flex;
      align-items: center;
      gap: 10px;
      margin-bottom: 6px;
    }

    .ld-judge-avatar {
      width: 22px;
      height: 22px;
      border-radius: 50%;
      background: rgba(255, 255, 255, .10);
      border: 1px solid rgba(255, 255, 255, .35);
      display: grid;
      place-items: center;
      font-size: 11px;
      font-weight: 800;
      color: #fff;
    }

    .ld-judge-label {
      font-size: 11px;
      font-weight: 800;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .78);
    }

    .ld-judge-play {
      margin-left: auto;
      width: 24px;
      height: 24px;
      display: grid;
      place-items: center;
      border-radius: 50%;
      background: rgba(255, 255, 255, .08);
      border: 1px solid rgba(255, 255, 255, .22);
      color: rgba(255, 255, 255, .78);
      cursor: pointer;
      transition: transform .12s ease, background .15s ease;
    }

    .ld-judge-play:hover {
      transform: scale(1.06);
      background: rgba(255, 255, 255, .16);
      color: #fff;
    }

    .ld-judge-banner-body {
      font-size: 13px;
      line-height: 1.55;
      color: rgba(255, 255, 255, .86);
    }

    /* b.348 — Judge INTERJECTION banner. Variant of the opening banner
   with a slightly different tint so the user can tell the two apart
   at a glance — interjections sit between rounds, openings only at
   the top. */
    .ld-judge-banner.ld-judge-interjection {
      margin-top: 14px;
      background:
        radial-gradient(60% 60% at 0% 0%, rgba(170, 200, 255, .16) 0%, transparent 70%),
        rgba(255, 255, 255, .06);
      border-color: rgba(180, 200, 255, .32);
    }

    /* b.348 — Continue-debate panel. Appears under the verdict when the
   debate is complete. Same liquid-glass language as the input bar
   and the revise-topic CTA so the system reads as one piece. */
    .ld-continue-panel {
      margin: 18px 0 4px;
      padding: 16px 16px 14px;
      border-radius: 18px;
      display: flex;
      flex-direction: column;
      gap: 10px;
      background:
        radial-gradient(60% 60% at 0% 0%, rgba(180, 200, 255, .16) 0%, transparent 70%),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: var(--lg-shadow);
    }

    .ld-continue-head {
      display: flex;
      flex-direction: column;
      gap: 3px;
    }

    .ld-continue-title {
      font-size: 13px;
      font-weight: 700;
      color: #fff;
    }

    .ld-continue-sub {
      font-size: 12px;
      line-height: 1.45;
      color: rgba(255, 255, 255, .66);
    }

    .ld-continue-input {
      width: 100%;
      resize: vertical;
      padding: 11px 13px;
      border-radius: 12px;
      background: rgba(0, 0, 0, .22);
      border: 1.5px solid rgba(255, 255, 255, .22);
      color: #fff;
      font-family: inherit;
      font-size: 14px;
      line-height: 1.5;
      outline: none;
      transition: border-color .15s, background .15s;
    }

    .ld-continue-input:focus {
      border-color: rgba(255, 255, 255, .45);
      background: rgba(0, 0, 0, .28);
    }

    .ld-continue-foot {
      display: flex;
      justify-content: flex-end;
    }

    .ld-continue-btn {
      display: inline-flex;
      align-items: center;
      gap: 10px;
      padding: 10px 8px 10px 18px;
      border-radius: 999px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .16), rgba(255, 255, 255, .04)),
        rgba(255, 255, 255, .06);
      border: 1.5px solid rgba(255, 255, 255, .40);
      color: #fff;
      font-family: inherit;
      font-size: 12px;
      font-weight: 700;
      letter-spacing: .06em;
      text-transform: uppercase;
      cursor: pointer;
      outline: none;
      transition: background .15s, border-color .15s, transform .12s;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .20) inset,
        0 -1px 0 rgba(0, 0, 0, .18) inset,
        0 6px 18px rgba(0, 0, 0, .22);
    }

    .ld-continue-btn:hover {
      transform: translateY(-1px);
      border-color: rgba(255, 255, 255, .55);
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .22), rgba(255, 255, 255, .06)),
        rgba(255, 255, 255, .10);
    }

    .ld-continue-btn:active {
      transform: translateY(0);
    }

    .ld-continue-btn:disabled,
    .ld-continue-btn.busy {
      opacity: .65;
      cursor: wait;
      transform: none;
    }

    /* b.375 — Previous-verdicts disclosure. When a user uses Continue
   Debate and a new verdict supersedes the old one, the prior verdict
   gets pushed up as a collapsible details element so the user can
   re-open it. Stacked rounds = nested chevrons. */
    .ld-prior-verdicts {
      display: flex;
      flex-direction: column;
      gap: 6px;
      margin-bottom: 14px;
    }

    .ld-prior-verdict {
      padding: 8px 12px;
      border-radius: 10px;
      background: rgba(255, 255, 255, .04);
      border: 1px solid rgba(255, 255, 255, .14);
    }

    .ld-prior-verdict>summary {
      cursor: pointer;
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .10em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .60);
      list-style: none;
      outline: none;
    }

    .ld-prior-verdict>summary::-webkit-details-marker {
      display: none;
    }

    .ld-prior-verdict>summary::before {
      content: '▸';
      display: inline-block;
      margin-right: 6px;
      font-size: 9px;
      transition: transform .15s ease;
      color: rgba(255, 255, 255, .45);
    }

    .ld-prior-verdict[open]>summary::before {
      transform: rotate(90deg);
    }

    .ld-prior-verdict-body {
      margin-top: 8px;
      font-size: 13px;
      line-height: 1.55;
      color: rgba(255, 255, 255, .78);
      white-space: pre-wrap;
    }

    /* b.375 — Locked state when the user can't afford another round.
   Slightly muted panel + the inline copy explains why. The button
   visually reads as "you can see it, but you can't press it yet." */
    .ld-continue-panel-locked {
      opacity: .86;
    }

    .ld-continue-panel-locked .ld-continue-input {
      cursor: not-allowed;
    }

    .ld-continue-panel-locked .ld-continue-btn {
      cursor: not-allowed;
      opacity: .6;
    }

    .ld-continue-panel-locked .ld-continue-btn:hover {
      transform: none;
      border-color: rgba(255, 255, 255, .40);
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .16), rgba(255, 255, 255, .04)),
        rgba(255, 255, 255, .06);
    }

    .ld-continue-btn-main {
      display: inline-flex;
      align-items: center;
    }

    .ld-continue-btn-cost {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      padding: 4px 12px 4px 10px;
      border-radius: 999px;
      background: rgba(0, 0, 0, .22);
      border: 1px solid rgba(255, 255, 255, .18);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .02em;
      text-transform: none;
    }

    .ld-continue-btn-cost .joy-coin {
      width: 1em;
      height: 1em;
    }

    .ld-continue-error {
      font-size: 11.5px;
      line-height: 1.45;
      color: rgba(255, 138, 138, .92);
      margin-top: 2px;
    }

    /* b.390 — Public-share confirmation modal. Rewritten from the b.290
   inline-styled dark-navy card to use the canonical liquid-glass
   tokens so it reads as part of the same design system as the input
   bar / persona menu / dialog primitives. */
    .soj-share-scrim {
      position: fixed;
      inset: 0;
      z-index: 99998;
      background: rgba(8, 10, 20, .55);
      -webkit-backdrop-filter: blur(10px) saturate(1.2);
      backdrop-filter: blur(10px) saturate(1.2);
      display: flex;
      align-items: center;
      justify-content: center;
      padding: 24px;
    }

    .soj-share-card {
      width: min(460px, 100%);
      padding: 22px 22px 18px;
      border-radius: 22px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .02)),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: var(--lg-shadow);
      color: #fff;
      font-family: var(--font-body);
    }

    .soj-share-eyebrow {
      font-size: 10px;
      font-weight: 800;
      letter-spacing: .18em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .55);
      margin-bottom: 10px;
    }

    .soj-share-head {
      font-family: var(--font-display);
      font-size: 20px;
      font-weight: 700;
      line-height: 1.3;
      margin-bottom: 14px;
    }

    .soj-share-body {
      font-size: 13.5px;
      line-height: 1.55;
      color: rgba(255, 255, 255, .78);
      padding: 12px 14px;
      border-radius: 12px;
      background: rgba(255, 255, 255, .04);
      border: 1px solid rgba(255, 255, 255, .10);
      margin-bottom: 10px;
    }

    .soj-share-body strong {
      display: block;
      margin-bottom: 4px;
      color: #fff;
      font-weight: 700;
    }

    .soj-share-warn {
      display: flex;
      align-items: flex-start;
      gap: 8px;
      padding: 10px 12px;
      border-radius: 10px;
      background: rgba(255, 180, 100, .10);
      border: 1px solid rgba(255, 180, 100, .28);
      font-size: 12.5px;
      line-height: 1.5;
      color: rgba(255, 220, 180, .92);
      margin-bottom: 18px;
    }

    .soj-share-warn-ico {
      flex: 0 0 auto;
      display: inline-flex;
      align-items: center;
      margin-top: 2px;
      color: rgba(255, 200, 140, .95);
    }

    .soj-share-foot {
      display: flex;
      gap: 10px;
      justify-content: flex-end;
    }

    .soj-share-btn {
      flex: 0 0 auto;
      padding: 11px 22px;
      border-radius: 999px;
      font-family: var(--font-display, system-ui);
      font-size: 12px;
      font-weight: 700;
      letter-spacing: .08em;
      text-transform: uppercase;
      cursor: pointer;
      outline: none;
      transition: background .15s, border-color .15s, transform .12s;
    }

    .soj-share-cancel {
      background: rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .22);
      color: rgba(255, 255, 255, .82);
    }

    .soj-share-cancel:hover {
      background: rgba(255, 255, 255, .12);
      border-color: rgba(255, 255, 255, .40);
      color: #fff;
    }

    .soj-share-ok {
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .18), rgba(255, 255, 255, .04)),
        rgba(255, 255, 255, .06);
      border: 1.5px solid var(--lg-stroke-hi, rgba(255, 255, 255, .45));
      color: #fff;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .30) inset,
        0 6px 18px rgba(0, 0, 0, .25);
    }

    .soj-share-ok:hover {
      transform: translateY(-1px);
      border-color: rgba(255, 255, 255, .65);
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .24), rgba(255, 255, 255, .06)),
        rgba(255, 255, 255, .10);
    }

    .soj-share-ok:active {
      transform: translateY(0);
    }

    /* b.347 — Revise-topic CTA. Sits under the panel grid when the judge
   abstained (topic was too unclear). Same liquid-glass language as
   the judge banner so it reads as part of the same conversation. */
    .ld-revise-cta {
      margin: 14px 0 4px;
      padding: 14px 16px;
      border-radius: 14px;
      display: flex;
      align-items: center;
      gap: 14px;
      flex-wrap: wrap;
      background:
        radial-gradient(60% 60% at 0% 0%, rgba(180, 160, 240, .14) 0%, transparent 70%),
        rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .22);
      -webkit-backdrop-filter: blur(18px) saturate(1.3);
      backdrop-filter: blur(18px) saturate(1.3);
    }

    .ld-revise-cta-body {
      flex: 1 1 220px;
      min-width: 0;
      display: flex;
      flex-direction: column;
      gap: 3px;
    }

    .ld-revise-cta-body strong {
      font-size: 13px;
      font-weight: 700;
      color: #fff;
    }

    .ld-revise-cta-body span {
      font-size: 12px;
      line-height: 1.45;
      color: rgba(255, 255, 255, .66);
    }

    .ld-revise-cta-btn {
      flex: 0 0 auto;
      padding: 10px 18px;
      border-radius: 999px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .16), rgba(255, 255, 255, .04)),
        rgba(255, 255, 255, .06);
      border: 1.5px solid rgba(255, 255, 255, .40);
      color: #fff;
      font-family: inherit;
      font-size: 12px;
      font-weight: 700;
      letter-spacing: .06em;
      text-transform: uppercase;
      cursor: pointer;
      outline: none;
      transition: background .15s, border-color .15s, transform .12s;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .20) inset,
        0 -1px 0 rgba(0, 0, 0, .18) inset,
        0 6px 18px rgba(0, 0, 0, .22);
    }

    .ld-revise-cta-btn:hover {
      transform: translateY(-1px);
      border-color: rgba(255, 255, 255, .55);
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .22), rgba(255, 255, 255, .06)),
        rgba(255, 255, 255, .10);
    }

    .ld-revise-cta-btn:active {
      transform: translateY(0);
    }

    /* Live-debate panels — extend the standard .ce-dm-panel recipe
   with role-aware accent tints and an "active speaker" pop. */
    .ld-live-panel {
      min-height: 200px;
      max-height: 48vh;
    }

    .ld-live-panel[data-ldrole="for"] {
      border-color: rgba(16, 163, 127, .30);
    }

    .ld-live-panel[data-ldrole="against"] {
      border-color: rgba(204, 124, 94, .30);
    }

    .ld-live-panel[data-ldrole="neutral"] {
      border-color: rgba(138, 126, 239, .30);
    }

    .ld-live-panel[data-ldrole="user"] {
      border-color: rgba(252, 166, 0, .35);
    }

    .ld-live-panel[data-status="speaking"] {
      border-width: 1.5px;
      box-shadow:
        0 0 0 1px rgba(255, 255, 255, .45) inset,
        0 0 28px rgba(255, 255, 255, .18);
      transform: translateY(-2px);
    }

    .ld-live-panel[data-status="speaking"][data-ldrole="for"] {
      box-shadow: 0 0 0 1px rgba(16, 163, 127, .55) inset, 0 0 32px rgba(16, 163, 127, .30);
    }

    .ld-live-panel[data-status="speaking"][data-ldrole="against"] {
      box-shadow: 0 0 0 1px rgba(204, 124, 94, .55) inset, 0 0 32px rgba(204, 124, 94, .30);
    }

    .ld-live-panel[data-status="speaking"][data-ldrole="neutral"] {
      box-shadow: 0 0 0 1px rgba(138, 126, 239, .55) inset, 0 0 32px rgba(138, 126, 239, .30);
    }

    .ld-live-panel[data-status="speaking"][data-ldrole="user"] {
      box-shadow: 0 0 0 1px rgba(252, 166, 0, .55) inset, 0 0 32px rgba(252, 166, 0, .30);
    }

    .ld-live-panel:not(.ld-active):not([data-status="speaking"]) {
      opacity: .78;
    }

    .ld-live-panel.ld-active {
      opacity: 1;
    }

    .ld-panel-play {
      margin-left: auto;
      width: 22px;
      height: 22px;
      border-radius: 50%;
      display: grid;
      place-items: center;
      background: rgba(255, 255, 255, .08);
      border: 1px solid rgba(255, 255, 255, .22);
      color: rgba(255, 255, 255, .78);
      cursor: pointer;
      transition: transform .12s ease, background .15s ease;
    }

    .ld-panel-play:hover {
      transform: scale(1.08);
      background: rgba(255, 255, 255, .16);
      color: #fff;
    }

    /* b.294 — Tighter turn spacing. Was 8px top margin + 4px head-to-
   body — the head appeared isolated mid-stream with a visible gap
   above the streaming text. Now margins are minimal and the head
   sits flush against its body. */
    /* b.302 — Even tighter Round-N spacing. Earlier min-height:1.55em
   on the text container was reserving a full line-height of dead
   space below the "ROUND 1" header before any text streams in.
   Removed it; first-character pop is imperceptible compared to the
   dead-space ugliness. Margin-top also halved (14 → 6) so successive
   rounds within a panel hug closely. */
    .ld-panel-turn {
      margin-top: 6px;
      padding-top: 6px;
      border-top: 1px solid rgba(255, 255, 255, .10);
    }

    .ld-panel-turn:first-child {
      margin-top: 0;
      padding-top: 0;
      border-top: none;
    }

    .ld-panel-turn-head {
      font-size: 10px;
      font-weight: 800;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .55);
      margin-bottom: 1px;
    }

    .ld-panel-turn-text {
      font-size: 13px;
      line-height: 1.55;
      color: rgba(255, 255, 255, .92);
      white-space: pre-wrap;
      /* No min-height — let the element collapse until characters arrive. */
    }

    .ld-verdict-text {
      font-size: 13.5px;
      line-height: 1.6;
      color: rgba(255, 255, 255, .92);
      white-space: pre-wrap;
      padding: 10px 14px;
    }

    .ce-debate-modal[data-state="running"] .ce-dm-foot,
    .ce-debate-modal[data-state="replay"] .ce-dm-foot {
      display: none
    }

    .ce-dm-foot-section {
      display: none;
      flex-direction: column;
      align-items: center;
      gap: 12px;
    }

    .ce-debate-modal[data-state="pre-start"] [data-foot-section="pre-start"] {
      display: flex
    }

    .ce-debate-modal[data-state="complete"] [data-foot-section="complete"] {
      display: flex;
      flex-direction: row;
      align-items: center;
      justify-content: center;
      gap: 18px;
      flex-wrap: wrap;
    }

    .ce-dm-foot-hint {
      font-family: var(--font-ui);
      font-size: 12px;
      color: var(--text-muted);
      margin: 0;
      text-align: center;
      max-width: 560px;
      line-height: 1.5;
    }

    [data-foot-section="complete"] .ce-dm-foot-hint {
      text-align: right;
      max-width: none;
    }

    /* Blind-judging note in the modal header — small italic line
   under the question so users see "names stripped before the
   judge reads" as a real feature on every debate. */
    .ce-dm-blind-note {
      /* b.527 — Now lives inline in the Verdict panel head next to the
     JUDGED BY pill. Compact italic note styled to match the panel-
     status text. */
      font-family: var(--font-ui);
      font-size: 10.5px;
      color: var(--text-faint);
      font-style: italic;
      margin: 0;
      padding: 0 8px;
      line-height: 1.4;
      flex: 1 1 auto;
      min-width: 0;
      display: inline-flex;
      align-items: center;
    }

    /* Editable topic input — shown ONLY in pre-start state; replaces the
   static .ce-dm-question while user is composing. State machine
   swaps which one is visible. */
    .ce-dm-question-input {
      display: none;
      width: 100%;
      margin: 4px 0 4px;
      padding: 12px 14px;
      /* b.473 — Engine-popover recipe — same as the fixed Argue composer
     textarea. rgba(.06) wash + glass-border-strong + blur(32px) +
     drop shadow + 2 inset highlights at 20px radius. */
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      border-radius: 20px;
      color: #fff;
      font-family: inherit;
      font-size: 18px;
      font-weight: 700;
      line-height: 1.35;
      letter-spacing: -.005em;
      resize: vertical;
      min-height: 54px;
    }

    .ce-dm-question-input:focus {
      outline: none;
      border-color: rgba(255, 255, 255, .55);
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 -1px 0 rgba(0, 0, 0, .10),
        0 0 0 3px rgba(255, 255, 255, .10);
    }

    .ce-dm-question-input::placeholder {
      color: rgba(255, 255, 255, .42);
      font-weight: 600;
    }

    .ce-debate-modal[data-state="pre-start"] .ce-dm-question {
      display: none;
    }

    /* b.493 — Visibility gate now also keys on body[data-dm-state] so the
   hoisted textbox (moved to body root, escaping .ce-debate-modal in
   the DOM) still toggles on/off correctly with modal state. The
   original parent-relationship selector kept for elements that stay
   inside the modal (.ce-dm-question heading). */
    .ce-debate-modal[data-state="pre-start"] .ce-dm-question-input,
    body[data-dm-state="pre-start"] .ce-dm-question-input {
      display: block;
    }

    /* Modal-internal settings — Tier + Format (+ Voice when Live). All
   three toggles sit in ONE horizontal row to save vertical space.
   Hidden during running/complete so the user can't change mid-debate. */
    .ce-dm-settings {
      padding: 6px 28px 14px;
      border-bottom: 1px solid rgba(255, 255, 255, .08);
    }

    .ce-dm-settings-row {
      /* b.292 — Compact one-line layout. Each setting is a vertical
     stack: tiny label on top, pill toggle below. Wraps to two lines
     only on narrow viewports. */
      display: flex;
      flex-wrap: wrap;
      align-items: flex-end;
      gap: 16px 22px;
    }

    .ce-debate-modal[data-state="running"] .ce-dm-settings,
    .ce-debate-modal[data-state="complete"] .ce-dm-settings,
    .ce-debate-modal[data-state="replay"] .ce-dm-settings {
      display: none;
    }

    .ce-dm-setting-row {
      /* Was inline (label beside pill). Now vertical (label above). */
      display: flex;
      flex-direction: column;
      align-items: flex-start;
      gap: 4px;
    }

    .ce-dm-setting-row[hidden] {
      display: none;
    }

    .ce-dm-setting-label {
      font-size: 9.5px;
      font-weight: 800;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .55);
      /* No min-width — let the label hug the toggle width below. */
    }

    .ce-dm-pill-toggle {
      /* b.525 — Every property forced with !important. Plus a min-width
     so the toggle has room for the 1fr columns to distribute (an
     inline-grid sized to content shows the same tight layout as
     inline-flex). */
      display: inline-grid !important;
      grid-auto-flow: column !important;
      grid-auto-columns: 1fr !important;
      min-width: 240px !important;
      padding: 3px !important;
      border-radius: 999px !important;
      background: rgba(255, 255, 255, .08) !important;
      border: 1px solid rgba(255, 255, 255, .22) !important;
      -webkit-backdrop-filter: blur(40px) saturate(1.8) brightness(1.05) !important;
      backdrop-filter: blur(40px) saturate(1.8) brightness(1.05) !important;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .30) inset,
        0 -1px 0 rgba(0, 0, 0, .12) inset !important;
    }

    .ce-dm-pill-toggle button {
      /* b.525 — All centering properties forced with !important so they
     win the cascade. Parent is now inline-grid (b.525) — each button
     fills its 1fr column. display:flex inside the button with
     justify-content:center + text-align:center centers the label. */
      padding: 6px 14px !important;
      width: 100% !important;
      border-radius: 999px !important;
      background: transparent;
      border: 1px solid transparent;
      color: rgba(255, 255, 255, .55);
      font-size: 12px;
      font-weight: 700;
      letter-spacing: .04em;
      text-transform: uppercase;
      display: flex !important;
      align-items: center !important;
      justify-content: center !important;
      text-align: center !important;
      cursor: pointer;
      transition: color .15s ease, background .15s ease, border-color .15s ease;
    }

    .ce-dm-pill-toggle button:hover {
      color: rgba(255, 255, 255, .86);
    }

    .ce-dm-pill-toggle button.on {
      color: #fff;
      background: rgba(255, 255, 255, .10);
      border-color: rgba(255, 255, 255, .42);
      box-shadow: 0 1px 0 rgba(255, 255, 255, .40) inset;
    }

    /* Model Set preview popover —
   b.294 — DOM-PORTAL VERSION. The popover is appended to <body>
   (NOT to the debate modal), positioned absolutely at runtime via
   getBoundingClientRect on the active tier button. This puts it
   outside the modal's stacking + transform context, so it always
   layers cleanly above everything — no text-bleed.
   The visual surface is a layered liquid-glass: backdrop blur for
   the frosted feel + a heavily-opaque inner fill so text behind
   simply cannot show through. */
    .ce-dm-setting-modelset {
      position: relative;
    }

    .ce-dm-tier-popover {
      position: fixed;
      /* portal-positioned via JS */
      top: 0;
      left: 0;
      transform: translate(-50%, -100%) translateY(-12px);
      white-space: pre;
      padding: 14px 18px;
      min-width: 240px;
      /* b.512 — Canonical liquid-glass recipe. Was a solid #171c30 base
     with 3 radial-gradient tint overlays and a heavy 1.5px border,
     which read totally out of design. Now matches every other glass
     surface in the chat consoles. */
      background: rgba(255, 255, 255, .03);
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      border-radius: 14px;
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .16),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      color: #fff;
      font-size: 12.5px;
      line-height: 1.6;
      font-weight: 600;
      letter-spacing: .02em;
      text-transform: none;
      z-index: 99999;
      pointer-events: none;
      opacity: 0;
      visibility: hidden;
      transition: opacity .18s ease, transform .22s cubic-bezier(.2, .7, .2, 1), visibility 0s linear .22s;
    }

    .ce-dm-tier-popover.is-visible {
      opacity: 1;
      visibility: visible;
      transform: translate(-50%, -100%) translateY(-6px);
      transition: opacity .18s ease, transform .22s cubic-bezier(.2, .7, .2, 1), visibility 0s linear 0s;
    }

    .ce-dm-tier-popover::after {
      content: '';
      position: absolute;
      left: 50%;
      bottom: -6px;
      transform: translateX(-50%) rotate(45deg);
      width: 11px;
      height: 11px;
      /* b.512 — Arrow matches the popover's glass surface. */
      background: rgba(255, 255, 255, .03);
      border-right: 1px solid rgba(255, 255, 255, .18);
      border-bottom: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
    }

    /* Round 2 button — same .ce-dm-start-btn anatomy as the Start
   button so it reads as the same primary CTA. The push-back text
   input was removed; closing the modal now drops the user back
   into the chat thread where they can ask follow-up questions
   directly (the debate's full transcript is already in history). */


    /* Start button — same segmented anatomy as the input-bar Send
   button. Label on left, coin cost segment on right with a
   border-left divider. Active glow + radial wash so it reads
   as the primary CTA in the modal. */
    .ce-dm-start-btn {
      display: inline-flex;
      align-items: center;
      height: 48px;
      padding: 0;
      border-radius: 999px;
      /* b.510 — Strip --active-tint radial + --active-glow shadow that
     painted the green theme color onto the START DEBATE / START
     CONSENSUS button. Now pure liquid glass — no solid color. */
      background: rgba(255, 255, 255, .03);
      border: 1.5px solid rgba(255, 255, 255, .32);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .30) inset,
        0 -1px 0 rgba(0, 0, 0, .12) inset,
        0 28px 64px -18px rgba(0, 0, 0, .55);
      font-family: var(--font-display);
      font-weight: 800;
      font-size: 13px;
      letter-spacing: .04em;
      color: var(--text);
      cursor: pointer;
      text-transform: uppercase;
      transition: transform .15s var(--ease), border-color .15s var(--ease);
      overflow: hidden;
      line-height: 1;
    }

    .ce-dm-start-btn:hover {
      border-color: rgba(255, 255, 255, .55);
    }

    .ce-dm-start-btn:hover {
      transform: translateY(-1px)
    }

    .ce-dm-start-label {
      padding: 0 22px;
      height: 100%;
      display: inline-flex;
      align-items: center;
    }

    .ce-dm-start-cost {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 0 16px;
      height: 100%;
      border-left: 1px solid rgba(255, 255, 255, .22);
      background: rgba(255, 255, 255, .05);
      font-size: 13px;
    }

    .ce-dm-start-cost .joy-coin {
      width: 1.7em;
      height: 1.7em
    }

    /* In-thread "View live debate" CTA on rendered debate blocks */
    .ce-debate-controls {
      display: flex;
      align-items: center;
      gap: 8px;
      flex-wrap: wrap;
    }

    .ce-debate-view-btn {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .04em;
      text-transform: uppercase;
      padding: 6px 12px;
      border-radius: 999px;
      background:
        radial-gradient(120% 100% at 30% 0%, var(--active-tint), transparent 70%),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      color: var(--text);
      cursor: pointer;
      transition: transform .15s var(--ease);
      box-shadow: 0 0 14px var(--active-glow);
    }

    .ce-debate-view-btn:hover {
      transform: translateY(-1px)
    }

    .ce-debate-view-btn .arr {
      transition: transform .2s var(--ease)
    }

    /* ARGUE BLOCK — single chat-thread row that represents an entire
   argue session. Reuses the debate-block visual language so the
   user instantly recognises it as "this is a saved console-mode
   chat", with a Continue button that reopens the console pre-loaded
   with the conversation. */
    .ce-argue-block {
      display: flex;
      flex-direction: column;
      gap: 10px;
      max-width: 78%;
      align-self: flex-start;
    }

    .ce-argue-summary {
      padding: 14px 18px;
      border-radius: var(--r-lg);
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: var(--lg-shadow);
      font-size: 14.5px;
      line-height: 1.55;
    }

    .ce-argue-controls {
      display: flex
    }

    .ce-argue-view-btn {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .04em;
      text-transform: uppercase;
      padding: 6px 12px;
      border-radius: 999px;
      background:
        radial-gradient(120% 100% at 30% 0%, var(--active-tint), transparent 70%),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      color: var(--text);
      cursor: pointer;
      transition: transform .15s var(--ease);
      box-shadow: 0 0 14px var(--active-glow);
    }

    .ce-argue-view-btn:hover {
      transform: translateY(-1px)
    }

    .ce-argue-view-btn .arr {
      transition: transform .2s var(--ease)
    }

    .ce-argue-view-btn:hover .arr {
      transform: translate(2px, -2px)
    }

    .ce-debate-view-btn:hover .arr {
      transform: translate(2px, -2px)
    }

    /* Inline "View live ↗" button shown on the thinking indicator
   during an active debate — always visible while the debate runs
   so the user can re-open the modal if they dismissed it. */
    .ce-live-btn {
      margin-left: 8px;
      display: inline-flex;
      align-items: center;
      gap: 5px;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .04em;
      text-transform: uppercase;
      padding: 5px 11px;
      border-radius: 999px;
      background:
        radial-gradient(120% 100% at 30% 0%, var(--active-tint), transparent 70%),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      color: var(--text);
      cursor: pointer;
      box-shadow: 0 0 14px var(--active-glow);
      transition: transform .15s var(--ease);
    }

    .ce-live-btn:hover {
      transform: translateY(-1px)
    }

    .ce-live-btn-arrow {
      transition: transform .2s var(--ease)
    }

    .ce-live-btn:hover .ce-live-btn-arrow {
      transform: translate(2px, -2px)
    }

    /* ----------------------------------------------------------------
   VOICE ARGUE — Whisper integration UI.
   Mic lives in the input-tools row but only renders in Argue mode.
   Three states:
     · default      — same look as other tool buttons
     · recording    — red pulse, expanded to show duration timer
     · transcribing — calm wait state while Whisper processes
   The input-row also takes a soft red glow while listening so the
   user gets a clear visual that the mic is hot.
   ---------------------------------------------------------------- */
    .ce-mic-btn {
      position: relative
    }

    .ce-mic-btn.recording {
      width: auto;
      padding: 0 12px;
      gap: 6px;
      background: rgba(255, 80, 96, .18);
      border-color: rgba(255, 80, 96, .55);
      color: #ff7f88;
      box-shadow: 0 0 18px rgba(255, 80, 96, .30);
      animation: ce-mic-pulse 1.4s ease-in-out infinite;
    }

    .ce-mic-btn.recording svg {
      width: 14px;
      height: 14px
    }

    .ce-mic-btn .ce-mic-time {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      color: inherit;
      font-variant-numeric: tabular-nums;
    }

    .ce-mic-btn.transcribing {
      background: var(--lg-fill-active);
      color: var(--text);
      pointer-events: none;
      opacity: .85;
    }

    .ce-mic-btn.transcribing svg {
      animation: cr 1.5s linear infinite
    }

    @keyframes ce-mic-pulse {

      0%,
      100% {
        box-shadow: 0 0 18px rgba(255, 80, 96, .30)
      }

      50% {
        box-shadow: 0 0 30px rgba(255, 80, 96, .55)
      }
    }

    .ce-input-row.listening {
      border-color: rgba(255, 80, 96, .55) !important;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .55) inset,
        0 -1px 0 rgba(255, 255, 255, .18) inset,
        0 0 0 1px rgba(255, 255, 255, .10) inset,
        0 0 28px rgba(255, 80, 96, .25) !important;
    }

    /* Debate mode synthesis-judge selector — same unified-pill anatomy
   as the intensity dial. The "Synthesis judge" label sits inside
   the pill, separated by a thin vertical divider; the three judge
   buttons render as flat segments rather than standalone pills.
   Re-clicking an active judge segment cycles its variant tier
   (Haiku → Sonnet → Opus, etc.) — the variant label appears
   beside the model name when active. */
    .ce-judge {
      display: inline-flex;
      align-items: center;
      gap: 2px;
      padding: 3px 3px 3px 12px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      border-radius: 999px;
    }

    .ce-judge .ce-judge-label {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      color: var(--text-faint);
      padding-right: 10px;
      margin-right: 2px;
      border-right: 1px solid var(--lg-stroke);
      white-space: nowrap;
      letter-spacing: .01em;
    }

    /* Flatten the model-pill inside the judge container — drop its
   own border / blur / shadow so it reads as a segment, not a
   standalone pill. Active state is just a subtle background tint
   plus the variant label, matching the intensity dial. */
    .ce-judge .ce-model-pill {
      background: transparent !important;
      border: 0 !important;
      -webkit-backdrop-filter: none !important;
      backdrop-filter: none !important;
      box-shadow: none !important;
      padding: 5px 10px !important;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      color: var(--text-faint);
      display: inline-flex;
      align-items: center;
      gap: 5px;
      border-radius: 999px;
      transition: all .2s var(--ease);
    }

    .ce-judge .ce-model-pill:hover {
      color: var(--text);
      background: var(--lg-fill-hover) !important;
    }

    .ce-judge .ce-model-pill.on {
      color: var(--text);
      background: var(--lg-fill-active) !important;
    }

    .ce-judge .ce-model-pill[data-disabled="1"] {
      opacity: .45;
      cursor: not-allowed;
    }

    .ce-judge .ce-model-pill .ce-model-variant {
      /* Variant label always shown in Debate mode so the user can see
     which specific model variant will fire under the current tier
     (Standard → Haiku/4o-mini/Flash, Pro → Opus/4o/2.5 Pro). */
      font-weight: 500;
      opacity: .72;
      display: inline;
    }

    .ce-judge .ce-model-pill .ce-model-variant::before {
      content: '·';
      margin: 0 5px;
      opacity: .5;
    }

    /* Tier selector buttons (Standard / Pro) don't render a model dot
   — they're tier choices, not model picks. The "Tier" label was
   removed; pad the container symmetrically so Standard / Pro sit
   evenly inside the pill instead of inheriting the label's left
   padding from .ce-judge. */
    .ce-judge.ce-tier {
      padding: 3px;
    }

    .ce-judge.ce-tier .ce-model-pill {
      padding: 5px 14px !important;
    }

    /* ----------------------------------------------------------------
   VERDICT OVERLAY — opens above the debate modal when the user
   clicks the synth-panel strip. Full-width verdict reading + a
   Summarise CTA. Lives at z-index 140, above the debate modal
   (100) and all the popovers (120). Closing returns the user to
   the debate modal in 'complete' state.
   ---------------------------------------------------------------- */
    .ce-verdict-overlay {
      position: fixed;
      inset: 0;
      z-index: 140;
      display: flex;
      align-items: center;
      justify-content: center;
      padding: 24px;
      /* Instant open / instant close — no opacity fade. */
      opacity: 0;
      visibility: hidden;
      pointer-events: none;
    }

    .ce-verdict-overlay.open {
      opacity: 1;
      visibility: visible;
      pointer-events: auto;
    }

    .ce-vo-backdrop {
      position: absolute;
      inset: 0;
      /* Fully transparent — no scrim, no blur. The theme video plays
     unmolested behind the verdict overlay; the liquid-glass shell
     is the only thing layered on top. Backdrop element still
     exists for click-to-close (data-vo-close). */
      background: transparent;
    }

    .ce-vo-shell {
      position: relative;
      /* Same sizing rule as the debate shell — locked width, auto
     height, capped at viewport. Verdict shrinks to fit its body
     instead of always rendering at full viewport height; pairs with
     the debate console so swapping between them feels natural
     (each surface sizes to content, neither holds onto stretched
     dead space). */
      width: 100%;
      max-width: var(--console-w);
      height: auto;
      max-height: var(--console-h-max);
      display: flex;
      flex-direction: column;
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      border-radius: 28px;
      /* Match debate modal's box-shadow so the swap reads as the same
     surface. The over-bright multi-layer shadow we had before made
     the verdict feel like a different element popping in over the
     debate console; matching them makes it feel like content
     re-rendering inside one persistent shell. */
      box-shadow: var(--lg-shadow);
      overflow: hidden;
      /* No scale-in / no fade — instant open and close. */
    }

    .ce-vo-head {
      display: flex;
      align-items: flex-start;
      gap: 18px;
      padding: 22px 24px 16px;
      border-bottom: 1px solid var(--lg-stroke);
      flex-shrink: 0;
    }

    .ce-vo-head-text {
      flex: 1;
      min-width: 0
    }

    .ce-vo-eyebrow {
      display: inline-flex;
      align-items: center;
      gap: 7px;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .12em;
      text-transform: uppercase;
      color: var(--accent-text);
      margin-bottom: 6px;
    }

    .ce-vo-eyebrow::before {
      content: '';
      width: 6px;
      height: 6px;
      border-radius: 50%;
      background: var(--accent-bright);
      box-shadow: 0 0 10px var(--accent-bright);
    }

    .ce-vo-question {
      font-family: var(--font-display);
      font-size: 21px;
      font-weight: 600;
      letter-spacing: -.01em;
      color: var(--text);
      line-height: 1.35;
      margin: 0;
      word-wrap: break-word;
    }

    .ce-vo-close {
      width: 36px;
      height: 36px;
      border-radius: 50%;
      border: 1px solid var(--lg-stroke);
      background: var(--lg-fill);
      color: var(--text);
      cursor: pointer;
      font-size: 18px;
      line-height: 1;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      transition: all .2s var(--ease);
      flex-shrink: 0;
    }

    .ce-vo-close:hover {
      background: var(--lg-fill-active)
    }

    .ce-vo-body {
      flex: 1;
      overflow-y: auto;
      /* Shell is now 1200px wide (matching the debate modal) but verdict
     prose at that full width is uncomfortable to read — long lines
     break paragraph rhythm. We center an inner 880px reading column
     inside the 1200px shell so the visual footprint stays seamless
     with the debate console while text stays comfortable. */
      padding: 24px 28px;
      font-size: 15px;
      line-height: 1.6;
      color: var(--text);
      scrollbar-width: thin;
      scrollbar-color: var(--lg-stroke) transparent;
    }

    .ce-vo-body>* {
      max-width: 880px;
      margin-left: auto;
      margin-right: auto;
    }

    .ce-vo-body::-webkit-scrollbar {
      width: 6px
    }

    .ce-vo-body::-webkit-scrollbar-thumb {
      background: var(--lg-stroke);
      border-radius: 3px
    }

    .ce-vo-foot {
      display: flex;
      align-items: center;
      justify-content: space-between;
      gap: 18px;
      padding: 14px 24px 16px;
      border-top: 1px solid var(--lg-stroke);
      flex-shrink: 0;
      flex-wrap: wrap;
    }

    .ce-vo-foot-hint {
      font-family: var(--font-ui);
      font-size: 12px;
      color: var(--text-muted);
      margin: 0;
    }

    /* b.291 — Share row. Three pill-style buttons (Transcript, Audio,
   Share link) sit on the right of the verdict overlay foot. Each
   button is a small liquid-glass chip — matches the design system
   without competing with the primary Summarise CTA above. */
    .ce-vo-share-row {
      display: flex;
      align-items: center;
      gap: 8px;
      flex-wrap: wrap;
    }

    .ce-vo-share-btn {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 7px 12px;
      border-radius: 999px;
      background: rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .22);
      color: rgba(255, 255, 255, .86);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .04em;
      text-transform: uppercase;
      cursor: pointer;
      transition: transform .12s ease, background .15s ease, border-color .15s ease, color .15s ease;
    }

    .ce-vo-share-btn:hover {
      background: rgba(255, 255, 255, .14);
      border-color: rgba(255, 255, 255, .40);
      color: #fff;
      transform: translateY(-1px);
    }

    .ce-vo-share-btn:disabled {
      opacity: .45;
      cursor: default;
      transform: none;
    }

    .ce-vo-share-btn.is-done {
      background: rgba(120, 200, 140, .18);
      border-color: rgba(120, 200, 140, .55);
      color: #d8ffe5;
    }

    /* Summarise button — same segmented anatomy as the Send / Start /
   Round 2 buttons. Label + cost segment, border-left divider. */
    .ce-vo-summarise-btn {
      display: inline-flex;
      align-items: center;
      height: 44px;
      padding: 0;
      border-radius: 999px;
      background:
        radial-gradient(120% 100% at 30% 0%, var(--active-tint), transparent 70%),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .55) inset,
        0 -1px 0 rgba(255, 255, 255, .18) inset,
        0 0 0 1px rgba(255, 255, 255, .10) inset,
        0 0 22px var(--active-glow);
      font-family: var(--font-display);
      font-weight: 800;
      font-size: 13px;
      letter-spacing: .04em;
      color: var(--text);
      cursor: pointer;
      text-transform: uppercase;
      transition: transform .15s var(--ease);
      overflow: hidden;
      line-height: 1;
      flex-shrink: 0;
    }

    .ce-vo-summarise-btn:hover {
      transform: translateY(-1px)
    }

    .ce-vo-summarise-btn:disabled {
      opacity: .55;
      cursor: not-allowed;
      transform: none
    }

    .ce-vo-summarise-label {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      padding: 0 18px;
      height: 100%;
    }

    .ce-vo-summarise-ico {
      font-size: 14px;
      line-height: 1
    }

    .ce-vo-summarise-cost {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 0 14px;
      height: 100%;
      border-left: 1px solid rgba(255, 255, 255, .22);
      background: rgba(255, 255, 255, .05);
      font-size: 13px;
    }

    .ce-vo-summarise-cost .joy-coin {
      width: 1.7em;
      height: 1.7em
    }

    /* Quick-summary card — emerald wash so it visually distinguishes
   from the verdict body below. Sits at the top of the overlay
   body when a summary has been generated. */
    .ce-vo-summary {
      margin-bottom: 24px;
      padding: 14px 18px;
      border-radius: 14px;
      background: var(--active-tint);
      border: 1px solid var(--active-glow);
    }

    .ce-vo-summary-head {
      display: flex;
      align-items: center;
      gap: 8px;
      margin-bottom: 8px;
    }

    .ce-vo-summary-mark {
      font-size: 14px;
      filter: drop-shadow(0 0 6px var(--accent-text));
    }

    .ce-vo-summary-label {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .08em;
      text-transform: uppercase;
      color: var(--accent-text);
    }

    .ce-vo-summary-body {
      font-size: 14px;
      line-height: 1.55;
      color: var(--text);
    }

    /* ----------------------------------------------------------------
   VOICE ARGUE OVERLAY
   Fullscreen, liquid-glass shell. The visual centerpiece is an
   animated orb at the centre of the stage — three concentric rings
   pulse outward when the model is speaking, the orb itself scales
   with audio amplitude (CSS var --vc-amp updated by JS each frame),
   and the whole thing tints amber-warm in idle, cool-blue while
   listening, violet while thinking, and theme-accent glow while
   speaking. Lives at z-index 150 (above debate / verdict / popovers).
   ---------------------------------------------------------------- */
    .ce-voice-overlay {
      position: fixed;
      inset: 0;
      z-index: 150;
      display: flex;
      align-items: center;
      justify-content: center;
      padding: 24px;
      opacity: 0;
      visibility: hidden;
      pointer-events: none;
      /* Audio-driven amplitude (0–1). JS writes this every animation
     frame from the AnalyserNode; CSS reads it to scale the orb /
     ring brightness so the visual responds to live audio. */
      --vc-amp: 0;
    }

    .ce-voice-overlay.open {
      opacity: 1;
      visibility: visible;
      pointer-events: auto;
    }

    .ce-vc-backdrop {
      position: absolute;
      inset: 0;
      background: transparent;
    }

    .ce-vc-shell {
      position: relative;
      width: 100%;
      max-width: var(--console-w);
      height: auto;
      max-height: var(--console-h-max);
      display: flex;
      flex-direction: column;
      /* b.482 — Zero-tint canonical recipe. Background transparent, .10
     hairline border, .06 top inset highlight, .12 bottom dark inset
     for depth, saturate 1.5. No white wash anywhere. */
      background: rgba(255, 255, 255, .03);
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      border-radius: 28px;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .16) inset,
        0 -1px 0 rgba(0, 0, 0, .10) inset,
        0 24px 60px -12px rgba(0, 0, 0, .55);
      isolation: isolate;
      overflow: hidden;
    }

    /* Head — eyebrow + title + close, mirroring debate / verdict modals */
    .ce-vc-head {
      display: flex;
      align-items: flex-start;
      gap: 18px;
      padding: 22px 24px 16px;
      border-bottom: 1px solid var(--lg-stroke);
      flex-shrink: 0;
    }

    .ce-vc-head-text {
      flex: 1;
      min-width: 0
    }

    .ce-vc-eyebrow {
      display: inline-flex;
      align-items: center;
      gap: 7px;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 800;
      letter-spacing: .12em;
      text-transform: uppercase;
      color: var(--accent-text);
      margin-bottom: 6px;
    }

    .ce-vc-eyebrow::before {
      content: '';
      width: 6px;
      height: 6px;
      border-radius: 50%;
      background: var(--accent-bright);
      box-shadow: 0 0 10px var(--accent-bright);
      animation: vc-eyebrow-pulse 1.6s ease-in-out infinite;
    }

    @keyframes vc-eyebrow-pulse {

      0%,
      100% {
        opacity: .4;
        transform: scale(.85)
      }

      50% {
        opacity: 1;
        transform: scale(1.15)
      }
    }

    .ce-vc-title {
      font-family: var(--font-display);
      font-size: 24px;
      line-height: 1.2;
      font-weight: 600;
      color: var(--text);
      margin: 0;
      /* b.500 — Align with .ce-vc-eyebrow text. The eyebrow's ::before
     dot (6px) + gap (7px) = 13px before its text. Mirror as
     padding-left so "Pick a scenario..." sits flush under
     "COACH · SETUP" / "ARGUE · SETUP". */
      padding-left: 13px;
    }

    .ce-vc-close {
      width: 36px;
      height: 36px;
      border-radius: 50%;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      color: var(--text);
      font-size: 18px;
      line-height: 1;
      cursor: pointer;
      flex-shrink: 0;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      transition: background .15s var(--ease), transform .15s var(--ease);
    }

    .ce-vc-close:hover {
      background: var(--lg-fill-active);
      transform: rotate(90deg)
    }

    /* THREAD — chat-style bubbles for the entire argue conversation.
   Both text turns and voice turns end up here; the bubbles are the
   same regardless of input modality. */
    .ce-vc-thread {
      flex: 1;
      overflow-y: auto;
      padding: 18px 28px;
      display: flex;
      flex-direction: column;
      gap: 14px;
      min-height: 240px;
      scrollbar-width: thin;
      scrollbar-color: var(--lg-stroke) transparent;
    }

    .ce-vc-thread::-webkit-scrollbar {
      width: 6px
    }

    .ce-vc-thread::-webkit-scrollbar-thumb {
      background: var(--lg-stroke);
      border-radius: 3px
    }

    .ce-vc-empty {
      margin: auto;
      padding: 24px;
      text-align: center;
      color: var(--text-muted);
      font-family: var(--font-ui);
      font-size: 13px;
      max-width: 420px;
    }

    .ce-vc-empty p {
      margin: 0;
      line-height: 1.5
    }

    .ce-vc-bubble {
      max-width: 78%;
      padding: 12px 16px 14px;
      border-radius: 16px;
      font-size: 14.5px;
      line-height: 1.5;
      color: var(--text);
      border: 1px solid var(--lg-stroke);
      background: var(--lg-fill);
      display: flex;
      flex-direction: column;
      gap: 4px;
    }

    .ce-vc-bubble-label {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .12em;
      text-transform: uppercase;
      color: var(--text-muted);
    }

    .ce-vc-bubble.you {
      align-self: flex-end;
      background: linear-gradient(140deg, var(--active-tint), transparent 80%), var(--lg-fill);
      border-color: var(--lg-stroke-hi);
    }

    .ce-vc-bubble.them {
      align-self: flex-start;
    }

    .ce-vc-bubble.thinking .ce-vc-bubble-text {
      color: var(--text-muted);
      font-style: italic;
      display: inline-flex;
      gap: 4px;
      align-items: center;
    }

    .ce-vc-bubble-text {
      margin: 0
    }

    /* Voice row — sits inside .ce-vc-input when input-mode="voice".
   Small inline orb + state caption + control buttons, all on one
   row with similar height to the text input row above. Toggling
   between text and voice swaps row contents only — the thread is
   never resized, never scrolled, never broken. */
    .ce-vc-voice-row {
      display: none;
      align-items: center;
      gap: 14px;
      flex-wrap: wrap;
    }

    .ce-voice-overlay[data-input-mode="voice"] .ce-vc-voice-row {
      display: flex
    }

    .ce-vc-voice-state-wrap {
      flex: 1;
      min-width: 120px;
      display: flex;
      align-items: center;
      gap: 8px;
    }

    .ce-vc-voice-tip {
      font-family: var(--font-ui);
      font-size: 11.5px;
      line-height: 1.4;
      color: var(--text-muted);
      letter-spacing: .01em;
    }

    .ce-vc-voice-tip b {
      color: var(--accent-text);
      font-weight: 700;
    }

    .ce-vc-voice-actions {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      flex-wrap: wrap;
    }

    /* ORB — compact inline element living in the voice row. Sized to
   match the input row height so it feels like part of the bar, not
   a separate panel. Three concentric rings still pulse outward
   while the model is speaking; the orb itself scales with audio
   amplitude during listening / speaking. */
    .ce-vc-orb-wrap {
      position: relative;
      width: 64px;
      height: 64px;
      display: flex;
      align-items: center;
      justify-content: center;
      flex-shrink: 0;
    }

    .ce-vc-ring {
      position: absolute;
      inset: 0;
      border-radius: 50%;
      border: 1.5px solid var(--accent-bright);
      opacity: 0;
      pointer-events: none;
      transform: scale(.8);
    }

    .ce-vc-ring-1 {
      animation-delay: 0s
    }

    .ce-vc-ring-2 {
      animation-delay: .55s
    }

    .ce-vc-ring-3 {
      animation-delay: 1.1s
    }

    /* Speaking state — rings emanate outward in a stagger, like a
   sound wave radiating from the orb. */
    .ce-voice-overlay[data-state="speaking"] .ce-vc-ring {
      animation: vc-ring-pulse 1.8s ease-out infinite;
    }

    @keyframes vc-ring-pulse {
      0% {
        transform: scale(.85);
        opacity: .55;
        border-color: var(--accent-bright)
      }

      70% {
        transform: scale(1.55);
        opacity: .05
      }

      100% {
        transform: scale(1.7);
        opacity: 0
      }
    }

    /* The orb itself — radial gradient, two layers (inner + core) for
   depth. Scales with --vc-amp during listening so the user can
   see "the mic is hearing me". */
    .ce-vc-orb {
      position: relative;
      width: 48px;
      height: 48px;
      border-radius: 50%;
      background: radial-gradient(circle at 35% 30%,
          rgba(255, 255, 255, .85),
          var(--accent-bright) 35%,
          var(--accent-text) 65%,
          rgba(0, 0, 0, .4) 100%);
      box-shadow:
        0 0 30px var(--active-glow),
        0 0 0 1.5px rgba(255, 255, 255, .18) inset,
        0 0 0 4px rgba(255, 255, 255, .04);
      transform: scale(calc(.92 + var(--vc-amp, 0) * .25));
      transition: transform .08s linear, box-shadow .25s var(--ease);
      animation: vc-orb-breath 4.2s ease-in-out infinite;
    }

    @keyframes vc-orb-breath {

      0%,
      100% {
        filter: brightness(.92)
      }

      50% {
        filter: brightness(1.12)
      }
    }

    .ce-vc-orb-inner {
      position: absolute;
      inset: 7px;
      border-radius: 50%;
      background: radial-gradient(circle at 60% 60%,
          rgba(255, 255, 255, .18),
          transparent 60%);
      pointer-events: none;
    }

    .ce-vc-orb-core {
      position: absolute;
      inset: 42%;
      border-radius: 50%;
      background: rgba(255, 255, 255, .85);
      filter: blur(4px);
      opacity: .7;
    }

    /* State-specific orb tints. Override accent-bright/-text via local
   custom props so the animation rules above pick up the right colours
   without needing keyframe duplication per state. */
    .ce-voice-overlay[data-state="idle"] {
      --vc-tint-bright: var(--accent-bright);
      --vc-tint-text: var(--accent-text);
    }

    .ce-voice-overlay[data-state="listening"] .ce-vc-orb {
      /* Cooler / brighter when actively hearing the user — feedback that
     the mic stream is live. */
      background: radial-gradient(circle at 35% 30%,
          rgba(255, 255, 255, .92),
          #6ea7ff 35%,
          #2c5fb8 65%,
          rgba(0, 0, 0, .45) 100%);
      box-shadow:
        0 0 calc(80px + var(--vc-amp, 0) * 60px) rgba(110, 167, 255, .55),
        0 0 0 1.5px rgba(255, 255, 255, .22) inset;
    }

    .ce-voice-overlay[data-state="thinking"] .ce-vc-orb {
      /* Violet sweep + slow rotation while the model formulates. */
      background: conic-gradient(from 0deg,
          rgba(255, 255, 255, .0),
          rgba(170, 128, 240, .85),
          rgba(110, 167, 255, .6),
          rgba(255, 255, 255, .0));
      animation: vc-orb-spin 1.6s linear infinite;
    }

    @keyframes vc-orb-spin {
      to {
        transform: rotate(360deg)
      }
    }

    .ce-voice-overlay[data-state="speaking"] .ce-vc-orb {
      /* Theme-accent glow + warmer tint when delivering the rebuttal. */
      background: radial-gradient(circle at 35% 30%,
          rgba(255, 255, 255, .95),
          var(--accent-bright) 30%,
          var(--accent-text) 60%,
          rgba(0, 0, 0, .4) 100%);
      box-shadow:
        0 0 calc(100px + var(--vc-amp, 0) * 80px) var(--active-glow),
        0 0 0 1.5px rgba(255, 255, 255, .30) inset;
      animation: none;
      /* breath replaced by ring-pulse outside */
    }

    .ce-voice-overlay[data-state="error"] .ce-vc-orb {
      background: radial-gradient(circle at 35% 30%,
          rgba(255, 255, 255, .85),
          #ff6b78 35%,
          #b8323d 65%,
          rgba(0, 0, 0, .4) 100%);
    }

    /* State caption — short text beside the inline orb describing what's
   happening right now (Listening… / Thinking… / Speaking…). Was a
   block element under the standalone stage; now it's an inline label
   next to the compact orb. */
    .ce-vc-state {
      font-family: var(--font-ui);
      font-size: 14px;
      font-weight: 600;
      color: var(--text-muted);
      letter-spacing: .02em;
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
    }

    .ce-voice-overlay[data-state="listening"] .ce-vc-state {
      color: #9bbcff
    }

    .ce-voice-overlay[data-state="thinking"] .ce-vc-state {
      color: #c8a8ff
    }

    .ce-voice-overlay[data-state="speaking"] .ce-vc-state {
      color: var(--accent-text)
    }

    .ce-voice-overlay[data-state="error"] .ce-vc-state {
      color: #ff8b94
    }

    /* INPUT AREA — wraps both the text input row and the voice action
   row. Only one shows at a time, switched via data-input-mode. */
    .ce-vc-input {
      flex-shrink: 0;
      border-top: 1px solid var(--lg-stroke);
      /* b.399 — Transparent so the parent shell frost shows through. */
      background: transparent;
      padding: 14px 22px 16px;
    }

    /* TEXT input row — visible when input-mode="text". Textarea wrap
   on the left (textarea + cost chip pinned to its bottom-right);
   send button; vertical divider; Voice mode toggle on the right. */
    .ce-vc-text-row {
      display: flex;
      align-items: flex-end;
      gap: 10px;
    }

    .ce-voice-overlay[data-input-mode="voice"] .ce-vc-text-row {
      display: none
    }

    .ce-vc-textarea {
      flex: 1;
      min-width: 0;
      padding: 11px 14px;
      /* b.456 — EXACT engine-popover recipe per user request. Every
     parameter copied verbatim from .engine-popover (the SELECT A
     VIDEO ENGINE container the user pointed at as the target look):
       background       rgba(255,255,255,.06)
       border           1px solid var(--glass-border-strong)
       backdrop-filter  blur(32px)   (no saturate, no brightness)
       box-shadow       drop + 2 inset highlights
       border-radius    20px
     Applied with !important so the cascade can't override. The
     textbox is already hoisted to <body> (b.451) so its painting
     context is body root, which is where .engine-popover lives. */
      background: rgba(255, 255, 255, .06) !important;
      border: 1px solid var(--glass-border-strong) !important;
      -webkit-backdrop-filter: blur(32px) !important;
      backdrop-filter: blur(32px) !important;
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 0 0 1px rgba(255, 255, 255, .04) !important;
      border-radius: 20px !important;
      color: var(--text);
      font-family: var(--font-body);
      font-size: 14.5px;
      line-height: 1.5;
      resize: none;
      max-height: 140px;
      outline: none;
      transition: border-color .15s var(--ease);
    }

    .ce-vc-textarea:focus {
      border-color: rgba(255, 255, 255, .55) !important;
      /* Preserve the engine-popover shadow stack on focus + focus ring. */
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 0 0 1px rgba(255, 255, 255, .04),
        0 0 0 3px var(--active-tint) !important;
    }

    .ce-vc-textarea::placeholder {
      color: var(--text-muted);
      opacity: .7
    }

    /* Send button — same pattern as the main chat .ce-send-btn: pill
   shape, arrow on the left, cost segment bordered off on the right.
   Reads as a single committed action with the price right where
   the click lands. */
    .ce-vc-text-send {
      display: inline-flex;
      align-items: stretch;
      height: 40px;
      border-radius: 999px;
      /* b.404 — Full clean glass recipe so the Begin / Begin coaching
     button reads as a real glass surface. Previous accent-gradient +
     var(--lg-fill) recipe stacked an opaque coloured tint that read
     as milky against the dark shell. */
      background: rgba(255, 255, 255, .08);
      border: 1px solid rgba(255, 255, 255, .22);
      -webkit-backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .30) inset,
        0 -1px 0 rgba(0, 0, 0, .12) inset,
        0 8px 22px rgba(0, 0, 0, .30);
      color: #fff;
      cursor: pointer;
      flex-shrink: 0;
      transition: transform .15s var(--ease), box-shadow .15s var(--ease);
      overflow: hidden;
    }

    .ce-vc-text-send:hover {
      transform: translateY(-1px);
      box-shadow: 0 0 26px var(--active-glow)
    }

    .ce-vc-text-send:disabled {
      opacity: .4;
      cursor: not-allowed;
      box-shadow: none
    }

    .ce-vc-send-main {
      display: inline-flex;
      align-items: center;
      justify-content: center;
      padding: 0 12px 0 14px;
    }

    .ce-vc-send-cost {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      padding: 0 12px;
      border-left: 1px solid rgba(255, 255, 255, .22);
      background: rgba(255, 255, 255, .05);
      font-family: var(--font-display);
      font-weight: 800;
      font-size: 13px;
      letter-spacing: .02em;
      color: var(--text);
      transition: background .25s var(--ease);
    }

    .ce-vc-send-cost .joy-coin {
      width: 1.55em;
      height: 1.55em
    }

    /* Free-tier wash — same emerald pattern as the main chat send. */
    .ce-vc-send-cost.free {
      background: var(--active-tint);
    }

    .ce-vc-send-free-ico {
      font-size: 18px;
      font-weight: 600;
      line-height: 1;
      letter-spacing: -.05em;
      color: var(--accent-text);
    }

    .ce-vc-send-free-label {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 800;
      letter-spacing: .08em;
      text-transform: uppercase;
      color: var(--accent-text);
    }

    .ce-vc-text-divider {
      width: 1px;
      height: 36px;
      background: var(--lg-stroke);
      margin: 0 4px;
    }

    .ce-vc-voice-toggle {
      position: relative;
      display: inline-flex;
      align-items: center;
      gap: 8px;
      padding: 9px 14px;
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      border-radius: 999px;
      color: var(--accent-text);
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 700;
      cursor: pointer;
      flex-shrink: 0;
      transition: transform .15s var(--ease), background .15s var(--ease);
    }

    .ce-vc-voice-toggle:hover {
      transform: translateY(-1px);
      background: var(--lg-fill-hover);
    }

    .ce-vc-voice-toggle-glow {
      position: absolute;
      inset: -2px;
      border-radius: 999px;
      border: 1.5px solid var(--accent-bright);
      opacity: .45;
      pointer-events: none;
      animation: vc-btn-pulse 2.4s ease-out infinite;
    }

    /* Control row — voice picker + intensity + cost meter (mode-aware).
   No background fill any more — earlier the strip had its own
   var(--lg-fill) which read as a "two-tone" shell-within-shell.
   Now it sits flush on the same console surface, separated only by
   a hairline rule, which is more compact and less visually busy. */
    .ce-vc-controls {
      display: flex;
      flex-wrap: wrap;
      align-items: flex-end;
      gap: 12px 20px;
      padding: 14px 24px 12px;
      border-bottom: 1px solid var(--lg-stroke);
    }

    .ce-vc-control {
      display: flex;
      flex-direction: column;
      gap: 6px;
      min-width: 0;
    }

    .ce-vc-control-label {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 800;
      letter-spacing: .12em;
      text-transform: uppercase;
      color: var(--text-muted);
    }

    .ce-vc-pill {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      padding: 7px 12px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      border-radius: 999px;
      color: var(--text);
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 600;
      cursor: pointer;
      transition: background .15s var(--ease), border-color .15s var(--ease);
    }

    .ce-vc-pill:hover {
      background: var(--lg-fill-hover);
      border-color: var(--lg-stroke-hi)
    }

    .ce-vc-brain-dot {
      width: 8px;
      height: 8px;
      border-radius: 50%;
      background: var(--accent-bright);
      box-shadow: 0 0 8px var(--accent-bright);
    }

    .ce-vc-brain-dot.gpt {
      background: #10a37f;
      box-shadow: 0 0 8px rgba(16, 163, 127, .7)
    }

    .ce-vc-brain-dot.claude {
      background: #cd6f47;
      box-shadow: 0 0 8px rgba(205, 111, 71, .7)
    }

    .ce-vc-brain-dot.gemini {
      background: #a78bfa;
      box-shadow: 0 0 8px rgba(167, 139, 250, .7)
    }

    .ce-vc-brain-variant {
      font-size: 11px;
      font-weight: 500;
      color: var(--text-muted);
      padding-left: 2px;
      border-left: 1px solid var(--lg-stroke);
      padding-left: 8px;
      margin-left: 2px;
    }

    .ce-vc-pill-caret {
      font-size: 9px;
      color: var(--text-muted);
      margin-left: 2px
    }

    /* Intensity 3-button group — same pattern as the main meta-row
   intensity selector but tuned for this surface. */
    .ce-vc-intensity {
      display: inline-flex;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      border-radius: 999px;
      padding: 3px;
      gap: 2px;
    }

    .ce-vc-intensity button {
      padding: 5px 12px;
      border: none;
      background: transparent;
      border-radius: 999px;
      color: var(--text-muted);
      font-family: var(--font-ui);
      font-size: 12px;
      font-weight: 600;
      cursor: pointer;
      transition: background .15s var(--ease), color .15s var(--ease);
    }

    .ce-vc-intensity button:hover {
      color: var(--text)
    }

    .ce-vc-intensity button.on {
      background: var(--lg-fill-hover);
      color: var(--text);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .55), 0 0 12px rgba(255, 255, 255, .05);
    }

    /* The argue brain is now picked OUTSIDE the console (meta row above
   the chat bar). The in-console pill would be a duplicate, so it's
   permanently hidden — kept in the DOM for the JS that updates it. */
    .ce-vc-control-model {
      display: none
    }

    /* MODE-AWARE PARAMS — voice-specific controls hidden in text mode;
   they appear once the user toggles to voice. Text mode keeps the
   strip simple: just intensity (brain is in the meta row above the
   chat bar, per-reply cost is inside the input row). */
    .ce-voice-overlay[data-input-mode="text"] .ce-vc-control-voice,
    .ce-voice-overlay[data-input-mode="text"] .ce-vc-control-meter {
      display: none;
    }

    /* Voice-rate banner — sits inline at the far right of the controls
   row. Visible whenever input-mode is voice (both idle and active).
   IDLE shows the rate + slider + budget; ACTIVE swaps to the rate +
   elapsed timer + cumulative spent. Replaced the old standalone
   Cost meter — one banner does both jobs so the row stays clean. */
    .ce-vc-estimate {
      display: none;
      align-items: center;
      gap: 12px;
      margin-left: auto;
      /* push to far-right of the flex row */
      padding: 8px 14px;
      border: 1.5px dashed var(--lg-stroke-hi);
      border-radius: 14px;
      font-family: var(--font-ui);
    }

    .ce-voice-overlay[data-input-mode="voice"] .ce-vc-estimate {
      display: inline-flex;
    }

    /* Once a conversation is live, swap the dashed border to a solid
   one — visual signal that this is now a live readout, not a
   pre-commit estimate. */
    .ce-voice-overlay[data-state="listening"] .ce-vc-estimate,
    .ce-voice-overlay[data-state="thinking"] .ce-vc-estimate,
    .ce-voice-overlay[data-state="speaking"] .ce-vc-estimate {
      border-style: solid;
      border-color: var(--lg-stroke-hi);
    }

    /* Show budget (slider) when idle, live readout when active. */
    .ce-vc-live {
      display: none
    }

    .ce-voice-overlay[data-state="idle"] .ce-vc-budget {
      display: flex
    }

    .ce-voice-overlay[data-state="idle"] .ce-vc-live {
      display: none
    }

    .ce-voice-overlay[data-state="listening"] .ce-vc-budget,
    .ce-voice-overlay[data-state="thinking"] .ce-vc-budget,
    .ce-voice-overlay[data-state="speaking"] .ce-vc-budget {
      display: none
    }

    .ce-voice-overlay[data-state="listening"] .ce-vc-live,
    .ce-voice-overlay[data-state="thinking"] .ce-vc-live,
    .ce-voice-overlay[data-state="speaking"] .ce-vc-live {
      display: flex
    }

    .ce-vc-live {
      flex-direction: column;
      gap: 1px;
      font-family: var(--font-ui);
      line-height: 1.15;
    }

    .ce-vc-live-row {
      display: flex;
      align-items: baseline;
      gap: 8px;
      font-size: 11px;
      color: var(--text-muted);
      white-space: nowrap;
    }

    .ce-vc-live-label {
      font-size: 9px;
      font-weight: 700;
      letter-spacing: .14em;
      text-transform: uppercase;
    }

    .ce-vc-live-spent {
      display: inline-flex;
      align-items: center;
      gap: 4px;
      color: var(--text);
    }

    .ce-vc-live-spent b {
      font-weight: 700;
      font-size: 13px
    }

    .ce-vc-live-spent .joy-coin {
      width: 1.15em;
      height: 1.15em
    }

    /* Timer styling — tabular nums so the digits don't jiggle. */
    .ce-vc-live .ce-vc-meter-time {
      font-variant-numeric: tabular-nums;
      font-weight: 700;
      font-size: 13px;
      color: var(--accent-text);
    }

    .ce-vc-estimate-label {
      display: flex;
      flex-direction: column;
      gap: 1px;
      line-height: 1.1;
    }

    .ce-vc-estimate-eyebrow {
      font-size: 9px;
      font-weight: 700;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: var(--accent-text);
    }

    .ce-vc-estimate-rate {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      font-size: 14px;
      font-weight: 700;
      color: var(--text);
    }

    .ce-vc-estimate-rate-unit {
      color: var(--text-muted);
      font-weight: 500;
      font-size: 11px;
    }

    .ce-vc-estimate-bar {
      width: 1px;
      align-self: stretch;
      background: var(--lg-stroke);
    }

    /* Budget pane — summary line on top + slider below + min/max scale.
   Sits inside the estimate banner; scales with user input so cost
   updates in real time as they drag. Slider styled to match the
   liquid-glass language: thin accented track, glowing thumb. */
    .ce-vc-budget {
      display: flex;
      flex-direction: column;
      gap: 5px;
      min-width: 200px;
    }

    .ce-vc-budget-summary {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      font-size: 12px;
      color: var(--text-muted);
      white-space: nowrap;
      font-family: var(--font-ui);
    }

    .ce-vc-budget-summary b {
      color: var(--text);
      font-weight: 700;
      font-size: 13px;
    }

    .ce-vc-budget-cost {
      display: inline-flex;
      align-items: center;
      gap: 4px;
      margin-left: 2px;
    }

    .ce-vc-budget-cost .joy-coin {
      width: 1.15em;
      height: 1.15em
    }

    .ce-vc-budget-slider {
      -webkit-appearance: none;
      appearance: none;
      width: 100%;
      height: 4px;
      background: rgba(255, 255, 255, .10);
      border-radius: 2px;
      outline: none;
      cursor: pointer;
    }

    .ce-vc-budget-slider::-webkit-slider-thumb {
      -webkit-appearance: none;
      appearance: none;
      width: 14px;
      height: 14px;
      border-radius: 50%;
      background: var(--accent-bright);
      border: 2px solid #fff;
      box-shadow: 0 0 10px var(--active-glow);
      cursor: pointer;
      transition: transform .12s var(--ease);
    }

    .ce-vc-budget-slider::-webkit-slider-thumb:hover {
      transform: scale(1.15)
    }

    .ce-vc-budget-slider::-moz-range-thumb {
      width: 14px;
      height: 14px;
      border-radius: 50%;
      background: var(--accent-bright);
      border: 2px solid #fff;
      box-shadow: 0 0 10px var(--active-glow);
      cursor: pointer;
    }

    .ce-vc-budget-scale {
      display: flex;
      justify-content: space-between;
      font-size: 9px;
      color: var(--text-muted);
      font-family: var(--font-ui);
      letter-spacing: .06em;
      margin-top: -1px;
    }

    /* Cost meter — rate + elapsed timer + cumulative spent. Reads at a
   glance: how much per minute, how long so far, how many coins it
   adds up to. Updates every second from JS. */
    .ce-vc-meter {
      display: inline-flex;
      align-items: center;
      gap: 12px;
      padding: 7px 14px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke-hi);
      border-radius: 14px;
      font-family: var(--font-ui);
      font-size: 13px;
      color: var(--text);
    }

    .ce-vc-meter-rate,
    .ce-vc-meter-spent {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      font-weight: 600;
    }

    .ce-vc-meter-rate-unit {
      font-weight: 500;
      color: var(--text-muted);
      font-size: 11px;
    }

    .ce-vc-meter-divider {
      width: 1px;
      height: 18px;
      background: var(--lg-stroke);
    }

    .ce-vc-meter-time {
      font-variant-numeric: tabular-nums;
      font-weight: 700;
      color: var(--accent-text);
    }

    .ce-vc-meter-spent-amt {
      display: inline-flex;
      align-items: center;
      gap: 4px;
      color: var(--text-muted);
      font-size: 12px;
    }

    /* Old standalone action row removed in favor of .ce-vc-voice-row's
   inline buttons. Selector kept inert in case anything else still
   references it. */
    .ce-vc-actions {
      display: none
    }

    .ce-vc-btn {
      position: relative;
      display: inline-flex;
      align-items: center;
      gap: 7px;
      padding: 8px 14px;
      border-radius: 999px;
      border: 1.5px solid var(--lg-stroke);
      background: var(--lg-fill);
      color: var(--text);
      font-family: var(--font-ui);
      font-size: 12.5px;
      font-weight: 600;
      cursor: pointer;
      transition: transform .18s var(--ease), background .18s var(--ease), border-color .18s var(--ease), box-shadow .18s var(--ease);
      overflow: visible;
    }

    .ce-vc-btn:hover {
      transform: translateY(-1px);
      background: var(--lg-fill-hover)
    }

    .ce-vc-btn-primary {
      border-color: var(--lg-stroke-hi);
      background: linear-gradient(140deg, var(--active-tint), transparent 60%), var(--lg-fill);
      box-shadow: 0 0 28px var(--active-glow);
    }

    .ce-vc-btn-primary .ce-vc-btn-pulse {
      position: absolute;
      inset: -2px;
      border-radius: 999px;
      border: 1.5px solid var(--accent-bright);
      opacity: .7;
      animation: vc-btn-pulse 2.4s ease-out infinite;
      pointer-events: none;
    }

    @keyframes vc-btn-pulse {
      0% {
        transform: scale(1);
        opacity: .55
      }

      100% {
        transform: scale(1.18);
        opacity: 0
      }
    }

    .ce-vc-btn-end {
      border-color: rgba(255, 107, 120, .45);
      color: #ff8b94;
    }

    .ce-vc-btn-end:hover {
      background: rgba(255, 107, 120, .10);
      border-color: rgba(255, 107, 120, .65);
    }

    .ce-vc-btn-secondary.is-muted {
      background: var(--active-tint);
      border-color: var(--lg-stroke-hi);
      color: var(--accent-text);
    }

    /* Bottom hint — small instructional line. */
    /* Hint pill in the top-right of the head — replaces the old bottom
   strip that wasted vertical space. Compact, muted, content changes
   per input mode via JS. */
    .ce-vc-head-right {
      display: flex;
      align-items: center;
      gap: 14px;
      flex-shrink: 0;
    }

    .ce-vc-head-hint {
      font-family: var(--font-ui);
      font-size: 11.5px;
      font-weight: 500;
      color: var(--text-muted);
      letter-spacing: .02em;
      max-width: 280px;
      text-align: right;
      line-height: 1.35;
    }

    /* ----------------------------------------------------------------
   COACH CONSOLE — additions on top of the .ce-voice-overlay base.
   The shell, head, params strip, thread, and input area all reuse
   the argue-console CSS. New stuff:
     - setup card (template grid + scenario + Begin) shown pre-start
     - impression meter (top-right of head, replaces hint pill)
     - end-of-session report overlay
   ---------------------------------------------------------------- */

    /* Show setup card only in the setup state; hide thread + input. */
    .ce-coach-overlay[data-state="setup"] .ce-coach-setup {
      display: flex
    }

    .ce-coach-overlay[data-state="setup"] .ce-vc-thread {
      display: none
    }

    .ce-coach-overlay[data-state="setup"] .ce-vc-input {
      display: none
    }

    /* Params strip is fully hidden in setup state — Difficulty moved to
   the head's top-right, Voice picker is irrelevant pre-session. */
    .ce-coach-overlay[data-state="setup"] .ce-vc-controls {
      display: none
    }

    /* Once the session is live, the user has committed to their chosen
   input mode at setup. Don't offer the cross-mode toggle anymore —
   text users don't see Voice, voice users don't see Type-back. */
    .ce-coach-overlay:not([data-state="setup"]) #ceCoachVoiceToggle {
      display: none
    }

    .ce-coach-overlay:not([data-state="setup"]) #ceCoachBackToTextBtn {
      display: none
    }

    /* Also drop the divider that sits before the voice toggle in the
   text row, since the toggle is gone. */
    .ce-coach-overlay:not([data-state="setup"]) #ceCoachVoiceToggle+.ce-vc-text-divider,
    .ce-coach-overlay:not([data-state="setup"]) .ce-vc-text-row .ce-vc-text-divider {
      display: none
    }

    /* Difficulty pills in the head are visible only during setup; once
   the session is live, you don't change difficulty mid-flight. */
    .ce-coach-head-difficulty {
      display: none
    }

    .ce-coach-overlay[data-state="setup"] .ce-coach-head-difficulty {
      display: inline-flex
    }

    .ce-coach-overlay:not([data-state="setup"]) .ce-coach-setup {
      display: none
    }

    /* Compact the inline difficulty pill in the head so it sits nicely
   next to the close button without dominating the row. */
    .ce-coach-head-difficulty button {
      padding: 4px 11px;
      font-size: 11.5px;
    }

    .ce-coach-setup {
      display: none;
      flex: 1;
      flex-direction: column;
      /* b.516 — Tighter gap (was 10) so coach setup fits in viewport
     without scrolling — large scenario grid + brain row + mode
     cards + composer was overflowing. */
      gap: 6px;
      padding: 8px 22px 10px;
      overflow-y: auto;
      min-height: 0;
    }

    .ce-coach-setup-section {
      display: flex;
      flex-direction: column;
      gap: 6px;
    }

    .ce-coach-setup-label {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 800;
      letter-spacing: .12em;
      text-transform: uppercase;
      color: var(--text-muted);
    }

    .ce-coach-template-grid {
      display: grid;
      grid-template-columns: repeat(auto-fill, minmax(155px, 1fr));
      gap: 6px;
    }

    .ce-coach-template-card {
      display: flex;
      align-items: center;
      justify-content: center;
      gap: 8px;
      padding: 10px 11px;
      /* b.481 — "Bleed-through" variant of the liquid-glass recipe per
     user request for these tiles specifically. Wash dropped to .01
     (was .03) so the orbs come through nearly unobstructed, blur
     reduced to 24px (was 40px) so the orb colors remain recognisable
     instead of being smeared into uniform tone, saturate bumped to
     2.0 (was 1.7) so the colors that DO come through pop. Border
     and insets unchanged so the tile is still cleanly defined. */
      background: rgba(255, 255, 255, .01);
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(24px) saturate(2.0);
      backdrop-filter: blur(24px) saturate(2.0);
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .16),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      border-radius: 20px;
      color: var(--text);
      font-family: var(--font-ui);
      font-size: 12px;
      font-weight: 600;
      cursor: pointer;
      text-align: center;
      transition: transform .15s var(--ease), border-color .15s var(--ease), background .15s var(--ease);
    }

    .ce-coach-template-card .ce-coach-template-name {
      display: block;
      width: 100%;
      text-align: center;
    }

    .ce-coach-template-card:hover {
      transform: translateY(-1px);
      border-color: var(--lg-stroke-hi);
      background: var(--lg-fill-hover);
    }

    .ce-coach-template-card.on {
      background: var(--lg-fill-hover);
      border-color: rgba(255, 255, 255, .55);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .22) inset, 0 0 18px rgba(255, 255, 255, .06);
    }

    .ce-coach-template-icon {
      width: 20px;
      height: 20px;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      font-size: 14px;
      flex-shrink: 0;
    }

    .ce-coach-template-name {
      flex: 1;
      line-height: 1.2
    }

    .ce-coach-scenario {
      width: 100%;
      padding: 9px 13px;
      /* b.473 — Engine-popover recipe (matches Argue composer textbox). */
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      border-radius: 20px;
      color: var(--text);
      font-family: var(--font-body);
      font-size: 13px;
      line-height: 1.45;
      resize: none;
      min-height: 54px;
      max-height: 140px;
      outline: none;
      transition: border-color .15s var(--ease);
    }

    .ce-coach-scenario:focus {
      border-color: var(--lg-stroke-hi);
      box-shadow: 0 0 0 3px var(--active-tint);
    }

    .ce-coach-scenario::placeholder {
      color: var(--text-muted);
      opacity: .7
    }

    /* Brain row — host for the same argue-brain capsule, embedded
   inside the setup card instead of the meta row. */
    .ce-coach-brain-row {
      display: flex;
      align-items: center;
    }

    /* MODE CARDS — Text vs Voice side-by-side, with the active one
   getting an accent border. The Voice card grows when selected
   (duration pills + total cost slot in). */
    .ce-coach-mode-cards {
      display: grid;
      grid-template-columns: 1fr 1fr;
      gap: 10px;
    }

    .ce-coach-mode-card {
      /* b.556 — position:relative so the COACH BRAIN switch absolutely
     positioned inside the text card has an anchor (mirrors Argue).
     b.557 — Compacted to match Argue exactly: padding 11/14 → 10/12,
     gap 8 → 6. */
      position: relative;
      display: flex;
      flex-direction: column;
      gap: 6px;
      padding: 10px 12px;
      text-align: left;
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      border-radius: 14px;
      cursor: pointer;
      transition: all .18s var(--ease);
      font-family: var(--font-ui);
      color: var(--text);
      outline: none;
    }

    /* b.556 — Match Argue's visibility rules for the in-card brain
   switch on the COACH mode cards. Switch only renders inside the
   ACTIVE (.on) text card; voice card never shows one. */
    .ce-coach-mode-card:not(.on) .ce-vc-text-brain {
      display: none !important;
    }

    .ce-coach-mode-card[data-cmode="voice"] .ce-vc-text-brain {
      display: none !important;
    }

    .ce-coach-mode-card:focus-visible {
      border-color: var(--accent-bright);
      box-shadow: 0 0 0 3px var(--active-tint);
    }

    .ce-coach-mode-card:hover {
      /* b.557 — Match Argue's hover (no Y-translate, soft bg lift). */
      background: var(--lg-fill-hover);
      border-color: rgba(255, 255, 255, .22);
    }

    .ce-coach-mode-card.on {
      background: var(--lg-fill-hover);
      border-color: rgba(255, 255, 255, .55);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .22), 0 6px 22px rgba(255, 255, 255, .05);
    }

    /* b.557 — Hide radio dot on Coach mode cards (matches Argue b.529).
   The card's .on background/border already signals selection. */
    .ce-coach-mode-card .ce-coach-mode-radio {
      display: none !important;
    }

    /* b.557 — Hide the prominent "20 / minute" price on the VOICE card
   (the summary chip at top-right replaces it). Text card keeps its
   "1 per reply" price. Mirrors Argue's b.530 rule. */
    .ce-coach-mode-card[data-cmode="voice"] .ce-coach-mode-price {
      display: none !important;
    }

    /* b.557 — Voice summary moves from a separate pill below the slider
   to an absolutely-positioned chip at the top-right of the voice
   card. Matches Argue's compact layout. */
    .ce-coach-mode-card[data-cmode="voice"] .ce-coach-voice-summary {
      position: absolute !important;
      top: 8px !important;
      right: 10px !important;
      margin: 0 !important;
      padding: 0 !important;
      background: transparent !important;
      border: 0 !important;
      display: inline-flex !important;
      align-items: center;
      gap: 6px;
      font-size: 11.5px;
    }

    .ce-coach-mode-card[data-cmode="voice"] .ce-coach-voice-summary-block {
      display: inline-flex;
      align-items: baseline;
      gap: 3px;
    }

    .ce-coach-mode-card[data-cmode="voice"] .ce-coach-voice-summary-num {
      font-size: 13px;
      font-weight: 700;
      line-height: 1;
    }

    .ce-coach-mode-card[data-cmode="voice"] .ce-coach-voice-summary-unit {
      font-size: 10.5px;
      color: var(--text-muted);
      font-weight: 600;
    }

    .ce-coach-mode-card[data-cmode="voice"] .ce-coach-voice-summary-eq {
      font-size: 11px;
      color: var(--text-muted);
    }

    .ce-coach-mode-card[data-cmode="voice"] .ce-coach-voice-summary .joy-coin {
      width: 1em;
      height: 1em;
    }

    .ce-coach-mode-head {
      /* b.557 — gap 10 → 8 to match Argue. */
      display: flex;
      align-items: center;
      gap: 8px;
    }

    .ce-coach-mode-ico {
      font-size: 18px;
      line-height: 1
    }

    .ce-coach-mode-name {
      /* b.557 — Display font + tighter letter-spacing to match Argue. */
      flex: 1;
      font-family: var(--font-display);
      font-size: 14px;
      font-weight: 700;
      letter-spacing: -.005em;
      color: var(--text);
    }

    .ce-coach-mode-radio {
      width: 16px;
      height: 16px;
      border-radius: 50%;
      border: 1.5px solid var(--lg-stroke);
      flex-shrink: 0;
      transition: border-color .15s var(--ease), background .15s var(--ease);
      position: relative;
    }

    .ce-coach-mode-card.on .ce-coach-mode-radio {
      border-color: rgba(255, 255, 255, .85);
      background: radial-gradient(circle, rgba(255, 255, 255, .85) 35%, transparent 45%);
      box-shadow: 0 0 6px rgba(255, 255, 255, .5);
    }

    .ce-coach-mode-body {
      display: flex;
      flex-direction: column;
      gap: 6px;
    }

    .ce-coach-mode-price {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      font-size: 15px;
      font-weight: 800;
      font-family: var(--font-display);
    }

    .ce-coach-mode-price .joy-coin {
      width: 1.3em;
      height: 1.3em
    }

    .ce-coach-mode-price-unit {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 500;
      color: var(--text-muted);
      letter-spacing: .04em;
    }

    .ce-coach-mode-free-ico {
      font-size: 24px;
      font-weight: 600;
      line-height: 1;
      letter-spacing: -.05em;
      color: var(--accent-text);
    }

    .ce-coach-mode-free-label {
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 800;
      letter-spacing: .08em;
      text-transform: uppercase;
      color: var(--accent-text);
    }

    .ce-coach-mode-hint {
      margin: 0;
      font-size: 11.5px;
      color: var(--text-muted);
      display: inline-flex;
      align-items: center;
      gap: 5px;
      flex-wrap: wrap;
      line-height: 1.45;
    }

    .ce-coach-mode-total {
      display: inline-flex;
      align-items: center;
      gap: 3px;
      color: var(--text);
      font-weight: 700;
    }

    .ce-coach-mode-total .joy-coin {
      width: 1.05em;
      height: 1.05em
    }

    .ce-coach-mode-total b {
      font-weight: 800
    }

    /* Prominent voice summary — minutes + coins as big numbers, with
   an ≈ between. Replaces the muted "Talk for X min ≈ Y" prose. */
    .ce-coach-voice-summary {
      display: inline-flex;
      align-items: center;
      gap: 10px;
      padding: 6px 12px;
      background: rgba(255, 255, 255, .04);
      border: 1px solid var(--lg-stroke);
      border-radius: 12px;
      align-self: flex-start;
    }

    .ce-coach-voice-summary-block {
      display: inline-flex;
      align-items: baseline;
      gap: 4px;
    }

    .ce-coach-voice-summary-num {
      font-family: var(--font-display);
      font-size: 18px;
      font-weight: 800;
      letter-spacing: -.01em;
      color: var(--text);
      line-height: 1;
      font-variant-numeric: tabular-nums;
    }

    .ce-coach-voice-summary-unit {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .10em;
      text-transform: uppercase;
      color: var(--text-muted);
    }

    .ce-coach-voice-summary-eq {
      font-family: var(--font-display);
      font-size: 14px;
      font-weight: 600;
      color: var(--text-muted);
      line-height: 1;
    }

    .ce-coach-voice-summary .joy-coin {
      width: 1.3em;
      height: 1.3em;
      align-self: center;
    }

    /* Tier warning — soft amber pill below the brain capsule. Visible
   only when a light-tier brain (Haiku / 4o-mini / Flash) is on. */
    /* DATING QUESTIONNAIRE — entry button + popup form. Liquid-glass
   throughout. Button only renders for the dating template. */
    .ce-coach-dating-btn {
      display: flex;
      align-items: center;
      gap: 14px;
      padding: 12px 16px;
      margin-top: 10px;
      border-radius: 14px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .02)),
        var(--lg-fill);
      border: 1px solid rgba(255, 255, 255, .22);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      color: var(--text);
      font-family: var(--font-ui);
      text-align: left;
      cursor: pointer;
      transition: all .18s var(--ease);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .18) inset,
        0 -1px 0 rgba(0, 0, 0, .18) inset,
        0 6px 20px rgba(0, 0, 0, .18);
    }

    .ce-coach-dating-btn:hover {
      border-color: rgba(255, 255, 255, .36);
      transform: translateY(-1px);
    }

    .ce-coach-dating-btn-spark {
      font-size: 18px;
      color: #ffd86e;
      text-shadow: 0 0 12px rgba(255, 216, 110, .4);
      flex-shrink: 0;
    }

    .ce-coach-dating-btn-text {
      flex: 1;
      min-width: 0;
      display: flex;
      flex-direction: column;
      gap: 2px;
    }

    .ce-coach-dating-btn-text b {
      font-family: var(--font-display);
      font-size: 13.5px;
      font-weight: 700;
      letter-spacing: -.005em;
      color: var(--text);
    }

    .ce-coach-dating-btn-text span {
      font-size: 11.5px;
      line-height: 1.4;
      color: var(--text-muted);
    }

    .ce-coach-dating-btn-caret {
      font-size: 14px;
      color: var(--text-muted);
      flex-shrink: 0;
      transition: transform .18s var(--ease);
    }

    .ce-coach-dating-btn:hover .ce-coach-dating-btn-caret {
      transform: translateX(3px);
      color: var(--text);
    }

    /* Popup overlay */
    .ce-coach-dating-overlay {
      position: fixed;
      inset: 0;
      display: none;
      align-items: center;
      justify-content: center;
      z-index: 300;
      padding: 24px;
    }

    .ce-coach-dating-overlay:not([hidden]) {
      display: flex;
    }

    .ce-coach-dating-backdrop {
      position: absolute;
      inset: 0;
      background: rgba(0, 0, 0, .55);
      -webkit-backdrop-filter: blur(8px);
      backdrop-filter: blur(8px);
    }

    .ce-coach-dating-shell {
      position: relative;
      width: min(680px, 100%);
      max-height: calc(100vh - 48px);
      display: flex;
      flex-direction: column;
      border-radius: 20px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .02)),
        var(--lg-fill);
      border: 1px solid rgba(255, 255, 255, .16);
      -webkit-backdrop-filter: blur(40px) saturate(180%);
      backdrop-filter: blur(40px) saturate(180%);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .18) inset,
        0 -1px 0 rgba(0, 0, 0, .20) inset,
        0 0 0 1px rgba(255, 255, 255, .06) inset,
        0 32px 72px rgba(0, 0, 0, .55),
        0 8px 24px rgba(0, 0, 0, .30);
      overflow: hidden;
    }

    .ce-coach-dating-head {
      padding: 18px 22px 14px;
      border-bottom: 1px solid rgba(255, 255, 255, .08);
      display: flex;
      align-items: flex-start;
      justify-content: space-between;
      gap: 12px;
    }

    .ce-coach-dating-title {
      font-family: var(--font-display);
      font-size: 20px;
      font-weight: 700;
      letter-spacing: -.005em;
      color: var(--text);
      margin: 4px 0 4px;
    }

    .ce-coach-dating-sub {
      font-size: 12.5px;
      line-height: 1.5;
      color: var(--text-muted);
      margin: 0;
    }

    .ce-coach-dating-body {
      flex: 1;
      overflow-y: auto;
      padding: 14px 22px 6px;
      display: flex;
      flex-direction: column;
      gap: 18px;
    }

    .ce-coach-dating-section {
      display: flex;
      flex-direction: column;
      gap: 10px;
    }

    .ce-coach-dating-section-label {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .16em;
      text-transform: uppercase;
      color: var(--text-faint);
    }

    .ce-coach-dating-hint {
      font-weight: 500;
      letter-spacing: .04em;
      text-transform: none;
      color: var(--text-faint);
      margin-left: 6px;
    }

    .ce-coach-dating-grid {
      display: grid;
      grid-template-columns: 1fr 1fr;
      gap: 10px;
    }

    .ce-coach-dating-field {
      display: flex;
      flex-direction: column;
      gap: 4px;
    }

    .ce-coach-dating-field-wide {
      grid-column: 1 / -1;
    }

    .ce-coach-dating-field span {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      letter-spacing: .04em;
      color: var(--text-muted);
    }

    .ce-coach-dating-field input,
    .ce-coach-dating-field select {
      font-family: var(--font-body);
      font-size: 13.5px;
      line-height: 1.4;
      color: var(--text);
      background: rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .14);
      border-radius: 10px;
      padding: 8px 11px;
      outline: none;
      transition: border-color .15s var(--ease), background .15s var(--ease);
    }

    .ce-coach-dating-field input::placeholder {
      color: var(--text-faint);
      font-style: italic;
    }

    .ce-coach-dating-field input:focus,
    .ce-coach-dating-field select:focus {
      border-color: rgba(255, 255, 255, .36);
      background: rgba(255, 255, 255, .08);
    }

    .ce-coach-dating-field select option {
      background: #15192a;
      color: var(--text);
    }

    /* Practice chips multi-select */
    .ce-coach-dating-checks-label {
      display: block;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      letter-spacing: .04em;
      color: var(--text-muted);
      margin-bottom: 8px;
    }

    .ce-coach-dating-chip-row {
      display: flex;
      flex-wrap: wrap;
      gap: 6px;
    }

    .ce-coach-dating-chip {
      padding: 6px 12px;
      border-radius: 999px;
      background: rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .14);
      color: var(--text-muted);
      font-family: var(--font-ui);
      font-size: 11.5px;
      font-weight: 600;
      cursor: pointer;
      transition: all .15s var(--ease);
    }

    .ce-coach-dating-chip:hover {
      background: rgba(255, 255, 255, .10);
      color: var(--text);
    }

    .ce-coach-dating-chip.is-on {
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .16), rgba(255, 255, 255, .06));
      border-color: rgba(255, 255, 255, .45);
      color: var(--text);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .18) inset;
    }

    .ce-coach-dating-foot {
      padding: 14px 22px 18px;
      border-top: 1px solid rgba(255, 255, 255, .08);
      display: flex;
      justify-content: flex-end;
      gap: 10px;
    }

    @media (max-width: 640px) {
      .ce-coach-dating-grid {
        grid-template-columns: 1fr;
      }

      .ce-coach-dating-shell {
        max-height: calc(100vh - 24px);
      }

      .ce-coach-dating-overlay {
        padding: 12px;
      }

      .ce-coach-dating-head {
        padding: 14px 16px 12px;
      }

      .ce-coach-dating-body {
        padding: 12px 16px 4px;
      }

      .ce-coach-dating-foot {
        padding: 12px 16px 14px;
      }
    }

    .ce-coach-tier-warning {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      margin-top: 4px;
      padding: 6px 12px;
      background: rgba(252, 166, 0, .10);
      border: 1px solid rgba(252, 166, 0, .30);
      border-radius: 10px;
      font-family: var(--font-ui);
      font-size: 11.5px;
      line-height: 1.4;
      color: #ffc266;
      max-width: 760px;
    }

    /* 2026-05-10 b.165 — when the tier warning is visible, lay out the
   parent .ce-coach-setup-section as a grid: label spans the top row,
   brain-row sits in column 1 of row 2, warning sits in column 2 of
   row 2 (right of the brain row, no extra vertical space, no scroll). */
    .ce-coach-setup-section:has(.ce-coach-tier-warning:not([hidden])) {
      display: grid !important;
      grid-template-columns: auto 1fr !important;
      grid-template-rows: auto auto !important;
      column-gap: 14px !important;
      row-gap: 6px !important;
      align-items: center !important;
    }

    .ce-coach-setup-section:has(.ce-coach-tier-warning:not([hidden]))>.ce-coach-setup-label {
      grid-column: 1 / -1 !important;
    }

    .ce-coach-setup-section:has(.ce-coach-tier-warning:not([hidden]))>.ce-coach-brain-row {
      grid-column: 1 !important;
      grid-row: 2 !important;
    }

    .ce-coach-setup-section:has(.ce-coach-tier-warning:not([hidden]))>.ce-coach-tier-warning {
      grid-column: 2 !important;
      grid-row: 2 !important;
      justify-self: end !important;
      margin-top: 0 !important;
    }

    .ce-coach-tier-warning-ico {
      font-size: 14px;
      flex-shrink: 0;
      line-height: 1;
    }

    .ce-coach-tier-warning-text {
      color: rgba(255, 210, 140, .92);
    }

    .ce-coach-tier-warning-text b {
      color: #ffd680;
      font-weight: 700;
    }

    /* Talk-time dial — slider styled to match the liquid-glass language.
   Track is a thin frosted line, thumb is an accent-bright dot with
   glow. Min/max scale labels sit under the track. */
    .ce-coach-dial {
      display: flex;
      flex-direction: column;
      gap: 4px;
      width: 100%;
      padding: 4px 0 2px;
    }

    .ce-coach-dial-input {
      -webkit-appearance: none;
      appearance: none;
      width: 100%;
      height: 5px;
      background: rgba(255, 255, 255, .10);
      border-radius: 3px;
      outline: none;
      cursor: pointer;
    }

    .ce-coach-dial-input::-webkit-slider-thumb {
      -webkit-appearance: none;
      appearance: none;
      width: 16px;
      height: 16px;
      border-radius: 50%;
      background: #fff;
      border: 2px solid rgba(255, 255, 255, .55);
      box-shadow: 0 0 0 4px rgba(255, 255, 255, .05), 0 2px 8px rgba(0, 0, 0, .3);
      cursor: pointer;
      transition: transform .12s var(--ease);
    }

    .ce-coach-dial-input::-webkit-slider-thumb:hover {
      transform: scale(1.18)
    }

    .ce-coach-dial-input::-moz-range-thumb {
      width: 16px;
      height: 16px;
      border-radius: 50%;
      background: #fff;
      border: 2px solid rgba(255, 255, 255, .55);
      box-shadow: 0 0 0 4px rgba(255, 255, 255, .05), 0 2px 8px rgba(0, 0, 0, .3);
      cursor: pointer;
    }

    .ce-coach-dial-scale {
      display: flex;
      justify-content: space-between;
      font-family: var(--font-ui);
      font-size: 9px;
      font-weight: 600;
      letter-spacing: .10em;
      text-transform: uppercase;
      color: var(--text-muted);
    }

    /* Begin button — now carries an integrated cost segment on its right. */
    /* b.558 — Legacy chip styling for .ce-coach-begin-cost retired.
   The unified pill version further down (matching Argue) is the
   source of truth. This block kept as a no-op shield in case any
   other selector still relies on the class existing here. */
    .ce-coach-begin-cost {
      background: transparent;
      border: 0;
    }

    .ce-coach-begin-cost.free {
      background: transparent;
      color: var(--accent-text);
    }

    .ce-coach-begin-cost .joy-coin {
      width: 1.15em;
      height: 1.15em
    }

    .ce-coach-setup-foot {
      display: flex;
      align-items: center;
      justify-content: space-between;
      gap: 14px;
      margin-top: auto;
      padding-top: 4px;
    }

    .ce-coach-setup-foot-hint {
      font-family: var(--font-ui);
      font-size: 11px;
      color: var(--text-muted);
      max-width: 380px;
      line-height: 1.35;
    }

    /* Begin button — b.558 redesign to match Argue's embedded pill
   anatomy. Two cells (label + cost) sharing the same glass surface,
   no internal divider, no inner backgrounds. Taller (44px), bolder
   white-light selection, subtle hover lift. The button reads as a
   single confident pill instead of a flat tag-on-a-tag look. */
    .ce-coach-begin-btn {
      position: relative;
      display: inline-flex;
      align-items: center;
      height: 44px;
      padding: 0;
      border-radius: 999px;
      border: 1.5px solid rgba(255, 255, 255, .30);
      background: rgba(255, 255, 255, .04);
      -webkit-backdrop-filter: blur(22px) saturate(1.30);
      backdrop-filter: blur(22px) saturate(1.30);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .18) inset,
        0 -1px 0 rgba(255, 255, 255, .06) inset,
        0 18px 36px -12px rgba(0, 0, 0, .45);
      color: #fff;
      cursor: pointer;
      transition: transform .18s var(--ease), background .18s var(--ease), border-color .18s var(--ease);
      font-family: var(--font-display);
      text-transform: uppercase;
      letter-spacing: .04em;
      line-height: 1;
      overflow: hidden;
    }

    .ce-coach-begin-btn:hover:not(:disabled) {
      transform: translateY(-1px);
      background: rgba(255, 255, 255, .10);
      border-color: rgba(255, 255, 255, .45);
    }

    .ce-coach-begin-btn:disabled {
      opacity: .4;
      cursor: not-allowed;
      box-shadow: none;
      transform: none
    }

    .ce-coach-begin-btn .ce-vc-btn-pulse {
      border-color: rgba(255, 255, 255, .55)
    }

    .ce-coach-begin-btn:disabled .ce-vc-btn-pulse {
      display: none
    }

    .ce-coach-begin-label {
      padding: 0 16px;
      height: 100%;
      display: inline-flex;
      align-items: center;
      font-family: var(--font-display);
      font-size: 13px;
      font-weight: 700;
      letter-spacing: .04em;
      color: #fff;
      white-space: nowrap;
    }

    /* Cost cell — rides on the button's own glass surface, no inner
   background or hairline divider (matches Argue b.542). Subtle left
   padding-gap separates it from the label. */
    .ce-coach-begin-cost {
      padding: 0 16px 0 4px;
      height: 100%;
      display: inline-flex;
      align-items: center;
      gap: 5px;
      font-family: var(--font-display);
      font-size: 14px;
      font-weight: 800;
      letter-spacing: .02em;
      color: #fff;
      line-height: 1;
      background: transparent !important;
      border: 0 !important;
      margin: 0 !important;
      text-transform: none;
    }

    .ce-coach-begin-cost .joy-coin {
      width: 1.2em;
      height: 1.2em
    }

    .ce-coach-begin-num {
      font-variant-numeric: tabular-nums
    }

    /* "/ reply" suffix shown in text mode — softer weight + opacity so
   the coin number reads as primary and the per-reply qualifier as
   metadata, matching the Text card's "1 per reply" treatment. */
    .ce-coach-begin-suffix {
      font-size: 11px;
      font-weight: 600;
      letter-spacing: .04em;
      opacity: .72;
      margin-left: 2px;
      text-transform: none;
    }

    .ce-coach-begin-cost.free {
      color: var(--accent-text)
    }

    .ce-coach-begin-free-label {
      font-family: var(--font-ui);
      font-size: 12px;
      font-weight: 800;
      letter-spacing: .12em;
      text-transform: uppercase;
    }

    /* IMPRESSION METER — radial-style horizontal track in the head's
   top-right. Color zones: red 0-30 / amber 30-60 / lime 60-80 /
   green 80-100. The fill smooth-tweens on each score update. */
    .ce-coach-meter {
      display: inline-flex;
      align-items: center;
      gap: 10px;
      padding: 6px 12px;
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      border-radius: 14px;
      font-family: var(--font-ui);
    }

    .ce-coach-meter-track {
      width: 120px;
      height: 6px;
      background: rgba(255, 255, 255, .10);
      border-radius: 3px;
      overflow: hidden;
      position: relative;
    }

    .ce-coach-meter-fill {
      height: 100%;
      width: 50%;
      border-radius: 3px;
      background: linear-gradient(90deg, #ff6b78, #ffc266 45%, #6bd989 80%, #4cc775);
      transition: width .6s var(--ease);
    }

    .ce-coach-meter-label {
      display: flex;
      flex-direction: column;
      gap: 0;
      line-height: 1;
    }

    .ce-coach-meter-eyebrow {
      font-size: 9px;
      font-weight: 700;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: var(--text-muted);
    }

    .ce-coach-meter-value {
      font-size: 15px;
      font-weight: 800;
      color: var(--text);
      font-variant-numeric: tabular-nums;
    }

    /* End-session pill in the head — visible only during live state.
   Distinct from the X close button: this triggers the report panel
   and finalises the session. Quiet red border + label so it reads
   as terminal but not panic-button. */
    .ce-coach-end-pill {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 6px 12px;
      background: rgba(255, 107, 120, .10);
      border: 1px solid rgba(255, 107, 120, .40);
      border-radius: 999px;
      color: #ff8b94;
      font-family: var(--font-ui);
      font-size: 12px;
      font-weight: 700;
      letter-spacing: .04em;
      cursor: pointer;
      transition: background .15s var(--ease), border-color .15s var(--ease), transform .15s var(--ease);
      white-space: nowrap;
    }

    .ce-coach-end-pill:hover {
      background: rgba(255, 107, 120, .18);
      border-color: rgba(255, 107, 120, .65);
      transform: translateY(-1px);
    }

    /* End pill only visible during live state (not setup). */
    .ce-coach-overlay[data-state="setup"] #ceCoachHeadEndBtn {
      display: none
    }

    .ce-coach-overlay:not([data-state="setup"]) #ceCoachHeadEndBtn {
      display: inline-flex
    }

    /* Coach-mode bubble: append a subtle judge-score badge. */
    .ce-vc-bubble[data-judge]::after {
      content: attr(data-judge);
      display: inline-block;
      margin-top: 8px;
      padding: 2px 8px;
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .10em;
      text-transform: uppercase;
      border-radius: 999px;
      border: 1px solid var(--lg-stroke);
      color: var(--text-muted);
      background: rgba(255, 255, 255, .04);
    }

    /* REPORT OVERLAY */
    .ce-coach-report-overlay {
      position: fixed;
      inset: 0;
      z-index: 160;
      display: flex;
      align-items: center;
      justify-content: center;
      padding: 24px;
      opacity: 0;
      visibility: hidden;
      pointer-events: none;
    }

    .ce-coach-report-overlay.open {
      opacity: 1;
      visibility: visible;
      pointer-events: auto;
    }

    .ce-coach-report-shell {
      width: 100%;
      max-width: 640px;
      max-height: calc(100vh - 48px);
      display: flex;
      flex-direction: column;
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      border-radius: 24px;
      box-shadow: var(--lg-shadow);
      overflow: hidden;
    }

    .ce-coach-report-head {
      display: flex;
      align-items: flex-start;
      justify-content: space-between;
      gap: 16px;
      padding: 22px 24px 14px;
      border-bottom: 1px solid var(--lg-stroke);
    }

    .ce-coach-report-title {
      font-family: var(--font-display);
      font-size: 22px;
      font-weight: 600;
      margin: 0;
    }

    .ce-coach-report-body {
      flex: 1;
      overflow-y: auto;
      padding: 20px 24px;
      font-family: var(--font-body);
      font-size: 14px;
      line-height: 1.55;
    }

    .ce-coach-report-loading {
      text-align: center;
      color: var(--text-muted);
      padding: 40px 0;
      font-style: italic;
    }

    .ce-coach-report-error {
      color: #ff8b94;
      text-align: center;
      font-size: 13px;
      padding: 18px 0;
    }

    /* Score panel — big number with color-coded zone, headline, meta. */
    .ce-coach-report-score {
      display: flex;
      flex-direction: column;
      align-items: center;
      gap: 6px;
      padding: 18px;
      margin-bottom: 18px;
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      border-radius: 18px;
      position: relative;
      overflow: hidden;
    }

    .ce-coach-report-score::before {
      content: '';
      position: absolute;
      inset: 0;
      background: linear-gradient(180deg, transparent, rgba(255, 255, 255, .04));
      pointer-events: none;
    }

    .ce-coach-report-score[data-zone="great"] {
      border-color: rgba(76, 199, 117, .55);
      box-shadow: 0 0 24px rgba(76, 199, 117, .18) inset
    }

    .ce-coach-report-score[data-zone="good"] {
      border-color: rgba(107, 217, 137, .45);
      box-shadow: 0 0 24px rgba(107, 217, 137, .14) inset
    }

    .ce-coach-report-score[data-zone="mid"] {
      border-color: rgba(255, 194, 102, .50);
      box-shadow: 0 0 24px rgba(255, 194, 102, .14) inset
    }

    .ce-coach-report-score[data-zone="low"] {
      border-color: rgba(255, 139, 148, .55);
      box-shadow: 0 0 24px rgba(255, 139, 148, .16) inset
    }

    .ce-coach-report-score[data-zone="fail"] {
      border-color: rgba(255, 107, 120, .65);
      box-shadow: 0 0 30px rgba(255, 107, 120, .22) inset
    }

    .ce-coach-report-score-num {
      font-family: var(--font-display);
      font-size: 56px;
      font-weight: 800;
      letter-spacing: -.02em;
      color: var(--text);
      line-height: 1;
      font-variant-numeric: tabular-nums;
    }

    .ce-coach-report-score-num span {
      font-size: 22px;
      font-weight: 600;
      color: var(--text-muted);
      margin-left: 2px;
    }

    .ce-coach-report-score[data-zone="great"] .ce-coach-report-score-num,
    .ce-coach-report-score[data-zone="good"] .ce-coach-report-score-num {
      color: #9bd9b0
    }

    .ce-coach-report-score[data-zone="mid"] .ce-coach-report-score-num {
      color: #ffd28a
    }

    .ce-coach-report-score[data-zone="low"] .ce-coach-report-score-num {
      color: #ff8b94
    }

    .ce-coach-report-score[data-zone="fail"] .ce-coach-report-score-num {
      color: #ff7984
    }

    .ce-coach-report-score-headline {
      font-family: var(--font-display);
      font-size: 16px;
      font-weight: 700;
      color: var(--text);
      text-align: center;
    }

    .ce-coach-report-score-meta {
      font-family: var(--font-ui);
      font-size: 10.5px;
      font-weight: 600;
      letter-spacing: .10em;
      text-transform: uppercase;
      color: var(--text-muted);
    }

    /* Report text body — bullet sections with tight rhythm. */
    .ce-coach-report-text h2 {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 800;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: var(--accent-text);
      margin: 18px 0 8px;
      padding-bottom: 6px;
      border-bottom: 1px solid var(--lg-stroke);
    }

    .ce-coach-report-text h2:first-child {
      margin-top: 0
    }

    .ce-coach-report-text ul {
      margin: 0 0 4px;
      padding-left: 20px;
      list-style: none;
    }

    .ce-coach-report-text ul li {
      position: relative;
      padding: 5px 0;
      font-size: 13.5px;
      line-height: 1.5;
      color: var(--text);
    }

    .ce-coach-report-text ul li::before {
      content: '';
      position: absolute;
      left: -14px;
      top: 13px;
      width: 5px;
      height: 5px;
      border-radius: 50%;
      background: var(--accent-bright);
    }

    .ce-coach-report-text p {
      /* Defensive — if the model accidentally writes a paragraph,
     style it minimally so it doesn't break the layout. */
      margin: 6px 0;
      font-size: 13.5px;
      line-height: 1.5;
      color: var(--text);
    }

    .ce-coach-report-foot {
      display: flex;
      align-items: center;
      justify-content: flex-end;
      gap: 10px;
      padding: 14px 24px 18px;
      border-top: 1px solid var(--lg-stroke);
    }

    /* Coach mode in chat history — rendered as an argue-style block but
   with its own meta line ("Coach · Tech interview · 78/100"). */
    .ce-coach-block {
      display: flex;
      flex-direction: column;
      gap: 10px;
      max-width: 78%;
      align-self: flex-start;
    }

    .ce-coach-block .ce-argue-summary {
      margin: 0
    }

    /* Voice-mode entry pill — sits next to the intensity dial in the
   argue meta row. Distinct enough to read as the primary action of
   argue mode (the thing you click to actually start a voice fight),
   not just another control. Soft accent glow + subtle pulse to
   invite the click without being a flashing red button. */
    .ce-voice-entry {
      position: relative;
      display: inline-flex;
      align-items: center;
      gap: 8px;
      padding: 7px 14px;
      margin-left: 10px;
      background: linear-gradient(140deg, var(--active-tint), transparent 70%), var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      border-radius: 999px;
      color: var(--accent-text);
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 700;
      cursor: pointer;
      box-shadow: 0 0 22px var(--active-glow);
      transition: transform .18s var(--ease), box-shadow .18s var(--ease), background .18s var(--ease);
      white-space: nowrap;
    }

    .ce-voice-entry:hover {
      transform: translateY(-1px);
      box-shadow: 0 0 32px var(--active-glow);
    }

    .ce-voice-entry-glow {
      position: absolute;
      inset: -3px;
      border-radius: 999px;
      border: 1.5px solid var(--accent-bright);
      opacity: .55;
      pointer-events: none;
      animation: ce-voice-entry-pulse 2.6s ease-out infinite;
    }

    @keyframes ce-voice-entry-pulse {
      0% {
        transform: scale(1);
        opacity: .45
      }

      100% {
        transform: scale(1.16);
        opacity: 0
      }
    }

    .ce-voice-entry svg {
      flex-shrink: 0;
      color: var(--accent-text);
    }

    .ce-voice-entry-label {
      letter-spacing: .02em
    }

    .ce-voice-entry-tag {
      display: inline-block;
      padding: 2px 7px;
      font-size: 9px;
      font-weight: 800;
      letter-spacing: .15em;
      text-transform: uppercase;
      color: #fff;
      background: var(--accent-bright);
      border-radius: 999px;
      box-shadow: 0 0 10px var(--accent-bright);
    }

    /* Field tag — the tiny "voice argue" badge beside the ElevenLabs
   label in settings, so users see why they're being asked for it. */
    .ce-field-tag {
      display: inline-block;
      padding: 2px 8px;
      margin-left: 8px;
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .10em;
      text-transform: uppercase;
      color: var(--accent-text);
      background: var(--active-tint);
      border: 1px solid var(--lg-stroke-hi);
      border-radius: 999px;
      vertical-align: middle;
    }

    /* ----------------------------------------------------------------
   TIER POPOVER — anchored briefly above Standard / Pro on click.
   Shows the three contestant models that will run at that tier so
   the user gets immediate visual confirmation of what's happening.
   Same liquid-glass anatomy as the rest of the app + a small
   downward caret to signal "this connects to that button". Auto-
   dismisses after a couple of seconds, or on click-outside / Esc.
   ---------------------------------------------------------------- */
    .ce-tier-popover {
      /* b.395 — Clean glass recipe — single white wash + strong blur +
     saturate + brightness uplift, NO white-wash gradient on top.
     The b.390 recipe layered three white surfaces (gradient + var
     --lg-fill + var --lg-shadow inset highlights), which masked the
     real backdrop colour and produced a milky card. Real glass takes
     its colour from the blur, not from a layer on top. */
      position: fixed;
      z-index: 120;
      padding: 14px 16px;
      background: rgba(255, 255, 255, .08);
      border: 1px solid rgba(255, 255, 255, .22);
      -webkit-backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      border-radius: 18px;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .30) inset,
        0 -1px 0 rgba(0, 0, 0, .12) inset,
        0 24px 60px -12px rgba(0, 0, 0, .55);
      font-family: var(--font-ui);
      min-width: 240px;
      max-width: 300px;
      opacity: 0;
      transform: translateY(6px) scale(.96);
      transform-origin: bottom center;
      transition: opacity .22s var(--ease-out), transform .22s var(--ease-out);
      pointer-events: none;
    }

    .ce-tier-popover.open {
      opacity: 1;
      transform: translateY(0) scale(1);
      pointer-events: auto;
    }

    .ce-tp-eyebrow {
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .08em;
      text-transform: uppercase;
      color: var(--text-faint);
      display: flex;
      align-items: center;
      gap: 7px;
      margin-bottom: 11px;
    }

    .ce-tp-eyebrow::before {
      content: '';
      width: 6px;
      height: 6px;
      border-radius: 50%;
      background: var(--accent-bright);
      box-shadow: 0 0 10px var(--accent-bright);
      animation: ce-pulse 1.4s var(--ease) infinite;
    }

    .ce-tp-list {
      list-style: none;
      padding: 0;
      margin: 0;
      display: flex;
      flex-direction: column;
      gap: 9px;
    }

    .ce-tp-list li {
      display: flex;
      align-items: center;
      gap: 11px;
      font-size: 13px;
      font-weight: 600;
      color: var(--text);
    }

    .ce-tp-dot {
      width: 9px;
      height: 9px;
      border-radius: 50%;
      flex-shrink: 0;
    }

    .ce-tp-dot.gpt {
      background: #10a37f;
      box-shadow: 0 0 10px rgba(16, 163, 127, .55)
    }

    .ce-tp-dot.claude {
      background: #cc7c5e;
      box-shadow: 0 0 10px rgba(204, 124, 94, .55)
    }

    .ce-tp-dot.gemini {
      background: #8a7eef;
      box-shadow: 0 0 10px rgba(138, 126, 239, .55)
    }

    .ce-tp-name {
      font-weight: 700;
      flex: 1
    }

    .ce-tp-variant {
      font-weight: 500;
      font-size: 11px;
      color: var(--text-muted);
      background: var(--lg-fill);
      padding: 3px 9px;
      border-radius: 999px;
      border: 1px solid var(--lg-stroke);
      letter-spacing: .01em;
    }

    /* Downward caret — same glass treatment so the popover reads as
   a single tear-drop pointing at its anchor button. */
    .ce-tp-caret {
      position: absolute;
      bottom: -7px;
      left: 50%;
      transform: translateX(-50%) rotate(45deg);
      width: 13px;
      height: 13px;
      background: var(--lg-fill);
      border-right: 1.5px solid var(--lg-stroke-hi);
      border-bottom: 1.5px solid var(--lg-stroke-hi);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
    }

    /* ----------------------------------------------------------------
   JUDGE TRIGGER PILL — single dropdown-style button that replaces
   the inline three-pill judge selector. Shows the current judge +
   tier-locked variant + a downward caret. Clicking opens the
   judge popover (built atop .ce-tier-popover) where the user
   picks a different judge.
   ---------------------------------------------------------------- */
    .ce-judge-trigger {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      padding: 5px 12px 5px 14px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      border-radius: 999px;
      font-family: var(--font-ui);
      font-size: 11.5px;
      color: var(--text);
      cursor: pointer;
      transition: all .2s var(--ease);
    }

    .ce-judge-trigger:hover {
      background: var(--lg-fill-hover)
    }

    .ce-judge-trigger.open {
      background: var(--lg-fill-active);
      border-color: var(--lg-stroke-hi);
    }

    .ce-jt-label {
      font-size: 11px;
      font-weight: 600;
      color: var(--text-faint);
      padding-right: 10px;
      border-right: 1px solid var(--lg-stroke);
      letter-spacing: .01em;
    }

    .ce-jt-current {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      font-weight: 600;
    }

    .ce-jt-current .ce-model-dot {
      width: 8px;
      height: 8px;
      border-radius: 50%;
      flex-shrink: 0;
    }

    .ce-jt-current[data-model="gpt"] .ce-model-dot {
      background: #10a37f
    }

    .ce-jt-current[data-model="claude"] .ce-model-dot {
      background: #cc7c5e
    }

    .ce-jt-current[data-model="gemini"] .ce-model-dot {
      background: #8a7eef
    }

    .ce-jt-current .ce-jt-variant {
      font-weight: 500;
      opacity: .72;
    }

    .ce-jt-current .ce-jt-variant::before {
      content: '·';
      margin: 0 5px;
      opacity: .5;
    }

    .ce-jt-caret {
      font-size: 10px;
      color: var(--text-muted);
      transition: transform .25s var(--ease);
      margin-left: 2px;
    }

    .ce-judge-trigger.open .ce-jt-caret {
      transform: rotate(180deg)
    }

    /* ----------------------------------------------------------------
   JUDGE POPOVER — clickable rows that select the judge. Built on
   the .ce-tier-popover base; adds list-row hover + selected
   states for the three judge picks. No auto-dismiss — stays open
   until the user picks or clicks outside / Escape.
   ---------------------------------------------------------------- */
    .ce-judge-popover .ce-tp-list {
      gap: 3px;
    }

    .ce-judge-popover .ce-jp-row {
      display: flex;
      align-items: center;
      gap: 11px;
      padding: 9px 12px;
      border-radius: 12px;
      cursor: pointer;
      transition: background .15s var(--ease);
      font-size: 13px;
      font-weight: 600;
      color: var(--text);
    }

    .ce-judge-popover .ce-jp-row:hover {
      background: var(--lg-fill-hover)
    }

    .ce-judge-popover .ce-jp-row.on {
      background:
        radial-gradient(120% 100% at 30% 0%, var(--active-tint), transparent 70%),
        var(--lg-fill-active);
    }

    .ce-judge-popover .ce-jp-row[data-disabled="1"] {
      opacity: .45;
      cursor: not-allowed;
    }

    .ce-judge-popover .ce-jp-name {
      font-weight: 700;
      flex: 1
    }

    .ce-judge-popover .ce-jp-variant {
      font-weight: 500;
      font-size: 11px;
      color: var(--text-muted);
      background: var(--lg-fill);
      padding: 3px 9px;
      border-radius: 999px;
      border: 1px solid var(--lg-stroke);
      letter-spacing: .01em;
    }

    .ce-judge-popover .ce-jp-check {
      width: 14px;
      height: 14px;
      flex-shrink: 0;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      color: var(--accent-text);
      font-weight: 700;
      font-size: 13px;
    }

    .ce-judge-popover .ce-jp-row:not(.on) .ce-jp-check {
      visibility: hidden
    }

    /* Argue mode intensity dial — unified control. The "Intensity"
   label is rendered INSIDE the same pill container as the three
   options, separated by a thin vertical divider, so the whole
   thing reads as one element rather than a label-plus-pill duo. */
    .ce-intensity {
      display: inline-flex;
      align-items: center;
      gap: 2px;
      padding: 3px 3px 3px 12px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      border-radius: 999px;
    }

    .ce-intensity .ce-int-label {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      color: var(--text-faint);
      padding-right: 10px;
      margin-right: 2px;
      border-right: 1px solid var(--lg-stroke);
      white-space: nowrap;
      letter-spacing: .01em;
    }

    .ce-intensity button {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      padding: 5px 10px;
      border-radius: 999px;
      background: transparent;
      border: 0;
      color: var(--text-faint);
      cursor: pointer;
      transition: all .2s var(--ease);
    }

    .ce-intensity button:hover {
      color: var(--text);
      background: var(--lg-fill-hover)
    }

    .ce-intensity button.on {
      background: var(--lg-fill-active);
      color: var(--text);
    }


/* ════════════════════════════════════════════════════════════════════
   SLIDER + CHAT VOICE-MODE/DM/COACH/VM-STRIP — extracted in b.846.
   The "MODERN LIQUID-GLASS SLIDER (b.510)" section header in the
   original file was misleading: only ~26 of the 4066 lines are actual
   slider rules. The bulk is .ce-dm-* (chat direct message / voice call),
   .ce-vm-* (voice mode strip), .ce-coach-* (coach mode), and various
   body[data-ce-mode=*] state rules. All chat-engine-related.

   Slider rules ARE universal — they target generic .ce-vc-dial-input,
   .ce-coach-dial-input, etc. Living in chat.css works since chat.css
   is linked in <head> globally, but ideally they'd move to universal.css
   in a future re-home pass.
   ════════════════════════════════════════════════════════════════════ */

    /* ════════════════════════════════════════════════════════════
   MODERN LIQUID-GLASS SLIDER (b.510) — applies to every slider
   across the app so they share a single visual language.
   ────────────────────────────────────────────────────────────
   Replaces the old circular thumb with a HORIZONTAL RECTANGLE
   thumb (rounded corners) sitting on a thin glass-pill track.
   Targets the existing slider class names so we don't have to
   re-class HTML.
   ════════════════════════════════════════════════════════════ */
    .ce-vc-dial-input,
    .ce-vc-budget-slider,
    .ce-coach-dial-input,
    .ms-tempo-slider,
    .dm-duration-slider,
    input[type="range"].lg-glass-slider {
      -webkit-appearance: none !important;
      appearance: none !important;
      width: 100%;
      /* b.513 — Input is 20px tall (room for the thumb to sit centered).
     The 6px track is drawn by ::-webkit-slider-runnable-track inside
     this container — that way the thumb's vertical position is
     calculated against the visible track, not against the input's
     full height. Eliminates the "thumb floats above track" issue. */
      height: 20px !important;
      background: transparent !important;
      border-radius: 0 !important;
      outline: none !important;
      cursor: pointer;
      padding: 0 !important;
      border: 0 !important;
      box-shadow: none !important;
      vertical-align: middle;
      --val: 0%;
    }

    /* The actual visible track — drawn inside the 20px input. Picks up
   --val to fill bright white behind the thumb. */
    .ce-vc-dial-input::-webkit-slider-runnable-track,
    .ce-vc-budget-slider::-webkit-slider-runnable-track,
    .ce-coach-dial-input::-webkit-slider-runnable-track,
    .ms-tempo-slider::-webkit-slider-runnable-track,
    .dm-duration-slider::-webkit-slider-runnable-track,
    input[type="range"].lg-glass-slider::-webkit-slider-runnable-track {
      -webkit-appearance: none !important;
      appearance: none !important;
      height: 6px !important;
      background:
        linear-gradient(to right,
          rgba(255, 255, 255, .55) 0%,
          rgba(255, 255, 255, .55) var(--val),
          rgba(255, 255, 255, .08) var(--val),
          rgba(255, 255, 255, .08) 100%) !important;
      border-radius: 999px !important;
      border: 0 !important;
      box-shadow:
        inset 0 1px 0 rgba(0, 0, 0, .18),
        inset 0 -1px 0 rgba(255, 255, 255, .06) !important;
    }

    /* Webkit thumb — horizontal rectangle with curved corners.
   b.518 — Thumb is now nearly opaque (.85 base + heavy blur) so the
   track behind it can't bleed through. The shimmer band is still
   present but rides on top of an opaque cap. */
    @keyframes lg-thumb-sheen {
      0% {
        background-position: 200% 0;
      }

      100% {
        background-position: -200% 0;
      }
    }

    .ce-vc-dial-input::-webkit-slider-thumb,
    .ce-vc-budget-slider::-webkit-slider-thumb,
    .ce-coach-dial-input::-webkit-slider-thumb,
    .ms-tempo-slider::-webkit-slider-thumb,
    .dm-duration-slider::-webkit-slider-thumb,
    input[type="range"].lg-glass-slider::-webkit-slider-thumb {
      -webkit-appearance: none !important;
      appearance: none !important;
      width: 28px !important;
      height: 18px !important;
      border-radius: 6px !important;
      /* Layered background: a NEARLY OPAQUE white base (.85) so the
     track behind the thumb can't be seen through it, with a
     shimmering brighter band animating left→right on top. */
      background:
        linear-gradient(110deg,
          rgba(255, 255, 255, 0) 0%,
          rgba(255, 255, 255, 0) 35%,
          rgba(255, 255, 255, .60) 50%,
          rgba(255, 255, 255, 0) 65%,
          rgba(255, 255, 255, 0) 100%) 0 0 / 220% 100% no-repeat,
        rgba(255, 255, 255, .85) !important;
      background-color: rgba(255, 255, 255, .85) !important;
      background-repeat: no-repeat !important;
      border: 1px solid rgba(255, 255, 255, .85) !important;
      -webkit-backdrop-filter: blur(40px) saturate(1.8) !important;
      backdrop-filter: blur(40px) saturate(1.8) !important;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .70) inset,
        0 -1px 0 rgba(0, 0, 0, .20) inset,
        0 4px 14px -4px rgba(0, 0, 0, .45) !important;
      cursor: grab;
      transition: transform .12s var(--ease), border-color .15s var(--ease);
      margin-top: -7px;
      /* center 20px thumb (18 + 2 border) on 6px track */
      animation: lg-thumb-sheen 3.4s linear infinite;
    }

    .ce-vc-dial-input::-webkit-slider-thumb:hover,
    .ce-vc-budget-slider::-webkit-slider-thumb:hover,
    .ce-coach-dial-input::-webkit-slider-thumb:hover,
    .ms-tempo-slider::-webkit-slider-thumb:hover,
    .dm-duration-slider::-webkit-slider-thumb:hover,
    input[type="range"].lg-glass-slider::-webkit-slider-thumb:hover {
      background: rgba(255, 255, 255, .28) !important;
      border-color: rgba(255, 255, 255, .85) !important;
      transform: scaleX(1.08) scaleY(1.05);
    }

    .ce-vc-dial-input::-webkit-slider-thumb:active,
    .ce-vc-budget-slider::-webkit-slider-thumb:active,
    .ce-coach-dial-input::-webkit-slider-thumb:active,
    .ms-tempo-slider::-webkit-slider-thumb:active,
    .dm-duration-slider::-webkit-slider-thumb:active,
    input[type="range"].lg-glass-slider::-webkit-slider-thumb:active {
      cursor: grabbing;
      transform: scaleX(1.04) scaleY(1.02);
    }

    /* Firefox track + thumb mirror. */
    .ce-vc-dial-input::-moz-range-track,
    .ce-vc-budget-slider::-moz-range-track,
    .ce-coach-dial-input::-moz-range-track,
    .ms-tempo-slider::-moz-range-track,
    .dm-duration-slider::-moz-range-track,
    input[type="range"].lg-glass-slider::-moz-range-track {
      height: 6px !important;
      background: rgba(255, 255, 255, .08) !important;
      border-radius: 999px !important;
      border: 0 !important;
    }

    .ce-vc-dial-input::-moz-range-thumb,
    .ce-vc-budget-slider::-moz-range-thumb,
    .ce-coach-dial-input::-moz-range-thumb,
    .ms-tempo-slider::-moz-range-thumb,
    .dm-duration-slider::-moz-range-thumb,
    input[type="range"].lg-glass-slider::-moz-range-thumb {
      width: 28px !important;
      height: 18px !important;
      border-radius: 6px !important;
      background: rgba(255, 255, 255, .18) !important;
      border: 1px solid rgba(255, 255, 255, .55) !important;
      -webkit-backdrop-filter: blur(20px) saturate(1.5) !important;
      backdrop-filter: blur(20px) saturate(1.5) !important;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .40) inset,
        0 -1px 0 rgba(0, 0, 0, .18) inset,
        0 4px 14px -4px rgba(0, 0, 0, .45) !important;
      cursor: grab;
    }

    /* === CHAT ENGINE CSS START === */
    /* All chat-engine styles use the .ce- prefix to guarantee zero
   collision with existing classes (.dm-, .story-, .modes-, .tab-,
   .tile-, .input-, .bal-, .auth-). Drops cleanly into production
   index.html without affecting any other surface. */

    .main {
      position: relative;
      z-index: 5;
      height: calc(100vh - 64px);
      display: flex;
      flex-direction: column;
      padding: 0 22px 22px;
      overflow: hidden;
    }

    .ce-stage {
      flex: 1;
      display: flex;
      flex-direction: column;
      align-items: stretch;
      min-height: 0;
      max-width: 1080px;
      width: 100%;
      margin: 0 auto;
      padding-top: 18px;
      gap: 18px;
    }

    /* Three-way mode selector — compact, lives in the meta row above
   the input, right-aligned beside the model pills. Smaller padding
   and font than the original full-width version, but keeps the
   same liquid-glass active treatment so it reads as a peer of the
   model pills rather than a heavier UI element. */
    .ce-mode-selector {
      /* 2026-05-11 b.251 — unified segmented-wrapper recipe. Matches the
     VS IMAGE/VIDEO wrapper exactly (b.251 revision below) so the
     two surfaces' connected segmented switches read as identical
     UI elements. Light .06 wash, 22px blur with brightness, .22
     border. */
      display: inline-flex;
      align-items: center;
      gap: 3px;
      padding: 3px;
      background: rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .22);
      -webkit-backdrop-filter: blur(22px) saturate(1.30) brightness(1.04);
      backdrop-filter: blur(22px) saturate(1.30) brightness(1.04);
      border-radius: 999px;
      box-shadow: 0 1px 0 rgba(255, 255, 255, .10) inset;
    }

    .ce-mode-btn {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 6px 12px;
      border-radius: 999px;
      background: transparent;
      border: 0;
      font-family: var(--font-ui);
      font-size: 12px;
      font-weight: 600;
      letter-spacing: .01em;
      color: var(--text-muted);
      cursor: pointer;
      transition: all .2s var(--ease);
      position: relative;
      white-space: nowrap;
    }

    .ce-mode-btn:hover {
      color: var(--text);
      background: var(--lg-fill-hover);
    }

    /* SELECTED MODE PILL — 2026-05-11 b.250 — UNIFIED ACTIVE-STATE
   RECIPE. The Music Studio look (thin white outline on dark glass,
   no inset halo, no outer glow) is the design-system reference.
   Was: bright inset + outer glow that read as a halo and made the
   Chat surface feel louder than Music. Now: just the border + the
   shared glass fill, identical to the segmented controls in VS and
   the SLOW/MEDIUM/FAST switch in MS. */
    .ce-mode-btn.on {
      color: var(--text);
      background: var(--lg-fill-hover);
      border: 1.5px solid rgba(255, 255, 255, .55);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: none;
      padding: 4.5px 10.5px;
    }

    .ce-mode-btn .ce-mb-ico {
      display: inline-flex;
      align-items: center;
      justify-content: center;
      width: 12px;
      height: 12px;
    }

    .ce-mode-btn .ce-mb-ico svg {
      width: 12px;
      height: 12px
    }

    /* Conversation thread */
    .ce-thread {
      flex: 1;
      overflow-y: auto;
      display: flex;
      flex-direction: column;
      gap: 18px;
      padding: 8px 4px 8px 4px;
      scrollbar-width: thin;
      scrollbar-color: var(--lg-stroke) transparent;
    }

    .ce-thread::-webkit-scrollbar {
      width: 6px
    }

    .ce-thread::-webkit-scrollbar-thumb {
      background: var(--lg-stroke);
      border-radius: 3px
    }

    .ce-msg {
      display: flex;
      flex-direction: column;
      max-width: 78%;
      font-family: var(--font-body);
    }

    .ce-msg-user {
      align-self: flex-end;
      align-items: flex-end;
    }

    .ce-msg-ai {
      align-self: flex-start;
      align-items: flex-start;
    }

    .ce-msg-bubble {
      padding: 14px 18px;
      border-radius: var(--r-lg);
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: var(--lg-shadow);
      font-size: 14.5px;
      line-height: 1.55;
      color: var(--text);
      word-wrap: break-word;
    }

    /* ----------------------------------------------------------------
   MARKDOWN RENDERING — applied inside chat bubbles, debate panels,
   synthesis verdict, and inline transcript voices. Tuned to feel
   native to the liquid-glass aesthetic: subdued headings, soft
   inset code blocks, tight bullet spacing.
   ---------------------------------------------------------------- */
    .ce-md-p {
      margin: 0 0 .65em
    }

    .ce-md-p:last-child {
      margin-bottom: 0
    }

    .ce-md-h {
      font-family: var(--font-display);
      font-weight: 700;
      line-height: 1.3;
      margin: .85em 0 .3em;
      color: var(--text);
    }

    .ce-md-h:first-child {
      margin-top: 0
    }

    .ce-md-h1 {
      font-size: 1.25em;
      letter-spacing: -.005em
    }

    .ce-md-h2 {
      font-size: 1.12em
    }

    .ce-md-h3 {
      font-size: 1.04em
    }

    .ce-md-ul {
      margin: .4em 0 .65em;
      padding-left: 1.4em;
      list-style: disc;
    }

    .ce-md-ul li {
      margin: .18em 0
    }

    .ce-md-ul ul {
      list-style: circle;
      margin: .2em 0
    }

    .ce-md-pre {
      margin: .6em 0;
      padding: 11px 14px;
      background: rgba(0, 0, 0, .32);
      border: 1px solid var(--lg-stroke);
      border-radius: 10px;
      overflow-x: auto;
      font-family: ui-monospace, "SF Mono", Menlo, Consolas, monospace;
      font-size: .88em;
      line-height: 1.5;
      white-space: pre;
    }

    .ce-md-pre code {
      background: none;
      padding: 0;
      border: 0
    }

    .ce-md-code {
      font-family: ui-monospace, "SF Mono", Menlo, Consolas, monospace;
      font-size: .92em;
      background: rgba(0, 0, 0, .28);
      padding: 1.5px 6px;
      border-radius: 5px;
      border: 1px solid var(--lg-stroke);
    }

    .ce-md-h+.ce-md-p,
    .ce-md-h+.ce-md-ul {
      margin-top: 0
    }

    /* Confidence dot trios — appear inline beside factual claims in
   the verdict. Three tiers: HIGH = all voices agreed (theme accent
   bright), MED = partial agreement (amber), LOW = single voice
   (muted). Hover for an explanatory tooltip. */
    .ce-conf {
      display: inline-block;
      font-size: .78em;
      margin-left: 6px;
      letter-spacing: 0;
      vertical-align: 1px;
      cursor: help;
      font-family: ui-monospace, "SF Mono", Menlo, Consolas, monospace;
    }

    .ce-conf-high {
      color: var(--accent-bright)
    }

    .ce-conf-med {
      color: #ffc266
    }

    .ce-conf-low {
      color: var(--text-faint)
    }

    .ce-msg-user .ce-msg-bubble {
      background:
        radial-gradient(120% 100% at 30% 0%, var(--active-tint), transparent 70%),
        var(--lg-fill-hover);
      border: 1.5px solid var(--lg-stroke-hi);
    }

    .ce-msg-meta {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      color: var(--text-faint);
      margin-top: 6px;
      display: flex;
      align-items: center;
      gap: 8px;
      letter-spacing: .02em;
    }

    .ce-meta-left {
      display: inline-flex;
      align-items: center;
      gap: 6px;
    }

    /* Copy button on AI replies — right-aligned in the meta row, quiet
   by default, brightens on hover. Switches label + colour briefly
   on successful copy as immediate feedback. */
    .ce-msg-copy {
      margin-left: auto;
      display: inline-flex;
      align-items: center;
      gap: 5px;
      padding: 3px 9px;
      background: transparent;
      border: 1px solid var(--lg-stroke);
      border-radius: 999px;
      color: var(--text-muted);
      font-family: var(--font-ui);
      font-size: 10.5px;
      font-weight: 600;
      letter-spacing: .04em;
      cursor: pointer;
      opacity: 0;
      transition: opacity .15s var(--ease), color .15s var(--ease), border-color .15s var(--ease), background .15s var(--ease);
    }

    .ce-msg-ai:hover .ce-msg-copy {
      opacity: .85
    }

    .ce-msg-copy:hover {
      opacity: 1;
      color: var(--text);
      border-color: var(--lg-stroke-hi);
      background: var(--lg-fill-hover);
    }

    .ce-msg-copy.is-copied {
      opacity: 1;
      color: var(--accent-text);
      border-color: var(--accent-bright);
      background: var(--active-tint);
    }

    .ce-msg-meta .ce-meta-dot {
      width: 5px;
      height: 5px;
      border-radius: 50%;
      background: var(--active-glow);
    }

    /* Debate transcript collapsible */
    .ce-debate-block {
      display: flex;
      flex-direction: column;
      gap: 10px;
      max-width: 78%;
      align-self: flex-start;
    }

    .ce-debate-summary {
      padding: 14px 18px;
      border-radius: var(--r-lg);
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: var(--lg-shadow);
      font-size: 14.5px;
      line-height: 1.55;
      white-space: pre-wrap;
    }

    .ce-debate-toggle {
      align-self: flex-start;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      letter-spacing: .04em;
      text-transform: uppercase;
      padding: 6px 12px;
      border-radius: 999px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      color: var(--text-muted);
      cursor: pointer;
      transition: all .2s var(--ease);
    }

    .ce-debate-toggle:hover {
      color: var(--text);
      background: var(--lg-fill-hover)
    }

    .ce-debate-transcript {
      display: none;
      flex-direction: column;
      gap: 10px;
      padding-left: 0;
    }

    .ce-debate-transcript.open {
      display: flex
    }

    .ce-debate-voice {
      padding: 12px 16px;
      border-radius: var(--r-md);
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      font-size: 13.5px;
      line-height: 1.5;
      white-space: pre-wrap;
    }

    .ce-debate-voice-label {
      font-family: var(--font-ui);
      font-size: 10.5px;
      font-weight: 700;
      letter-spacing: .08em;
      text-transform: uppercase;
      color: var(--text-faint);
      margin-bottom: 6px;
      display: flex;
      align-items: center;
      gap: 6px;
    }

    .ce-debate-voice-label .ce-vl-dot {
      width: 7px;
      height: 7px;
      border-radius: 50%;
    }

    .ce-vl-dot.gpt {
      background: #10a37f
    }

    .ce-vl-dot.claude {
      background: #cc7c5e
    }

    .ce-vl-dot.gemini {
      background: #8a7eef
    }

    /* Welcome / empty state */
    .ce-welcome {
      flex: 1;
      display: flex;
      flex-direction: column;
      align-items: center;
      justify-content: center;
      text-align: center;
      gap: 16px;
      padding: 40px 20px;
      /* b.188 — welcome auto-fades 5s after the chat surface mounts.
     Transition runs on opacity + transform; height is collapsed via
     max-height so the input bar can drift up into the freed space. */
      transition: opacity .6s var(--ease, ease), transform .6s var(--ease, ease), max-height .6s var(--ease, ease), padding .6s var(--ease, ease);
      max-height: 1000px;
      overflow: hidden;
    }

    .ce-welcome.is-fading {
      opacity: 0;
      transform: translateY(-8px) scale(.985);
      max-height: 0;
      padding-top: 0;
      padding-bottom: 0;
      pointer-events: none;
    }

    /* b.188 — Liquid-glass capsule around the headline + supporting copy
   so the floating text reads cleanly against video / image themes
   instead of fighting the background for legibility. */
    .ce-welcome-card {
      display: flex;
      flex-direction: column;
      align-items: center;
      justify-content: center;
      gap: 14px;
      padding: 26px 32px;
      border-radius: 24px;
      max-width: 640px;
      background: var(--lg-fill, rgba(255, 255, 255, .08));
      border: 1px solid var(--lg-stroke, rgba(255, 255, 255, .14));
      -webkit-backdrop-filter: var(--lg-blur, blur(18px) saturate(1.4));
      backdrop-filter: var(--lg-blur, blur(18px) saturate(1.4));
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .10) inset,
        0 -1px 0 rgba(0, 0, 0, .18) inset,
        0 18px 50px -18px rgba(0, 0, 0, .55);
    }

    .ce-welcome h1 {
      font-family: var(--font-display);
      font-size: 34px;
      font-weight: 700;
      letter-spacing: -.02em;
      color: var(--text);
      margin: 0;
    }

    .ce-welcome h1 em {
      font-style: normal;
      font-weight: 500;
      background: linear-gradient(120deg, var(--accent-bright), var(--accent-text));
      -webkit-background-clip: text;
      background-clip: text;
      color: transparent;
    }

    .ce-welcome p {
      font-size: 15px;
      color: var(--text-muted);
      max-width: 520px;
      line-height: 1.6;
      margin: 0;
    }

    .ce-welcome-hints {
      display: flex;
      flex-wrap: wrap;
      gap: 8px;
      justify-content: center;
      margin-top: 12px;
    }

    .ce-welcome-hint {
      font-family: var(--font-ui);
      font-size: 12px;
      padding: 8px 14px;
      border-radius: 999px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      color: var(--text-muted);
      cursor: pointer;
      transition: all .2s var(--ease);
    }

    .ce-welcome-hint:hover {
      color: var(--text);
      background: var(--lg-fill-hover);
    }

    /* Input bar — same liquid-glass anatomy as production input-bar */
    .ce-inputbar {
      display: flex;
      flex-direction: column;
      gap: 5px;
      width: 100%;
    }

    /* b.330 — Inline Voice Mode strip. Replaces the textarea row when
   Voice Mode is active. Same liquid-glass treatment as .ce-input-row
   so the swap is visually consistent. When `.ce-inputbar[data-vm="on"]`
   we hide `.ce-input-row` and the meta row above, leaving only the
   strip + the mode tab bar above the input. */
    .ce-vm-strip {
      /* b.334 — Single 8px gap everywhere so spacing reads as symmetric.
     align-items:center keeps every cell vertically centred regardless
     of its own internal height. The billing note + close button push
     to the right via margin-left:auto on .ce-vm-strip-close. */
      display: flex;
      align-items: center;
      gap: 8px;
      flex-wrap: wrap;
      padding: 8px 8px 8px 12px;
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      border-radius: 22px;
      box-shadow: var(--lg-shadow);
      min-height: 60px;
      row-gap: 6px;
    }

    .ce-vm-strip-orb {
      flex: 0 0 auto;
      width: 36px;
      height: 36px;
      border-radius: 50%;
      display: grid;
      place-items: center;
      background:
        radial-gradient(circle at 30% 30%, rgba(255, 255, 255, .32), rgba(255, 255, 255, .04) 65%),
        rgba(255, 255, 255, .04);
      border: 1.5px solid rgba(255, 255, 255, .42);
      color: #fff;
      transition: background .3s, border-color .3s, box-shadow .3s;
      position: relative;
    }

    .ce-vm-strip-orb svg {
      width: 18px;
      height: 18px;
      opacity: .92;
    }

    .ce-vm-strip[data-state="listening"] .ce-vm-strip-orb {
      background:
        radial-gradient(circle at 30% 30%, rgba(120, 200, 140, .50), rgba(120, 200, 140, .10) 65%),
        rgba(255, 255, 255, .04);
      border-color: rgba(120, 200, 140, .55);
      box-shadow: 0 0 0 0 rgba(120, 200, 140, .4);
      animation: vmStripPulse 2s ease-out infinite;
    }

    .ce-vm-strip[data-state="speaking"] .ce-vm-strip-orb {
      background:
        radial-gradient(circle at 30% 30%, rgba(180, 200, 255, .55), rgba(180, 200, 255, .10) 65%),
        rgba(255, 255, 255, .04);
      border-color: rgba(180, 200, 255, .55);
      animation: vmStripBreathe 1.4s ease-in-out infinite alternate;
    }

    .ce-vm-strip[data-state="connecting"] .ce-vm-strip-orb {
      animation: vmStripBreathe 1.2s ease-in-out infinite alternate;
    }

    @keyframes vmStripPulse {
      0% {
        box-shadow: 0 0 0 0 rgba(120, 200, 140, .5);
      }

      100% {
        box-shadow: 0 0 0 14px rgba(120, 200, 140, 0);
      }
    }

    @keyframes vmStripBreathe {
      0% {
        transform: scale(0.97);
      }

      100% {
        transform: scale(1.04);
      }
    }

    .ce-vm-strip-state {
      /* b.334 — non-growing, no internal padding so the gap is purely
     the strip's 8px gap. Eliminates the extra space the user saw. */
      flex: 0 0 auto;
      display: flex;
      flex-direction: column;
      min-width: 0;
      padding: 0;
    }

    .ce-vm-strip-eyebrow {
      font-size: 9px;
      font-weight: 800;
      letter-spacing: .18em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .55);
    }

    .ce-vm-strip-label {
      font-size: 13px;
      font-weight: 700;
      color: #fff;
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
    }

    /* b.334 — Billing note. Desktop: sits to the right of the Start
   button on the same line. Mobile (≤900px): wraps onto a second
   full-width row inside the strip, still ONE line of text. */
    .ce-vm-strip-note {
      flex: 0 1 auto;
      display: none;
      max-width: 340px;
      font-size: 11.5px;
      line-height: 1.35;
      color: rgba(255, 255, 255, .72);
      font-weight: 500;
      padding-left: 2px;
      white-space: normal;
    }

    .ce-vm-strip[data-state="idle"] .ce-vm-strip-note {
      display: block;
    }

    /* Close pin always floats to the far right of the strip. */
    .ce-vm-strip-close {
      margin-left: auto;
    }

    /* b.590 — Conviction bar (argue voice mode) */
    .ce-vm-strip-conv {
      display: flex;
      align-items: center;
      gap: 6px;
    }

    .ce-vm-strip-conv-track {
      width: 48px;
      height: 4px;
      border-radius: 2px;
      background: rgba(255, 255, 255, .15);
      overflow: hidden;
      flex-shrink: 0;
    }

    .ce-vm-strip-conv-fill {
      height: 100%;
      width: 0%;
      border-radius: 2px;
      background: linear-gradient(90deg, rgba(255, 255, 255, .5), rgba(255, 255, 255, .9));
      transition: width .4s ease;
    }

    [data-theme="day"] .ce-vm-strip-conv-track {
      background: rgba(0, 0, 0, .12);
    }

    [data-theme="day"] .ce-vm-strip-conv-fill {
      background: linear-gradient(90deg, rgba(0, 0, 0, .35), rgba(0, 0, 0, .65));
    }

    @media (max-width: 900px) {

      /* Idle state on mobile: note becomes a full-width second row
     under the controls. Allowed to be one wrapped paragraph since
     screen width forces it to span the whole strip anyway. */
      .ce-vm-strip[data-state="idle"] .ce-vm-strip-note {
        flex-basis: 100%;
        order: 99;
        /* always last in the flex order */
        max-width: none;
        padding: 4px 4px 2px;
        font-size: 11px;
        white-space: normal;
      }
    }

    .ce-vm-strip-persona {
      /* b.333 — non-growing; sits flush next to the state block. */
      position: relative;
      flex: 0 0 auto;
      width: auto;
      max-width: 220px;
    }

    .ce-vm-strip-persona-trigger {
      /* b.333 — auto-width so the pill is just wide enough for the label,
     not stretching to fill a flex column. */
      width: auto;
      display: inline-flex;
      align-items: center;
      justify-content: space-between;
      gap: 6px;
      padding: 7px 12px;
      border-radius: 999px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .02)),
        rgba(255, 255, 255, .04);
      border: 1px solid rgba(255, 255, 255, .22);
      color: #fff;
      font-family: inherit;
      font-size: 12px;
      font-weight: 600;
      letter-spacing: .01em;
      cursor: pointer;
      outline: none;
      transition: background .15s, border-color .15s;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .15) inset,
        0 -1px 0 rgba(0, 0, 0, .18) inset;
    }

    .ce-vm-strip-persona-trigger:hover {
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .16), rgba(255, 255, 255, .04)),
        rgba(255, 255, 255, .07);
      border-color: rgba(255, 255, 255, .36);
    }

    .ce-vm-strip-persona-trigger[aria-expanded="true"] {
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .18), rgba(255, 255, 255, .05)),
        rgba(255, 255, 255, .08);
      border-color: rgba(255, 255, 255, .40);
    }

    .ce-vm-strip-persona-name {
      flex: 1;
      text-align: left;
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
      color: #fff;
    }

    .ce-vm-strip-persona-caret {
      font-size: 9px;
      opacity: .7;
      transition: transform .18s;
    }

    .ce-vm-strip-persona-trigger[aria-expanded="true"] .ce-vm-strip-persona-caret {
      transform: rotate(180deg);
    }

    .ce-vm-strip-persona-menu {
      /* b.337 — Portaled to document.body on first open so the menu sits
     OUTSIDE the already-frosted .ce-vm-strip stacking context. The
     b.336 nested fix relied on a dark scrim because the inner
     backdrop-filter was effectively no-op against a parent that
     already had its own filter. With the menu now in <body>, the
     backdrop-filter sees the real chat background (theme video +
     orbs) directly, so we can use the canonical input-bar recipe:
     var(--lg-fill) + var(--lg-stroke) + var(--lg-blur) +
     var(--lg-shadow). Layered with a soft white wash so contrast
     holds even on bright frames of the theme video. JS computes
     left/top from the trigger's getBoundingClientRect on open. */
      position: fixed;
      z-index: 10001;
      min-width: 280px;
      max-width: 340px;
      padding: 6px;
      border-radius: 22px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .02)),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: var(--lg-shadow);
      max-height: 70vh;
      overflow-y: auto;
    }

    /* b.337 — Voice picker section pinned at the top of the persona
   menu. Renders as a thin sub-block: a label row + a row of voice
   chips. Selecting a voice updates the trigger label and persists
   to localStorage; on next session start, the chosen voice is sent
   to /api/realtime-session as context.voice. */
    .ce-vm-strip-voice-section {
      padding: 8px 8px 10px;
    }

    .ce-vm-strip-section-head {
      display: flex;
      align-items: center;
      justify-content: space-between;
      padding: 0 4px 6px;
      font-size: 9px;
      font-weight: 800;
      letter-spacing: .18em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .55);
    }

    /* b.338 — Voice picker is now a dropdown (trigger + expandable list)
   instead of the b.337 chip row. The trigger sits inline as a single
   wide pill showing the current voice name + dot; tapping expands the
   list below where every option is one row: dot · name · short desc on
   the same line. Selecting an option collapses the list and updates
   the trigger label. */
    .ce-vm-strip-voice-trigger {
      width: 100%;
      display: flex;
      align-items: center;
      gap: 8px;
      padding: 9px 12px;
      border-radius: 12px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .02)),
        rgba(255, 255, 255, .04);
      border: 1px solid rgba(255, 255, 255, .22);
      color: #fff;
      font-family: inherit;
      font-size: 13px;
      font-weight: 600;
      letter-spacing: .01em;
      cursor: pointer;
      outline: none;
      transition: background .15s, border-color .15s;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .15) inset,
        0 -1px 0 rgba(0, 0, 0, .18) inset;
    }

    .ce-vm-strip-voice-trigger:hover {
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .16), rgba(255, 255, 255, .04)),
        rgba(255, 255, 255, .07);
      border-color: rgba(255, 255, 255, .36);
    }

    .ce-vm-strip-voice-trigger[aria-expanded="true"] {
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .18), rgba(255, 255, 255, .05)),
        rgba(255, 255, 255, .08);
      border-color: rgba(255, 255, 255, .40);
    }

    .ce-vm-strip-voice-trigger-dot {
      width: 8px;
      height: 8px;
      border-radius: 50%;
      background: rgba(255, 255, 255, .85);
      flex: 0 0 auto;
    }

    .ce-vm-strip-voice-trigger-name {
      flex: 1 1 auto;
      text-align: left;
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
    }

    .ce-vm-strip-voice-trigger-desc {
      flex: 0 1 auto;
      font-size: 11.5px;
      font-weight: 500;
      color: rgba(255, 255, 255, .55);
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
      max-width: 60%;
    }

    .ce-vm-strip-voice-trigger-caret {
      flex: 0 0 auto;
      font-size: 9px;
      opacity: .7;
      transition: transform .18s;
    }

    .ce-vm-strip-voice-trigger[aria-expanded="true"] .ce-vm-strip-voice-trigger-caret {
      transform: rotate(180deg);
    }

    /* b.341 — Anchor for the voice trigger. Still position:relative for
   tidiness, but the list itself is portaled out to <body> on first
   open (see vmStripPortalVoiceList in JS), so it no longer renders
   inside this anchor at runtime. */
    .ce-vm-strip-voice-anchor {
      position: relative;
    }

    .ce-vm-strip-voice-list {
      /* b.341 — PORTALED to <body>. Same fix the persona menu got in
     b.337: nested backdrop-filter doesn't actually blur — the inner
     filter tries to operate against a parent whose own backdrop-filter
     has already flattened its backdrop into the parent's rendering, so
     content behind bleeds through unblurred (visible in the previous
     screenshot: persona rows showing clearly through the floating
     voice list). By moving the list out to <body>, it sits in a fresh
     stacking context where backdrop-filter operates against the real
     chat background — the persona menu glass and theme video both
     blur correctly. JS sets left/top from the trigger's
     getBoundingClientRect on every open + on resize/scroll. Canonical
     liquid-glass recipe matches the input bar / persona menu so the
     three frosted surfaces read as a single visual language. */
      display: none;
      position: fixed;
      z-index: 10002;
      /* above the parent persona menu (10001) */
      min-width: 280px;
      max-width: 340px;
      padding: 6px;
      border-radius: 16px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .02)),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: var(--lg-shadow);
    }

    .ce-vm-strip-voice-list[data-open="1"] {
      display: flex;
      flex-direction: column;
      gap: 2px;
    }

    .ce-vm-strip-voice-opt {
      display: flex;
      align-items: center;
      gap: 8px;
      width: 100%;
      padding: 8px 10px;
      border-radius: 9px;
      background: transparent;
      border: 0;
      color: #fff;
      font-family: inherit;
      font-size: 13px;
      font-weight: 500;
      text-align: left;
      cursor: pointer;
      transition: background .12s;
    }

    .ce-vm-strip-voice-opt:hover {
      background: rgba(255, 255, 255, .06);
    }

    .ce-vm-strip-voice-opt[data-selected="1"] {
      background: rgba(255, 255, 255, .10);
    }

    .ce-vm-strip-voice-opt-dot {
      width: 8px;
      height: 8px;
      border-radius: 50%;
      background: rgba(255, 255, 255, .85);
      flex: 0 0 auto;
    }

    .ce-vm-strip-voice-opt-name {
      flex: 0 0 auto;
      min-width: 62px;
      font-weight: 600;
    }

    .ce-vm-strip-voice-opt-desc {
      flex: 1 1 auto;
      font-size: 11.5px;
      font-weight: 500;
      color: rgba(255, 255, 255, .60);
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
    }

    .ce-vm-strip-voice-opt[data-selected="1"]::after {
      content: '';
      margin-left: auto;
      width: 13px;
      height: 13px;
      background: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='white' stroke-width='2.6' stroke-linecap='round' stroke-linejoin='round'><polyline points='20 6 9 17 4 12'/></svg>") center/contain no-repeat;
      opacity: .95;
      flex: 0 0 auto;
    }

    /* Voice-specific dot colors — both on trigger and in option list. */
    .ce-vm-strip-voice-trigger[data-voice="default"] .ce-vm-strip-voice-trigger-dot,
    .ce-vm-strip-voice-opt[data-voice="default"] .ce-vm-strip-voice-opt-dot {
      background: rgba(255, 255, 255, .85);
    }

    .ce-vm-strip-voice-trigger[data-voice="alloy"] .ce-vm-strip-voice-trigger-dot,
    .ce-vm-strip-voice-opt[data-voice="alloy"] .ce-vm-strip-voice-opt-dot {
      background: #c8c8d2;
    }

    .ce-vm-strip-voice-trigger[data-voice="echo"] .ce-vm-strip-voice-trigger-dot,
    .ce-vm-strip-voice-opt[data-voice="echo"] .ce-vm-strip-voice-opt-dot {
      background: #7eb3ff;
    }

    .ce-vm-strip-voice-trigger[data-voice="fable"] .ce-vm-strip-voice-trigger-dot,
    .ce-vm-strip-voice-opt[data-voice="fable"] .ce-vm-strip-voice-opt-dot {
      background: #a7e0c4;
    }

    .ce-vm-strip-voice-trigger[data-voice="onyx"] .ce-vm-strip-voice-trigger-dot,
    .ce-vm-strip-voice-opt[data-voice="onyx"] .ce-vm-strip-voice-opt-dot {
      background: #5a5a72;
    }

    .ce-vm-strip-voice-trigger[data-voice="nova"] .ce-vm-strip-voice-trigger-dot,
    .ce-vm-strip-voice-opt[data-voice="nova"] .ce-vm-strip-voice-opt-dot {
      background: #ffb3a7;
    }

    .ce-vm-strip-voice-trigger[data-voice="shimmer"] .ce-vm-strip-voice-trigger-dot,
    .ce-vm-strip-voice-opt[data-voice="shimmer"] .ce-vm-strip-voice-opt-dot {
      background: #e7c4ff;
    }

    .ce-vm-strip-voice-note {
      padding: 6px 4px 0;
      font-size: 10.5px;
      line-height: 1.45;
      color: rgba(255, 255, 255, .55);
    }

    /* b.337 — Divider between Voice and Persona sections. Same hairline
   treatment as .ce-vm-strip-counters borders so the menu reads as a
   unified card with two ordered controls inside. */
    .ce-vm-strip-menu-divider {
      height: 1px;
      margin: 0 4px 6px;
      background: rgba(255, 255, 255, .10);
    }

    .ce-vm-strip-persona-section {
      padding: 2px 0 4px;
    }

    .ce-vm-strip-persona-opt {
      display: flex;
      align-items: center;
      gap: 8px;
      width: 100%;
      padding: 10px 12px;
      border-radius: 12px;
      background: transparent;
      border: 0;
      color: #fff;
      font-family: inherit;
      font-size: 13.5px;
      font-weight: 500;
      text-align: left;
      cursor: pointer;
      transition: background .12s;
    }

    .ce-vm-strip-persona-opt:hover {
      background: rgba(255, 255, 255, .08);
    }

    .ce-vm-strip-persona-opt[data-selected="1"] {
      background: rgba(255, 255, 255, .12);
    }

    .ce-vm-strip-persona-opt[data-selected="1"]::after {
      content: '';
      margin-left: auto;
      width: 14px;
      height: 14px;
      background: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='white' stroke-width='2.4' stroke-linecap='round' stroke-linejoin='round'><polyline points='20 6 9 17 4 12'/></svg>") center/contain no-repeat;
      opacity: .95;
    }

    .ce-vm-strip-counters {
      flex: 0 0 auto;
      display: flex;
      gap: 14px;
      padding: 0 8px;
      border-left: 1px solid rgba(255, 255, 255, .10);
      border-right: 1px solid rgba(255, 255, 255, .10);
    }

    .ce-vm-strip-counter {
      display: flex;
      flex-direction: column;
      align-items: center;
      min-width: 46px;
    }

    .ce-vm-strip-counter-lbl {
      font-size: 9px;
      font-weight: 800;
      letter-spacing: .16em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .55);
    }

    .ce-vm-strip-counter-val {
      font-size: 14px;
      font-weight: 700;
      color: #fff;
      font-variant-numeric: tabular-nums;
    }

    .ce-vm-strip-cta {
      flex: 0 0 auto;
      display: inline-flex;
      align-items: center;
      gap: 8px;
      padding: 10px 18px;
      border-radius: 999px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .16), rgba(255, 255, 255, .04)),
        rgba(255, 255, 255, .05);
      border: 1px solid rgba(255, 255, 255, .30);
      color: #fff;
      font-family: inherit;
      font-size: 12.5px;
      font-weight: 700;
      letter-spacing: .02em;
      cursor: pointer;
      outline: none;
      transition: background .15s, border-color .15s, transform .15s;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .20) inset,
        0 -1px 0 rgba(0, 0, 0, .22) inset,
        0 6px 18px rgba(0, 0, 0, .22);
    }

    .ce-vm-strip-cta:hover {
      transform: translateY(-1px);
      border-color: rgba(255, 255, 255, .44);
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .22), rgba(255, 255, 255, .06)),
        rgba(255, 255, 255, .08);
    }

    .ce-vm-strip-cta:active {
      transform: translateY(0);
    }

    .ce-vm-strip-cta.danger {
      border-color: rgba(229, 138, 138, .42);
      background:
        linear-gradient(180deg, rgba(229, 138, 138, .14), rgba(229, 138, 138, .04)),
        rgba(255, 255, 255, .04);
    }

    .ce-vm-strip-cta.danger:hover {
      border-color: rgba(229, 138, 138, .6);
      background:
        linear-gradient(180deg, rgba(229, 138, 138, .22), rgba(229, 138, 138, .06)),
        rgba(255, 255, 255, .06);
    }

    .ce-vm-strip-cta-cost {
      display: inline-flex;
      align-items: center;
      gap: 3px;
      padding-left: 10px;
      border-left: 1px solid rgba(255, 255, 255, .22);
      font-weight: 700;
    }

    .ce-vm-strip-cta-cost .joy-coin {
      width: 1em;
      height: 1em;
    }

    .ce-vm-strip-close {
      flex: 0 0 auto;
      width: 32px;
      height: 32px;
      border-radius: 50%;
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .18);
      color: #fff;
      cursor: pointer;
      outline: none;
      display: grid;
      place-items: center;
      transition: background .15s, border-color .15s;
    }

    .ce-vm-strip-close:hover {
      background: rgba(255, 255, 255, .06);
      border-color: rgba(255, 255, 255, .32);
    }

    .ce-vm-strip-close svg {
      width: 14px;
      height: 14px;
    }

    /* Swap: when voice mode is active, hide the textarea row + the meta
   row (mode pills, model pills, history) so the strip stands alone
   in the bar slot. The chat-mode tabs above the input STAY visible
   (they live on a separate row) so the user can still see they're
   in chat mode. */
    .ce-inputbar[data-vm="on"] .ce-input-row,
    .ce-inputbar[data-vm="on"] .ce-input-meta,
    .ce-inputbar[data-vm="on"] .ce-file-row {
      display: none !important;
    }

    /* b.625 — belt-and-suspenders: body.vm-active is set by openVoiceMode()
   before vmStripMount(), so this fires even if dataset.vm propagation lags */
    body.vm-active .ce-input-row,
    body.vm-active .ce-input-meta,
    body.vm-active .ce-file-row {
      display: none !important;
    }

    /* b.334 — Mobile: compact every control, push Start to the far
   right of the top row, drop the billing note onto a second row. */
    @media (max-width: 720px) {
      .ce-vm-strip {
        gap: 6px;
        padding: 8px 8px 6px 10px;
      }

      /* The Start CTA gets margin-left:auto so it floats to the right
     edge of the top row while everything else hugs the mic. The
     close button (its own margin-left:auto rule) ends up after it. */
      .ce-vm-strip-cta {
        margin-left: auto;
        padding: 8px 14px;
        font-size: 12px;
        gap: 6px;
      }

      /* Mobile Start button: shorter label, no "session" word — just
     "Start" + the coin cost. */
      .ce-vm-strip-cta#ceVmStripStart>span:first-child::after {
        content: '';
      }

      .ce-vm-strip-cta-cost {
        padding-left: 6px;
      }

      /* Tighter persona pill so it sits flush with the state block. */
      .ce-vm-strip-persona-trigger {
        padding: 6px 10px;
        font-size: 11.5px;
      }

      .ce-vm-strip-persona-name {
        max-width: 120px;
      }

      /* Smaller counters, no dividers — they were noisy on small screens. */
      .ce-vm-strip-counters {
        padding: 0 4px;
        gap: 8px;
        border: 0;
      }

      .ce-vm-strip-counter-val {
        font-size: 13px;
      }

      .ce-vm-strip-counter-lbl {
        font-size: 8.5px;
      }

      /* Smaller orb so it doesn't dominate. */
      .ce-vm-strip-orb {
        width: 32px;
        height: 32px;
      }

      .ce-vm-strip-orb svg {
        width: 16px;
        height: 16px;
      }

      /* State block stays compact. */
      .ce-vm-strip-state {
        min-width: 0;
      }

      .ce-vm-strip-state .ce-vm-strip-label {
        font-size: 12px;
      }

      .ce-vm-strip-state .ce-vm-strip-eyebrow {
        font-size: 8.5px;
      }

      /* Close pin sits to the far right after the CTA. */
      .ce-vm-strip-close {
        width: 28px;
        height: 28px;
      }
    }

    /* Tiny phones — drop the counters' label row entirely and shrink
   the persona name to keep one line. */
    @media (max-width: 480px) {
      .ce-vm-strip-counter-lbl {
        display: none;
      }

      .ce-vm-strip-persona-name {
        max-width: 80px;
      }

      .ce-vm-strip-counters {
        padding: 0 2px;
      }
    }

    /* Shorter Start label on mobile — "Start" not "Start session". */
    @media (max-width: 720px) {
      .ce-vm-strip-cta#ceVmStripStart>span:first-child {
        font-size: 0;
        line-height: 0;
      }

      .ce-vm-strip-cta#ceVmStripStart>span:first-child::before {
        content: 'Start';
        font-size: 12px;
        line-height: normal;
      }
    }

    .ce-input-row {
      /* b.210 — switched from align-items:flex-end (which let the
     textarea creep above the top border when single-line because
     it's taller than the 36px tool icons) to flex-end-anchored-but-
     centred-when-short. The flex now uses `align-items: center` so
     a one-line textarea aligns vertically with the icons; when the
     textarea grows (multi-line) it stretches downward and the
     icons stay anchored at the bottom via their own align-self. */
      display: flex;
      align-items: center;
      gap: 10px;
      padding: 3px 10px 3px 14px;
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      border-radius: 24px;
      box-shadow: var(--lg-shadow);
    }

    /* b.813 — REVERTED to canonical `align-self: flex-end` (original behavior
       since b.210). The b.792 change to `align-self: center` was unconditional
       (outside any @media block) and BLED INTO MOBILE, breaking the mobile
       layout. Desktop's `center` requirement is now correctly handled by
       styles/chat.css (linked LAST in <head>, extracted in b.840) which
       wins via cascade order. Mobile keeps the original flex-end behavior
       so the send button stays anchored to the bottom when textarea grows
       past one line. */
    .ce-input-row .ce-input-tools,
    .ce-input-row .ce-send-btn {
      align-self: flex-end;
    }

    .ce-input-row:focus-within {
      /* 2026-05-11 b.250 — unified focus state. Was a bright multi-layer
     inset + colored glow that lit up the bar like neon. Now matches
     the toned focus on the VS/MS input rows: brighter rim, one faint
     inner highlight, no outer glow. */
      border-color: rgba(255, 255, 255, 0.40);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .10) inset,
        0 0 0 1px rgba(255, 255, 255, .06) inset,
        0 24px 60px -22px rgba(0, 0, 0, .65);
    }

    .ce-input-tools {
      display: flex;
      align-items: center;
      gap: 6px;
      padding: 4px 0;
    }

    .ce-tool-btn {
      width: 36px;
      height: 36px;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      border-radius: 999px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      color: var(--text-muted);
      cursor: pointer;
      transition: all .2s var(--ease);
      position: relative;
    }

    .ce-tool-btn:hover {
      color: var(--text);
      background: var(--lg-fill-hover)
    }

    /* Icon sized to 17px so the refined Lucide-style paths breathe inside
   the 36px circle without dominating it. Pairs with the 1.6 stroke
   weight for a crisp, premium look at desktop sizes. */
    .ce-tool-btn svg {
      width: 17px;
      height: 17px
    }

    /* File button — white glow when files are attached (matches skill btn) */
    #ceFileBtn.is-on {
      color: var(--text);
      background: rgba(255, 255, 255, .22);
      border-color: rgba(255, 255, 255, .38);
      box-shadow: 0 0 0 2px rgba(255, 255, 255, .10);
    }

    /* Web-search toggle — white glow when search is armed (matches skill/file btns) */

    /* ── SKILLS SYSTEM b.611 ────────────────────────────────────────────
   ce-skill-toggle-btn  zap circle; inherits ce-tool-btn
   ce-input-tools.skill-mode  hides all regular buttons + toggle
   ce-skill-mode-row  inline flex row: Add Skill pill + chip + params + exit
   ce-skill-popup / ce-param-popup  position:fixed via JS, body-appended
   ─────────────────────────────────────────────────────────────────── */

    /* Zap toggle lit when skill mode is on */
    .ce-skill-toggle-btn.skill-mode-on {
      color: var(--text);
      background: rgba(255, 255, 255, .22);
      border-color: rgba(255, 255, 255, .38);
      box-shadow: 0 0 0 2px rgba(255, 255, 255, .10);
    }

    /* b.618 — hard-guarantee the skill button is always interactive */
    #ceSkillBtn {
      pointer-events: auto !important;
      position: relative !important;
      z-index: 9999 !important;
      cursor: pointer !important;
    }

    /* Hide ALL regular tool buttons + the toggle itself inside skill mode */
    /* b.632 — skill mode: toolbar AND the meta row (mode tabs + model pills)
   both vanish; only the skill-mode-row strip + textarea remain */
    .ce-inputbar.skill-mode .ce-tool-btn:not(#ceSkillBtn),
    .ce-inputbar.skill-mode .ce-input-meta,
    .ce-inputbar.skill-mode .ce-file-row {
      display: none !important;
    }

    /* Inline skill mode row */
    .ce-skill-mode-row {
      display: flex;
      align-items: center;
      gap: 8px;
      padding: 2px 2px;
      min-height: 40px;
    }

    /* "Add Skill" frosted glass pill */
    .ce-add-skill-btn {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      height: 30px;
      padding: 0 12px 0 9px;
      border-radius: 999px;
      border: 1px solid rgba(255, 255, 255, .18);
      background: rgba(255, 255, 255, .09);
      color: var(--text);
      font-size: 12.5px;
      white-space: nowrap;
      cursor: pointer;
      backdrop-filter: blur(14px) saturate(1.3);
      -webkit-backdrop-filter: blur(14px) saturate(1.3);
      transition: background .15s;
    }

    .ce-add-skill-btn:hover {
      background: rgba(255, 255, 255, .16);
    }

    .ce-add-skill-btn svg {
      width: 12px;
      height: 12px;
      flex-shrink: 0;
    }

    /* Skill picker popup — position:fixed set in JS, appended to body */
    .ce-skill-popup {
      width: 242px;
      max-height: 340px;
      overflow-y: auto;
      background: rgba(255, 255, 255, .09);
      border: 1px solid rgba(255, 255, 255, .22);
      border-radius: 20px;
      padding: 8px;
      z-index: 9900;
      backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      -webkit-backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .45) inset,
        0 -1px 0 rgba(255, 255, 255, .10) inset,
        0 0 0 1px rgba(255, 255, 255, .06) inset,
        0 24px 64px rgba(0, 0, 0, .55),
        0 4px 20px rgba(0, 0, 0, .35);
    }

    /* Liquid-glass scrollbar for skill list */
    .ce-skill-popup::-webkit-scrollbar {
      width: 4px;
    }

    .ce-skill-popup::-webkit-scrollbar-track {
      background: transparent;
    }

    .ce-skill-popup::-webkit-scrollbar-thumb {
      background: rgba(255, 255, 255, .18);
      border-radius: 9px;
    }

    .ce-skill-search {
      display: block;
      width: 100%;
      background: rgba(255, 255, 255, .07);
      border: 1px solid rgba(255, 255, 255, .16);
      border-radius: 12px;
      padding: 7px 11px;
      font-size: 12.5px;
      color: var(--text);
      margin-bottom: 6px;
      outline: none;
      box-shadow: 0 1px 0 rgba(255, 255, 255, .10) inset;
      transition: border-color .15s, background .15s;
    }

    .ce-skill-search:focus {
      background: rgba(255, 255, 255, .11);
      border-color: rgba(255, 255, 255, .30);
    }

    .ce-skill-search::placeholder {
      color: rgba(255, 255, 255, .35);
    }

    .ce-skill-cat {
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .07em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .5);
      padding: 7px 8px 3px;
    }

    .ce-skill-item {
      display: flex;
      align-items: center;
      gap: 8px;
      padding: 8px 10px;
      border-radius: 12px;
      cursor: pointer;
      font-size: 13px;
      color: var(--text);
      transition: background .12s, box-shadow .12s;
    }

    .ce-skill-item:hover {
      background: rgba(255, 255, 255, .10);
      box-shadow: 0 1px 0 rgba(255, 255, 255, .15) inset;
    }

    .ce-skill-item svg {
      width: 14px;
      height: 14px;
      flex-shrink: 0;
      opacity: .65;
    }

    /* Active skill chip */
    .ce-skill-chip {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      height: 28px;
      padding: 0 8px 0 11px;
      border-radius: 999px;
      border: 1px solid rgba(255, 255, 255, .32);
      background: rgba(255, 255, 255, .10);
      backdrop-filter: blur(18px) saturate(1.4);
      -webkit-backdrop-filter: blur(18px) saturate(1.4);
      box-shadow: 0 1px 0 rgba(255, 255, 255, .35) inset, 0 0 0 1px rgba(255, 255, 255, .08) inset;
    }

    .ce-skill-chip-name {
      font-family: var(--font-body, 'Lora', Georgia, serif);
      font-style: italic;
      font-size: 13px;
      color: var(--text);
      white-space: nowrap;
    }

    .ce-skill-chip-close {
      font-size: 10.5px;
      color: rgba(255, 255, 255, .45);
      cursor: pointer;
      padding: 2px 3px;
      border-radius: 50%;
      line-height: 1;
      transition: color .15s;
    }

    .ce-skill-chip-close:hover {
      color: var(--text);
    }

    /* Param pills */
    .ce-param-pills {
      display: flex;
      align-items: center;
      gap: 4px;
    }

    .ce-param-pill {
      display: inline-flex;
      align-items: center;
      gap: 2px;
      height: 26px;
      padding: 0 9px;
      border-radius: 999px;
      border: 1px solid rgba(255, 255, 255, .13);
      background: rgba(255, 255, 255, .07);
      backdrop-filter: blur(10px);
      -webkit-backdrop-filter: blur(10px);
      font-size: 11.5px;
      color: var(--text);
      cursor: pointer;
      white-space: nowrap;
      transition: background .12s;
    }

    .ce-param-pill:hover {
      background: rgba(255, 255, 255, .13);
    }

    .ce-param-label {
      opacity: .55;
      font-size: 10.5px;
    }

    .ce-param-val {
      font-weight: 500;
    }

    /* Param popup — position:fixed set in JS, appended to body */
    .ce-param-popup {
      min-width: 168px;
      max-height: min(320px, calc(100vh - 100px));
      overflow-y: auto;
      background: rgba(255, 255, 255, .09);
      border: 1px solid rgba(255, 255, 255, .22);
      border-radius: 16px;
      padding: 5px;
      z-index: 9950;
      backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      -webkit-backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .45) inset,
        0 -1px 0 rgba(255, 255, 255, .10) inset,
        0 0 0 1px rgba(255, 255, 255, .06) inset,
        0 16px 48px rgba(0, 0, 0, .5),
        0 4px 16px rgba(0, 0, 0, .3);
    }

    .ce-param-opt {
      padding: 8px 12px;
      border-radius: 11px;
      font-size: 13px;
      color: var(--text);
      cursor: pointer;
      transition: background .1s, box-shadow .1s;
    }

    .ce-param-opt:hover {
      background: rgba(255, 255, 255, .10);
      box-shadow: 0 1px 0 rgba(255, 255, 255, .14) inset;
    }

    .ce-param-opt.selected {
      background: rgba(255, 255, 255, .14);
      color: var(--text);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .40) inset,
        0 0 0 1px rgba(255, 255, 255, .28);
    }

    /* Exit skill mode × */
    .ce-exit-skill-btn {
      display: inline-flex;
      align-items: center;
      justify-content: center;
      width: 26px;
      height: 26px;
      border-radius: 50%;
      border: 1px solid rgba(255, 255, 255, .11);
      background: rgba(255, 255, 255, .06);
      color: rgba(255, 255, 255, .4);
      font-size: 10px;
      cursor: pointer;
      flex-shrink: 0;
      transition: background .15s, color .15s;
    }

    .ce-exit-skill-btn:hover {
      background: rgba(255, 255, 255, .13);
      color: var(--text);
    }

    /* Skill-mode model selector — flows immediately after param pills */
    .ce-skill-model-sel {
      display: flex;
      align-items: center;
      gap: 4px;
      flex-shrink: 0;
      margin-left: 6px;
    }

    /* Pills inherit ALL styles from the main .ce-model-pill rules —
   dot colours, active state, hover — zero overrides needed.
   Only thing we adjust is font-size to match the compact skill row. */
    .ce-skill-model-sel .ce-model-pill {
      font-size: 12.5px;
    }

    /* Force [hidden] to work even when class sets display:flex/inline-flex */
    #ceSkillModeRow[hidden],
    #ceSkillChip[hidden],
    #ceAddSkillWrap[hidden],
    .ce-skill-popup[hidden],
    .ce-param-popup[hidden] {
      display: none !important;
    }

    .ce-web-btn.is-on {
      color: var(--text);
      background: rgba(255, 255, 255, .22);
      border-color: rgba(255, 255, 255, .38);
      box-shadow: 0 0 0 2px rgba(255, 255, 255, .10);
    }

    .ce-web-btn.is-on:hover {
      color: var(--text);
      background: rgba(255, 255, 255, .28);
      filter: none;
    }

    .ce-tool-btn .ce-tool-badge {
      position: absolute;
      top: -3px;
      right: -3px;
      min-width: 16px;
      height: 16px;
      border-radius: 999px;
      background: var(--accent-bright);
      color: #0a1f12;
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      padding: 0 4px;
      box-shadow: 0 0 0 2px var(--bg-deep);
    }

    .ce-textarea {
      flex: 1;
      font-family: var(--font-body);
      font-size: 15px;
      line-height: 1.55;
      color: var(--text);
      background: transparent;
      border: 0;
      outline: 0;
      resize: none;
      /* b.210 — single-line textarea now sits at 36px to match the tool
     icon height, with vertical padding centring the text inside its
     own box. Combined with align-items:center on the row, this kills
     the "text floating above the top border" bug — the text now
     vertically centres against the icons cleanly. max-height
     unchanged so longer messages still scroll inside the box.
     2026-05-11 b.254 — bumped left padding from 4 → 14 so the caret
     and placeholder sit comfortably away from the gear icon. The
     row's gap:10 between the tool group and the textarea was
     leaving the text crammed against its own left edge. */
      min-height: 36px;
      max-height: 180px;
      padding: 6px 4px 6px 14px;
      caret-color: var(--text);
      display: block;
    }

    .ce-textarea::placeholder {
      color: var(--text-faint)
    }

    /* Send button — segmented pill matching production .btn-create
   anatomy: fixed 48px height, two child segments separated by a
   border-left, coin at 1.7em inside the cost segment. The arrow
   replaces the old "Send" text — clean upward chevron, the chat-
   industry-standard send glyph (matches ChatGPT, Claude, Perplexity).
   Padding lives on the segments, not the parent, so the divider
   runs cleanly from edge to edge. */
    .ce-send-btn {
      /* 2026-05-11 b.261 — liquid-glass pass. User feedback: the .10
     white wash + .45 border + brightness(1.04) read as "white-
     tinted" rather than glass. Tuned for transparency:
       bg .10 → .04 (lets bg show through more)
       border .45 → .30 (softer rim)
       brightness 1.04 → 1.0 (no white-boost)
     Added a subtle top-edge inset highlight (.18) for glass-
     refraction feel. Hover deepens the bg + brightens the rim. */
      display: inline-flex;
      align-items: center;
      height: 48px;
      padding: 0;
      border-radius: 999px;
      background: rgba(255, 255, 255, .04);
      border: 1.5px solid rgba(255, 255, 255, .30);
      -webkit-backdrop-filter: blur(22px) saturate(1.30);
      backdrop-filter: blur(22px) saturate(1.30);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .18) inset,
        0 -1px 0 rgba(255, 255, 255, .06) inset;
      font-family: var(--font-display);
      font-weight: 700;
      font-size: 13px;
      letter-spacing: .02em;
      color: #ffffff;
      cursor: pointer;
      transition: transform .15s var(--ease), background .15s var(--ease), border-color .15s var(--ease);
      white-space: nowrap;
      overflow: hidden;
      line-height: 1;
    }

    .ce-send-btn:hover:not(:disabled) {
      background: rgba(255, 255, 255, .10);
      border-color: rgba(255, 255, 255, .45);
    }

    .ce-send-btn:hover {
      transform: translateY(-1px)
    }

    .ce-send-btn:disabled {
      opacity: .4;
      cursor: not-allowed;
      transform: none
    }

    .ce-send-main {
      display: inline-flex;
      align-items: center;
      justify-content: center;
      padding: 0 18px;
      height: 100%;
    }

    .ce-send-arrow {
      width: 18px;
      height: 18px;
      flex-shrink: 0;
      color: var(--text);
    }

    /* Cost segment — matches production .btn-create .bc-cost exactly:
   bordered separator on the left, faint inset background, display
   font at 13px/800, coin sized at 1.7em (so it scales with the
   font and reads as a substantial token rather than a small icon). */
    .ce-send-btn .ce-send-cost {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 0 14px;
      height: 100%;
      border-left: 1px solid rgba(255, 255, 255, .22);
      background: rgba(255, 255, 255, .05);
      font-family: var(--font-display);
      font-weight: 800;
      font-size: 13px;
      letter-spacing: .02em;
      color: var(--text);
      transition: background .25s var(--ease);
    }

    .ce-send-cost .joy-coin {
      width: 1.7em;
      height: 1.7em
    }

    /* In Argue / Coach modes, the brain (and therefore the cost) is
   chosen INSIDE the console setup — never on the chat send button.
   Hide the cost pill entirely so users only see the arrow. CSS-level
   guard so no JS path can accidentally restore it. */
    body[data-ce-mode="argue"] .ce-send-btn .ce-send-cost,
    body[data-ce-mode="coach"] .ce-send-btn .ce-send-cost {
      display: none !important;
    }

    /* "∞ Free" state — slightly brighter glass instead of an accent
   wash. Stays glass; reads as "no cost" via a white-light tint. */
    .ce-send-btn .ce-send-cost.free {
      background: rgba(255, 255, 255, .10);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .18) inset;
    }

    .ce-send-free-ico {
      font-size: 16px;
      font-weight: 600;
      line-height: 1;
      letter-spacing: -.05em;
      color: var(--text);
      display: inline-flex;
      align-items: center;
      /* Optical nudge: the ∞ glyph sits slightly above its em-box centre
     in most UI fonts, so a 1px lift visually centres it against the
     uppercase FREE label sitting next to it. */
      transform: translateY(-1px);
    }

    .ce-send-free-label {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 800;
      line-height: 1;
      letter-spacing: .08em;
      text-transform: uppercase;
      color: var(--text);
      display: inline-flex;
      align-items: center;
    }

    /* b.756 — `.ce-send-auto-label` rule removed. The "Auto" send-label
       branch (model === 'auto') became unreachable when the Auto routing
       pill was retired; the JS that rendered <span class="ce-send-auto-label">
       was stripped in the same build. */

    /* Below-input row: model selector + intensity dial */
    .ce-input-meta {
      display: flex;
      align-items: center;
      gap: 10px;
      padding: 0 4px;
      font-family: var(--font-ui);
      font-size: 11.5px;
      color: var(--text-faint);
      flex-wrap: wrap;
    }

    /* Generic flex row used by the model/judge pill group. Renamed
   from .ce-input-meta-left because the modes now sit to its left
   — the row is no longer "leftmost", just a row of pills. */
    .ce-pill-row {
      display: flex;
      align-items: center;
      gap: 6px;
      flex-wrap: wrap
    }

    .ce-input-meta-center {
      display: flex;
      align-items: center;
      gap: 8px
    }

    /* Variant label inside an active model pill. Only shown when the
   pill is .on, so an inactive pill stays compact. Cycling through
   tiers re-renders the label so the user always sees which variant
   they're about to send to. */
    .ce-model-pill .ce-model-variant {
      display: none;
      font-weight: 500;
      opacity: .72;
    }

    .ce-model-pill.on .ce-model-variant {
      display: inline
    }

    .ce-model-pill .ce-model-variant::before {
      content: '·';
      margin: 0 5px;
      opacity: .5;
    }

    /* Meta-row right cluster — Chat History + New Chat sit together
   on the far right of the meta row. margin-left:auto on the
   container pushes both rightward in one go. */
    .ce-meta-actions {
      margin-left: auto;
      display: inline-flex;
      align-items: center;
      gap: 6px;
    }

    .ce-history-btn,
    .ce-newchat-btn {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      font-family: var(--font-ui);
      font-size: 11.5px;
      font-weight: 600;
      padding: 6px 12px;
      border-radius: 999px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      color: var(--text-muted);
      cursor: pointer;
      transition: all .2s var(--ease);
      white-space: nowrap;
    }

    .ce-history-btn:hover,
    .ce-newchat-btn:hover {
      color: var(--text);
      background: var(--lg-fill-hover);
    }

    .ce-history-btn.open {
      background: var(--lg-fill-active);
      border-color: var(--lg-stroke-hi);
      color: var(--text);
    }

    .ce-history-btn .ce-hb-ico,
    .ce-newchat-btn .ce-nc-ico {
      width: 13px;
      height: 13px;
      flex-shrink: 0;
    }

    /* Chat history popover — wider + taller than the tier/judge
   popovers since it lists potentially many sessions. Has its
   own internal layout: sticky search header + scrollable list. */
    .ce-history-popover {
      width: 380px;
      max-width: calc(100vw - 32px);
      max-height: 60vh;
      display: flex;
      flex-direction: column;
      padding: 0;
      /* override base 14px 18px — sections handle padding */
      overflow: hidden;
    }

    .ce-hp-head {
      /* Equal vertical padding so the search input sits visually centered
     in the head strip. The 5px values balance against the rounded
     corner of the popover so the search reads as evenly inset on
     top and bottom. */
      padding: 5px 8px;
      border-bottom: 1px solid var(--lg-stroke);
      flex-shrink: 0;
    }

    .ce-hp-search {
      width: 100%;
      padding: 8px 12px;
      font-family: var(--font-ui);
      font-size: 13px;
      color: var(--text);
      /* Subtle inset look — the search sits INSIDE the popover surface
     rather than floating on top. Slightly recessed background +
     soft rectangle radius reads as "this belongs here". */
      background: rgba(255, 255, 255, .04);
      border: 1px solid var(--lg-stroke);
      border-radius: 10px;
      outline: 0;
      transition: border-color .2s var(--ease), background .2s var(--ease);
    }

    .ce-hp-search:focus {
      background: rgba(255, 255, 255, .06);
      border-color: var(--lg-stroke-hi);
    }

    .ce-hp-search:focus {
      border-color: var(--lg-stroke-hi)
    }

    .ce-hp-search::placeholder {
      color: var(--text-faint);
      font-style: italic
    }

    .ce-hp-list {
      flex: 1;
      overflow-y: auto;
      /* No padding — items handle their own. Scrollbar gutter hugs the
     right edge of the popover; widened to 8px and styled with no
     side margin so the thumb visually touches the popover border. */
      padding: 0;
      scrollbar-width: thin;
      scrollbar-color: var(--lg-stroke-hi) transparent;
    }

    .ce-hp-list::-webkit-scrollbar {
      width: 8px
    }

    .ce-hp-list::-webkit-scrollbar-track {
      background: transparent;
      margin: 0
    }

    .ce-hp-list::-webkit-scrollbar-thumb {
      background: var(--lg-stroke-hi);
      border-radius: 0;
      /* sharp edge against the popover border */
      border: 0;
    }

    .ce-hp-list::-webkit-scrollbar-thumb:hover {
      background: var(--text-muted);
    }

    .ce-hp-empty {
      padding: 32px 14px;
      text-align: center;
      font-family: var(--font-ui);
      font-size: 12px;
      font-style: italic;
      color: var(--text-faint);
      line-height: 1.5;
    }

    /* Each row = clickable button (left) + 3-dot more button (right). */
    .ce-hp-row {
      display: flex;
      align-items: stretch;
      position: relative;
      transition: background .15s var(--ease);
    }

    .ce-hp-row:hover {
      background: var(--lg-fill-hover)
    }

    .ce-hp-row:hover .ce-hp-more {
      opacity: 1
    }

    .ce-hp-item {
      flex: 1;
      min-width: 0;
      display: block;
      text-align: left;
      /* Tighter padding-left, more on right to give breathing room next
     to the 3-dot button. */
      padding: 8px 4px 8px 12px;
      background: transparent;
      border: 0;
      cursor: pointer;
    }

    .ce-hp-item-head {
      display: flex;
      align-items: center;
      gap: 8px;
      margin-bottom: 3px;
    }

    .ce-hp-title {
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 700;
      color: var(--text);
      flex: 1;
      min-width: 0;
      overflow: hidden;
      text-overflow: ellipsis;
      white-space: nowrap;
    }

    .ce-hp-time {
      font-family: var(--font-ui);
      font-size: 10.5px;
      font-weight: 600;
      color: var(--text-faint);
      flex-shrink: 0;
    }

    .ce-hp-preview {
      font-family: var(--font-body);
      font-size: 11.5px;
      line-height: 1.4;
      color: var(--text-muted);
      /* No more icon-induced indent — preview starts at the same x
     as the title since the badge is gone. */
      display: -webkit-box;
      -webkit-line-clamp: 2;
      -webkit-box-orient: vertical;
      overflow: hidden;
    }

    /* 3-dot button — visible on hover or focus. Sits inside the row,
   to the right of the clickable area. */
    .ce-hp-more {
      flex-shrink: 0;
      width: 28px;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      background: transparent;
      border: 0;
      color: var(--text-muted);
      cursor: pointer;
      opacity: 0;
      transition: opacity .15s var(--ease), background .15s var(--ease), color .15s var(--ease);
      border-radius: 8px;
      margin: 6px 6px 6px 0;
    }

    .ce-hp-more:hover {
      background: var(--lg-fill-active);
      color: var(--text);
      opacity: 1;
    }

    /* Floating action menu anchored to the 3-dot button. */
    .ce-hp-rowmenu {
      position: fixed;
      z-index: 140;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke-hi);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      border-radius: 10px;
      box-shadow: var(--lg-shadow);
      padding: 4px;
      min-width: 120px;
    }

    .ce-hp-rowmenu-action {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      width: 100%;
      padding: 7px 10px;
      background: transparent;
      border: 0;
      border-radius: 7px;
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 600;
      color: var(--text);
      cursor: pointer;
      text-align: left;
      transition: background .15s var(--ease);
    }

    .ce-hp-rowmenu-action:hover {
      background: var(--lg-fill-hover)
    }

    .ce-hp-rowmenu-delete {
      color: #ff8b94
    }

    .ce-hp-rowmenu-delete:hover {
      background: rgba(255, 107, 120, .12)
    }

    .ce-model-pill {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 5px 10px;
      border-radius: 999px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      color: var(--text-muted);
      cursor: pointer;
      transition: all .2s var(--ease);
      font-weight: 600;
    }

    .ce-model-pill:hover {
      color: var(--text);
      background: var(--lg-fill-hover)
    }

    .ce-model-pill.on {
      color: var(--text);
      background: var(--lg-fill-hover);
      border-color: rgba(255, 255, 255, .55);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .20) inset, 0 0 14px rgba(255, 255, 255, .05);
    }

    .ce-model-pill[data-disabled="1"] {
      opacity: .45;
      cursor: not-allowed;
    }

    .ce-model-dot {
      width: 7px;
      height: 7px;
      border-radius: 50%
    }

    /* ARGUE BRAIN CAPSULE — single rounded container holding the label,
   a vertical divider, and three provider segments. Reads as one
   unit, mirrors the intensity-dial pattern (label-as-segment, then
   selectable options inside the same shell). */
    .ce-argue-brain-group {
      display: inline-flex;
      align-items: center;
      padding: 3px;
      gap: 2px;
      /* b.404 — Full clean glass recipe. */
      background: rgba(255, 255, 255, .08);
      border: 1px solid rgba(255, 255, 255, .22);
      -webkit-backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      backdrop-filter: blur(40px) saturate(1.8) brightness(1.05);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .30) inset,
        0 -1px 0 rgba(0, 0, 0, .12) inset;
      border-radius: 999px;
    }

    .ce-ab-label {
      display: inline-flex;
      align-items: center;
      padding: 0 10px 0 12px;
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: var(--text-muted);
      white-space: nowrap;
    }

    .ce-ab-divider {
      width: 1px;
      height: 18px;
      background: var(--lg-stroke);
      margin: 0 4px 0 2px;
    }

    .ce-ab-seg {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 5px 12px;
      border: none;
      background: transparent;
      border-radius: 999px;
      color: var(--text-muted);
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 600;
      cursor: pointer;
      transition: background .15s var(--ease), color .15s var(--ease);
      white-space: nowrap;
    }

    .ce-ab-seg:hover {
      color: var(--text);
      background: var(--lg-fill-hover)
    }

    .ce-ab-seg.on {
      background: var(--lg-fill-hover);
      color: var(--text);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .55), 0 0 12px rgba(255, 255, 255, .05);
    }

    .ce-ab-seg[data-disabled="1"] {
      opacity: .4;
      cursor: not-allowed;
    }

    .ce-ab-seg[data-disabled="1"]:hover {
      background: transparent;
      color: var(--text-muted)
    }

    .ce-ab-dot {
      width: 7px;
      height: 7px;
      border-radius: 50%;
      flex-shrink: 0;
    }

    .ce-ab-dot.gpt {
      background: #10a37f
    }

    .ce-ab-dot.claude {
      background: #cc7c5e
    }

    .ce-ab-dot.gemini {
      background: #8a7eef
    }

    .ce-ab-variant {
      padding-left: 8px;
      margin-left: 2px;
      border-left: 1px solid var(--lg-stroke);
      color: var(--text-muted);
      font-weight: 500;
      font-size: 12px;
    }

    .ce-model-pill[data-model="gpt"] .ce-model-dot,
    .ce-model-pill[data-argue-provider="gpt"] .ce-model-dot {
      background: #10a37f
    }

    .ce-model-pill[data-model="claude"] .ce-model-dot,
    .ce-model-pill[data-argue-provider="claude"] .ce-model-dot {
      background: #cc7c5e
    }

    .ce-model-pill[data-model="gemini"] .ce-model-dot,
    .ce-model-pill[data-argue-provider="gemini"] .ce-model-dot {
      background: #8a7eef
    }

    /* b.756 — `.ce-model-pill[data-model="auto"] .ce-model-dot` rule
       removed. The Auto routing pill was retired long ago, so no element
       in the live DOM carries data-model="auto"; this rule never matched. */

    /* File chips */
    .ce-file-row {
      display: flex;
      flex-wrap: wrap;
      gap: 6px;
      padding: 0 6px;
    }

    .ce-file-chip {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 5px 10px;
      border-radius: 999px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      font-family: var(--font-ui);
      font-size: 11.5px;
      font-weight: 600;
      color: var(--text-muted);
      max-width: 240px;
    }

    .ce-file-chip .ce-fc-name {
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
    }

    .ce-file-chip .ce-fc-x {
      border: 0;
      background: transparent;
      color: var(--text-faint);
      cursor: pointer;
      width: 16px;
      height: 16px;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      border-radius: 50%;
      font-size: 14px;
      line-height: 1;
    }

    .ce-file-chip .ce-fc-x:hover {
      background: var(--lg-fill-hover);
      color: var(--text)
    }

    /* Settings modal */
    .ce-modal-back {
      position: fixed;
      inset: 0;
      z-index: 90;
      /* Same treatment as the debate modal + verdict overlay backdrops —
     transparent. The chat page disappears via body.ce-popup-open
     instead of being covered with a scrim, so the only thing the
     user sees behind the modal is the theme video. */
      background: transparent;
      display: none;
      align-items: center;
      justify-content: center;
      padding: 24px;
    }

    .ce-modal-back.open {
      display: flex
    }

    .ce-modal {
      width: 100%;
      max-width: 520px;
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      border-radius: 24px;
      box-shadow: var(--lg-shadow);
      padding: 24px 24px 20px;
    }

    .ce-modal h3 {
      font-family: var(--font-display);
      font-size: 20px;
      font-weight: 700;
      margin-bottom: 6px;
    }

    .ce-modal p.ce-modal-sub {
      font-size: 13px;
      color: var(--text-muted);
      margin-bottom: 18px;
      line-height: 1.5;
    }

    .ce-field {
      margin-bottom: 14px
    }

    .ce-field label {
      display: block;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .06em;
      text-transform: uppercase;
      color: var(--text-faint);
      margin-bottom: 6px;
    }

    .ce-field input {
      width: 100%;
      padding: 12px 14px;
      font-family: var(--font-ui);
      font-size: 13px;
      color: var(--text);
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      border-radius: 12px;
      outline: 0;
      transition: border-color .2s var(--ease);
    }

    .ce-field input:focus {
      border-color: var(--lg-stroke-hi)
    }

    .ce-field input::placeholder {
      color: var(--text-faint)
    }

    .ce-field-help {
      font-size: 11px;
      color: var(--text-faint);
      margin-top: 5px;
      line-height: 1.4;
    }

    .ce-field-help a {
      color: var(--text-muted);
      text-decoration: underline
    }

    .ce-modal-foot {
      display: flex;
      align-items: center;
      justify-content: space-between;
      margin-top: 20px;
      gap: 10px;
    }

    .ce-modal-note {
      font-size: 11px;
      color: var(--text-faint);
      line-height: 1.4;
      flex: 1
    }

    .ce-modal-save {
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 700;
      padding: 10px 18px;
      border-radius: 999px;
      background:
        radial-gradient(120% 100% at 30% 0%, var(--active-tint), transparent 70%),
        var(--lg-fill);
      border: 1.5px solid var(--lg-stroke-hi);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      box-shadow: 0 0 18px var(--active-glow);
      color: var(--text);
      cursor: pointer;
    }

    /* Loading state */
    .ce-thinking {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      padding: 14px 18px;
      border-radius: var(--r-lg);
      background: var(--lg-fill);
      border: 1.5px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      align-self: flex-start;
      max-width: 78%;
    }

    .ce-thinking .ce-dot {
      width: 6px;
      height: 6px;
      border-radius: 50%;
      background: var(--text-muted);
      animation: ce-pulse 1.2s var(--ease) infinite;
    }

    .ce-thinking .ce-dot:nth-child(2) {
      animation-delay: .15s
    }

    .ce-thinking .ce-dot:nth-child(3) {
      animation-delay: .30s
    }

    .ce-thinking-label {
      font-family: var(--font-ui);
      font-size: 12px;
      font-weight: 600;
      color: var(--text-muted);
      margin-left: 4px;
    }

    .ce-thinking.ce-searching .ce-thinking-label {
      animation: ce-search-blink 1.6s ease-in-out infinite;
    }

    @keyframes ce-search-blink {

      0%,
      100% {
        opacity: .45
      }

      50% {
        opacity: .9
      }
    }

    @keyframes ce-pulse {

      0%,
      100% {
        opacity: .3;
        transform: scale(.85)
      }

      50% {
        opacity: 1;
        transform: scale(1.1)
      }
    }

    /* ----------------------------------------------------------------
   LIVE DEBATE MODAL — opens during active debates AND on click of
   "View live debate" on any rendered debate block. Three model
   panels animate in side-by-side as each model completes; a
   synthesis panel sits below the grid and lights up once the
   judge pass has run. Liquid-glass language matches the rest of
   the app; no new design primitives invented.
   ---------------------------------------------------------------- */
    .ce-debate-modal {
      position: fixed;
      inset: 0;
      z-index: 100;
      display: flex;
      align-items: center;
      justify-content: center;
      padding: 24px;
      /* Instant open / instant close — no opacity fade, no scale. The
     visibility flip is enough to gate clicks; everything else
     happens in the same frame so popups feel snappy. */
      opacity: 0;
      visibility: hidden;
      pointer-events: none;
    }

    .ce-debate-modal.open {
      opacity: 1;
      visibility: visible;
      pointer-events: auto;
    }

    /* Universal popup pattern — when ANY fullscreen popup is open
   (settings, debate, verdict), the chat page (header + main) is
   hidden so only the theme video plays behind the popup's liquid-
   glass shell. Closing the topmost popup brings the next layer
   back; closing the last one brings the chat page back. State is
   preserved everywhere — we just toggle visibility, never tear
   the DOM down. Instant flip, no fade. */
    body.ce-popup-open .header,
    body.ce-popup-open .main {
      visibility: hidden;
      opacity: 0;
      pointer-events: none;
    }

    /* Stacked-popup case: when the verdict overlay sits on top of the
   debate modal, the debate modal is also hidden so the verdict has
   only the theme video behind it. Closing the verdict reveals the
   debate modal again with no state loss. Instant flip, no fade. */
    body.ce-verdict-open .ce-debate-modal {
      visibility: hidden;
      pointer-events: none;
      opacity: 0;
    }

    /* Same pattern for the coach session report — when it opens, the
   coach console behind it disappears so only the report sits over
   the theme video. Closing the report restores the console with
   full state intact. */
    body.ce-coach-report-open .ce-coach-overlay {
      visibility: hidden;
      pointer-events: none;
      opacity: 0;
    }

    .ce-dm-backdrop {
      position: absolute;
      inset: 0;
      /* Fully transparent — no scrim, no blur. The theme video plays
     unmolested behind the modal so the liquid-glass shell sits on
     top of a clean moving background. The backdrop element still
     exists for click-to-close (data-dm-close); it just has no
     visual presence. */
      background: transparent;
    }

    /* Console dimensions — shared between the debate modal and the
   verdict overlay. Width is locked so both surfaces line up
   horizontally; height is content-driven (auto, capped at viewport)
   so each surface only takes the vertical space its content actually
   needs. Earlier versions used a fixed --console-h, which left a
   block of dead space below the verdict strip on debates that fit
   in less than the full viewport. Now: the shell grows when Round 2
   is offered or when the verdict body is long, and shrinks when the
   content is short — no permanent stretched footprint. */
    :root {
      --console-w: 1200px;
      --console-h-max: calc(100vh - 48px);
    }

    .ce-dm-shell {
      position: relative;
      width: 100%;
      max-width: var(--console-w);
      height: auto;
      max-height: var(--console-h-max);
      display: flex;
      flex-direction: column;
      /* b.482 — Zero-tint canonical recipe. Stripped the .03 white wash
     entirely (background now transparent), softened border to .10,
     dropped top inset highlight from .16 to .06, lowered saturate
     from 1.7 to 1.5 so the bg colors aren't blown out without the
     white to balance them. Net effect: orbs come through without any
     white wash, blur stays heavy enough to feel like glass. */
      background: rgba(255, 255, 255, .03);
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      border-radius: 28px;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .16) inset,
        0 -1px 0 rgba(0, 0, 0, .10) inset,
        0 24px 60px -12px rgba(0, 0, 0, .55);
      isolation: isolate;
      overflow: hidden;
    }

    .ce-dm-head {
      display: flex;
      align-items: flex-start;
      gap: 18px;
      /* b.516 — Compressed top + bottom padding (was 22 / 16) so the
     debate modal fits in viewport without scrolling, mirroring the
     consensus layout. */
      padding: 14px 24px 10px;
      border-bottom: 1px solid var(--lg-stroke);
      flex-shrink: 0;
    }

    .ce-dm-head-text {
      flex: 1;
      min-width: 0
    }

    .ce-dm-eyebrow {
      display: inline-flex;
      align-items: center;
      gap: 7px;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .12em;
      text-transform: uppercase;
      color: var(--text-faint);
      margin-bottom: 6px;
    }

    .ce-dm-eyebrow::before {
      content: '';
      width: 7px;
      height: 7px;
      border-radius: 50%;
      background: var(--accent-bright);
      box-shadow: 0 0 12px var(--accent-bright);
      animation: ce-pulse 1.5s var(--ease) infinite;
    }

    /* b.526 — Eyebrow row: [Debate · LIVE-DOT] [{i}] [inline info text].
   Click the {i} to reveal the description inline (no box, no panel —
   just text in the empty space to the right). */
    .ce-dm-eyebrow-row {
      display: flex;
      align-items: center;
      gap: 10px;
      margin-bottom: 6px;
    }

    .ce-dm-eyebrow-row>.ce-dm-eyebrow {
      margin-bottom: 0;
      /* row owns the bottom spacing */
    }

    .ce-dm-info-btn {
      flex: 0 0 auto;
      width: 20px;
      height: 20px;
      border-radius: 50%;
      border: 1px solid rgba(255, 255, 255, .28);
      background: rgba(255, 255, 255, .04);
      color: rgba(255, 255, 255, .78);
      font-family: var(--font-display);
      font-size: 11px;
      font-weight: 700;
      font-style: italic;
      line-height: 1;
      cursor: pointer;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      padding: 0;
      transition: background .15s var(--ease), border-color .15s var(--ease), color .15s var(--ease);
    }

    .ce-dm-info-btn:hover,
    .ce-dm-info-btn[aria-expanded="true"] {
      background: rgba(255, 255, 255, .10);
      border-color: rgba(255, 255, 255, .55);
      color: #fff;
    }

    .ce-dm-info-text {
      flex: 1 1 auto;
      min-width: 0;
      font-family: var(--font-body);
      font-size: 11.5px;
      font-style: italic;
      line-height: 1.4;
      color: rgba(255, 255, 255, .62);
      letter-spacing: .005em;
      text-transform: none;
    }

    .ce-dm-info-text[hidden] {
      display: none;
    }

    .ce-dm-question {
      font-family: var(--font-display);
      font-size: 20px;
      font-weight: 600;
      letter-spacing: -.01em;
      color: var(--text);
      line-height: 1.35;
      margin: 0;
      /* b.500 — Align heading text with the eyebrow's text. Eyebrow has
     a 7px ::before dot + 7px gap = 14px before its text. Mirror that
     as padding-left so the heading "P" of "Pick a scenario..." sits
     directly under the "C" of "COACH · SETUP" (and same in Debate /
     Consensus / Argue). */
      padding-left: 14px;
      word-wrap: break-word;
    }

    .ce-dm-close {
      width: 36px;
      height: 36px;
      border-radius: 50%;
      border: 1px solid var(--lg-stroke);
      background: var(--lg-fill);
      color: var(--text);
      cursor: pointer;
      font-size: 18px;
      line-height: 1;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      transition: all .2s var(--ease);
      flex-shrink: 0;
    }

    .ce-dm-close:hover {
      background: var(--lg-fill-active)
    }

    .ce-dm-body {
      flex: 1;
      overflow-y: auto;
      /* b.516 — Compressed body padding + gap so the debate modal fits
     in viewport. Was 20/24/24 + gap 14. */
      padding: 10px 24px 12px;
      display: flex;
      flex-direction: column;
      gap: 10px;
      scrollbar-width: thin;
      scrollbar-color: var(--lg-stroke) transparent;
    }

    .ce-dm-body::-webkit-scrollbar {
      width: 6px
    }

    .ce-dm-body::-webkit-scrollbar-thumb {
      background: var(--lg-stroke);
      border-radius: 3px
    }

    .ce-dm-grid {
      display: grid;
      grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
      gap: 14px;
    }

    .ce-dm-panel {
      display: flex;
      flex-direction: column;
      /* b.490 — Option A: strip wash from inner element so it doesn't
     compound with the shell's .03 wash. Top inset softened from .16
     to .10 so it doesn't add a visible white edge on the top rim. */
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      border-radius: 20px;
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      overflow: hidden;
      /* b.521 — Further trimmed (280 → 220, 55vh → 42vh) to keep the
     verdict area visible without scrolling on smaller viewports. */
      min-height: 220px;
      max-height: 42vh;
      transition: all .35s var(--ease);
      position: relative;
    }

    /* b.514 — Topic-row layout: textbox on the left, MODEL SET pill on
   the right. Container wraps the textarea inside .ce-dm-head-text.
   JS relocates the original .ce-dm-setting-modelset into the slot
   on boot. */
    .ce-dm-topic-row {
      display: flex;
      align-items: center;
      gap: 16px;
      width: 100%;
    }

    .ce-dm-topic-row .ce-dm-question-input {
      flex: 1 1 auto;
      min-width: 0;
    }

    .ce-dm-head-modelslot {
      flex: 0 0 auto;
      display: flex;
      align-items: center;
    }

    .ce-dm-head-modelslot:empty {
      display: none;
      /* until JS move runs, textbox takes full width */
    }

    .ce-dm-head-modelslot>.ce-dm-setting-row {
      display: flex;
      flex-direction: column;
      /* b.516 — center label + pill horizontally inside the slot. */
      align-items: center;
      gap: 6px;
      margin: 0;
    }

    .ce-dm-head-modelslot>.ce-dm-setting-row>.ce-dm-setting-label {
      font-size: 9.5px;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: var(--text-faint);
      white-space: nowrap;
      text-align: center;
    }

    .ce-dm-panel[data-status="thinking"]::before {
      content: '';
      position: absolute;
      inset: -1px;
      border-radius: 20px;
      padding: 1.5px;
      background: linear-gradient(120deg,
          transparent 30%,
          var(--active-glow) 50%,
          transparent 70%);
      -webkit-mask: linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0);
      mask: linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0);
      -webkit-mask-composite: xor;
      mask-composite: exclude;
      background-size: 200% 200%;
      animation: dm-shimmer 2.4s linear infinite;
      pointer-events: none;
    }

    @keyframes dm-shimmer {
      0% {
        background-position: 0% 50%
      }

      100% {
        background-position: 200% 50%
      }
    }

    .ce-dm-panel[data-status="done"] {
      border-color: var(--lg-stroke-hi);
      box-shadow:
        0 0 0 1px var(--lg-stroke-hi) inset,
        0 0 24px var(--active-glow);
    }

    .ce-dm-panel[data-status="error"] {
      border-color: rgba(255, 80, 96, .45);
      box-shadow: 0 0 22px rgba(255, 80, 96, .20);
    }

    /* Per-panel stance selector — sits at the very top of each model
   panel. Three flat buttons: For (emerald), Against (red),
   Neutral (grey). Editable in pre-start state, locked once the
   debate is running so the user can still see what each model
   was assigned. */
    .ce-dm-stance {
      display: flex;
      align-items: stretch;
      gap: 3px;
      padding: 6px;
      border-bottom: 1px solid var(--lg-stroke);
    }

    .ce-dm-stance-btn {
      flex: 1;
      padding: 5px 6px;
      /* b.511 — transparent 1px border so selecting an option (which
     adds a visible 1px rim) doesn't shift the row layout. */
      border: 1px solid transparent;
      background: transparent;
      border-radius: 8px;
      font-family: var(--font-ui);
      font-size: 10.5px;
      font-weight: 700;
      letter-spacing: .06em;
      text-transform: uppercase;
      color: var(--text-faint);
      cursor: pointer;
      /* b.523 — Explicitly center the label horizontally + vertically
     within each stance button. */
      display: inline-flex;
      align-items: center;
      justify-content: center;
      text-align: center;
      transition: all .2s var(--ease);
    }

    .ce-dm-stance-btn:hover {
      color: var(--text);
      background: var(--lg-fill-hover);
    }

    /* b.511 — Every .on stance now carries the same liquid-glass rim
   so it reads as "selected" against any background. The colored
   tint stays (For=green, Against=red, Custom=amber, Neutral=neutral)
   but is wrapped in a clear hairline border that telegraphs the
   active state regardless of the bg behind it. */
    .ce-dm-stance-btn[data-stance="for"].on {
      background: var(--active-tint);
      color: var(--accent-text);
      border: 1px solid rgba(255, 255, 255, .55);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .20) inset,
        0 0 12px var(--active-glow);
    }

    .ce-dm-stance-btn[data-stance="against"].on {
      background: rgba(255, 80, 96, .20);
      color: #ff7f88;
      border: 1px solid rgba(255, 255, 255, .55);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .20) inset,
        0 0 12px rgba(255, 80, 96, .25);
    }

    .ce-dm-stance-btn[data-stance="neutral"].on {
      background: var(--lg-fill-active);
      color: var(--text);
      border: 1px solid rgba(255, 255, 255, .55);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .20) inset;
    }

    /* Custom stance — amber accent so it visually distinguishes from
   the three presets. Slightly different active treatment since the
   button label may show truncated user-entered text. */
    .ce-dm-stance-btn[data-stance="custom"] {
      flex: 1.4;
      /* a bit wider since it can hold text */
      text-transform: none;
      letter-spacing: .02em;
    }

    .ce-dm-stance-btn[data-stance="custom"].on {
      background: rgba(252, 166, 0, .20);
      color: #ffc266;
      border: 1px solid rgba(255, 255, 255, .55);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .20) inset,
        0 0 12px rgba(252, 166, 0, .30);
    }

    /* Custom-stance inline input row — sits flush against the stance
   row above it, edge-to-edge with the panel sides. No rounded
   corners, no internal margin: it reads as a continuation of the
   stance row, not a separate floating field. */
    .ce-dm-stance-custom {
      padding: 0;
      border-bottom: 1px solid var(--lg-stroke);
    }

    .ce-dm-stance-input {
      display: block;
      width: 100%;
      padding: 10px 14px;
      font-family: var(--font-ui);
      font-size: 11.5px;
      color: var(--text);
      background: transparent;
      border: 0;
      border-top: 1px solid var(--lg-stroke);
      border-radius: 0;
      outline: 0;
      transition: background .2s var(--ease), box-shadow .2s var(--ease);
    }

    .ce-dm-stance-input:focus {
      background: var(--lg-fill);
      box-shadow: inset 0 0 0 1.5px rgba(252, 166, 0, .55);
    }

    .ce-dm-stance-input::placeholder {
      color: var(--text-faint);
      font-style: italic;
    }

    /* Lock stance buttons once the debate starts — visible (so user
   sees what was assigned) but no longer interactive. */
    .ce-debate-modal:not([data-state="pre-start"]) .ce-dm-stance-btn {
      cursor: default;
      pointer-events: none;
    }

    .ce-debate-modal:not([data-state="pre-start"]) .ce-dm-stance-btn:not(.on) {
      opacity: .35;
    }

    .ce-dm-panel-head {
      display: flex;
      align-items: center;
      gap: 8px;
      padding: 13px 16px;
      border-bottom: 1px solid var(--lg-stroke);
    }

    .ce-dm-panel-dot {
      width: 10px;
      height: 10px;
      border-radius: 50%;
      flex-shrink: 0;
    }

    .ce-dm-panel-name {
      font-family: var(--font-ui);
      font-size: 13px;
      font-weight: 700;
      letter-spacing: .02em;
      color: var(--text);
      flex: 1;
    }

    .ce-dm-panel-status {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      color: var(--text-faint);
    }

    .ce-dm-panel[data-status="done"] .ce-dm-panel-status {
      color: var(--accent-bright)
    }

    .ce-dm-panel[data-status="error"] .ce-dm-panel-status {
      color: #ff7f88
    }

    .ce-dm-panel-body {
      flex: 1;
      /* min-height:0 is the magic line — flex children default to
     min-height:auto which means they refuse to shrink below their
     content size, defeating overflow-y:auto. Setting it to 0 lets
     the body actually scroll within the panel's max-height. */
      min-height: 0;
      overflow-y: auto;
      padding: 14px 16px 16px;
      font-size: 13.5px;
      line-height: 1.55;
      color: var(--text);
      white-space: pre-wrap;
      word-wrap: break-word;
      scrollbar-width: thin;
      scrollbar-color: var(--lg-stroke) transparent;
    }

    .ce-dm-panel-body::-webkit-scrollbar {
      width: 4px
    }

    .ce-dm-panel-body::-webkit-scrollbar-thumb {
      background: var(--lg-stroke);
      border-radius: 2px
    }

    .ce-dm-thinking {
      display: flex;
      align-items: center;
      justify-content: center;
      height: 100%;
      min-height: 120px;
      gap: 8px;
    }

    .ce-dm-thinking-dot {
      width: 8px;
      height: 8px;
      border-radius: 50%;
      background: var(--active-glow);
      animation: ce-pulse 1.4s var(--ease) infinite;
    }

    .ce-dm-thinking-dot:nth-child(2) {
      animation-delay: .2s
    }

    .ce-dm-thinking-dot:nth-child(3) {
      animation-delay: .4s
    }

    /* Synthesis panel — sits below the grid, full width, slight inner
   wash to read as the "verdict" panel without breaking the glass. */
    .ce-dm-panel-synth {
      min-height: 0;
      /* b.510 — Strip --active-tint radial gradient (theme green) and
     --lg-fill solid base. The verdict panel inherits the canonical
     glass recipe from .ce-dm-panel; no colored overlay needed. */
      background: transparent;
    }

    .ce-dm-panel-synth[data-status="done"] {
      /* b.510 — Active state: brighter rim, no green glow. */
      border-color: rgba(255, 255, 255, .45) !important;
      box-shadow:
        0 0 0 1px rgba(255, 255, 255, .20) inset,
        0 0 28px rgba(255, 255, 255, .10) !important;
    }

    .ce-dm-panel-synth-mark {
      display: inline-flex;
      align-items: center;
      justify-content: center;
      width: 18px;
      height: 18px;
      border-radius: 6px;
      background: var(--accent-bright);
      color: #0a1f12;
      font-size: 11px;
      font-weight: 800;
      flex-shrink: 0;
    }

    /* In-modal judge trigger — sits inside the synth panel head and
   replaces the meta-row judge selector. Compact pill so it fits
   neatly between the "Synthesis" label and the status text. */
    .ce-dm-panel-synth .ce-dm-panel-name {
      flex: none
    }

    .ce-dm-panel-synth .ce-dm-panel-status {
      margin-left: auto
    }

    .ce-dm-judge-trigger {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      padding: 4px 10px;
      border-radius: 999px;
      /* b.473 — Engine-popover recipe (matches Argue composer textbox). */
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      color: var(--text-muted);
      cursor: pointer;
      transition: all .2s var(--ease);
      flex: none;
    }

    .ce-dm-judge-trigger:hover {
      color: var(--text);
      background: var(--lg-fill-hover)
    }

    .ce-dm-judge-trigger.open {
      background: var(--lg-fill-active);
      border-color: var(--lg-stroke-hi);
    }

    .ce-djt-prefix {
      font-size: 10px;
      font-weight: 700;
      opacity: .65;
      text-transform: uppercase;
      letter-spacing: .06em;
    }

    .ce-djt-name {
      font-weight: 700;
      color: var(--text)
    }

    .ce-djt-variant {
      font-weight: 500;
      opacity: .72
    }

    .ce-djt-variant::before {
      content: '·';
      margin: 0 4px;
      opacity: .5
    }

    .ce-dm-judge-trigger .ce-jt-caret {
      font-size: 9px;
      color: var(--text-muted);
      margin-left: 1px;
      transition: transform .25s var(--ease);
    }

    .ce-dm-judge-trigger.open .ce-jt-caret {
      transform: rotate(180deg)
    }

    /* Lock the judge trigger when running / replay — visible (so user
   can see who's judging) but not interactive. Caret hidden so it
   doesn't read as clickable. */
    .ce-debate-modal[data-state="running"] .ce-dm-judge-trigger,
    .ce-debate-modal[data-state="replay"] .ce-dm-judge-trigger {
      pointer-events: none;
    }

    .ce-debate-modal[data-state="running"] .ce-dm-judge-trigger .ce-jt-caret,
    .ce-debate-modal[data-state="replay"] .ce-dm-judge-trigger .ce-jt-caret {
      display: none;
    }

    .ce-dm-panel-synth {
      /* Synth panel is a thin strip in waiting/thinking/done states —
     the modal body never needs to scroll. When the verdict is
     ready (done state), the whole strip becomes a click target
     that opens the verdict in a separate overlay. */
      flex: none;
      min-height: 0;
      max-height: none;
    }

    .ce-dm-panel-synth .ce-dm-panel-body {
      font-family: var(--font-body);
      font-size: 14.5px;
    }

    .ce-dm-panel-synth[data-status="done"] {
      /* Click target when verdict is ready. Hide the body entirely;
     the head IS the affordance. Hover lifts + glows to make it
     obvious it's interactive. */
      cursor: pointer;
      transition: transform .15s var(--ease), box-shadow .25s var(--ease), border-color .25s var(--ease);
    }

    .ce-dm-panel-synth[data-status="done"]:hover {
      transform: translateY(-1px);
      border-color: var(--lg-stroke-hi);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .55) inset,
        0 -1px 0 rgba(255, 255, 255, .18) inset,
        0 0 0 1px rgba(255, 255, 255, .10) inset,
        0 0 36px var(--active-glow);
    }

    .ce-dm-panel-synth[data-status="done"] .ce-dm-panel-body {
      display: none;
    }

    /* "Open ↗" affordance — only visible when verdict is ready. */
    .ce-dm-synth-open {
      display: none;
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .06em;
      text-transform: uppercase;
      color: var(--accent-text);
      margin-left: 8px;
    }

    .ce-dm-panel-synth[data-status="done"] .ce-dm-synth-open {
      display: inline-flex;
      align-items: center;
      gap: 4px;
    }

    .ce-dm-panel-synth[data-status="done"] .ce-dm-synth-open::after {
      content: '↗';
      font-weight: 800;
    }

    .ce-dm-synth-wait {
      color: var(--text-muted);
      font-size: 13px;
      font-style: italic;
      margin: 0;
      padding: 0;
      line-height: 1.45;
    }

    /* b.393 — When the synth panel is in waiting/thinking state (verdict
   not yet ready), shrink the body padding so the placeholder text
   hugs the header. The default .ce-dm-panel-body padding (14/16/16)
   left ~50px of dead space between the "VERDICT · JUDGED BY GPT"
   header and the italic explanation. New padding: 8px top, 16px
   sides, 12px bottom — placeholder reads as continuation of the
   header, not a separate block. */
    .ce-dm-panel-synth:not([data-status="done"]) .ce-dm-panel-body {
      padding: 8px 16px 12px;
    }

    /* Modal footer — two state-driven sections inside one footer
   container. pre-start: column (hint above Start button). complete:
   row (hint inline beside Round 2 button — keeps the footer to a
   single line so the verdict above stays visible without scrolling). */
    .ce-dm-foot {
      display: flex;
      flex-direction: column;
      align-items: stretch;
      /* b.521 — Zero outer padding because the foot-section grid now
     owns its own padding (and includes the room for absolutely-
     positioned corner buttons). */
      padding: 0;
      border-top: 1px solid var(--lg-stroke);
      flex-shrink: 0;
    }

    /* b.522 — Foot-section as a flex column with justify-content:end so
   the text hints push down to the BOTTOM of the foot, just above
   the absolutely-positioned corner buttons. Center-aligned
   horizontally for the descriptive copy. */
    .ce-dm-foot-section[data-foot-section="pre-start"] {
      display: flex !important;
      flex-direction: column !important;
      justify-content: flex-end !important;
      /* push text to bottom */
      align-items: center !important;
      /* center horizontally */
      gap: 2px;
      margin: 0;
    }

    /* .ce-dm-start-row stays in flow but contains only the absolutely-
   positioned buttons — so it collapses to zero height visually. */
    .ce-dm-foot-section[data-foot-section="pre-start"] .ce-dm-start-row {
      display: contents !important;
    }

    /* b.522 — Buttons pushed all the way into the modal's extreme
   corners. 4px from the bottom + 4px from the side (was 8/8). */
    /* Simulate button removed — Start button always centred. */
    .ce-dm-foot-section[data-foot-section="pre-start"] .ce-dm-start-btn {
      position: absolute !important;
      left: 50% !important;
      right: auto !important;
      bottom: 4px !important;
      transform: translateX(-50%) !important;
      z-index: 5;
    }

    /* b.527 — All foot text gone (descriptive copy lives in the i info
   popover; coin counter hidden). Section collapses to just the
   button strip: 56px tall (48px buttons + 4px top + 4px bottom). */
    .ce-dm-foot-section[data-foot-section="pre-start"] {
      padding: 0 !important;
      position: relative;
      min-height: 56px;
      height: 56px;
    }

    /* Hide every foot-hint paragraph so the "24 coins now…" text and any
   other hint stops occupying vertical space. */
    .ce-dm-foot-section[data-foot-section="pre-start"] .ce-dm-foot-hint {
      display: none !important;
    }

    .ce-dm-foot-section[data-foot-section="pre-start"]>.ce-dm-foot-hint {
      margin: 0 !important;
      line-height: 1.35;
      font-size: 11.5px;
      text-align: center;
    }

    /* Each hint <p> lands in column 2 (center). They stack vertically
   via auto-row placement, all center-aligned. Override the inline
   margin-top negatives that were used in the old column layout. */
    .ce-dm-foot-section[data-foot-section="pre-start"]>.ce-dm-foot-hint {
      grid-column: 2;
      text-align: center;
      margin: 0 !important;
      line-height: 1.4;
    }

    /* b.302 — Start row with Simulate button alongside Start.
   b.516 — Layout flipped: SIMULATE pinned LEFT, START DEBATE pinned
   RIGHT via flex order + justify-content:space-between. START's HTML
   order is unchanged so existing JS bindings keep working. */
    .ce-dm-start-row {
      display: flex;
      align-items: center;
      justify-content: space-between;
      gap: 12px;
      flex-wrap: wrap;
      width: 100%;
    }

    /* b.291 — compact variant used by the post-debate footer (just
   the "Run another round" button, no surrounding copy). Smaller
   vertical padding so the verdict above stays maximally visible. */
    .ce-dm-foot:has(.ce-dm-foot-compact) {
      padding: 10px 24px 12px;
    }

    .ce-dm-foot-compact {
      flex-direction: row !important;
      justify-content: center !important;
      gap: 0 !important;
    }

    /* User-join bar — visible during running and complete states. Lets
   the user speak (Whisper STT only) into the active debate. The
   bar collapses to a single button by default; clicking it opens
   the recorder, and when the recorder stops the bar expands to show
   the transcript preview with Cancel / Add to debate buttons. */
    .ce-dm-userjoin-bar {
      display: flex;
      flex-direction: column;
      align-items: center;
      gap: 10px;
      padding: 14px 24px 18px;
      border-top: 1px solid var(--lg-stroke);
    }

    .ce-debate-modal[data-state="pre-start"] .ce-dm-userjoin-bar,
    .ce-debate-modal[data-state="replay"] .ce-dm-userjoin-bar {
      display: none;
    }

    .ce-dm-user-join-cost {
      font-size: 11px;
      opacity: .78;
      letter-spacing: .02em;
      display: inline-flex;
      align-items: center;
      gap: 3px;
    }

    .ce-dm-user-join-cost .joy-coin {
      width: 11px;
      height: 11px;
    }

    .ce-dm-user-join-cost.paid {
      display: none;
    }

    .ce-dm-userjoin-preview {
      width: min(560px, 100%);
      display: flex;
      flex-direction: column;
      gap: 10px;
      padding: 14px 16px 14px;
      border-radius: 14px;
      background: rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .22);
    }

    .ce-dm-userjoin-preview textarea {
      width: 100%;
      resize: vertical;
      padding: 10px 12px;
      border-radius: 10px;
      background: rgba(0, 0, 0, .22);
      border: 1px solid rgba(255, 255, 255, .14);
      color: #fff;
      font-family: inherit;
      font-size: 14px;
      line-height: 1.5;
      outline: none;
    }

    .ce-dm-userjoin-preview textarea:focus {
      border-color: rgba(255, 255, 255, .45);
    }

    .ce-dm-userjoin-actions {
      display: flex;
      justify-content: flex-end;
      gap: 8px;
    }

    .ce-dm-userjoin-cancel,
    .ce-dm-userjoin-confirm {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 8px 16px;
      border-radius: 999px;
      font-size: 12px;
      font-weight: 700;
      letter-spacing: .04em;
      text-transform: uppercase;
      cursor: pointer;
      transition: transform .12s ease, background .15s ease, border-color .15s ease;
    }

    .ce-dm-userjoin-cancel {
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .22);
      color: rgba(255, 255, 255, .78);
    }

    .ce-dm-userjoin-cancel:hover {
      background: rgba(255, 255, 255, .08);
      color: #fff;
    }

    .ce-dm-userjoin-confirm {
      background: rgba(255, 210, 170, .18);
      border: 1px solid rgba(255, 210, 170, .55);
      color: #fff;
    }

    .ce-dm-userjoin-confirm:hover {
      background: rgba(255, 210, 170, .30);
    }

    .ce-dm-userjoin-error {
      font-size: 12px;
      color: #ff8a8a;
      margin: 0;
    }

    /* User turn card — sits in the debate transcript when the user
   contributes. Slightly different tint from the model turns so it
   reads as "your voice" without breaking the liquid-glass language. */
    .ld-turn.user {
      border-color: rgba(255, 210, 170, .35);
      background:
        radial-gradient(60% 60% at 0% 0%, rgba(255, 210, 170, .16) 0%, transparent 70%),
        rgba(255, 255, 255, .06);
    }

    .ld-turn.user .ld-avatar {
      background: rgba(255, 210, 170, .30);
      color: #fff;
    }


/* ════════════════════════════════════════════════════════════════════
   ARGUE CONSOLE + ARGUE SETUP COMPOSER + MOBILE chat surface optimisation.
   Extracted in b.849. 2214 lines moved from index.html top inline <style>
   (was lines 20565-22777 in b.848). All chat-engine related: Argue is a
   chat sub-mode. The "MOBILE chat surface optimisation" block contains
   leftover mobile-related rules that didn't fit the strict @media-only
   purge in b.843 — but those rules now have no effect since chat is
   desktop-only (still keeping them here for byte-identical move; can be
   audited later).
   ════════════════════════════════════════════════════════════════════ */

    /* ============================================================
   ARGUE CONSOLE — persona setup, conviction meter, switch sides.
   All liquid-glass: --lg-fill, --lg-stroke, --lg-blur. No solid
   panels. Stage toggle hides live chrome during setup and vice versa.
   ============================================================ */

    /* Stage gates — setup hides thread / input / controls; live hides
   the setup card. Without these, both layers render simultaneously. */
    .ce-voice-overlay[data-stage="setup"] .ce-vc-setup {
      display: flex;
    }

    .ce-voice-overlay[data-stage="setup"] .ce-vc-thread,
    .ce-voice-overlay[data-stage="setup"] .ce-vc-input,
    .ce-voice-overlay[data-stage="setup"] .ce-vc-controls,
    .ce-voice-overlay[data-stage="setup"] .ce-vc-conviction,
    .ce-voice-overlay[data-stage="setup"] .ce-vc-switch-btn,
    .ce-voice-overlay[data-stage="setup"] .ce-vc-head-hint {
      display: none !important;
    }

    .ce-voice-overlay:not([data-stage="setup"]) .ce-vc-setup {
      display: none;
    }

    /* SETUP CARD — scrollable container with persona grid + custom
   input + Begin button. Liquid-glass over the orb stage backdrop. */
    .ce-vc-setup {
      flex: 1;
      display: none;
      flex-direction: column;
      gap: 18px;
      padding: 24px 28px 22px;
      overflow-y: auto;
    }

    .ce-vc-setup-head {
      /* b.531 — Tighten head to kill dead space between the eyebrow
     and the title. Title row now hugs the eyebrow; the parent's
     18px gap handles spacing to the next section below.
     b.532 — position:relative so the brain slot can be lifted up
     to align its label with the eyebrow row. */
      display: flex;
      flex-direction: column;
      gap: 2px;
      padding-bottom: 0;
      position: relative;
    }

    /* b.531 — Title row: heading on the left + ARGUE BRAIN switch
   relocated into the slot on the right. align-items:flex-start so
   the title hugs the top alongside the eyebrow; the (taller) brain
   section extends downward into the title row's space rather than
   pushing the title down. */
    .ce-vc-setup-title-row {
      display: flex;
      align-items: flex-start;
      justify-content: space-between;
      gap: 16px;
      width: 100%;
      /* b.536 — Reserve-space padding-right removed: the brain stack no
     longer lives at the top-right of the head (it was moved into the
     Text chat mode card), so the title can use the full row width. */
      box-sizing: border-box;
    }

    .ce-vc-setup-title-row>.ce-vc-setup-title {
      flex: 1 1 auto;
      min-width: 0;
    }

    .ce-vc-brain-slot {
      flex: 0 0 auto;
      display: flex;
      align-items: center;
      /* b.532 — Lift the entire brain stack up to the eyebrow row so
     "ARGUE BRAIN — WHO POWERS…" label sits on the same line as
     "ARGUE · SETUP". The picker pill drops below into the title
     row's vertical space.
     b.533 — Nudged up 5px further per user request.
     b.534 — Fixed width + right anchor so the slot never resizes
     based on its content. Previously the slot sized to its widest
     child, so switching brain provider (different variant-chip
     widths) or revealing the tier warning (max-width 760px) made
     the slot grow leftward, dragging the pill with it. Now the
     right edge is locked, children right-align, and only their
     internal width changes — pill stays put. */
      position: absolute;
      top: -5px;
      right: 0;
      width: 540px;
    }

    .ce-vc-brain-slot:empty {
      display: none;
    }

    /* b.532 — When the brain slot is absolutely positioned, drop the
   title-row's right padding back at narrower widths. */
    @media (max-width: 900px) {
      .ce-vc-setup-title-row {
        padding-right: 0;
      }

      .ce-vc-brain-slot {
        position: static;
      }
    }

    /* When ARGUE BRAIN lands in the title slot: stacked column whose
   width = picker's natural width. Right edge of that column hugs
   the slot's right edge (justify-content:end on the grid). Label
   then text-align:center centers itself OVER the picker, not over
   the wider 540px slot. (b.535 — grid replaces b.534 flex-end so
   label centers above pill instead of right-anchoring.) */
    .ce-vc-brain-slot>.ce-vc-setup-section {
      display: grid;
      grid-template-columns: max-content;
      justify-content: end;
      gap: 6px;
      margin: 0;
      width: 100%;
    }

    .ce-vc-brain-slot>.ce-vc-setup-section>.ce-vc-setup-section-label {
      text-align: center;
    }

    /* b.535 — Tier warning removed per user request (no free tier in
   Argue anymore). Hide it inside the slot just in case JS still
   un-hides it. */
    .ce-vc-brain-slot .ce-coach-tier-warning {
      display: none !important;
    }

    .ce-vc-setup-eyebrow {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .16em;
      text-transform: uppercase;
      color: var(--text-faint);
    }

    .ce-vc-setup-title {
      font-family: var(--font-display);
      font-size: 22px;
      font-weight: 700;
      line-height: 1.2;
      letter-spacing: -.005em;
      color: var(--text);
      margin: 0;
    }

    .ce-vc-setup-sub {
      /* b.529 — Hidden per user; the "Type your position once you begin
     — or pick a persona first and dive in." subtitle was just dead
     space above the persona dropdown. */
      display: none !important;
    }

    .ce-vc-setup-section-label {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 800;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: var(--text-muted);
      margin-top: 4px;
    }

    /* SETUP SECTION wrapper — gives each section its own breathing room. */
    .ce-vc-setup-section {
      display: flex;
      flex-direction: column;
      gap: 8px;
    }

    /* Argue brain picker inside the setup card — same capsule pattern
   as the meta-row version, just placed here. align-self:flex-start
   keeps it from stretching to the full width like a section block. */
    .ce-vc-setup-brain-picker {
      align-self: flex-start;
    }

    .ce-vc-setup-brain-picker .ce-argue-brain-group {
      margin: 0;
    }

    /* PERSONA DROPDOWN — single trigger button, scrollable categorised
   menu. Liquid-glass throughout. White-light highlight on selection,
   no harsh accent fills. Closed = compact; open = panel slides down
   below the trigger with a soft scale-from-top animation. */
    .ce-vc-persona-dropdown {
      position: relative;
    }

    .ce-vc-persona-trigger {
      width: 100%;
      display: flex;
      align-items: center;
      gap: 12px;
      padding: 11px 14px;
      /* b.473 — Engine-popover recipe (matches Argue composer textbox). */
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      border-radius: 20px;
      color: var(--text);
      cursor: pointer;
      text-align: left;
      transition: all .18s var(--ease);
      font-family: inherit;
    }

    .ce-vc-persona-trigger:hover {
      background: var(--lg-fill-hover);
      border-color: rgba(255, 255, 255, .22);
    }

    .ce-vc-persona-dropdown[data-open="true"] .ce-vc-persona-trigger {
      border-color: rgba(255, 255, 255, .55);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .25), 0 6px 24px rgba(255, 255, 255, .06);
    }

    .ce-vc-persona-trigger-emoji {
      font-size: 22px;
      line-height: 1;
      flex-shrink: 0;
    }

    .ce-vc-persona-trigger-text {
      display: flex;
      flex-direction: column;
      gap: 2px;
      flex: 1;
      min-width: 0;
    }

    .ce-vc-persona-trigger-name {
      font-family: var(--font-display);
      font-size: 14px;
      font-weight: 700;
      letter-spacing: -.005em;
      color: var(--text);
    }

    .ce-vc-persona-trigger-desc {
      font-size: 11.5px;
      line-height: 1.4;
      color: var(--text-muted);
      font-weight: 500;
      overflow: hidden;
      text-overflow: ellipsis;
      white-space: nowrap;
    }

    .ce-vc-persona-trigger-caret {
      font-size: 12px;
      color: var(--text-faint);
      transition: transform .2s var(--ease);
      flex-shrink: 0;
    }

    .ce-vc-persona-dropdown[data-open="true"] .ce-vc-persona-trigger-caret {
      transform: rotate(180deg);
      color: var(--text);
    }

    .ce-vc-persona-menu {
      /* Reparented to <body> on first open (escapes ALL ancestor
     stacking / transform / overflow contexts). position:fixed +
     viewport-coord placement set via JS on open. */
      position: fixed;
      display: none;
      /* Hard-hidden when closed */
      max-height: 380px;
      overflow-y: auto;
      padding: 8px;
      /* b.498 — Canonical liquid-glass recipe per user request. */
      background: rgba(255, 255, 255, .03);
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      border-radius: 20px;
      z-index: 1200;
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .16),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      opacity: 0;
      transform: translateY(-4px) scale(.98);
      transform-origin: top center;
      transition: opacity .15s var(--ease), transform .15s var(--ease);
    }

    .ce-vc-persona-menu::-webkit-scrollbar-track {
      background: transparent;
    }

    .ce-vc-persona-menu::-webkit-scrollbar-thumb {
      background: rgba(255, 255, 255, .14);
      border-radius: 999px;
    }

    /* Revealed only when the parent dropdown is open. Switches display
   first so the menu actually exists in the layout before opacity
   transitions in. */
    /* Open state — driven by data-open on the menu itself since the
   menu is reparented to <body> on first open and the dropdown
   ancestor selector no longer reaches it. Both states stay valid
   for safety (covers initial render before the move). */
    .ce-vc-persona-dropdown[data-open="true"] .ce-vc-persona-menu,
    .ce-vc-persona-menu[data-open="true"] {
      display: block;
      opacity: 1;
      pointer-events: auto;
      transform: translateY(0) scale(1);
    }

    .ce-vc-persona-menu::-webkit-scrollbar {
      width: 6px;
    }

    .ce-vc-persona-menu::-webkit-scrollbar-thumb {
      background: var(--lg-stroke);
      border-radius: 3px;
    }

    .ce-vc-persona-group {
      display: flex;
      flex-direction: column;
      gap: 1px;
      padding: 2px 0;
    }

    .ce-vc-persona-group+.ce-vc-persona-group {
      margin-top: 6px;
      padding-top: 8px;
      border-top: 1px solid rgba(255, 255, 255, .06);
    }

    .ce-vc-persona-group-label {
      font-family: var(--font-ui);
      font-size: 9.5px;
      font-weight: 700;
      letter-spacing: .18em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .42);
      padding: 6px 12px 4px;
    }

    .ce-vc-persona-option {
      display: flex;
      align-items: center;
      gap: 10px;
      width: 100%;
      padding: 9px 12px;
      border-radius: 10px;
      background: transparent;
      border: 1px solid transparent;
      color: var(--text);
      cursor: pointer;
      text-align: left;
      transition: background .12s var(--ease);
      font-family: inherit;
    }

    .ce-vc-persona-option:hover {
      background: rgba(255, 255, 255, .07);
    }

    .ce-vc-persona-option.is-active {
      /* Subtle white-light highlight + the checkmark on the right.
     No harsh outline — the row just glows lightly. */
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .04));
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .12) inset,
        0 0 0 1px rgba(255, 255, 255, .10) inset;
      border-color: transparent;
    }

    .ce-vc-persona-option-emoji {
      font-size: 16px;
      line-height: 1;
      flex-shrink: 0;
    }

    .ce-vc-persona-option-text {
      display: flex;
      flex-direction: column;
      gap: 1px;
      flex: 1;
      min-width: 0;
    }

    .ce-vc-persona-option-name {
      font-size: 13px;
      font-weight: 600;
      color: var(--text);
    }

    .ce-vc-persona-option-desc {
      font-size: 11px;
      line-height: 1.35;
      color: var(--text-muted);
      font-weight: 500;
    }

    .ce-vc-persona-option-check {
      font-size: 13px;
      font-weight: 800;
      color: var(--text);
      opacity: 0;
      transition: opacity .12s var(--ease);
      flex-shrink: 0;
    }

    .ce-vc-persona-option.is-active .ce-vc-persona-option-check {
      opacity: 1;
    }

    /* MODE CARDS — Text vs Voice. Mirror of coach mode-cards with same
   liquid-glass + white-light selection language. */
    .ce-vc-mode-cards {
      display: grid;
      grid-template-columns: 1fr 1fr;
      gap: 10px;
    }

    .ce-vc-mode-card {
      /* b.529 — Compacted: padding 14 → 10/12, gap 10 → 6, smaller
     border-radius. Radio dot is hidden (display:none below) and the
     coin price is absolutely positioned at the top-right corner. */
      position: relative;
      display: flex;
      flex-direction: column;
      gap: 6px;
      padding: 10px 12px;
      background: transparent;
      border: 1px solid rgba(255, 255, 255, .18);
      -webkit-backdrop-filter: blur(40px) saturate(1.7);
      backdrop-filter: blur(40px) saturate(1.7);
      box-shadow:
        0 28px 64px -18px rgba(0, 0, 0, .55),
        inset 0 1px 0 rgba(255, 255, 255, .10),
        inset 0 -1px 0 rgba(0, 0, 0, .10);
      border-radius: 14px;
      cursor: pointer;
      transition: all .18s var(--ease);
    }

    /* Hide the radio dot — replaced by the coin price chip in its
   place at the top-right corner. */
    .ce-vc-mode-card .ce-vc-mode-radio {
      display: none !important;
    }

    /* b.530 — Removed: previous absolute-position price chip at top-right.
   The user wants the voice card's "5 min ≈ 55 coins" summary moved
   there instead (see the rule below). The .ce-vc-mode-price renders
   naturally inside .ce-vc-mode-body for text card; on voice card
   it's redundant with the summary so we hide it. */
    .ce-vc-mode-card .ce-vc-mode-price {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      font-size: 12px;
      font-weight: 700;
    }

    .ce-vc-mode-card[data-vmode="voice"] .ce-vc-mode-price {
      display: none !important;
    }

    .ce-vc-mode-card .ce-vc-mode-price .joy-coin {
      width: 1em;
      height: 1em;
    }

    .ce-vc-mode-card .ce-vc-mode-price-unit {
      font-size: 10.5px;
      color: var(--text-muted);
      font-weight: 600;
    }

    /* Voice summary ("5 min ≈ 55 coins") absolutely positioned at the
   top-right corner of the voice card, taking the place where the
   radio dot used to sit. */
    .ce-vc-mode-card[data-vmode="voice"] .ce-vc-voice-summary {
      position: absolute !important;
      top: 8px !important;
      right: 10px !important;
      margin: 0 !important;
      padding: 0 !important;
      display: inline-flex !important;
      align-items: center;
      gap: 6px;
      font-size: 11.5px;
    }

    .ce-vc-mode-card[data-vmode="voice"] .ce-vc-voice-summary-block {
      display: inline-flex;
      align-items: baseline;
      gap: 3px;
    }

    .ce-vc-mode-card[data-vmode="voice"] .ce-vc-voice-summary-num {
      font-size: 13px;
      font-weight: 700;
      line-height: 1;
    }

    .ce-vc-mode-card[data-vmode="voice"] .ce-vc-voice-summary-unit {
      font-size: 10.5px;
      color: var(--text-muted);
      font-weight: 600;
    }

    .ce-vc-mode-card[data-vmode="voice"] .ce-vc-voice-summary-eq {
      font-size: 11px;
      color: var(--text-muted);
    }

    .ce-vc-mode-card[data-vmode="voice"] .ce-vc-voice-summary .joy-coin {
      width: 1em;
      height: 1em;
    }

    .ce-vc-mode-card:hover {
      background: var(--lg-fill-hover);
      border-color: rgba(255, 255, 255, .22);
    }

    .ce-vc-mode-card.on {
      background: var(--lg-fill-hover);
      border-color: rgba(255, 255, 255, .55);
      box-shadow: 0 0 0 1px rgba(255, 255, 255, .22), 0 6px 22px rgba(255, 255, 255, .05);
    }

    .ce-vc-mode-head {
      display: flex;
      align-items: center;
      gap: 8px;
    }

    .ce-vc-mode-ico {
      font-size: 18px;
      line-height: 1;
    }

    .ce-vc-mode-name {
      font-family: var(--font-display);
      font-size: 14px;
      font-weight: 700;
      letter-spacing: -.005em;
      color: var(--text);
      flex: 1;
    }

    .ce-vc-mode-radio {
      width: 14px;
      height: 14px;
      border-radius: 50%;
      border: 1.5px solid rgba(255, 255, 255, .35);
      position: relative;
      transition: all .18s var(--ease);
    }

    .ce-vc-mode-card.on .ce-vc-mode-radio {
      border-color: rgba(255, 255, 255, .85);
    }

    .ce-vc-mode-card.on .ce-vc-mode-radio::after {
      content: '';
      position: absolute;
      inset: 2px;
      border-radius: 50%;
      background: rgba(255, 255, 255, .85);
      box-shadow: 0 0 6px rgba(255, 255, 255, .5);
    }

    .ce-vc-mode-body {
      display: flex;
      flex-direction: column;
      gap: 6px;
    }

    .ce-vc-mode-price {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      font-family: var(--font-display);
      font-size: 14px;
      font-weight: 700;
      color: var(--text);
    }

    .ce-vc-mode-price .joy-coin {
      width: 1.1em;
      height: 1.1em;
    }

    .ce-vc-mode-price-unit {
      font-size: 11px;
      font-weight: 600;
      color: var(--text-muted);
      margin-left: 1px;
    }

    .ce-vc-mode-hint {
      font-size: 11.5px;
      line-height: 1.4;
      color: var(--text-muted);
      margin: 0;
    }

    /* b.537 — COMPACT ARGUE BRAIN pinned to the top-right of the Text
   chat mode card. Mirror position to the voice card's "5 min ≈ 60
   coins" summary; both cards now have a small chip in the same
   corner so they read as a pair. No external label — the pill's own
   "BRAIN" segment is the only label needed, and the surrounding
   "Text chat" card title already says where it applies.

   Reverts b.536's bottom-section layout (which made the card much
   taller than the voice card and broke visual balance).

   Visibility:
   - Only the selected (.on) text card shows the brain switch.
   - The voice card never gets one (defensive selector below). */
    .ce-vc-text-brain {
      position: absolute;
      top: 8px;
      right: 10px;
      margin: 0;
      padding: 0;
      background: transparent;
      border: none;
    }

    /* Compact pill: tight padding + small font so it fits the card's
   top-right without crowding the "Text chat" title on the left.
   Overrides the global .ce-argue-brain-group / .ce-ab-* sizes. */
    .ce-vc-text-brain .ce-argue-brain-group {
      padding: 2px !important;
      gap: 1px !important;
      border-radius: 999px;
    }

    .ce-vc-text-brain .ce-ab-label {
      padding: 0 7px 0 9px !important;
      font-size: 9px !important;
      letter-spacing: .16em !important;
    }

    .ce-vc-text-brain .ce-ab-divider {
      height: 13px !important;
      margin: 0 2px !important;
    }

    .ce-vc-text-brain .ce-ab-seg {
      padding: 3px 8px !important;
      font-size: 11px !important;
      gap: 4px !important;
    }

    .ce-vc-text-brain .ce-ab-dot {
      width: 6px !important;
      height: 6px !important;
    }

    .ce-vc-text-brain .ce-ab-variant {
      padding-left: 5px !important;
      margin-left: 1px !important;
      font-size: 10px !important;
    }

    /* Hide the brain switch on the unselected text card, AND on the
   voice card itself (defensive — the picker only exists in the
   text card's DOM, but covers any accidental clone). */
    .ce-vc-mode-card:not(.on) .ce-vc-text-brain {
      display: none !important;
    }

    .ce-vc-mode-card[data-vmode="voice"] .ce-vc-text-brain {
      display: none !important;
    }

    /* Voice dial (inside voice mode card) */
    .ce-vc-dial {
      display: flex;
      flex-direction: column;
      gap: 2px;
      margin-top: 2px;
    }

    .ce-vc-dial-input {
      -webkit-appearance: none;
      appearance: none;
      width: 100%;
      height: 6px;
      background: rgba(255, 255, 255, .08);
      border-radius: 999px;
      outline: none;
    }

    .ce-vc-dial-input::-webkit-slider-thumb {
      -webkit-appearance: none;
      appearance: none;
      width: 16px;
      height: 16px;
      border-radius: 50%;
      background: #fff;
      border: 2px solid rgba(255, 255, 255, .55);
      cursor: pointer;
      box-shadow: 0 0 0 4px rgba(255, 255, 255, .05), 0 2px 8px rgba(0, 0, 0, .3);
      transition: transform .12s var(--ease);
    }

    .ce-vc-dial-input::-webkit-slider-thumb:hover {
      transform: scale(1.12);
    }

    .ce-vc-dial-input::-moz-range-thumb {
      width: 16px;
      height: 16px;
      border-radius: 50%;
      background: #fff;
      border: 2px solid rgba(255, 255, 255, .55);
      cursor: pointer;
    }

    .ce-vc-dial-scale {
      display: flex;
      justify-content: space-between;
      font-family: var(--font-ui);
      font-size: 9.5px;
      color: var(--text-faint);
      margin-top: 2px;
    }

    .ce-vc-voice-summary {
      display: flex;
      align-items: center;
      gap: 8px;
      padding-top: 4px;
    }

    .ce-vc-voice-summary-block {
      display: inline-flex;
      align-items: baseline;
      gap: 3px;
      font-family: var(--font-display);
    }

    .ce-vc-voice-summary-num {
      font-size: 18px;
      font-weight: 800;
      letter-spacing: -.01em;
      color: var(--text);
      font-variant-numeric: tabular-nums;
    }

    .ce-vc-voice-summary-unit {
      font-size: 11px;
      font-weight: 600;
      color: var(--text-muted);
    }

    .ce-vc-voice-summary-eq {
      font-size: 14px;
      color: var(--text-faint);
      font-weight: 600;
    }

    .ce-vc-voice-summary-block .joy-coin {
      width: 1.1em;
      height: 1.1em;
    }

    /* Begin button cost suffix — softer hairline divider that matches
   the rest of the glass language. White light, not a hard rule. */
    .ce-vc-setup-begin-cost {
      display: inline-flex;
      align-items: center;
      gap: 5px;
      margin-left: 10px;
      padding-left: 12px;
      border-left: 1px solid rgba(255, 255, 255, .14);
      font-family: var(--font-display);
      font-weight: 800;
      color: var(--text);
      opacity: .92;
    }

    .ce-vc-setup-begin-cost .joy-coin {
      width: 1.2em;
      height: 1.2em;
    }

    .ce-vc-setup-begin-num {
      font-variant-numeric: tabular-nums;
    }

    .ce-vc-setup-begin-suffix {
      font-size: 11px;
      font-weight: 600;
      opacity: .72;
      margin-left: 1px;
    }

    .ce-vc-setup-begin-cost.free {
      border-left: none;
      padding-left: 0;
      margin-left: 8px;
    }

    .ce-vc-setup-begin-free {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 800;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: var(--text);
      opacity: .85;
    }

    /* CUSTOM PERSONA — textarea wrapper. */
    .ce-vc-custom-wrap {
      /* b.511 — Old !important overrides removed. The .lg-glass-input
     primitive class (added on the HTML element) now provides the
     wrapper's glass + 14px rounded corners + 1px hairline. Only
     layout-specific properties left here. */
      display: flex;
      flex-direction: column;
      gap: 10px;
    }

    .ce-vc-custom-label {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .14em;
      text-transform: uppercase;
      color: var(--text-faint);
    }

    .ce-vc-custom-input {
      /* b.505 — ROOT CAUSE FOUND. Line ~810 has a global rule with
     !important: `[data-theme] textarea{border-radius:22px !important}`.
     EVERY textarea on the page got 22px rounded corners — that was
     the visible inner rounded shape behind the placeholder. Override
     to 0 here + force every invisible property with !important so
     no other global rule can paint a boundary on this textarea. */
      width: 100% !important;
      max-width: 100% !important;
      box-sizing: border-box !important;
      display: block !important;
      font-family: var(--font-body);
      font-size: 13.5px;
      line-height: 1.45;
      color: var(--text);
      background: transparent !important;
      background-color: transparent !important;
      border: 0 !important;
      border-radius: 0 !important;
      outline: 0 !important;
      box-shadow: none !important;
      resize: vertical;
      min-height: 44px;
      padding: 0 !important;
      margin: 0 !important;
    }

    .ce-vc-custom-input::placeholder {
      color: var(--text-faint);
      font-style: italic;
    }

    /* SETUP FOOT — Begin button row. */
    .ce-vc-setup-foot {
      display: flex;
      justify-content: stretch;
      padding-top: 6px;
    }

    /* b.311 — Unified composer: textarea on the left, Begin button
   embedded on the right. Replaces the old standalone Begin button
   so the user can type their position right here without leaving
   the setup card. Mirrors the main chat-composer aesthetic. */
    /* ════════════════════════════════════════════════════════════
   b.513 — ARGUE SETUP COMPOSER · MIRRORS MAIN CHAT .ce-input-row
   ────────────────────────────────────────────────────────────
   Pattern matches the main chat composer exactly: an outer rounded
   glass row that holds a transparent textarea + a SEPARATE pill
   button on the right. Same dimensions, same glass recipe, same
   button anatomy (label cell + cost cell with hairline divider).
   The .lg-glass-input class on .ce-vc-setup-composer provides the
   canonical glass; this rule overrides padding so the row hosts
   its children edge-to-edge. */
    .ce-vc-setup-composer {
      position: relative;
      flex: 1 1 auto;
      display: flex;
      align-items: center;
      /* b.516 — gap:0 so the Begin button hugs the right side of the
     shell directly; padding on the right side reduced from 10 to 4
     so the button is pushed further right (closer to the shell's
     right edge, covering more of it).
     b.538 — Left padding 18 → 13 per user request: shift placeholder
     and typed text 5px to the left.
     b.539 — Left padding 13 → 3 per user request: another 10px left.
     b.551 — Right padding bumped 4 → 150 because the Begin button
     is now position:absolute and no longer reserves space in the
     flex track. Without this, the textarea would flow under it. */
      gap: 0;
      padding: 8px 150px 8px 3px !important;
      border-radius: 24px !important;
    }

    .ce-vc-setup-composer-input {
      flex: 1 1 auto;
      /* Transparent textarea — the parent composer carries the glass. */
      background: transparent !important;
      border: 0 !important;
      outline: 0 !important;
      box-shadow: none !important;
      border-radius: 0 !important;
      resize: none;
      color: var(--text);
      font-family: var(--font-body);
      font-size: 14.5px;
      line-height: 1.45;
      letter-spacing: -.005em;
      min-height: 32px;
      max-height: 160px;
      /* b.520 — Reverted: placeholder + typed text sit LEFT-aligned at
     the start of the box per user request. */
      text-align: left;
      /* b.541 — margin / padding / width moved out into the [data-theme]
     rule below. Reason: `textarea.lg-glass-bare` (specificity 0,1,1)
     was winning against `.ce-vc-setup-composer-input` (0,1,0) for
     all three properties, so b.538/b.539/b.540 only worked when the
     parent shell's padding-left was also being reduced — not from
     any change to the textarea itself. Authoring the override at a
     higher specificity finally lands it on the textarea. */
    }

    /* b.541 — Higher-specificity override (0,2,1) so we beat the
   `textarea.lg-glass-bare` global at 0,1,1. Applies margin/padding/
   width to the actual textarea so left-shifts in this rule take
   effect.
   b.542 — Layered approach to GUARANTEE the left shift sticks. The
   previous attempts kept being silently overridden somewhere in the
   cascade. Three redundant mechanisms now:
   (a) `transform: translateX(-30px)` — almost no global rule sets
       `transform` on textareas, so this is the safe one.
   (b) Maximum-specificity selector (0,4,2) chaining every class on
       the element so no other rule can win on margin/padding/width.
   (c) `text-indent` as an extra nudge for the placeholder/first
       line in case transforms ever get clipped. */
    [data-theme] .ce-vc-setup .ce-vc-setup-composer textarea.ce-vc-setup-composer-input.lg-glass-bare {
      padding: 8px 6px !important;
      margin: 0 !important;
      width: auto !important;
      flex: 1 1 auto !important;
      transform: translateX(-30px) !important;
      text-indent: 0 !important;
    }

    .ce-vc-setup-composer-input::placeholder {
      color: rgba(255, 255, 255, .42);
      font-style: italic;
    }

    /* Begin button — separate pill, same anatomy as the main chat
   .ce-send-btn. 48px tall, padding:0 on shell, divided label/cost
   cells with a hairline border between them. */
    .ce-vc-setup-composer-btn {
      /* b.551 — Switched from flex-stretched sizing to POSITION:ABSOLUTE
     so the pill literally fills the shell from outer-top to outer-
     bottom regardless of textarea content height. The composer
     parent has position:relative (above), so top/right/bottom = -1px
     pins the button's outer border line directly onto the shell's
     outer border line. This is more reliable than relying on
     align-self:stretch + negative margins, which kept leaving a
     visible vertical gap. */
      position: absolute;
      top: -1px;
      right: -1px;
      bottom: -1px;
      display: inline-flex;
      align-items: center;
      height: auto;
      padding: 0;
      /* b.520 — Shift dialed BACK 20px (was +25, now +5). Begin pill
     sits comfortably inside the composer's right edge.
     b.541 — Shifted ANOTHER 15px right per user request: +5 → +20.
     b.543 — Reverted b.541's +20 shift back to +5 (button looked
     stretched past the shell's right edge with margin-right also at
     -20px).
     b.544 — Shift the button 15px right via TRANSFORM ONLY (margin
     stays at -5px). This moves only the visual position; layout
     space and button width stay identical to b.543, so no
     stretched-looking pill this time.
     b.545 — Shifted ANOTHER 5px right per user request: +20 → +25.
     b.546 — Negative top/bottom margins (-8px each) so the button
     extends through the composer shell's 8px vertical padding and
     visually matches the shell's full inside-edge height.
     b.547 — Nudged 5px LEFT per user request: +25 → +20.
     b.548 — Nudged 8px LEFT per user request: +20 → +12.
     b.549 — Increased vertical bleed so the pill's outer edges
     align EXACTLY with the shell's outer edges. The shell has 8px
     vertical padding + 1px border = 9px inset on each side; +1px
     extra (10px total) covers the button's own border alignment so
     the pill reads as the same height as the surrounding shell.
     Top/bottom margins: -8 → -10.
     b.551 — Moved to position:absolute (top/right/bottom -1px each)
     so vertical fill is guaranteed. Margins now zero. The previous
     translateX(12px) horizontal offset is preserved so the button's
     horizontal placement stays where the user wanted.
     b.552 — Nudged 10px LEFT per user request: +12 → +2.
     b.553 — Nudged 1px LEFT per user request: +2 → +1. */
      margin: 0;
      transform: translateX(1px);
      border-radius: 999px;
      background: rgba(255, 255, 255, .04);
      border: 1.5px solid rgba(255, 255, 255, .30);
      -webkit-backdrop-filter: blur(22px) saturate(1.30);
      backdrop-filter: blur(22px) saturate(1.30);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .18) inset,
        0 -1px 0 rgba(255, 255, 255, .06) inset;
      color: #fff;
      font-family: var(--font-display);
      font-weight: 700;
      font-size: 13px;
      letter-spacing: .04em;
      text-transform: uppercase;
      cursor: pointer;
      transition: transform .15s var(--ease), background .15s var(--ease), border-color .15s var(--ease);
      overflow: hidden;
      line-height: 1;
    }

    .ce-vc-setup-composer-btn:hover:not(:disabled) {
      /* b.553 — Hover transform matches resting +1px x-shift. */
      transform: translate(1px, -1px);
      background: rgba(255, 255, 255, .10);
      border-color: rgba(255, 255, 255, .45);
    }

    .ce-vc-setup-composer-btn:disabled {
      opacity: .4;
      cursor: not-allowed;
      transform: none;
    }

    .ce-vc-setup-composer-btn-label {
      /* b.545 — Horizontal padding 18 → 11 to tighten the BEGIN cell.
     b.546 — Tightened further: 11 → 8. */
      padding: 0 8px;
      height: 100%;
      display: inline-flex;
      align-items: center;
      font-weight: 700;
    }

    /* Cost cell — b.542: removed the lighter wash + hairline divider
   that produced a visible two-tone "second layer" inside the Begin
   pill (per user feedback). The cost text + coin now ride on the
   button's own glass surface with no inner cell. */
    .ce-vc-setup-begin-cost {
      /* b.545 — Compact pass: gap 6 → 4, padding 0 14px → 0 8px.
     b.546 — Tighter again: gap 4 → 3, padding 0 8px → 0 5px. */
      display: inline-flex;
      align-items: center;
      gap: 3px;
      padding: 0 5px;
      height: 100%;
      border-left: 0 !important;
      background: transparent !important;
      font-size: 13px;
      font-weight: 700;
      letter-spacing: .02em;
      text-transform: none;
    }

    .ce-vc-setup-begin-cost .joy-coin {
      width: 1.4em;
      height: 1.4em;
    }

    .ce-vc-setup-composer-btn-arrow {
      display: inline-flex;
      align-items: center;
      justify-content: center;
      /* b.545 — Padding-right 14 → 9; small left padding so the arrow
     doesn't sit flush against the coin/cost.
     b.546 — Tighter: 9 → 6 right; left 2 → 1. */
      padding: 0 6px 0 1px;
      height: 100%;
      font-size: 14px;
      font-weight: 700;
      opacity: .85;
    }

    @media (max-width: 640px) {
      .ce-vc-setup-composer {
        border-radius: 14px;
      }

      .ce-vc-setup-composer-input {
        padding: 12px 14px;
        font-size: 14px;
        min-height: 48px;
      }

      .ce-vc-setup-composer-btn {
        padding: 9px 12px;
        font-size: 12.5px;
        margin: 5px;
      }
    }

    /* Begin button — proper liquid-glass pill. Lighter base + layered
   highlight gradient + soft border that just kisses the edge. The
   white-light effect comes from inset shadow + ambient glow, NOT
   from a heavy stroked outline. */
    .ce-vc-setup-begin {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      padding: 11px 22px;
      border-radius: 999px;
      background:
        linear-gradient(180deg, rgba(255, 255, 255, .10), rgba(255, 255, 255, .02)),
        var(--lg-fill);
      border: 1px solid rgba(255, 255, 255, .22);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      color: var(--text);
      font-family: var(--font-display);
      font-size: 14px;
      font-weight: 800;
      letter-spacing: -.005em;
      cursor: pointer;
      transition: all .18s var(--ease);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .18) inset,
        0 -1px 0 rgba(0, 0, 0, .20) inset,
        0 8px 24px rgba(0, 0, 0, .22),
        0 0 0 0 rgba(255, 255, 255, 0);
    }

    .ce-vc-setup-begin:hover:not(:disabled) {
      transform: translateY(-1px);
      border-color: rgba(255, 255, 255, .36);
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .24) inset,
        0 -1px 0 rgba(0, 0, 0, .22) inset,
        0 12px 30px rgba(0, 0, 0, .28),
        0 0 22px rgba(255, 255, 255, .08);
    }

    .ce-vc-setup-begin:active:not(:disabled) {
      transform: translateY(0);
    }

    .ce-vc-setup-begin:disabled {
      opacity: .40;
      cursor: not-allowed;
      transform: none;
      box-shadow: none;
    }

    /* CONVICTION METER — sits in the controls row on the extreme right,
   in line with the Intensity dial. Inverted Coach impression-meter
   pattern. Color shifts by zone. */
    .ce-vc-conviction {
      display: flex;
      flex-direction: column;
      gap: 5px;
      min-width: 160px;
      max-width: 220px;
      padding: 6px 12px;
      border-radius: 10px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      align-self: center;
      margin-left: auto;
      /* push to the extreme right of the row */
    }

    .ce-vc-conviction-track {
      height: 4px;
      border-radius: 999px;
      background: rgba(255, 255, 255, .08);
      overflow: hidden;
    }

    .ce-vc-conviction-fill {
      height: 100%;
      width: 0%;
      border-radius: 999px;
      background: #dc4a4a;
      /* default: opposed */
      transition: width .55s var(--ease), background-color .35s var(--ease);
    }

    .ce-vc-conviction[data-zone="dismissive"] .ce-vc-conviction-fill {
      background: #9b2a2a;
    }

    .ce-vc-conviction[data-zone="firm"] .ce-vc-conviction-fill {
      background: #dc4a4a;
    }

    .ce-vc-conviction[data-zone="hearing"] .ce-vc-conviction-fill {
      background: #f59e0b;
    }

    .ce-vc-conviction[data-zone="considering"] .ce-vc-conviction-fill {
      background: #d6c14a;
    }

    .ce-vc-conviction[data-zone="thinking"] .ce-vc-conviction-fill {
      background: #a4ce4f;
    }

    .ce-vc-conviction[data-zone="shifted"] .ce-vc-conviction-fill {
      background: var(--accent-bright, #5be17a);
    }

    .ce-vc-conviction[data-zone="concede"] .ce-vc-conviction-fill {
      background: linear-gradient(90deg, var(--accent-bright, #5be17a), #ffd86e);
    }

    /* Floating ± delta pop — appears briefly above the meter on every
   turn so the user sees the per-turn nudge, not just a creeping bar. */
    .ce-vc-conviction {
      position: relative;
    }

    .ce-vc-conviction-pop {
      position: absolute;
      right: 10px;
      top: -22px;
      font-family: var(--font-display);
      font-size: 14px;
      font-weight: 800;
      letter-spacing: -.005em;
      pointer-events: none;
      opacity: 0;
      animation: ce-conv-pop 1.4s var(--ease) forwards;
      font-variant-numeric: tabular-nums;
      text-shadow: 0 1px 4px rgba(0, 0, 0, .35);
    }

    .ce-vc-conviction-pop.pos {
      color: #5be17a;
    }

    .ce-vc-conviction-pop.neg {
      color: #ff6b6b;
    }

    @keyframes ce-conv-pop {
      0% {
        opacity: 0;
        transform: translateY(4px) scale(.85);
      }

      20% {
        opacity: 1;
        transform: translateY(0) scale(1.05);
      }

      60% {
        opacity: 1;
        transform: translateY(-4px) scale(1);
      }

      100% {
        opacity: 0;
        transform: translateY(-12px) scale(.95);
      }
    }

    .ce-vc-conviction-label {
      display: flex;
      align-items: baseline;
      justify-content: space-between;
      gap: 8px;
      font-family: var(--font-ui);
    }

    .ce-vc-conviction-eyebrow {
      font-size: 9px;
      font-weight: 700;
      letter-spacing: .1em;
      text-transform: uppercase;
      color: var(--text-muted);
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
    }

    .ce-vc-conviction-value {
      font-size: 11px;
      font-weight: 800;
      color: var(--text);
      font-variant-numeric: tabular-nums;
    }

    .ce-vc-conviction.pulse {
      animation: ce-conv-pulse .45s var(--ease);
    }

    @keyframes ce-conv-pulse {
      0% {
        transform: scale(1);
      }

      35% {
        transform: scale(1.04);
      }

      100% {
        transform: scale(1);
      }
    }

    /* SWITCH SIDES BUTTON — appears in head after 3+ assistant turns. */
    .ce-vc-switch-btn {
      display: inline-flex;
      align-items: center;
      gap: 6px;
      padding: 6px 11px;
      border-radius: 999px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur-light);
      backdrop-filter: var(--lg-blur-light);
      color: var(--text-muted);
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 600;
      letter-spacing: .02em;
      cursor: pointer;
      transition: all .18s var(--ease);
      align-self: center;
    }

    .ce-vc-switch-btn:hover {
      background: var(--lg-fill-hover);
      color: var(--text);
    }

    .ce-vc-switch-btn.is-on {
      background: var(--accent-bright);
      color: #0a1f12;
      border-color: transparent;
    }

    /* SESSION SUMMARY — appended to thread when argue session ends.
   Compact, structured, in-context (no separate modal). */
    .ce-vc-summary {
      margin: 14px 8px 10px;
      padding: 14px 16px;
      border-radius: 16px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      -webkit-backdrop-filter: var(--lg-blur);
      backdrop-filter: var(--lg-blur);
      display: flex;
      flex-direction: column;
      gap: 8px;
    }

    .ce-vc-summary-head {
      display: flex;
      align-items: flex-start;
      justify-content: space-between;
      gap: 12px;
    }

    .ce-vc-summary-eyebrow {
      font-family: var(--font-ui);
      font-size: 10px;
      font-weight: 700;
      letter-spacing: .16em;
      text-transform: uppercase;
      color: var(--text-faint);
      margin-top: 4px;
    }

    .ce-vc-summary-score {
      font-family: var(--font-display);
      font-size: 32px;
      font-weight: 800;
      letter-spacing: -.01em;
      line-height: 1;
      color: var(--text);
    }

    .ce-vc-summary-score span {
      font-size: 14px;
      font-weight: 600;
      color: var(--text-faint);
      margin-left: 2px;
    }

    .ce-vc-summary-score[data-zone="firm"] {
      color: #dc4a4a;
    }

    .ce-vc-summary-score[data-zone="hearing"] {
      color: #f59e0b;
    }

    .ce-vc-summary-score[data-zone="thinking"] {
      color: #a4ce4f;
    }

    .ce-vc-summary-score[data-zone="shifted"] {
      color: var(--accent-bright, #5be17a);
    }

    .ce-vc-summary-score[data-zone="concede"] {
      color: #ffd86e;
    }

    .ce-vc-summary-zone {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 700;
      letter-spacing: .12em;
      text-transform: uppercase;
      color: var(--text-muted);
    }

    .ce-vc-summary-verdict {
      font-size: 14px;
      line-height: 1.5;
      color: var(--text);
      margin-top: 2px;
    }

    .ce-vc-summary-row {
      font-size: 12.5px;
      line-height: 1.45;
      color: var(--text-muted);
      display: flex;
      align-items: center;
      gap: 6px;
      flex-wrap: wrap;
    }

    .ce-vc-summary-row em {
      color: var(--text);
      font-style: normal;
    }

    .ce-vc-summary-delta {
      font-family: var(--font-ui);
      font-size: 11px;
      font-weight: 800;
      padding: 2px 8px;
      border-radius: 999px;
      font-variant-numeric: tabular-nums;
    }

    .ce-vc-summary-delta.pos {
      background: rgba(91, 225, 122, .16);
      color: #5be17a;
    }

    .ce-vc-summary-delta.neg {
      background: rgba(220, 74, 74, .16);
      color: #dc4a4a;
    }

    .ce-vc-summary-trend {
      font-size: 12px;
      line-height: 1.5;
      color: var(--text-muted);
      font-style: italic;
      padding: 6px 0 0;
      border-top: 1px dashed var(--lg-stroke);
      margin-top: 4px;
    }

    .ce-vc-summary-trend b {
      color: var(--text);
      font-weight: 700;
      font-style: normal;
    }

    .ce-vc-summary-actions {
      display: flex;
      gap: 8px;
      flex-wrap: wrap;
      margin-top: 6px;
    }

    .ce-vc-summary-btn {
      flex: 1;
      min-width: 140px;
      padding: 8px 12px;
      border-radius: 10px;
      background: var(--lg-fill);
      border: 1px solid var(--lg-stroke);
      color: var(--text);
      font-family: var(--font-ui);
      font-size: 12px;
      font-weight: 600;
      cursor: pointer;
      transition: all .18s var(--ease);
    }

    .ce-vc-summary-btn:hover {
      background: var(--lg-fill-hover);
      border-color: var(--lg-stroke-hi, var(--lg-stroke));
    }

    /* Mobile — argue setup stack tighter, persona grid single column. */
    @media (max-width: 640px) {
      .ce-vc-setup {
        padding: 16px 14px 14px;
        gap: 14px;
      }

      .ce-vc-setup-title {
        font-size: 18px;
      }

      .ce-vc-setup-sub {
        font-size: 12.5px;
      }

      .ce-vc-persona-grid {
        grid-template-columns: 1fr 1fr;
        gap: 6px;
      }

      .ce-vc-persona-card {
        min-height: 64px;
        padding: 9px 10px;
      }

      .ce-vc-persona-name {
        font-size: 12.5px;
      }

      .ce-vc-persona-desc {
        font-size: 10.5px;
        -webkit-line-clamp: 2;
      }

      .ce-vc-conviction {
        min-width: 100px;
        max-width: 130px;
        padding: 4px 8px;
      }

      .ce-vc-conviction-eyebrow {
        font-size: 8.5px;
      }

      .ce-vc-switch-btn span {
        display: none;
      }

      .ce-vc-switch-btn {
        padding: 6px;
      }
    }

    /* Empty hidden helpers */
    [hidden] {
      display: none !important
    }

    /* === CHAT ENGINE CSS END === */


    /* ============================================================
   MOBILE — chat surface optimisation.
   Everything inside these media queries activates ONLY at smaller
   viewports. Desktop CSS above is untouched, so layout is pixel-
   identical at 769px+. Three breakpoints:
     - ≤900px  : tablet / iPad portrait — minor tightening
     - ≤640px  : phone landscape & most phones — real reflow
     - ≤380px  : small phones — final compaction
   Touch targets stay ≥44px wherever a user taps. Input fonts stay
   ≥16px so iOS Safari doesn't auto-zoom. The liquid-glass system
   (--lg-fill / --lg-blur) is preserved everywhere — only sizes,
   spacing, and stacking change.
   ============================================================ */

    @media (max-width: 900px) {

      /* HEADER — tighten paddings, drop build-tag, shrink balance text */
      .header {
        padding: 10px 14px;
        gap: 10px;
      }

      .build-tag {
        display: none;
      }

      .brand-name {
        font-size: 15px;
      }

      .tabs {
        gap: 2px;
      }

      .bal-amount,
      .bal-daily {
        padding: 5px 10px;
        font-size: 11px;
      }

      .account-btn,
      .theme-toggle {
        padding: 6px 10px;
        font-size: 11px;
      }

      .bal-add {
        padding: 6px 10px;
        font-size: 11px;
      }

      /* STAGE / MAIN — ease padding so messages get more horizontal room */
      .main {
        padding: 0 14px 14px;
        height: calc(100vh - 56px);
      }

      .ce-stage {
        max-width: 100%;
      }

      .ce-thread {
        padding: 6px 2px;
      }

      /* INPUT — stack tools tighter, send pill stays comfortable */
      .ce-input-row {
        gap: 8px;
      }

      .ce-input-tools {
        gap: 4px;
      }

      .ce-tool-btn {
        width: 34px;
        height: 34px;
      }

      .ce-tool-btn svg {
        width: 15px;
        height: 15px;
      }
    }

    @media (max-width: 640px) {

      /* HEADER — collapse to two compact rows of essentials.
     Logo + balance up top; account/theme become icon-only.
     The tabs row (modes) is rendered separately below the header. */
      .header {
        padding: 8px 12px;
        gap: 6px;
        flex-wrap: wrap;
        row-gap: 8px;
      }

      .brand {
        flex: 1;
        min-width: 0;
      }

      .brand-name {
        font-size: 14px;
      }

      .brand-name em {
        display: none;
      }

      .tabs {
        order: 99;
        /* push to second row */
        flex-basis: 100%;
        overflow-x: auto;
        -webkit-overflow-scrolling: touch;
        scrollbar-width: none;
        padding-bottom: 2px;
      }

      .tabs::-webkit-scrollbar {
        display: none;
      }

      .tab-btn {
        flex: none;
      }

      /* Balance group — keep the two coin readouts visible, drop the
     "Add coins" button label down to a + glyph. */
      .bal-amount {
        padding: 4px 8px;
        font-size: 11px;
      }

      .bal-daily-label {
        display: none;
      }

      /* hide "FREE TODAY" caption */
      .bal-daily .num {
        font-size: 12px;
      }

      .bal-add {
        padding: 0;
        width: 30px;
        height: 30px;
        font-size: 18px;
        line-height: 1;
        border-radius: 999px;
        display: inline-flex;
        align-items: center;
        justify-content: center;
      }

      .bal-add::before {
        content: '+';
      }

      .bal-add {
        font-size: 0;
      }

      /* hide existing label text */
      .bal-add::before {
        font-size: 18px;
      }

      .account-btn {
        padding: 0;
        width: 34px;
        height: 34px;
        gap: 0;
      }

      .account-btn span:not(.ava) {
        display: none;
      }

      .theme-toggle {
        padding: 0;
        width: 34px;
        height: 34px;
        gap: 0;
      }

      .theme-toggle span {
        display: none;
      }

      /* MODE SELECTOR — horizontal scroll if needed; pill labels stay */
      .ce-mode-selector {
        overflow-x: auto;
        -webkit-overflow-scrolling: touch;
        scrollbar-width: none;
        padding-bottom: 2px;
        margin: 0 -14px;
        /* bleed to edges so scroll feels native */
        padding-left: 14px;
        padding-right: 14px;
      }

      .ce-mode-selector::-webkit-scrollbar {
        display: none;
      }

      .ce-mode-btn {
        flex: none;
        padding: 7px 12px;
        font-size: 13px;
      }

      /* WELCOME / HERO — smaller type, less vertical breathing room */
      .ce-welcome {
        padding: 24px 12px;
      }

      .ce-welcome h1 {
        font-size: 26px;
        line-height: 1.15;
      }

      .ce-welcome p {
        font-size: 14px;
      }

      .ce-welcome-hints {
        gap: 6px;
      }

      .ce-welcome-hint {
        padding: 8px 12px;
        font-size: 12px;
      }

      /* CHAT THREAD + BUBBLES — wider bubbles, tighter padding */
      .ce-thread {
        padding: 4px 0;
      }

      .ce-msg {
        max-width: 100%;
      }

      .ce-msg-bubble {
        padding: 12px 14px;
        font-size: 14.5px;
        line-height: 1.55;
      }

      .ce-msg-user .ce-msg-bubble {
        max-width: 88%;
      }

      .ce-msg-meta {
        font-size: 11px;
      }

      .ce-msg-copy {
        opacity: .7;
      }

      /* always visible — hover doesn't exist on touch */

      /* INPUT — full width, comfortable tap targets, one-row tools */
      .ce-inputbar {
        padding: 0;
      }

      .ce-input-row {
        padding: 3px 8px 3px 8px;
        gap: 6px;
        border-radius: 18px;
      }

      .ce-input-tools {
        gap: 3px;
        flex: none;
      }

      .ce-tool-btn {
        width: 36px;
        height: 36px;
      }

      .ce-tool-btn svg {
        width: 16px;
        height: 16px;
      }

      .ce-textarea {
        font-size: 16px;
        /* prevents iOS auto-zoom on focus */
        line-height: 1.45;
        min-height: 36px;
        padding: 6px 4px;
      }

      .ce-send-btn {
        min-width: 44px;
        min-height: 44px;
        padding: 6px 12px;
        border-radius: 14px;
      }

      .ce-send-arrow {
        width: 18px;
        height: 18px;
      }

      .ce-send-cost {
        font-size: 13px;
      }

      /* INPUT META (brain pills + actions row) — wrap, compact pills */
      .ce-input-meta {
        flex-wrap: wrap;
        gap: 6px;
        row-gap: 8px;
        padding: 6px 2px 0;
      }

      .ce-pill-row {
        gap: 4px;
        flex-wrap: wrap;
      }

      .ce-model-pill {
        padding: 5px 10px;
        font-size: 12px;
      }

      .ce-meta-actions {
        gap: 4px;
        margin-left: auto;
      }

      .ce-history-btn,
      .ce-newchat-btn {
        padding: 6px 10px;
        font-size: 12px;
      }

      .ce-history-btn .ce-hb-ico,
      .ce-newchat-btn .ce-nc-ico {
        width: 14px;
        height: 14px;
      }

      /* ARGUE BRAIN GROUP — only shows in argue mode but worth covering */
      .ce-argue-brain-group {
        flex-wrap: wrap;
        padding: 4px 6px;
      }

      .ce-ab-label {
        font-size: 10px;
      }

      .ce-ab-seg {
        padding: 5px 9px;
        font-size: 11px;
      }

      /* FILE CHIPS — let them wrap to multiple rows */
      .ce-file-row {
        padding: 4px 0;
      }

      .ce-file-chip {
        font-size: 11px;
        padding: 4px 8px;
        max-width: 100%;
      }

      .ce-file-chip .ce-fc-name {
        max-width: 140px;
      }

      /* HISTORY POPOVER — go near-fullscreen on phone for usability */
      .ce-history-popover {
        position: fixed !important;
        inset: auto 8px 8px 8px !important;
        width: auto !important;
        max-width: none !important;
        max-height: 78vh !important;
        border-radius: 20px;
      }

      .ce-hp-head {
        padding: 10px 12px;
      }

      .ce-hp-search {
        font-size: 14px;
        padding: 9px 12px;
      }

      .ce-hp-list {
        padding: 4px 6px 8px;
      }

      .ce-hp-row {
        padding: 8px 8px;
      }

      .ce-hp-title {
        font-size: 13.5px;
      }

      .ce-hp-preview {
        font-size: 12px;
        -webkit-line-clamp: 2;
      }

      .ce-hp-time {
        font-size: 10.5px;
      }

      /* SETTINGS / API KEYS MODAL — full-bleed bottom sheet feel */
      .ce-modal {
        width: calc(100% - 24px);
        max-width: none;
        padding: 18px 16px;
        border-radius: 20px;
        max-height: 88vh;
        overflow-y: auto;
      }

      .ce-modal h3 {
        font-size: 17px;
      }

      .ce-field input {
        font-size: 16px;
      }

      /* iOS zoom guard */
      .ce-modal-foot {
        flex-wrap: wrap;
        gap: 8px;
      }

      .ce-modal-save {
        flex: 1;
        min-width: 120px;
      }

      /* DEBATE MODAL — already has its own polish; just shrink shell */
      .ce-dm-shell {
        width: calc(100% - 16px);
        max-width: none;
        max-height: 92vh;
      }

      .ce-dm-head {
        padding: 10px 12px;
      }

      .ce-dm-question {
        font-size: 14px;
      }

      .ce-dm-body {
        padding: 8px 12px;
      }

      .ce-dm-grid {
        grid-template-columns: 1fr;
        gap: 10px;
      }

      /* stack the 3 voices */
      .ce-dm-stance {
        flex-wrap: wrap;
        gap: 4px;
      }

      .ce-dm-stance-btn {
        padding: 5px 10px;
        font-size: 11px;
      }

      /* CODE BLOCKS — keep them readable on narrow screens */
      .ce-md-pre {
        font-size: 12.5px;
        padding: 10px 12px;
        border-radius: 10px;
      }

      .ce-md-code {
        font-size: .92em;
      }

      /* THINKING INDICATOR — slightly smaller dots */
      .ce-thinking {
        padding: 8px 12px;
      }

      .ce-thinking .ce-dot {
        width: 5px;
        height: 5px;
      }

      /* ORBS — pull them in so they don't overflow & wreck performance */
      .orb-1 {
        width: 280px;
        height: 280px;
      }

      .orb-2 {
        width: 240px;
        height: 240px;
      }

      .orb-3 {
        width: 200px;
        height: 200px;
      }

      .orb-4 {
        width: 180px;
        height: 180px;
      }

      .orb-5 {
        width: 220px;
        height: 220px;
      }

      .orb-6 {
        width: 160px;
        height: 160px;
      }
    }

    @media (max-width: 380px) {

      /* SMALL PHONES — final compaction. Drop anything we can hide
     without losing functionality. Brand becomes icon-only. */
      .header {
        padding: 6px 10px;
      }

      .brand-name {
        font-size: 13px;
      }

      .bal-daily {
        display: none;
      }

      /* free counter hidden — wallet still shown */
      .ce-mode-btn {
        padding: 6px 10px;
        font-size: 12px;
      }

      .ce-welcome h1 {
        font-size: 22px;
      }

      .ce-welcome p {
        font-size: 13px;
      }

      .ce-msg-bubble {
        padding: 10px 12px;
        font-size: 14px;
      }

      .ce-tool-btn {
        width: 34px;
        height: 34px;
      }

      .ce-send-btn {
        min-width: 42px;
        padding: 5px 10px;
      }

      .ce-send-cost {
        font-size: 12px;
      }

      .ce-model-pill {
        padding: 4px 9px;
        font-size: 11.5px;
      }

      .ce-history-btn span:not(.ce-hb-ico),
      .ce-newchat-btn span:not(.ce-nc-ico) {
        display: none;
      }

      .ce-history-btn,
      .ce-newchat-btn {
        padding: 0;
        width: 34px;
        height: 34px;
        display: inline-flex;
        align-items: center;
        justify-content: center;
      }
    }

    /* iOS notch — respect the safe area at the bottom so the input row
   doesn't sit under the home indicator. Safe to apply at every size;
   evaluates to 0 on devices without insets. */
    @supports (padding: env(safe-area-inset-bottom)) {
      @media (max-width: 640px) {
        .main {
          padding-bottom: max(14px, env(safe-area-inset-bottom));
        }
      }
    }


/* ════════════════════════════════════════════════════════════════════
   FINAL MEGA-BLOCK SWEEP — extracted in b.864.
   2324 lines / 85KB moved from index.html top inline <style>
   in one final pass. Mix of:
   - Scene-card amber strip-out (small VS rule, will be re-homed later)
   - MAIN (universal; will be re-homed later)
   - Chat mobile dead code (b.722-b.748 leftovers)
   - SKILL CHIP × + COPY BUTTON POLISH (b.748, chat skill mode)
   - STORY BOARD horizontal scene strip (small VS rule)
   - UNIFIED INPUT BAR + VISUAL STUDIO ITER 3 (cross-surface input bar)
   - INLINE MUSIC STUDIO LAYOUT PARITY (chat input bar mirrors MS)
   - MOBILE-ONLY PASS (b.270, mostly dead chat mobile)

   These are intentionally lumped together to clear the top inline <style>.
   Future cleanup sessions can re-sort them into universal.css /
   visual-studio.css / music-studio.css. For now they're in chat.css
   because most are chat-related and chat.css is linked LAST in <head>
   (cascade-friendly).
   ════════════════════════════════════════════════════════════════════ */



    /* TOP UNIVERSAL FOUNDATION (Theme/Day/Orbs/Sweeper, 720 lines) → styles/universal.css in b.860. */
    /* BAL-CARD compact vertical dropdown (b.428) block (1133 lines)
       → styles/universal.css in b.852. */
    /* Scene-card amber strip-out (b.864) (59 lines) → styles/visual-studio.css in b.872. */
    /* MAIN (122 lines) → styles/universal.css in b.870 (re-home). */
    /* b.722-b.744 dead chat-mobile docs/rules (397 lines) PURGED in b.873.
       Chat is desktop-only since b.843; mobile-landing.css owns the mobile takeover. */
    /* ============================================================
       b.748 — SKILL CHIP × + COPY BUTTON POLISH
       ============================================================
       (1) The × close icon on the skill chip duplicates the toolkit
       reset path (tap "+" → tap ⭐ to toggle off, or tap X close in
       the toolkit). Hide it on mobile per user request — skill
       dismissal goes through the toolkit only.

       (2) Copy button "Copied" state rendered with kerning artifacts
       on iOS Safari — letter-spacing .04em at 10.5px font caused
       weird glyph spacing. Zero letter-spacing on mobile, lock the
       icon flex-shrink, and slightly more padding so "Copied" has
       breathing room without squishing the label. */
    /* When the Chat Engine is active, hide EVERY Visual-Studio surface so
   only the chat surface renders. Same coverage as music-studio-active
   plus the music-studio-host itself. */
    body.chat-engine-active .chat,
    body.chat-engine-active .composer,
    body.chat-engine-active .composer-host,
    body.chat-engine-active .gallery,
    body.chat-engine-active .modes-screen,
    body.chat-engine-active .input-bar,
    body.chat-engine-active .video-tip,
    body.chat-engine-active .cinema-bar,
    body.chat-engine-active .chat-actions,
    body.chat-engine-active .director-bottom-btn,
    body.chat-engine-active .director-summary,
    body.chat-engine-active .director-default-bar,
    body.chat-engine-active .manual-return-btn,
    body.chat-engine-active #inputBar,
    body.chat-engine-active footer.input-bar,
    body.chat-engine-active .music-studio-host,
    body.chat-engine-active .story-board,
    [data-theme] body.chat-engine-active .story-board,
    [data-theme] body.chat-engine-active .story-board.active {
      display: none !important;
    }

    /* Hide the mode pill (Visual Studio sub-mode selector) in chat — it
   doesn't apply to the chat surface and the chat engine has its own
   mode selector inside the stage. */
    body.chat-engine-active .mode-pill,
    body.chat-engine-active #modePillTop {
      display: none !important;
    }

    /* b.568 — DEFENSIVE TAB-SCOPE GUARD.
   Visual Studio surfaces (the .chat container, its thread, every
   result bubble, the staged canvas frame, action rows, info
   overlays) must NEVER render when the user is on the Chat or
   Music tab. The existing `body.chat-engine-active .chat{
   display:none !important }` rule above is the primary mechanism,
   but it can be defeated by:
     - position:fixed children of .chat that establish their own
       paint context
     - .bubble.result.staged with transform creating a new stacking
       context that lifts the bubble visually
     - any later rule that wins specificity / source order
   This block double-locks the staged canvas + every result bubble
   to ONLY paint when on the Visual Studio tab (data-active-tab
   defaults to "visual" via setActiveTab). On any other tab —
   "chat", "music", or anything the future adds — every Visual
   Studio canvas element collapses to display:none with maximum
   specificity. The :where() wrapper keeps specificity at 0,1,0
   for the negation so we don't accidentally over-win against
   legitimate same-element rules in other contexts.
   Net effect: zero possibility of canvas bleeding into the chat
   surface, regardless of which path triggered the render. */
    body:not([data-active-tab="visual"]) #chat,
    body:not([data-active-tab="visual"]) #chat .thread,
    body:not([data-active-tab="visual"]) #chat .msg,
    body:not([data-active-tab="visual"]) #chat .bubble,
    body:not([data-active-tab="visual"]) #chat .bubble.result,
    body:not([data-active-tab="visual"]) #chat .bubble.result.staged,
    body:not([data-active-tab="visual"]) #chat .result-frame,
    body:not([data-active-tab="visual"]) #chat .result-actions,
    body.chat-engine-active #chat,
    body.chat-engine-active #chat .bubble.result,
    body.chat-engine-active #chat .bubble.result.staged,
    body.chat-engine-active #chat .result-frame,
    body.chat-engine-active #chat .result-actions,
    body.music-studio-active #chat,
    body.music-studio-active #chat .bubble.result,
    body.music-studio-active #chat .bubble.result.staged {
      display: none !important;
      visibility: hidden !important;
      pointer-events: none !important;
      opacity: 0 !important;
    }

    /* Inverse guard: when NOT on the chat tab, the chat-engine host
   must never paint either. Same protection in reverse direction
   so the chat-engine surface doesn't bleed into Visual Studio or
   Music Studio. */
    body:not([data-active-tab="chat"]) #chatEngine:not(.always-show),
    body:not(.chat-engine-active) #chatEngine {
      display: none !important;
      visibility: hidden !important;
      pointer-events: none !important;
    }

    /* b.569 — Music Studio tab-scope lockdown (mirror of the chat
   guard above, mirror of the Visual Studio guard further up).
   Music Studio renders inside a section.music-studio-inline-host
   that's appended to <body> on first activation. It must NEVER
   paint unless the user is actually on the Music tab. Without
   this, the inline studio could bleed into Visual Studio or the
   chat surface — same class of bug as the canvas-into-chat one
   that hit b.568. Belt-and-suspenders selectors:
     • data-active-tab attribute (canonical "which tab is up")
     • body.music-studio-active class (set by showMusicStudio)
   The host is only visible when BOTH are aligned with "music". */
    body:not([data-active-tab="music"]) .music-studio-inline-host,
    body:not(.music-studio-active) .music-studio-inline-host {
      display: none !important;
      visibility: hidden !important;
      pointer-events: none !important;
      opacity: 0 !important;
    }

    /* Belt-and-suspenders inverse — when ON the music tab, every
   Visual Studio surface (in addition to the rules higher up in
   this file) and every chat-engine element is forced down. The
   selectors here echo the chat-engine-active block so the two
   tabs apply identical hide pressure on the surfaces they
   aren't responsible for. */
    body[data-active-tab="music"] #chat,
    body[data-active-tab="music"] #chat .bubble.result,
    body[data-active-tab="music"] #chat .bubble.result.staged,
    body[data-active-tab="music"] #chat .result-frame,
    body[data-active-tab="music"] #chat .result-actions,
    body[data-active-tab="music"] .canvas-nav-row,
    body[data-active-tab="music"] .canvas-expose,
    body[data-active-tab="music"] #chatEngine,
    body.music-studio-active #chatEngine {
      display: none !important;
      visibility: hidden !important;
      pointer-events: none !important;
    }

    /* === LISTEN PAGE — public, no-auth audio player ===
   Constantly-animated bg, liquid-glass card, custom glass audio
   player. Activated when the URL has ?listen=… */
    body.listen-active {
      overflow: hidden;
    }

    body.listen-active .header,
    body.listen-active main.main,
    body.listen-active .modes-screen,
    body.listen-active .modal-back {
      display: none !important;
    }

    .listen-page {
      position: fixed;
      inset: 0;
      display: none;
      align-items: center;
      justify-content: center;
      z-index: 200;
      padding: 32px;
      background: linear-gradient(180deg, #06080e 0%, #03050a 100%);
      color: #f3f1ee;
      font-family: "Plus Jakarta Sans", ui-sans-serif, system-ui, sans-serif;
      overflow: hidden;
    }

    body.listen-active .listen-page {
      display: flex;
    }

    /* Six drifting blurred orbs as the constantly-animated bg. Each on
   its own slow drift cycle so the whole page breathes. */
    .listen-bg {
      position: absolute;
      inset: 0;
      overflow: hidden;
      pointer-events: none;
    }

    .listen-bg span {
      position: absolute;
      border-radius: 50%;
      filter: blur(110px) saturate(1.6);
      mix-blend-mode: screen;
      will-change: transform;
    }

    /* TEN drifting orbs at varying sizes/speeds with chromatic colors,
   each on a different cycle — they constantly mix, merge, separate.
   Cycles are intentionally short (10-18s) and unequal so the motion
   never repeats visibly. */
    .listen-bg span:nth-child(1) {
      width: 65vw;
      height: 65vw;
      top: -22%;
      left: -18%;
      background: rgba(252, 166, 0, .62);
      animation: listen-d1 12s ease-in-out infinite;
    }

    .listen-bg span:nth-child(2) {
      width: 58vw;
      height: 58vw;
      bottom: -18%;
      right: -12%;
      background: rgba(123, 95, 196, .62);
      animation: listen-d2 14s ease-in-out infinite;
    }

    .listen-bg span:nth-child(3) {
      width: 42vw;
      height: 42vw;
      top: 20%;
      left: 55%;
      background: rgba(186, 255, 210, .42);
      animation: listen-d3 11s ease-in-out infinite;
    }

    .listen-bg span:nth-child(4) {
      width: 40vw;
      height: 40vw;
      bottom: 15%;
      left: 8%;
      background: rgba(255, 140, 200, .42);
      animation: listen-d4 16s ease-in-out infinite;
    }

    .listen-bg span:nth-child(5) {
      width: 32vw;
      height: 32vw;
      top: 55%;
      left: 38%;
      background: rgba(140, 200, 255, .42);
      animation: listen-d5 13s ease-in-out infinite;
    }

    .listen-bg span:nth-child(6) {
      width: 30vw;
      height: 30vw;
      top: 5%;
      right: 22%;
      background: rgba(255, 210, 140, .42);
      animation: listen-d6 15s ease-in-out infinite;
    }

    .listen-bg span:nth-child(7) {
      width: 36vw;
      height: 36vw;
      top: 35%;
      right: 5%;
      background: rgba(180, 255, 180, .32);
      animation: listen-d7 17s ease-in-out infinite;
    }

    .listen-bg span:nth-child(8) {
      width: 28vw;
      height: 28vw;
      bottom: 25%;
      right: 35%;
      background: rgba(220, 150, 255, .34);
      animation: listen-d8 10s ease-in-out infinite;
    }

    .listen-bg span:nth-child(9) {
      width: 34vw;
      height: 34vw;
      top: 48%;
      left: 5%;
      background: rgba(255, 180, 120, .36);
      animation: listen-d9 18s ease-in-out infinite;
    }

    .listen-bg span:nth-child(10) {
      width: 26vw;
      height: 26vw;
      top: 8%;
      left: 30%;
      background: rgba(150, 220, 255, .36);
      animation: listen-d10 9s ease-in-out infinite;
    }

    @keyframes listen-d1 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(20vw, 18vh) scale(1.25)
      }
    }

    @keyframes listen-d2 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-22vw, -16vh) scale(1.20)
      }
    }

    @keyframes listen-d3 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-25vw, 14vh) scale(1.35)
      }
    }

    @keyframes listen-d4 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(24vw, -18vh) scale(.78)
      }
    }

    @keyframes listen-d5 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-15vw, -20vh) scale(1.30)
      }
    }

    @keyframes listen-d6 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-20vw, 22vh) scale(1.18)
      }
    }

    @keyframes listen-d7 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(18vw, -16vh) scale(.85)
      }
    }

    @keyframes listen-d8 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-25vw, 18vh) scale(1.4)
      }
    }

    @keyframes listen-d9 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(22vw, 22vh) scale(.80)
      }
    }

    @keyframes listen-d10 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-18vw, -22vh) scale(1.45)
      }
    }

    .listen-card {
      position: relative;
      z-index: 2;
      width: min(640px, 100%);
      padding: 56px 40px 40px;
      border-radius: 32px;
      background: rgba(255, 255, 255, .04);
      border: 1px solid rgba(255, 255, 255, .14);
      -webkit-backdrop-filter: blur(40px) saturate(1.5);
      backdrop-filter: blur(40px) saturate(1.5);
      box-shadow:
        0 0 0 1px rgba(255, 255, 255, .06) inset,
        0 30px 100px -16px rgba(0, 0, 0, .7);
      text-align: center;
    }

    .listen-brand {
      font-weight: 700;
      font-size: 13px;
      letter-spacing: .18em;
      text-transform: uppercase;
      color: rgba(255, 255, 255, .65);
      margin-bottom: 24px;
    }

    .listen-title {
      font-weight: 800;
      font-size: 32px;
      letter-spacing: -.015em;
      line-height: 1.2;
      margin-bottom: 6px;
    }

    .listen-sub {
      font-size: 13px;
      color: rgba(255, 255, 255, .55);
      margin-bottom: 28px;
      letter-spacing: .005em;
    }

    /* Liquid-glass custom audio player — replaces the native controls.
   Big play/pause + scrubber + time. No solid colors anywhere. */
    .listen-player {
      display: flex;
      align-items: center;
      gap: 14px;
      padding: 14px 16px;
      background: rgba(255, 255, 255, .04);
      border: 1px solid rgba(255, 255, 255, .14);
      border-radius: 18px;
      -webkit-backdrop-filter: blur(20px);
      backdrop-filter: blur(20px);
    }

    .listen-play {
      width: 48px;
      height: 48px;
      flex: 0 0 auto;
      display: grid;
      place-items: center;
      border-radius: 50%;
      background: rgba(255, 255, 255, .08);
      border: 1px solid rgba(255, 255, 255, .30);
      color: #fff;
      cursor: pointer;
      /* Pull up so the play button visually aligns with the scrubber
     bar — the time row beneath the bar drops the flex center,
     making the button sit lower. b.134 bumped from -9px to -19px
     after user feedback that it still wasn't high enough. */
      transform: translateY(-19px);
      transition: transform .15s ease, box-shadow .15s ease, background .15s ease;
      box-shadow: 0 0 18px rgba(255, 255, 255, .20);
    }

    .listen-play:hover {
      transform: translateY(-19px) scale(1.05);
      background: rgba(255, 255, 255, .14);
      box-shadow: 0 0 28px rgba(255, 255, 255, .40);
    }

    .listen-play:active {
      transform: translateY(-19px) scale(.96);
    }

    .listen-play svg {
      width: 18px;
      height: 18px;
    }

    .listen-play .icon-pause {
      display: none;
    }

    .listen-play.playing .icon-play {
      display: none;
    }

    .listen-play.playing .icon-pause {
      display: block;
    }

    .listen-scrubber {
      flex: 1 1 auto;
      min-width: 0;
      display: flex;
      flex-direction: column;
      gap: 6px;
    }

    .listen-scrubber-bar {
      position: relative;
      height: 6px;
      border-radius: 3px;
      background: rgba(255, 255, 255, .10);
      cursor: pointer;
      overflow: hidden;
    }

    .listen-scrubber-fill {
      position: absolute;
      inset: 0;
      width: 0%;
      background: linear-gradient(90deg, rgba(255, 255, 255, .85) 0%, rgba(255, 255, 255, .45) 100%);
      border-radius: 3px;
      transition: width .12s linear;
    }

    .listen-scrubber-time {
      display: flex;
      justify-content: space-between;
      font-size: 11px;
      font-weight: 600;
      color: rgba(255, 255, 255, .55);
      letter-spacing: .04em;
    }

    /* CTA — pure liquid glass, white halo on hover */
    .listen-cta {
      display: inline-flex;
      align-items: center;
      gap: 8px;
      margin-top: 14px;
      padding: 10px 22px;
      border-radius: 999px;
      background: transparent;
      border: 0;
      color: rgba(255, 255, 255, .55);
      font-weight: 600;
      font-size: 12px;
      letter-spacing: .04em;
      text-transform: uppercase;
      text-decoration: none;
      transition: color .15s ease;
    }

    .listen-cta:hover {
      color: #fff;
    }

    /* 2-way selector — Download MP3 / Share — single liquid-glass pill with
   a subtle divider. Replaces the previous two separate buttons. */
    .listen-actions {
      display: flex;
      align-items: stretch;
      margin-top: 24px;
      border-radius: 999px;
      background: rgba(255, 255, 255, .06);
      border: 1px solid rgba(255, 255, 255, .28);
      -webkit-backdrop-filter: blur(20px);
      backdrop-filter: blur(20px);
      box-shadow:
        0 0 0 1px rgba(255, 255, 255, .08) inset,
        0 0 22px rgba(255, 255, 255, .16);
      overflow: hidden;
    }

    .listen-actions button {
      flex: 1 1 0;
      display: inline-flex;
      align-items: center;
      justify-content: center;
      gap: 8px;
      padding: 13px 22px;
      background: transparent;
      border: 0;
      color: rgba(255, 255, 255, .86);
      font-weight: 700;
      font-size: 13px;
      letter-spacing: .01em;
      cursor: pointer;
      transition: background .15s ease, color .15s ease;
    }

    .listen-actions button:hover {
      background: rgba(255, 255, 255, .08);
      color: #fff;
    }

    .listen-actions button+button {
      border-left: 1px solid rgba(255, 255, 255, .14);
    }

    .listen-actions svg {
      width: 14px;
      height: 14px;
    }

    .listen-close {
      position: absolute;
      top: 16px;
      right: 16px;
      z-index: 3;
      width: 36px;
      height: 36px;
      border-radius: 50%;
      display: grid;
      place-items: center;
      background: rgba(255, 255, 255, .05);
      border: 1px solid rgba(255, 255, 255, .16);
      color: rgba(255, 255, 255, .75);
      font-size: 18px;
      line-height: 1;
      cursor: pointer;
      transition: all .15s ease;
      -webkit-backdrop-filter: blur(12px);
      backdrop-filter: blur(12px);
    }

    .listen-close:hover {
      color: #fff;
      background: rgba(255, 255, 255, .10);
    }

    /* === MUSIC PLAYING — bg-stage reacts to the playing song.
   Album-art colors override the orb palette and orb drift speed
   ramps up based on the song's tempo. Triggered via postMessage
   from the music studio iframe when audio starts playing. */
    body.music-playing .orb-1 {
      background: var(--song-orb-1, var(--orb-1)) !important;
    }

    body.music-playing .orb-2 {
      background: var(--song-orb-2, var(--orb-2)) !important;
    }

    body.music-playing .orb-3 {
      background: var(--song-orb-3, var(--orb-3)) !important;
    }

    body.music-playing .orb-4 {
      background: var(--song-orb-4, var(--orb-4)) !important;
    }

    body.music-playing .orb-5 {
      background: var(--song-orb-5, var(--orb-5)) !important;
    }

    body.music-playing .orb-6 {
      background: var(--song-orb-6, var(--orb-6)) !important;
    }

    body.music-playing .orb {
      /* AGGRESSIVE motion — 5-9s cycles instead of 22s, brighter, sharper */
      animation-duration: 6s, 5s, 7s, 8s, 5s, 9s !important;
      opacity: .85 !important;
      filter: blur(60px) saturate(1.7) !important;
    }

    /* Six extra "playback orbs" that ONLY appear when music plays —
   smaller, faster, and they cross-fade colors so the whole page
   feels like a dance floor while a song is on. */
    .bg-playback {
      position: fixed;
      inset: 0;
      z-index: 0;
      pointer-events: none;
      opacity: 0;
      transition: opacity .6s ease;
    }

    body.music-playing .bg-playback {
      opacity: 1;
    }

    .bg-playback span {
      position: absolute;
      border-radius: 50%;
      filter: blur(80px) saturate(1.8);
      mix-blend-mode: screen;
      will-change: transform;
    }

    .bg-playback span:nth-child(1) {
      width: 45vw;
      height: 45vw;
      top: -10%;
      left: 5%;
      background: var(--song-orb-1, #fca600);
      animation: bg-pb1 4s ease-in-out infinite;
    }

    .bg-playback span:nth-child(2) {
      width: 50vw;
      height: 50vw;
      bottom: -15%;
      right: 0%;
      background: var(--song-orb-2, #7b5fc4);
      animation: bg-pb2 5s ease-in-out infinite;
    }

    .bg-playback span:nth-child(3) {
      width: 38vw;
      height: 38vw;
      top: 30%;
      left: 55%;
      background: var(--song-orb-3, #5fc4a8);
      animation: bg-pb3 3s ease-in-out infinite;
    }

    .bg-playback span:nth-child(4) {
      width: 42vw;
      height: 42vw;
      bottom: 25%;
      left: 30%;
      background: var(--song-orb-4, #c45f9e);
      animation: bg-pb4 6s ease-in-out infinite;
    }

    .bg-playback span:nth-child(5) {
      width: 32vw;
      height: 32vw;
      top: 55%;
      left: 5%;
      background: var(--song-orb-5, #c4a85f);
      animation: bg-pb5 4.5s ease-in-out infinite;
    }

    .bg-playback span:nth-child(6) {
      width: 36vw;
      height: 36vw;
      top: 5%;
      right: 15%;
      background: var(--song-orb-6, #5f9ec4);
      animation: bg-pb6 3.5s ease-in-out infinite;
    }

    @keyframes bg-pb1 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(20vw, 18vh) scale(1.30)
      }
    }

    @keyframes bg-pb2 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-22vw, -16vh) scale(1.25)
      }
    }

    @keyframes bg-pb3 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-25vw, 15vh) scale(1.40)
      }
    }

    @keyframes bg-pb4 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(22vw, -22vh) scale(.78)
      }
    }

    @keyframes bg-pb5 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(18vw, -18vh) scale(1.35)
      }
    }

    @keyframes bg-pb6 {

      0%,
      100% {
        transform: translate(0, 0) scale(1)
      }

      50% {
        transform: translate(-20vw, 22vh) scale(1.18)
      }
    }

    body.music-playing .bg-stage::before {
      background: linear-gradient(180deg,
          rgba(0, 0, 0, .18) 0%,
          rgba(0, 0, 0, .40) 100%) !important;
    }

    /* Soft beat-pulse on the body itself when bass hits — gentle so it
   doesn't strobe but you feel the music in the background. */
    @keyframes ms-beat-pulse {

      0%,
      100% {
        background-color: transparent;
      }

      50% {
        background-color: rgba(var(--song-pulse-rgb, 255, 255, 255), .04);
      }
    }

    body.music-playing {
      animation: ms-beat-pulse var(--music-beat, 0.55s) ease-in-out infinite;
    }

    .chat {
      flex: 1;
      overflow-y: auto;
      overflow-x: hidden;
      padding: 0;
      scroll-behavior: smooth;
      scrollbar-width: thin;
      scrollbar-color: rgba(255, 255, 255, .18) transparent;
    }

    html[data-theme="day"] .chat {
      scrollbar-color: rgba(0, 0, 0, .18) transparent
    }

    .chat::-webkit-scrollbar {
      width: 8px
    }

    .chat::-webkit-scrollbar-thumb {
      background: rgba(255, 255, 255, .18);
      border-radius: 99px
    }

    html[data-theme="day"] .chat::-webkit-scrollbar-thumb {
      background: rgba(0, 0, 0, .18)
    }

    .thread {
      /* 2026-05-12 b.405 — Was max-width:1200px which left the conversation
     stranded in a column on wide displays. The chat engine surface uses
     the full viewport; Visual Studio's thread now matches: full-width
     with comfortable inline padding so user + AI bubbles spread across
     the screen the way chat does. Mobile inherits the same clamp on
     padding so it stays comfortable on narrow viewports.
     2026-05-12 b.409 — padding-bottom bumped from 18px to 220px so
     the last message clears the pinned input bar (controls row +
     input row ≈ 180-200px tall). Without it the most-recent card's
     action buttons rendered BEHIND the controls row at the bottom of
     the screen and looked clipped. */
      max-width: none;
      margin-inline: auto;
      padding: 18px clamp(14px, 4vw, 64px) 220px;
      display: flex;
      flex-direction: column;
      gap: 18px;
    }


    /* VISUAL STUDIO result/canvas cluster (Gallery/Messages/Stage/Timeline/Loader/Pong, 3171 lines) → styles/visual-studio.css in b.856. */
    /* INPUT BAR + ENGINE PILL + STORYBOARD MODAL (1379 lines) → styles/visual-studio.css in b.857. */
    /* DYNAMIC CONTROLS GATING (b.297/b.301) (1220 lines) → styles/visual-studio.css in b.853. */
    /* MODAL primitives (556 lines) → styles/universal.css in b.859. */
    /* STUDIOS mode picker + asset chips + setup modals (915 lines) → styles/universal.css in b.855. */
    /* STORY BOARD horizontal scene strip (64 lines) → styles/visual-studio.css in b.872. */
    /* ============================================================
   2026-05-10 b.156 — UNIFIED INPUT BAR (Music Studio is reference).
   Two stubborn problems were undoing earlier passes:
   (1) [data-theme] .input-row {…!important} at L4147 was overriding
       my plain .input-row rule (specificity 0,2,0 > 0,1,0). It set
       border-radius:999px (full pill), padding:0, min-height:56px,
       and reverted background to var(--lg-fill) — that's why Visual
       Studio kept rendering as a thin transparent pill.
   (2) .input-bar { contain:layout } creates a containing block for
       position:fixed in modern browsers, so my `bottom:22px` was
       resolving relative to .input-bar's box, not the viewport. That
       made Visual Studio's bar sit ~35px higher than chat's.
   Fix both: use [data-theme] selector to win specificity, and
   override .input-bar's contain to none.
   ============================================================ */

    /* Strip the legacy contain:layout so position:fixed on .input-row
   actually attaches to the viewport (not to .input-bar's box).
   b.908 — SCOPED TO CHAT SURFACE ONLY. Previously ungated, which leaked
   into Visual Studio and Music Studio: (a) the 96px padding-bottom
   reserved space VS doesn't need (its input bar is in normal flow, not
   position:fixed), pushing the layout off; (b) overriding VS's
   `contain:layout` (visual-studio.css:19117) reintroduced the boost-popover
   clipping bug that contain:layout was there to prevent. Gating to
   `body.chat-engine-active` keeps chat's pinned-bar layout working while
   letting VS/Music retain their own .input-bar treatments. */
    body.chat-engine-active .input-bar {
      contain: none !important;
      padding-bottom: 96px !important;
      /* reserve space for the pinned bar */
    }

    /* 2026-05-11 b.253 — UNIFIED INPUT-ROW RECIPE, calibrated for
   iframe-vs-parent rendering parity.
   Iframe quirk: backdrop-filter inside the MS iframe can't blur
   the parent's Garden video through the iframe boundary, so MS's
   `saturate(1.30)` is effectively a no-op. The same value applied
   on the parent's .ce-input-row / .input-row DOES saturate the
   live Garden colours behind the bar, making chat & VS read as
   more vivid / darker than the MS reference.
   Fix: drop saturate to 1.0 on the parent rule (same effective
   saturation as MS's nullified saturate), bump brightness from
   1.04 → 1.08 to nudge the bar slightly lighter so the white .06
   wash reads with the same airy weight as MS. The injected MS
   rule stays at saturate(1.30) — the parent's bg behind it isn't
   blurred anyway, so the value is harmless and we don't need to
   change the inject path. */
    [data-theme] .ce-input-row,
    [data-theme] .input-row,
    [data-embedded="true"] .ms-sw-input-row {
      /* 2026-05-11 b.255 — lightened the outer input-bar tint by ~10
     percentage points. Was rgba(255,255,255,.06), now .16 — gives
     the bar a noticeably airier wash so it reads less heavy against
     dark themes.
     2026-05-12 b.445 — backdrop-filter saturate dropped from 1.0
     to 0.2 so the Garden theme's green orbs no longer tint the bar
     when they drift behind it. At 1.0 the bar was reading green in
     the middle (where the orbs concentrate); 0.2 desaturates the
     backdrop to near-grayscale so the frosted surface stays neutral
     regardless of which theme is active. Border opacity bumped .22
     → .40 so the border doesn't pick up colour from the bg either. */
      background: rgba(255, 255, 255, .16) !important;
      border: 1.5px solid rgba(255, 255, 255, .40) !important;
      -webkit-backdrop-filter: blur(22px) saturate(0.2) brightness(1.08) !important;
      backdrop-filter: blur(22px) saturate(0.2) brightness(1.08) !important;
      border-radius: 24px !important;
      padding: 3px 10px 3px 14px !important;
      min-height: 0 !important;
      overflow: visible !important;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .55) inset,
        0 -1px 0 rgba(255, 255, 255, .18) inset,
        0 0 0 1px rgba(255, 255, 255, .10) inset,
        0 24px 60px -22px rgba(0, 0, 0, .65) !important;
    }

    [data-theme] .ce-input-row:focus-within,
    [data-theme] .input-row:focus-within,
    [data-embedded="true"] .ms-sw-input-row:focus-within {
      /* b.251 — match MS iframe focus exactly. The 24px white outer
     halo is intentional here (preserves all three inset layers and
     adds the soft luminous bloom on focus). */
      border-color: rgba(255, 255, 255, .45) !important;
      box-shadow:
        0 1px 0 rgba(255, 255, 255, .55) inset,
        0 -1px 0 rgba(255, 255, 255, .18) inset,
        0 0 0 1px rgba(255, 255, 255, .10) inset,
        0 0 24px rgba(255, 255, 255, .32) !important;
    }

    /* 2026-05-10 b.165 — bottom dead-space minimised. Input row now sits
   10px from viewport bottom (was 22). Controls row 18px above input.
   Same coordinates applied across chat (.ce-stage padding) + music
   inject so all three sit at the same Y. */
    [data-theme] .input-row {
      position: fixed !important;
      left: 22px !important;
      right: 22px !important;
      bottom: 8px !important;
      top: auto !important;
      width: auto !important;
      max-width: none !important;
      z-index: 9 !important;
    }

    /* Hide the pinned input-row when chat / music tabs are active. */
    body.chat-engine-active .input-row,
    body.music-studio-active .input-row {
      display: none !important;
    }

    /* VISUAL STUDIO ITER 3 (b.159) (90 lines) → styles/visual-studio.css in b.872. */
    /* INLINE MUSIC STUDIO LAYOUT PARITY (146 lines) → styles/music-studio.css in b.871 (re-home). */
    /* ============================================================
   2026-05-11 b.270 — MOBILE-ONLY PASS
   ============================================================
   ALL rules below live inside @media (max-width:720px) or smaller
   so the desktop styling is mathematically untouched. No rule
   here fires above 720px viewport width.
   Targets the top issues from the mobile audit:
     1. Top pills (MENU / MY COINS / MY ACCOUNT) collision
     2. Tabs row collision with pinned pills
     3. Visual Studio .controls row overflowing horizontally
     4. iOS notch / home indicator safe-area
     5. Modal close X hidden behind pinned top pills
     6. Tap targets <44px (accessibility)
     7. Tight input-bar gutters on narrow viewports
   ============================================================ */

    /* === 1. Top pills (MENU / MY COINS / MY ACCOUNT) === */
    @media (max-width:720px) {

      /* MENU pill — reset the desktop optical-offset shift, shrink
     min-width and padding so it doesn't crowd the right cluster. */
      .tabs-menu-pill {
        min-width: 96px !important;
        padding: 0 12px 6px !important;
        transform: translateX(-50%) !important;
      }

      /* MY ACCOUNT pill — pull hard against the right edge, shrink. */
      .account-menu-pill {
        right: 8px !important;
        min-width: 96px !important;
        font-size: 9.5px !important;
        padding: 0 12px 6px !important;
      }

      /* MY COINS pill — sits to the left of MY ACCOUNT; same compact
     shape so they don't overlap each other on iPhone widths. */
      .coins-menu-pill {
        right: 112px !important;
        min-width: 96px !important;
        padding: 0 12px 6px !important;
      }

      /* When MY COINS expands into the bal-card on hover/tap, pin it
     to the same right-anchor as the pill so it doesn't crash into
     the centred MENU pill. */
      body:not(.coins-collapsed) .bal-card:not(.signed-out) {
        right: 112px !important;
        top: 24px !important;
      }
    }

    /* === 2. Tabs row collision === */
    @media (max-width:720px) {

      /* The Chat/Visual/Music tab cluster (when visible — i.e. not
     collapsed into MENU) needs more horizontal breathing room.
     Tighten gaps and font size so the trio fits without colliding
     with the right-side pills. */
      [data-theme] .tabs {
        gap: 4px !important;
        padding: 0 8px !important;
      }

      [data-theme] .tabs .tab {
        height: 36px !important;
        padding: 0 10px !important;
        font-size: 10.5px !important;
        letter-spacing: .04em !important;
      }
    }

    /* === 3. Visual Studio .controls overflow === */
    @media (max-width:720px) {

      /* Let the controls row wrap onto multiple lines instead of
     overflowing horizontally. .controls is `flex-wrap:nowrap` by
     default so the IMAGE/VIDEO switch + HD + 16:9 + +REFERENCE
     PHOTO + MODE pill all jam into one strip and clip. */
      [data-theme] .controls {
        flex-wrap: wrap !important;
        gap: 6px !important;
        row-gap: 6px !important;
      }

      [data-theme] .toggle-grp button {
        min-width: 0 !important;
        padding: 8px 10px !important;
        font-size: 11px !important;
      }

      [data-theme] .toggle-grp[data-grp="duration"] button {
        min-width: 0 !important;
        padding: 8px 12px !important;
        font-size: 12px !important;
      }

      [data-theme] .ref-btn {
        padding: 8px 10px !important;
        font-size: 11px !important;
      }

      /* Cinema-mode (Video) pills — value labels can swell to 140px on
     desktop; clamp on mobile so three of them fit a row. */
      .cinema-bar {
        flex-wrap: wrap !important;
        gap: 4px !important;
      }

      .cinema-bar .cb-pill {
        height: 30px !important;
        padding: 3px 8px 3px 4px !important;
      }

      .cinema-bar .cb-pill .cb-value {
        max-width: 80px !important;
        font-size: 10px !important;
      }
    }

    /* === 4. iOS safe-area (notch / home indicator) === */
    @media (max-width:720px) {

      /* Add env(safe-area-inset-bottom) to every fixed bottom element
     so the home-indicator pill doesn't obscure the input row. */
      [data-theme] .input-row {
        bottom: calc(8px + env(safe-area-inset-bottom)) !important;
      }

      [data-theme] .controls {
        bottom: calc(74px + env(safe-area-inset-bottom)) !important;
      }

      .music-studio-inline-host .ms-sw-inputbar {
        bottom: calc(8px + env(safe-area-inset-bottom)) !important;
      }

      .music-studio-inline-host .ms-sw-meta {
        bottom: auto !important;
      }
    }

    /* === 5. Hide pinned top pills when a modal is open === */
    @media (max-width:720px) {

      /* MENU / MY COINS / MY ACCOUNT pills sit at z-index 90 and
     overlap modal close X buttons. Hide them while any modal is
     open so the close target is reachable. */
      body.modal-open .tabs-menu-pill,
      body.modal-open .coins-menu-pill,
      body.modal-open .account-menu-pill,
      body.cast-open .tabs-menu-pill,
      body.cast-open .coins-menu-pill,
      body.cast-open .account-menu-pill,
      body.director-open .tabs-menu-pill,
      body.director-open .coins-menu-pill,
      body.director-open .account-menu-pill,
      body.mm-open .tabs-menu-pill,
      body.mm-open .coins-menu-pill,
      body.mm-open .account-menu-pill {
        display: none !important;
      }
    }

    /* === 6. Tap target accessibility (≥44×44 per iOS HIG) === */
    @media (max-width:720px) {

      /* Theme toggle circle — desktop is 40px, bump to 44px on touch. */
      .theme-toggle-circle {
        width: 44px !important;
        height: 44px !important;
        transform: translateY(-10px) !important;
      }

      /* Header icon buttons (sign-in shortcut, coin-add) shrink to
     30-34px at the 640px breakpoint; bring them back to 44px so
     they're tappable. */
      [data-theme] .bal-add,
      [data-theme] .account-btn,
      [data-theme] .icon-btn {
        min-width: 44px !important;
        min-height: 44px !important;
      }
    }

    /* === 7. Tighter input-bar gutters on very narrow viewports === */
    @media (max-width:480px) {

      /* On iPhone SE (375px) and below, 22px each side leaves only
     ~330px for input contents. Pull gutters in to 10px so the
     textarea has breathing room. */
      [data-theme] .input-bar {
        padding-left: 10px !important;
        padding-right: 10px !important;
      }

      [data-theme] .input-row {
        left: 10px !important;
        right: 10px !important;
      }

      [data-theme] .controls {
        left: 10px !important;
        right: 10px !important;
      }

      .music-studio-inline-host .ms-sw-inputbar {
        left: 10px !important;
        right: 10px !important;
      }

      .music-studio-inline-host .ms-sw-meta {
        left: 10px !important;
        right: 10px !important;
      }
    }

    /* === 8. Misc readability fixes === */
    @media (max-width:720px) {

      /* Quality-tip popover anchors to left:0 of its parent toggle —
     on narrow viewports that pushes it past the right edge. Pin
     to viewport-centred instead. */
      .quality-tip {
        left: 50% !important;
        transform: translateX(-50%) !important;
        right: auto !important;
        width: calc(100vw - 24px) !important;
        max-width: 360px !important;
      }
    }

    @media (max-height:480px) {

      /* Landscape phone — the video tip at bottom:150px occupies most
     of the visible viewport. Pull it down + slim it. */
      .video-tip {
        bottom: 120px !important;
        padding: 8px 32px 8px 12px !important;
        font-size: 12px !important;
      }
    }

    /* IMAGE + VIDEO as a CONNECTED SWITCH (per user). Restore segmented
   container chrome for the mode group only — other toggle groups
   (quality, dim) stay as individual pills.
   2026-05-11 b.251 — unified segmented-wrapper recipe to match
   .ce-mode-selector (chat's GPT/4o-mini wrapper) verbatim. Was
   dark fill rgba(8,8,12,.20) + blur(28px) saturate(1.4), now light
   .06 wash + blur(22px) sat(1.30) bright(1.04) so VS and Chat read
   as identical UI elements. */
    [data-theme] .toggle-grp[data-grp="mode"] {
      border: 1px solid rgba(255, 255, 255, .22) !important;
      background: rgba(255, 255, 255, .06) !important;
      border-radius: 999px !important;
      padding: 3px !important;
      -webkit-backdrop-filter: blur(22px) saturate(1.30) brightness(1.04) !important;
      backdrop-filter: blur(22px) saturate(1.30) brightness(1.04) !important;
      box-shadow: 0 1px 0 rgba(255, 255, 255, .10) inset !important;
      gap: 0 !important;
      overflow: visible !important;
    }

    [data-theme] .toggle-grp[data-grp="mode"] button {
      /* Inside a connected segmented switch — drop individual pill
     border + bg, let the parent capsule own the chrome. */
      border: 0 !important;
      background: transparent !important;
      -webkit-backdrop-filter: none !important;
      backdrop-filter: none !important;
      box-shadow: none !important;
      padding: 6px 12px !important;
      border-radius: 999px !important;
    }

    [data-theme] .toggle-grp[data-grp="mode"] button.on {
      /* 2026-05-11 b.250 — segmented IMAGE/VIDEO active state.
     Matches Music Studio's SLOW/MEDIUM/FAST switch: a thin white
     outline inside the parent capsule, no outer glow. Border lives
     in an inset shadow (since the parent capsule owns the actual
     border) so the rim sits flush with the segment edge. */
      background: rgba(255, 255, 255, 0.10) !important;
      border: 0 !important;
      box-shadow:
        0 0 0 1.5px rgba(255, 255, 255, .55) inset !important;
    }

    /* TEXTAREA — push placeholder to the TOP-LEFT of the input row
   (matches music). Was vertically centered + indented by the row's
   align-items:flex-end. */
    [data-theme] .input-row {
      align-items: flex-start !important;
    }

    [data-theme] #prompt,
    [data-theme] textarea#prompt {
      align-self: flex-start !important;
      padding-top: 6px !important;
      padding-left: 6px !important;
    }

    /* Toggle-grp invisible (segmented wrapper, no chrome). */
    [data-theme] .toggle-grp {
      border: 0 !important;
      background: transparent !important;
      border-radius: 0 !important;
      padding: 0 !important;
      -webkit-backdrop-filter: none !important;
      backdrop-filter: none !important;
      box-shadow: none !important;
      overflow: visible !important;
      gap: 8px !important;
    }

    /* Pill recipe — readable size (7px/13px is the sweet spot, not 5/11). */
    [data-theme] .toggle-grp button,
    [data-theme] .ref-btn,
    [data-theme] .ref-add,
    [data-theme] .ref-thumb,
    [data-theme] .dim-btn,
    [data-theme] .aspect-pill,
    [data-theme] .aspect-btn,
    [data-theme] .mode-pill,
    [data-theme] .action-pill {
      background: rgba(8, 8, 12, 0.20) !important;
      border: 1px solid rgba(255, 255, 255, 0.18) !important;
      border-style: solid !important;
      /* kill .ref-btn's dashed border */
      -webkit-backdrop-filter: blur(28px) saturate(1.4) !important;
      backdrop-filter: blur(28px) saturate(1.4) !important;
      border-radius: 999px !important;
      color: rgba(255, 255, 255, 0.92) !important;
      font-weight: 700 !important;
      font-size: 11px !important;
      letter-spacing: .08em !important;
      text-transform: uppercase !important;
      padding: 7px 13px !important;
      height: auto !important;
      min-height: 0 !important;
      box-shadow: 0 1px 0 rgba(255, 255, 255, .08) inset !important;
      transition: all .18s cubic-bezier(.2, .8, .2, 1) !important;
      min-width: 0 !important;
    }

    [data-theme] .toggle-grp button:hover,
    [data-theme] .ref-btn:hover,
    [data-theme] .dim-btn:hover,
    [data-theme] .aspect-pill:hover,
    [data-theme] .mode-pill:hover {
      background: rgba(8, 8, 12, 0.35) !important;
      border-color: rgba(255, 255, 255, 0.40) !important;
      color: #ffffff !important;
    }

    [data-theme] .toggle-grp button.on {
      background: rgba(255, 255, 255, 0.10) !important;
      border: 1px solid rgba(255, 255, 255, 0.55) !important;
      color: #ffffff !important;
      box-shadow:
        0 0 0 1px rgba(255, 255, 255, .18) inset,
        0 0 16px rgba(255, 255, 255, .08) !important;
    }

    html[data-theme="day"] [data-theme] .toggle-grp button.on {
      color: #000 !important;
    }

    /* REFERENCE PHOTO label inner span — inherit pill typography. */
    [data-theme] .ref-btn .ref-btn-label {
      font: inherit !important;
      letter-spacing: inherit !important;
      text-transform: inherit !important;
      color: inherit !important;
    }

    /* CREATE button — target both .btn-create AND .btn-create.liquid
   (the .liquid class overrides my plain .btn-create rule). Force
   clean oval pill with two segments matching music's "Make the
   song | 110" anatomy. */
    [data-theme] .btn-create,
    [data-theme] .btn-create.liquid,
    [data-theme] .input-row .btn-create,
    [data-theme] .input-row .btn-create.liquid {
      height: auto !important;
      padding: 0 !important;
      border-radius: 999px !important;
      background: rgba(8, 8, 12, 0.20) !important;
      border: 1px solid rgba(255, 255, 255, 0.22) !important;
      box-shadow: 0 1px 0 rgba(255, 255, 255, .08) inset !important;
      -webkit-backdrop-filter: blur(28px) saturate(1.4) !important;
      backdrop-filter: blur(28px) saturate(1.4) !important;
      color: #ffffff !important;
      font-weight: 700 !important;
      font-size: 12px !important;
      letter-spacing: .06em !important;
      overflow: hidden !important;
    }

    [data-theme] .btn-create:hover,
    [data-theme] .btn-create.liquid:hover,
    [data-theme] .input-row .btn-create:hover {
      background: rgba(255, 255, 255, 0.10) !important;
      border-color: rgba(255, 255, 255, 0.40) !important;
      transform: none !important;
    }

    [data-theme] .btn-create .bc-main {
      padding: 9px 16px !important;
      height: auto !important;
      background: transparent !important;
      font-size: 12px !important;
      font-weight: 700 !important;
    }

    [data-theme] .btn-create .bc-cost {
      padding: 9px 14px !important;
      height: auto !important;
      background: transparent !important;
      border-left: 1px solid rgba(255, 255, 255, 0.22) !important;
      font-size: 12px !important;
      font-weight: 700 !important;
    }

    /* Kill EVERY decorative pseudo on .btn-create — the conic-blur halo
   was the source of the "weird glass box tint" bleeding outside. */
    [data-theme] .btn-create::before,
    [data-theme] .btn-create::after,
    [data-theme] .btn-create.liquid::before,
    [data-theme] .btn-create.liquid::after {
      content: none !important;
      display: none !important;
      opacity: 0 !important;
      background: none !important;
      filter: none !important;
    }

    /* Header pills cluster (Header/Brand/Tabs/Coins/Account, 1359 lines) → styles/universal.css in b.861. */
    /* Four Background Themes (548 lines) → styles/universal.css in b.862. */
