@font-face {
  font-family: 'Oceanwide';
  src: url('/static/fonts/Oceanwide-Regular.otf') format('opentype');
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}

@font-face {
  font-family: 'Oceanwide';
  src: url('/static/fonts/Oceanwide-Semibold.otf') format('opentype');
  font-weight: 600;
  font-style: normal;
  font-display: swap;
}

:root {
  /* Brand palette. NOTE: --tmb-blue is the CD primary override (#0081B6), NOT
   * the old brand-bible bright blue. CD locked invariant 1: the old bright blue
   * must never render as a fill/border/text colour anywhere on the order page;
   * the whole surface uses CD's darker, more legible primary (#0081B6). */
  --tmb-blue: #0081B6;
  --tmb-blue-dark: #0081b6;
  --tmb-blue-darker: #00638e;
  /* CD pressed/hover primary (--primary-pressed). */
  --tmb-blue-pressed: #006A96;
  --tmb-blue-soft: #eaf2ff;
  --tmb-cyan: #a8e5ff;
  /* MOBILEGIB-1 / CTATYPE-1, CD and Cliff 2026-07-28: white on #0081B6 is
   * the dated 4.41:1 exception, capped at 16px/500 or heavier. Smaller white
   * text requires a darker fill. #006A96 remains reserved for pressed. */
  --tmb-cta-bg: var(--tmb-blue-dark);
  --tmb-cta-bg-hover: var(--tmb-blue-pressed);

  /* Neutrals */
  --tmb-ink: #1d1e22;
  --tmb-muted: #585c62;
  --tmb-secondary: #71727a;
  --tmb-placeholder: #a2a4a8;
  --tmb-divider: #DEE2E6;
  --tmb-border: #d4d6dd;
  --tmb-surface: #ffffff;
  --tmb-surface-light: #f8f9fe;
  --tmb-page: #f8f9fe;

  /* Status */
  --tmb-green: #00a86b;
  --tmb-green-soft: #e6f7ee;
  --tmb-amber: #b45309;
  --tmb-amber-soft: #fef3c7;
  --tmb-red: #c41e3a;
  --tmb-red-soft: #fde8ec;

  /* Type */
  --tmb-font-head: 'Oceanwide', Arial, sans-serif;
  --tmb-font-body: 'Poppins', system-ui, -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;

  /* Radius */
  --tmb-radius-sm: 8px;
  --tmb-radius-md: 12px;
  --tmb-radius-lg: 16px;
  --tmb-radius-full: 9999px;

  /* Shadow / focus */
  --tmb-shadow-sm: 0 1px 2px 0 rgba(0, 0, 0, 0.05);
  --tmb-shadow: 0 10px 30px rgba(26, 45, 74, 0.07);
  --tmb-shadow-lg: 0 18px 40px rgba(26, 45, 74, 0.10);
  /* CD locked invariant 2: field focus is a 2px inset primary ring, no outer
   * glow. (Was an outer 3px glow in the old bright blue.) */
  --tmb-focus: inset 0 0 0 2px var(--tmb-blue-dark);

  /* Fixed header height (CD "Sticky Header (Spec)": 80px desktop). The header is
     a fixed-height bar; this token drives the page's top offset and the Order
     Card's dock position so they stay in sync. */
  --tmb-topbar-h: 80px;
}

* {
  box-sizing: border-box;
}

html {
  min-height: 100%;
  background: var(--tmb-page);
}

body {
  min-height: 100%;
  margin: 0;
  background: var(--tmb-page);
  color: var(--tmb-ink);
  font-family: var(--tmb-font-body);
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
}

button,
textarea,
a {
  font: inherit;
}

button {
  cursor: pointer;
}

.tmb-page {
  min-height: 100vh;
  padding: 28px 0 56px;
}

.tmb-topbar {
  /* CD "Sticky Header (Spec)": a FIXED bar pinned to the viewport top on ALL
   * viewports (Cliff 2026-06-02: mobile header is sticky + fades on scroll too,
   * matching desktop). It is a fixed height (var --tmb-topbar-h, tiered below:
   * 80px desktop / 72px tablet / 60px mobile = logo + 20px*2 padding) and only
   * the background + shadow FADE IN on scroll, lifting it to a clean white bar
   * (seamless #f8f9fe at rest - RO-037 no-banner). .is-scrolled is toggled by
   * chat.js when window.scrollY > 4.
   *
   * RO-042: the bar itself spans the full viewport so its background and the
   * on-scroll shadow reach the edges on wide monitors. Inner content stays
   * aligned with the page column via .tmb-topbar-inner.
   */
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  z-index: 20;
  width: 100%;
  height: var(--tmb-topbar-h);
  margin: 0;
  padding-top: 20px;
  padding-bottom: 20px;
  /* BARCENTRE-1 (Cliff 2026-08-23, Chrome emulation + his phone: "vertical
     spacing looks totally off"): the brand link is a 44px touch target
     (WCAG 2.5.5) inside a bar whose padding leaves a 20px content box, so as
     a block the inner row started at the padding edge and spilled 24px past
     the bottom - the 28px mark sat at 28..56 in the 60px phone bar (12px
     low; 6px on the tablet tier, 2px on desktop) and "? Sign in" with it.
     The bar centres its inner row instead; the height and padding the CD
     spec names are unchanged. */
  display: flex;
  align-items: center;
  background: var(--tmb-page);
  transition: background .25s ease, box-shadow .25s ease;
}

.tmb-topbar.is-scrolled {
  background: #fff;
  /* TOPBARSEAL-1 (CD .dtop.scrolled, 2026-08-18): the seal shadow, the
     mirror of the dock's. */
  box-shadow: 0 6px 16px rgba(6, 6, 22, 0.05);
}

/* The fixed header is out of flow, so reserve its height + a 16px gap at the
   top of the page on every viewport (CD: content/card sit at header-height +
   16px). */
.tmb-page {
  padding-top: calc(var(--tmb-topbar-h) + 16px);
}

/* Header HEIGHT tiers (CD hand-off snippet): desktop 80px (:root), tablet 72px,
   mobile 60px. Per-tier logo + side gutters are set just after the base
   .tmb-brand-logo / .tmb-topbar-inner rules below (they must follow those base
   rules so the media-query overrides win on source order). These run on CD's
   1024/768 breakpoints, independent of the 900/901 layout-mode split. */
@media (max-width: 1023px) {
  :root { --tmb-topbar-h: 72px; }
}
@media (max-width: 767px) {
  :root { --tmb-topbar-h: 60px; }
}

.tmb-topbar-inner {
  width: min(1440px, 100%);
  margin: 0 auto;
  padding: 0 56px;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
}

.tmb-brand {
  display: inline-flex;
  align-items: center;
  text-decoration: none;
  /* Touch target: WCAG 2.5.5 minimum 44x44 for the home link. The visible
   * logo height stays unchanged via the inner .tmb-brand-logo rule. */
  min-height: 44px;
  padding: 2px 4px;
  margin: 0 -4px;
  border-radius: var(--tmb-radius-sm);
}
.tmb-brand:focus-visible {
  outline: none;
  box-shadow: var(--tmb-focus);
}

.tmb-brand-logo {
  display: block;
  height: 40px;
  width: auto;
}

/* MARKONLY-1 (Cliff via CD, 2026-08-22; design-specs/cd/CLAUDE.md): on phones
   the header wears the ICON MARK alone - no word mark - rendered SQUARE
   (28x28) so it can never set the bar's height. Desktop keeps the full word
   mark. Reverses BARFIT-1's "the full logo stays". */
.tmb-brand-mark {
  display: none;
  width: 28px;
  height: 28px;
  flex: 0 0 28px;
}
@media (max-width: 767px) {
  .tmb-brand-logo { display: none; }
  .tmb-brand-mark { display: block; }
}

/* Per-tier logo size + header side gutters (CD hand-off). Placed AFTER the base
   .tmb-brand-logo / .tmb-topbar-inner so these media-query overrides win on
   source order. Desktop (>=1024): logo 40px / gutter 56px (kept at the
   page-column padding so the header stays aligned with content, RO-042).
   Tablet (768-1023): logo 36px / gutter 32px. Mobile (<768): logo 28px /
   gutter 20px (CD mobile header spec). */
@media (max-width: 1023px) {
  .tmb-brand-logo { height: 36px; }
  .tmb-topbar-inner { padding: 0 32px; }
}
@media (max-width: 767px) {
  .tmb-brand-logo { height: 28px; }
  .tmb-topbar-inner { padding: 0 20px; }
}

.tmb-domain {
  color: var(--tmb-secondary);
  font-size: 13px;
  font-weight: 500;
  letter-spacing: 0.02em;
}

.tmb-topbar-actions,
.tmb-checkout-topbar-actions {
  display: inline-flex;
  align-items: center;
  justify-content: flex-end;
  gap: 14px;
  min-width: 0;
}

.tmb-help {
  position: relative;
  flex: 0 0 auto;
}

.tmb-help-trigger {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 7px;
  min-width: 44px;
  min-height: 38px;
  padding: 9px 16px 9px 13px;
  border: 0;
  border-radius: var(--tmb-radius-full);
  background: transparent;
  color: var(--tmb-muted);
  font-family: var(--tmb-font-body);
  font-size: 14.5px;
  font-weight: 500;
  line-height: 1;
  cursor: pointer;
  transition: background 0.14s ease, color 0.14s ease;
}

.tmb-help-trigger:hover,
.tmb-help-trigger:focus-visible,
.tmb-help-trigger.is-open {
  background: var(--tmb-blue-soft);
  color: var(--tmb-blue);
  outline: none;
}

.tmb-help-trigger-icon {
  width: 20px;
  height: 20px;
  flex: 0 0 auto;
}

.tmb-help-popover {
  position: absolute;
  top: calc(100% + 10px);
  right: 0;
  width: 324px;
  padding: 18px 18px 16px;
  border-radius: 16px;
  background: #fff;
  box-shadow: 0 8px 24px rgba(6,6,22,.08), 0 0 0 1px var(--tmb-divider);
  z-index: 35;
}

.tmb-help-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  margin: 0 0 12px;
}

.tmb-help-title {
  color: var(--tmb-ink);
  font-size: 16px;
  font-weight: 700;
}

.tmb-help-close {
  width: 30px;
  height: 30px;
  border: 0;
  border-radius: var(--tmb-radius-full);
  background: transparent;
  color: var(--tmb-muted);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
  transition: background 0.14s ease, color 0.14s ease;
}

.tmb-help-close:hover,
.tmb-help-close:focus-visible {
  background: var(--tmb-blue-soft);
  color: var(--tmb-ink);
  outline: none;
}

.tmb-help-rows {
  display: flex;
  flex-direction: column;
  gap: 10px;
}

.tmb-help-row {
  width: 100%;
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 12px 14px;
  border: 1px solid var(--tmb-divider);
  border-radius: 12px;
  background: #fff;
  color: var(--tmb-ink);
  font-family: var(--tmb-font-body);
  text-align: left;
  text-decoration: none;
  cursor: pointer;
  transition: background 0.14s ease, border-color 0.14s ease;
}

.tmb-help-row:hover,
.tmb-help-row:focus-visible {
  background: var(--tmb-blue-soft);
  border-color: #cfe4ff;
  outline: none;
}

.tmb-help-ico {
  width: 40px;
  height: 40px;
  flex: 0 0 auto;
  border-radius: 10px;
  background: var(--tmb-blue-soft);
  color: var(--tmb-blue);
  display: inline-flex;
  align-items: center;
  justify-content: center;
}

.tmb-help-copy {
  min-width: 0;
  display: flex;
  flex-direction: column;
  gap: 1px;
}

.tmb-help-row-title {
  color: var(--tmb-ink);
  font-size: 14px;
  font-weight: 600;
  line-height: 1.35;
}

.tmb-help-row-sub {
  color: var(--tmb-muted);
  font-size: 12.5px;
  line-height: 1.35;
}

.tmb-help-copy-note {
  margin: 10px 2px 0;
  color: var(--tmb-blue-pressed);
  font-size: 12px;
  font-weight: 600;
}

.tmb-help-sheet-scrim,
.tmb-help-sheet {
  display: none;
}

body.tmb-help-open-mobile {
  overflow: hidden;
}

@media (max-width: 767px) {
  .tmb-topbar-actions,
  .tmb-checkout-topbar-actions {
    gap: 6px;
  }
  .tmb-help-trigger {
    width: 38px;
    min-width: 38px;
    height: 38px;
    min-height: 38px;
    padding: 0;
  }
  .tmb-help-trigger-label {
    position: absolute;
    width: 1px;
    height: 1px;
    padding: 0;
    margin: -1px;
    overflow: hidden;
    clip: rect(0, 0, 0, 0);
    white-space: nowrap;
    border: 0;
  }
  .tmb-help-trigger-icon {
    width: 22px;
    height: 22px;
  }
  /* PROGCHIP-1 (CD verdict 2026-08-21): Help paints 38px and touches 44px,
     the same pseudo-element target the progress chip and the composer send
     use - no layout cost, and the 14px gap keeps it clear of the chip's. */
  .tmb-help-trigger {
    position: relative;
  }
  .tmb-help-trigger::after {
    content: "";
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    width: 44px;
    height: 44px;
    border-radius: 999px;
  }
  .tmb-help-popover {
    display: none;
  }
  /* HELPCLIP-1 (Cliff 2026-08-08), CD design-specs/cd-help-sheet-layering-
     2026-08-08.md. The dim and sheet are direct children of the fixed shell,
     last in DOM order. Their old home inside .tmb-topbar was the whole bug:
     that header is position:relative + z-index:5, i.e. a STACKING CONTEXT, so
     these z-indexes could only rank against the topbar's own children while
     the header itself ranked at 5 - below the mobile dock (40), the Order Card
     scrim (45) and the expanded Order Card sheet (46). The dock therefore
     painted over Help and cut off its lower rows. A bigger number here could
     never have fixed that; re-parenting is the fix. 55/56 are this project's
     mechanical equivalent of CD's 40/41: both clear every dock and Order Card
     layer once Help lives in the shell's own stacking context. The dock itself
     is unchanged and sits behind the dim, which swallows its pointer events. */
  .tmb-help-sheet-scrim {
    display: block;
    position: fixed;
    inset: 0;
    z-index: 55;
    background: rgba(20, 30, 60, 0.42);
    touch-action: none;
    overscroll-behavior: contain;
    animation: tmb-overlay-fade 150ms cubic-bezier(.33, 1, .68, 1);
  }
  .tmb-help-sheet {
    display: flex;
    flex-direction: column;
    position: fixed;
    left: 0;
    right: 0;
    bottom: 0;
    z-index: 56;
    max-height: 78%;
    padding: 20px 20px max(36px, env(safe-area-inset-bottom));
    border-radius: 20px 20px 0 0;
    background: #fff;
    box-shadow: 0 -10px 40px -10px rgba(20,30,60,.25);
    opacity: 0;
    transform: translateY(4px);
    visibility: hidden;
    transition: opacity 150ms cubic-bezier(.33, 1, .68, 1),
                transform 150ms cubic-bezier(.33, 1, .68, 1),
                visibility 0s linear 150ms;
  }
  /* On the touch chat shell .tmb-page IS the fixed shell, so the Help layer is
     absolute inside it: bottom:0 and max-height:78% then resolve against the
     shell box instead of the iOS layout viewport, which is taller than the
     visible area whenever Safari's chrome is expanded. Checkout has no shell
     element, so it keeps the viewport-fixed form above. */
  .tmb-page > .tmb-help-sheet-scrim,
  .tmb-page > .tmb-help-sheet {
    position: absolute;
  }
  .tmb-help-sheet.is-open {
    opacity: 1;
    transform: translateY(0);
    visibility: visible;
    transition: opacity 150ms cubic-bezier(.33, 1, .68, 1),
                transform 150ms cubic-bezier(.33, 1, .68, 1);
  }
  .tmb-help-sheet[hidden],
  .tmb-help-sheet-scrim[hidden] {
    display: none !important;
  }
  /* Fixed header over an independently scrolling body: the rows are the only
     Help scroll region, so the title and close X stay put and every row is
     reachable inside the sheet however short the device is. No grabber - CD
     ruled Help has no swipe dismissal. */
  .tmb-help-sheet .tmb-help-head {
    flex: 0 0 auto;
    margin-bottom: 12px;
  }
  .tmb-help-sheet .tmb-help-rows {
    flex: 1 1 auto;
    min-height: 0;
    gap: 10px;
    overflow-y: auto;
    -webkit-overflow-scrolling: touch;
    overscroll-behavior: contain;
  }
}

/* HELPCLIP-1: instant under reduced motion. The override has to name
   .is-open too - it outranks the base rule on specificity, not on order. */
@media (max-width: 767px) and (prefers-reduced-motion: reduce) {
  .tmb-help-sheet,
  .tmb-help-sheet.is-open {
    transition: none;
    transform: none;
  }
  .tmb-help-sheet-scrim {
    animation: none;
  }
}

.tmb-account {
  position: relative;
}

.tmb-account-signin {
  height: auto;
  padding: 10px 22px;
  border: 0;
  border-radius: var(--tmb-radius-full);
  background: var(--tmb-surface);
  color: var(--tmb-ink);
  font-size: 14.5px;
  font-weight: 600;
  font-family: var(--tmb-font-body);
  cursor: pointer;
  box-shadow: 0 1px 2px rgba(20,30,60,.04), 0 0 0 1px #DEE2E6;
  transition: box-shadow 0.14s ease, background 0.14s ease, color 0.14s ease;
}

.tmb-account-signin:hover {
  box-shadow: 0 1px 2px rgba(20,30,60,.04), 0 0 0 1px var(--tmb-blue);
  background: var(--tmb-blue-soft);
  color: var(--tmb-blue-dark);
}

/* CD mobile: "Sign in" is a plain blue text link in the header, not the white
   pill used on desktop. */
@media (max-width: 767px) {
  .tmb-account-signin {
    padding: 0;
    background: transparent;
    box-shadow: none;
    color: var(--tmb-blue-dark);
  }
  .tmb-account-signin:hover {
    background: transparent;
    box-shadow: none;
    color: var(--tmb-blue-pressed);
  }
}

.tmb-account-chip {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  height: 36px;
  padding: 0 10px 0 6px;
  border: 1px solid var(--tmb-border);
  border-radius: var(--tmb-radius-full);
  background: var(--tmb-surface);
  color: var(--tmb-ink);
  font-size: 13px;
  font-weight: 600;
  font-family: var(--tmb-font-body);
  cursor: pointer;
  transition: border-color 0.14s ease, background 0.14s ease, color 0.14s ease;
}

.tmb-account-chip:hover,
.tmb-account-chip[aria-expanded="true"] {
  border-color: var(--tmb-blue);
  background: var(--tmb-blue-soft);
  color: var(--tmb-blue-dark);
}

.tmb-account-avatar {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 26px;
  height: 26px;
  border-radius: var(--tmb-radius-full);
  background: var(--tmb-blue);
  color: #fff;
  font-size: 12px;
  font-weight: 700;
  letter-spacing: 0.02em;
  text-transform: uppercase;
}

.tmb-account-label {
  max-width: 200px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.tmb-account-caret {
  width: 10px;
  height: 7px;
  color: var(--tmb-secondary);
  transition: transform 0.14s ease;
}

.tmb-account-chip[aria-expanded="true"] .tmb-account-caret {
  transform: rotate(180deg);
}

.tmb-account-menu {
  position: absolute;
  top: calc(100% + 8px);
  right: 0;
  min-width: 240px;
  padding: 6px;
  border: 1px solid var(--tmb-border);
  border-radius: var(--tmb-radius-md);
  background: var(--tmb-surface);
  box-shadow: var(--tmb-shadow-lg);
  z-index: 30;
}

.tmb-account-menu-id {
  padding: 10px 12px 12px;
  border-bottom: 1px solid var(--tmb-divider);
  margin-bottom: 6px;
}

.tmb-account-menu-name {
  margin: 0;
  font-size: 14px;
  font-weight: 600;
  color: var(--tmb-ink);
  word-break: break-word;
}

.tmb-account-menu-name:empty {
  display: none;
}

.tmb-account-menu-email {
  margin: 2px 0 0;
  font-size: 12px;
  color: var(--tmb-muted);
  word-break: break-all;
}

.tmb-account-signout {
  display: block;
  width: 100%;
  padding: 10px 12px;
  border: 0;
  border-radius: var(--tmb-radius-sm);
  background: transparent;
  color: var(--tmb-ink);
  font-size: 13px;
  font-weight: 600;
  font-family: var(--tmb-font-body);
  text-align: left;
  cursor: pointer;
  transition: background 0.14s ease, color 0.14s ease;
}

.tmb-account-signout:hover {
  background: var(--tmb-red-soft);
  color: var(--tmb-red);
}

.tmb-layout {
  width: min(1440px, 100%);
  margin: 0 auto;
  padding: 0 56px;
  display: grid;
  grid-template-columns: minmax(0, 1fr) 460px;
  gap: 64px;
  align-items: start;
  transition: grid-template-columns 280ms ease-out;
}

/* Phase 1b: when the order card is hidden (idle state), the layout collapses
   to a single column so the chat takes the full width. The card slides in
   from the right after the first server response. */
.tmb-layout:has(.tmb-order-card[hidden]) {
  grid-template-columns: 1fr;
}

.tmb-order-card.is-revealing {
  animation: tmb-card-reveal 320ms ease-out;
}

@keyframes tmb-card-reveal {
  from {
    transform: translateX(32px);
    opacity: 0;
  }
  to {
    transform: translateX(0);
    opacity: 1;
  }
}

.tmb-chat-area {
  min-width: 0;
}

.tmb-hero {
  /* margin-top is 0: the fixed header + .tmb-page padding-top reserve the top
     spacing on every viewport, so the hero aligns with the Order Card top. */
  margin: 0 0 26px;
}

.tmb-eyebrow,
.tmb-card-kicker {
  margin: 0 0 14px;
  /* EYEBROWTAP-1 (CD 2026-08-11): the eyebrow is a plain label - muted ink,
   * never blue and never interactive (no handler, href, role, cursor, hover,
   * or tap target). Blue read as a CTA and drew dead taps from ad traffic.
   * The kicker keeps its own colour in its later block. */
  color: var(--tmb-muted);
  text-transform: uppercase;
  font-size: 13px;
  line-height: 1.4;
  font-weight: 600;
  letter-spacing: 0.14em;
}

.tmb-card-kicker {
  color: #0081B6;
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
}

.tmb-hero h1 {
  max-width: 720px;
  margin: 0;
  color: var(--tmb-ink);
  /* Semibold (600): we ship Oceanwide Regular (400) + Semibold (600) only - no
   * true 800 face, so 800 faux-bolds and renders rough. 600 uses the real face
   * (Cliff 2026-06-03: go with semibold; a touch lighter than CD's 800 but clean). */
  font: 600 clamp(40px, 4.5vw, 72px)/1.02 var(--tmb-font-head);
  letter-spacing: -0.025em;
}

.tmb-hero p:last-child {
  max-width: 620px;
  margin: 18px 0 0;
  color: var(--tmb-muted);
  font-size: 18px;
  line-height: 1.55;
}

.tmb-chips {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}

.tmb-chips button {
  min-height: 44px;
  border: 0;
  border-radius: var(--tmb-radius-full);
  background: var(--tmb-surface);
  color: #006A96;
  box-shadow: inset 0 0 0 1.5px #c6e3f8;
  padding: 14px 28px;
  font-size: 16px;
  font-weight: 600;
  line-height: 1.5;
  transition: box-shadow 0.14s ease, background 0.14s ease, color 0.14s ease;
  /* CD "Composer Behavior (Demo)" chipIn: chips fade in rather than hard-cut
     (blind-QA B16-018 P2). */
  animation: tmb-chip-in 0.2s ease both;
}

@keyframes tmb-chip-in {
  from { opacity: 0; transform: translateY(3px); }
  to { opacity: 1; transform: none; }
}

@media (prefers-reduced-motion: reduce) {
  .tmb-chips button {
    animation: none;
  }
  .tmb-auth-provider-spinner {
    display: none;
    animation: none;
  }
}

.tmb-chips button:hover {
  box-shadow: inset 0 0 0 1.5px var(--tmb-blue);
  background: var(--tmb-blue-soft);
  color: #006A96;
}

/* CD .chip-action (solid): the primary/affirmative chip is a solid filled blue
   pill with white text. renderChips() tags it with .is-primary. */
.tmb-chips button.is-primary {
  background: var(--tmb-blue);
  color: #fff;
  box-shadow: none;
}

.tmb-chips button.is-primary:hover {
  background: var(--tmb-blue-pressed);
  color: #fff;
}

.tmb-log {
  min-height: 220px;
  max-height: 360px;
  overflow-y: auto;
  padding: 4px 2px 12px;
  display: flex;
  flex-direction: column;
  gap: 14px;
}

.tmb-log:empty {
  min-height: 0;
  padding: 0;
}

.tmb-message {
  width: fit-content;
  /* CD: flat 520px cap on desktop; the mobile override sets 306px. */
  max-width: 520px;
  padding: 12px 16px;
  border-radius: var(--tmb-radius-lg);
  font-size: 16px;
  font-weight: 500;
  line-height: 1.5;
  box-shadow: 0 5px 18px rgba(26, 45, 74, 0.06);
  white-space: pre-wrap;
  overflow-wrap: anywhere;
}

.tmb-message-user {
  margin-left: auto;
  background: var(--tmb-cta-bg);
  color: white;
  padding: 14px 22px;
  border-radius: 22px;
  border-top-right-radius: 6px;
  box-shadow: 0 6px 14px -6px rgba(0,129,182,.45);
}

.tmb-message-bot {
  background: #fff;
  border: 1.5px solid #c6e3f8;
  color: var(--tmb-ink);
  padding: 14px 22px;
  border-radius: 22px;
  border-top-left-radius: 6px;
  box-shadow: 0 1px 2px rgba(0, 129, 182, 0.06);
}

.tmb-message-summary {
  display: block;
  margin-top: 6px;
  color: var(--tmb-muted);
  font-size: 14px;
  line-height: 1.45;
}

/* Returning-offer recap (blind-QA B03-005/B03-006, 2026-07-06): CD FB-02's
   labeled saved-order list - fixed uppercase labels, one label: value per
   row. Mirrors the .bubble-bot .recap spec in Chat Bubbles (Fixed).html. */
.tmb-message-recap {
  list-style: none;
  margin: 12px 0 0;
  padding: 0;
  display: grid;
  grid-template-columns: max-content 1fr;
  gap: 6px 14px;
  font-size: 14px;
  line-height: 1.45;
  white-space: normal;
}

.tmb-message-recap li {
  display: contents;
}

.tmb-recap-label {
  font-size: 11px;
  font-weight: 700;
  color: var(--tmb-muted);
  letter-spacing: 0.08em;
  text-transform: uppercase;
  align-self: center;
  white-space: nowrap;
}

.tmb-recap-val {
  font-weight: 500;
  color: var(--tmb-ink);
  letter-spacing: -0.005em;
}

.tmb-message-pending {
  display: inline-flex;
  align-items: center;
  gap: 10px;
  color: var(--tmb-muted);
}

.tmb-message-pending.tmb-sendtime-pending {
  opacity: 0;
  transition: opacity 150ms ease-out;
}

.tmb-message-pending.tmb-sendtime-pending.is-visible {
  opacity: 1;
}

/* SENDTIME-1 no-jank amendment: the send batch pins the measured pixel
   height first, then this explicit zero-height exit rides the glide. */
.tmb-sendtime-exit {
  height: 0px !important;
  opacity: 0 !important;
  overflow: hidden !important;
  pointer-events: none;
  transition: height 150ms ease-out, opacity 150ms ease-out;
}

.tmb-turn-enter,
.tmb-turn-enter-interactive {
  opacity: 0;
  transition: opacity 150ms ease-out;
}

.tmb-turn-enter {
  transform: translateY(4px);
  transition: opacity 150ms ease-out, transform 150ms ease-out;
}

.tmb-turn-enter.is-visible,
.tmb-turn-enter-interactive.is-visible {
  opacity: 1;
}

.tmb-turn-enter.is-visible {
  transform: none;
}

/* Centered system chip (blind-QA B11-038, 2026-07-06; CD "Order Card
   (Mobile)" .system-chip): a quiet pill confirming a tap-to-edit jump -
   "You tapped {Step} to edit" - 11.5px/600 muted on an #eef0f4 pill. Not a
   chat bubble; it sits on its own centered row in the log. */
.tmb-system-row {
  align-self: center;
  display: flex;
  justify-content: center;
}

.tmb-system-chip {
  font-size: 11.5px;
  font-weight: 600;
  color: var(--tmb-muted);
  background: #eef0f4;
  padding: 5px 12px;
  border-radius: 999px;
}

/* CD system chip carries a leading "↺" glyph (Chat Bubbles sec. 4; folded
   into blind-QA B13-003/051). */
.tmb-system-chip::before {
  content: "\21BA";
  margin-right: 6px;
}

/* EDIT-1: one structured editor appended at the conversation frontier. The
   block is normal thread content, so history remains scrollable above it. */
.tmb-edit-block {
  align-self: stretch;
  width: min(100%, 620px);
  display: flex;
  flex-direction: column;
  gap: 12px;
  padding: 2px 0 8px;
}

.tmb-edit-block > .tmb-system-row {
  align-self: center;
}

.tmb-edit-surface-host {
  width: 100%;
}

.tmb-edit-surface-host > .inline-form-card,
.tmb-edit-surface-host > .tmb-care-selector,
.tmb-edit-surface-host > .tmb-washpros-selector {
  width: 100%;
  max-width: none;
}

.tmb-edit-cancel {
  align-self: center;
  border: 0;
  background: transparent;
  color: #585C62;
  padding: 4px 12px;
  font: inherit;
  font-size: 14px;
  font-weight: 500;
  line-height: 1.4;
  cursor: pointer;
}

.tmb-edit-cancel:hover {
  color: var(--tmb-ink);
  text-decoration: underline;
  text-underline-offset: 3px;
}

.tmb-edit-cancel:focus-visible {
  outline: 2px solid var(--tmb-blue-dark);
  outline-offset: 2px;
  border-radius: 4px;
}

/* EDITFADE-1 (Cliff 2026-07-22): resolved edit blocks render at FULL
   opacity - no fade. The old 0.68 fade is retired; do not restore it
   without a new Cliff ruling. */
.tmb-edit-block[data-open="0"] .tmb-edit-surface-host {
  display: none;
}

.tmb-edit-block[data-open="0"] .tmb-edit-cancel {
  display: none;
}

.tmb-structured-inert {
  pointer-events: none;
  user-select: text;
  filter: saturate(0.72);
}

.tmb-edit-empty {
  padding: 18px;
  border-radius: var(--tmb-radius-md);
  background: #fff;
  box-shadow: inset 0 0 0 1px var(--tmb-divider);
  color: var(--tmb-muted);
  font-size: 14px;
}

@media (max-width: 640px) {
  .tmb-edit-block {
    width: 100%;
  }

}

.tmb-dots {
  display: inline-flex;
  gap: 4px;
}

.tmb-dots span {
  width: 6px;
  height: 6px;
  border-radius: 50%;
  background: var(--tmb-blue);
  animation: tmb-dot 1s ease-in-out infinite;
}

.tmb-dots span:nth-child(2) {
  animation-delay: 0.15s;
}

.tmb-dots span:nth-child(3) {
  animation-delay: 0.3s;
}

@keyframes tmb-dot {
  0%, 80%, 100% {
    transform: translateY(0);
    opacity: 0.45;
  }
  40% {
    transform: translateY(-4px);
    opacity: 1;
  }
}

@keyframes tmb-chip-in-opacity {
  from { opacity: 0; }
  to { opacity: 1; }
}

.tmb-composer {
  --tmb-composer-inline-pad: 22px;
  --tmb-lock-icon-gap: 8px;
  position: relative;
  display: grid;
  grid-template-columns: minmax(0, 1fr) 44px;
  gap: 8px;
  align-items: center;
  /* CD .composer padding (14px 14px 14px 22px) - a substantial ~64px bar, not
   * a cramped single row. The textarea still auto-grows for multi-line input;
   * the flex-grow log above absorbs the extra height so the composer stays
   * bottom-anchored. */
  padding: 14px 14px 14px var(--tmb-composer-inline-pad);
  background: var(--tmb-surface);
  /* CD .composer { border-radius: 14px } */
  border-radius: 14px;
  box-shadow: 0 1px 2px rgba(20,30,60,.05), 0 0 0 1px var(--tmb-divider);
}

.tmb-address-suggestions {
  position: absolute;
  left: 12px;
  right: 74px;
  bottom: calc(100% + 8px);
  z-index: 20;
  overflow: hidden;
  border: 1px solid var(--tmb-border);
  border-radius: var(--tmb-radius-md);
  background: var(--tmb-surface);
  box-shadow: var(--tmb-shadow-lg);
}

.tmb-address-suggestions[hidden] {
  display: none;
}

.tmb-address-suggestions button {
  display: grid;
  width: 100%;
  gap: 2px;
  padding: 11px 13px;
  border: 0;
  border-bottom: 1px solid var(--tmb-divider);
  background: var(--tmb-surface);
  color: var(--tmb-ink);
  text-align: left;
  font-size: 14px;
  line-height: 1.3;
}

.tmb-address-suggestions button:last-child {
  border-bottom: 0;
}

.tmb-address-suggestions button:hover,
.tmb-address-suggestions button:focus,
.tmb-address-suggestions button.is-active {
  outline: 0;
  background: var(--tmb-blue-soft);
  box-shadow: inset 3px 0 0 0 var(--tmb-blue);
}

.tmb-address-suggestions small {
  color: var(--tmb-muted);
  font-size: 12px;
  line-height: 1.35;
}

.tmb-address-hint {
  position: absolute;
  left: 12px;
  right: 74px;
  bottom: -22px;
  margin: 0;
  color: var(--tmb-muted);
  font-size: 12px;
  line-height: 1.4;
  font-weight: 500;
}

.tmb-address-hint[hidden] {
  display: none;
}

.tmb-input {
  width: 100%;
  /* Single-row default; auto-grow to 5 rows max. JS auto-sizing in chat.js
   * (autoSizeInput) bumps the row height as content grows. */
  min-height: 36px;
  max-height: 150px;
  resize: none;
  border: 0;
  outline: 0;
  padding: 7px 8px 7px 0;
  color: var(--tmb-ink);
  background: transparent;
  font-size: 16px;
  line-height: 1.4;
  /* Defeat the user-agent default vertical-align that adds a couple of
   * descender pixels under textareas. */
  vertical-align: middle;
}

.tmb-input::placeholder {
  color: var(--tmb-placeholder);
  font-size: 16px;
}

/* MOBILE3FIX (2026-07-14): composer hints are always one line. This selector
   only applies while the textarea is empty, so typed customer text keeps the
   existing auto-grow and wrapping behaviour. */
.tmb-input:placeholder-shown {
  height: 36px;
  min-height: 36px;
  max-height: 36px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* Locked composer during the in-chat address picker (CD): the box greys out
   and nudges the customer to the address card above. */
.tmb-input.is-locked {
  cursor: not-allowed;
}
.tmb-composer:has(.tmb-input.is-locked) {
  background: #f3f4f8;
  box-shadow: 0 0 0 1px var(--tmb-divider);
}
.tmb-composer:has(.tmb-input.is-locked) .tmb-input::placeholder {
  color: var(--tmb-secondary);
}
/* CD .composer.locked: a padlock sits to the LEFT of the placeholder so the
   locked state reads clearly (the greyed send button stays). */
.tmb-composer:has(.tmb-input.is-locked)::before {
  content: '';
  position: absolute;
  left: var(--tmb-composer-inline-pad);
  top: 50%;
  transform: translateY(-50%);
  width: 18px;
  height: 18px;
  background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%239aa0a8' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Crect x='5' y='11' width='14' height='10' rx='2'/%3E%3Cpath d='M8 11V7a4 4 0 0 1 8 0v4'/%3E%3C/svg%3E") no-repeat center / contain;
  pointer-events: none;
  z-index: 1;
}
.tmb-composer:has(.tmb-input.is-locked) .tmb-input {
  padding-left: calc(18px + var(--tmb-lock-icon-gap));
}

.tmb-composer:focus-within {
  box-shadow: 0 1px 2px rgba(20,30,60,.05), 0 0 0 1px var(--tmb-border);
}

/* Checkout Focus (CD locked invariant 11; blind-QA B11-048, 2026-07-06): on a
   ready order the composer demotes to the GHOST treatment - transparent bar,
   hairline inset border, muted placeholder, grey send - so the filled Place
   order CTA is the only bright element (CD .composer.ghost / .m-composer.ghost,
   decision record Checkout Focus Option A). It stays interactive: hover or
   focus restores the solid surface, so editing is one tap away. Only the BAR
   goes transparent; the text/placeholder keep solid muted colors, so nothing
   reads see-through (Cliff 2026-07-04). */
.tmb-composer {
  transition: background-color 200ms ease, box-shadow 200ms ease;
}
.tmb-composer.tmb-composer--dimmed {
  /* Cliff 2026-07-13: must stay OPAQUE. The old transparent treatment let
     bubbles scrolled behind the sticky dock show through the input (their
     text superimposed on the placeholder). Page colour keeps the recessive
     look Cliff chose on 2026-07-04 while sealing the dock. */
  background: var(--tmb-page);
  box-shadow: inset 0 0 0 1px var(--tmb-divider);
}
.tmb-composer.tmb-composer--dimmed .tmb-input {
  color: var(--tmb-secondary);
}
.tmb-composer.tmb-composer--dimmed .tmb-input::placeholder {
  color: #aab0b8;
}
.tmb-composer.tmb-composer--dimmed .tmb-send {
  background: #eef0f4;
  color: #b3b8c0;
}
.tmb-composer.tmb-composer--dimmed:hover,
.tmb-composer.tmb-composer--dimmed:focus-within {
  background: var(--tmb-surface);
}
.tmb-composer.tmb-composer--dimmed:hover .tmb-input::placeholder,
.tmb-composer.tmb-composer--dimmed:focus-within .tmb-input::placeholder {
  color: var(--tmb-secondary);
}

.tmb-send {
  /* Sized to match the new single-row composer (composer total ~50px). */
  width: 36px;
  height: 36px;
  border: 0;
  border-radius: var(--tmb-radius-md);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: var(--tmb-surface-light);
  color: var(--tmb-placeholder);
  cursor: not-allowed;
  transition: background 0.14s ease, color 0.14s ease;
}

.tmb-send.is-ready {
  background: var(--tmb-cta-bg);
  color: white;
  cursor: pointer;
}

.tmb-send.is-ready:hover {
  background: var(--tmb-cta-bg-hover);
}

.tmb-send svg {
  width: 16px;
  height: 16px;
}

/* CHATTY-1 (CD "MobileComposer - composer change only", 2026-07-18 B1+C1
   slice; solid-at-rest ratified by Cliff 2026-07-19): on the touch shell the
   ACTIVE composer reads as a message input, not chrome - a blinking primary
   caret rests at the text start and the send is solid primary even while the
   field is empty. Locked and ghost (dimmed) composers keep their muted
   treatment so one-solid-action holds at Ready. Placeholder copy, dock
   position, and the peek bar are unchanged. Desktop is untouched. */
.tmb-caret {
  display: none;
  position: absolute; /* out of the composer grid's flow in every state */
  left: var(--tmb-composer-inline-pad);
  top: 50%;
  width: 2px;
  height: 18px;
  border-radius: 1px;
  background: var(--tmb-cta-bg);
  transform: translateY(-50%);
  pointer-events: none;
}

/* Every hide condition lives INSIDE the show selector - separate override
   rules lose the specificity battle against the :not(:has(...)) chain (a
   :not()/:has() counts its heaviest argument). The caret shows only while
   the ACTIVE composer is empty and unfocused; on focus the native caret
   takes over, and typed text keeps the resting one hidden. */
.tmb-page.tmb-touch-shell .tmb-composer:not(.tmb-composer--dimmed):not(:has(.tmb-input.is-locked)):not(:focus-within):has(.tmb-input:placeholder-shown) .tmb-caret {
  display: block;
  animation: tmb-cblink 1.1s steps(1, end) infinite; /* CD .m-composer.chatty .caret */
}

@keyframes tmb-cblink {
  50% { opacity: 0; }
}

@media (prefers-reduced-motion: reduce) {
  .tmb-page.tmb-touch-shell .tmb-composer .tmb-caret {
    animation: none; /* steady caret, no blink */
  }
}

.tmb-page.tmb-touch-shell .tmb-composer:not(.tmb-composer--dimmed):not(:has(.tmb-input.is-locked)) .tmb-input {
  padding-left: 6px; /* text and placeholder sit beside the resting caret */
}

.tmb-page.tmb-touch-shell .tmb-composer:not(.tmb-composer--dimmed):not(:has(.tmb-input.is-locked)) .tmb-input::placeholder {
  color: #6f747d; /* CD .m-composer.chatty .placeholder */
}

.tmb-page.tmb-touch-shell .tmb-composer:not(.tmb-composer--dimmed):not(:has(.tmb-input.is-locked)) .tmb-send {
  background: var(--tmb-cta-bg);
  color: #fff;
  cursor: pointer;
}

.tmb-chips {
  /* Chips sit ABOVE the composer now (CD "Composer Behavior" 2026-05-31): the
     12px gap goes below the tray, between the chips and the composer (CD
     .chip-row margin-bottom:12px), plus a little breathing room above to
     separate from the last message. */
  margin: 12px 0 12px;
}

.tmb-chips:empty {
  display: none;
}

.tmb-order-card {
  position: sticky;
  /* RO-043: sit BELOW the ~76px sticky topbar (top:0 on desktop) with the
   * same 24px breathing room the topbar has from the viewport edge.
   * Mobile re-pins this via position:fixed; bottom:... in the <=900px block. */
  top: 100px;
  background: var(--tmb-surface);
  border: 0;
  border-radius: 12px;
  box-shadow: 0 2px 8px rgba(20,30,60,.05), 0 0 0 1px #DEE2E6;
  overflow: hidden;
}

.tmb-card-mobile-toggle {
  display: none;
}

/* Mobile-only backdrop behind the expanded Order Card sheet (see the
   max-width:900px block for the visible state). Hidden everywhere by default;
   on desktop the card is inline with no toggle, so this never shows. */
.tmb-card-scrim {
  display: none;
}

/* M5 mobile bottom sheet (Cliff 2026-07-05): the expanded Order Card on
   mobile. Hidden everywhere by default; the max-width:900px block turns it
   into the CD bottom sheet. Desktop keeps the inline sidebar card and never
   renders this element. */
.tmb-sheet {
  display: none;
}

.tmb-card-inner {
  padding: 26px 26px 20px;
}

.tmb-card-header {
  display: flex;
  align-items: start;
  justify-content: space-between;
  gap: 14px;
  margin-bottom: 14px;
}

.tmb-card-header h2 {
  margin: 0;
  font: 800 26px/1.2 var(--tmb-font-head);
  letter-spacing: -0.015em;
  color: var(--tmb-ink);
}

.tmb-card-status {
  flex: 0 0 auto;
  display: inline-flex;
  min-height: 28px;
  align-items: center;
  border-radius: var(--tmb-radius-full);
  padding: 5px 12px;
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  /* CD .pill-status: never wraps. */
  white-space: nowrap;
}

.tmb-card-status.is-ready {
  color: #1f7a52;
  background: rgba(0,168,107,.12);
}

.tmb-card-status.is-ready::before {
  content: '';
  display: inline-block;
  width: 7px;
  height: 7px;
  margin-right: 7px;
  border-radius: 50%;
  background: #00a86b;
  box-shadow: 0 0 0 3px rgba(0,168,107,.18);
}

.tmb-card-status.is-in_progress {
  color: #5a5e66;
  background: #f3f4f8;
}

.tmb-card-status.is-in_progress::before {
  content: '';
  display: inline-block;
  width: 7px;
  height: 7px;
  margin-right: 7px;
  border-radius: 50%;
  background: var(--tmb-blue);
  box-shadow: 0 0 0 3px rgba(0,129,182,.18);
}

.tmb-card-status.is-idle {
  display: none;
}

/* Screen 0: the empty "ghost" card before the customer says anything. */
.tmb-card-status.is-empty {
  color: #8b8f97;
  background: #f3f4f8;
}

.tmb-card-status.is-empty::before {
  content: '';
  display: inline-block;
  width: 7px;
  height: 7px;
  margin-right: 7px;
  border-radius: 50%;
  background: #c8ccd4;
  box-shadow: 0 0 0 3px rgba(200,204,212,.28);
  opacity: 1;
}

.tmb-card-status.is-out_of_service {
  color: var(--tmb-red);
  background: var(--tmb-red-soft);
}

/* CD 10b/10b2 .pill-status Editing: while an edit detour is open the header
   pill flips to the soft-blue Editing treatment (matches .tmb-step-pill). */
.tmb-card-status.is-editing {
  color: #006A96;
  background: var(--tmb-blue-soft);
}

.tmb-card-status.is-editing::before {
  content: '';
  display: inline-block;
  width: 7px;
  height: 7px;
  margin-right: 7px;
  border-radius: 50%;
  background: var(--tmb-blue);
  box-shadow: 0 0 0 3px rgba(0,129,182,.18);
}

/* ----- numbered steps ----- */
.tmb-card-steps {
  margin: 0;
  padding: 0;
  list-style: none;
  /* CD: no top divider between header and step 1 - only the per-row
     border-bottom on each .tmb-step draws the dividers. */
}

.tmb-step {
  position: relative;
  border-bottom: 1px solid #DEE2E6;
  opacity: 0.38;
  transition: opacity .15s ease;
}

.tmb-step:last-child {
  border-bottom: 0;
}

.tmb-step.is-active,
.tmb-step.is-editing {
  opacity: 1;
}

.tmb-step-head {
  display: flex;
  align-items: center;
  gap: 14px;
  padding: 14px 0;
  cursor: pointer;
}

.tmb-step.is-upcoming .tmb-step-head {
  cursor: default;
}

.tmb-step-head:focus-visible {
  outline: 2px solid var(--tmb-blue);
  outline-offset: 2px;
  border-radius: 6px;
}

.tmb-step-badge {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 26px;
  height: 26px;
  border-radius: var(--tmb-radius-full);
  background: transparent;
  box-shadow: inset 0 0 0 1.5px #d6d9e0;
  color: var(--tmb-secondary);
  font-size: 12px;
  font-weight: 700;
}

.tmb-step.is-upcoming .tmb-step-badge {
  font-size: 12.5px;
  font-variant-numeric: tabular-nums;
}

.tmb-step-label {
  flex: 1 1 auto;
  min-width: 0;
  color: #585c62;
  font-size: 15px;
  font-weight: 500;
  letter-spacing: -0.005em;
}

.tmb-step-value {
  flex: 0 1 auto;
  min-width: 0;
  max-width: 220px;
  color: #9298a0;
  font-size: 13px;
  font-weight: 500;
  text-align: right;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

.tmb-step-prefill-head {
  flex: 0 1 auto;
  min-width: 0;
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  gap: 1px;
  text-align: right;
}

.tmb-step-source,
.tmb-step-detail-line.prefilled .source,
.tmb-sheet-line.source {
  color: var(--tmb-muted);
  font-size: 11.5px;
  font-weight: 600;
}

.tmb-step-hint {
  flex: 0 0 auto;
  color: var(--tmb-placeholder);
  font-size: 13.5px;
  font-weight: 500;
}

.tmb-step.is-active .tmb-step-badge,
.tmb-step.is-editing .tmb-step-badge {
  background: #0081B6;
  color: #fff;
  box-shadow: 0 0 0 4px rgba(0,129,182,.16);
}

.tmb-step.is-done .tmb-step-badge {
  width: 26px;
  height: 26px;
  border: 0;
  border-radius: 999px;
  background: #eaf2ff;
  color: #006A96;
  box-shadow: none;
  font-size: 12.5px;
  font-weight: 700;
  font-variant-numeric: tabular-nums;
}

.tmb-step-check,
.tmb-step-check svg {
  display: block;
  width: 12px;
  height: 12px;
}

.tmb-step.is-done {
  opacity: 1;
}

/* DONEROWS-1: completed rows read as a receipt at full opacity. Hover and
   keyboard focus still reveal the existing edit affordance. */
.tmb-step.is-done:hover,
.tmb-step.is-done:focus-within {
  opacity: 1;
}

.tmb-step.is-done .tmb-step-label {
  color: #8b8f97;
  font-size: 15px;
  font-weight: 500;
  letter-spacing: -0.005em;
}

.tmb-step.is-done .tmb-step-value {
  max-width: 220px;
  color: #1d1e22;
  font-size: 13px;
  font-weight: 600;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

.tmb-step.is-done .tmb-step-head {
  padding-right: 26px;
}

.tmb-step-edit {
  position: absolute;
  right: 4px;
  top: 15px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 18px;
  height: 18px;
  color: #006A96;
  opacity: 0;
  transition: opacity 0.14s ease;
  pointer-events: none;
}

.tmb-step.is-done .tmb-step-edit {
  top: 50%;
  transform: translateY(-50%);
}

.tmb-step-edit svg {
  width: 14px;
  height: 14px;
  display: block;
}

.tmb-step.is-done:hover .tmb-step-edit,
.tmb-step.is-done:focus-within .tmb-step-edit {
  opacity: 1;
}

/* EDITTAP-1, CD Transitions.EditStep act 1 beat 0 (RULED), verbatim:
   "t=0 - Edit press feedback. 98% scale, brightness .94, 150ms ease-out,
   concurrent - nothing waits on it." Same values as the address row press
   (.addr-pred-item) because it is the same design-system gesture: the press
   IS the acknowledgement. The pencil itself is pointer-events:none here - the
   whole row is the tap target - so the row carries the press. */
.tmb-step[data-step-tap] {
  transition: transform 0.15s ease-out, filter 0.15s ease-out;
}

.tmb-step[data-step-tap]:active {
  transform: scale(0.98);
  filter: brightness(0.94);
}

@media (prefers-reduced-motion: reduce) {
  .tmb-step[data-step-tap]:active {
    transform: none;
  }
}

/* Pickup location always uses the CD three-line anatomy: name, full-width
   address, then the optional clamped note. Other steps keep their values on
   the first line even when they carry a note. */
.tmb-step[data-step="pickup_location"] .tmb-step-head {
  flex-wrap: wrap;
  /* CD stacked rhythm (2026-07-13): name line to address line is a 3px flex
     gap - the base 14px gap is the COLUMN gap between badge and label only. */
  column-gap: 14px;
  row-gap: 3px;
}

.tmb-step[data-step="pickup_location"] .tmb-step-label {
  padding-right: 18px;
}

.tmb-step.has-note .tmb-step-value {
  flex-basis: calc(100% - 40px);
  max-width: none;
  margin-left: 40px;
  text-align: left;
  white-space: normal;
  overflow: visible;
  text-overflow: clip;
}

.tmb-step.has-note:not([data-step="pickup_location"]) .tmb-step-value {
  flex-basis: auto;
  max-width: 220px;
  margin-left: 0;
  text-align: right;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

.tmb-step[data-step="pickup_location"] .tmb-step-head > .tmb-step-prefill-head {
  flex-basis: calc(100% - 40px);
  max-width: none;
  margin-left: 40px;
  align-items: flex-start;
  text-align: left;
}

.tmb-step[data-step="pickup_location"] .tmb-step-prefill-head .tmb-step-value {
  flex-basis: auto;
  max-width: none;
  margin-left: 0;
  text-align: left;
  white-space: normal;
  overflow: visible;
  text-overflow: clip;
  /* CD stacked rhythm: the address line is 13px/1.5 (.step-meta type). */
  line-height: 1.5;
}

/* CD stacked rhythm (2026-07-13): value/address line to note line is 5px,
   and the row's 14px bottom padding moves to the note so the stack still
   ends 14px above the divider. */
.tmb-step.has-note .tmb-step-head {
  padding-bottom: 5px;
}

/* "Asking now" and "Editing" share one light-blue capsule; only the leading
   marker differs (dot vs pencil) so they read as one visual family. */
.tmb-step-pill {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  gap: 5px;
  padding: 3px 9px;
  border-radius: var(--tmb-radius-full);
  background: var(--tmb-blue-soft);
  /* CD confirmation round 2026-07-13: capsule text is pressed blue #006A96
     on #eaf2ff, not --tmb-blue-dark (the CTA keeps the token). */
  color: #006A96;
  font-size: 11px;
  font-weight: 700;
  white-space: nowrap;
}

.tmb-step-pill.is-asking {
  background: #eaf2ff;
  color: #006A96;
}

.tmb-step-pill.is-asking::before {
  content: "";
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: #0081B6;
}

.tmb-step-pill.is-editing::before {
  content: "\270E";
}

/* Tap-to-edit detour: pending rows keep their standard fade while completed
   receipt rows remain full-opacity under DONEROWS-1. */
.tmb-card-steps.has-detour .tmb-step.is-upcoming {
  opacity: 0.38;
}

/* Screen 0 ghost card: step rows are muted (opacity 0.38) to signal empty draft,
   matching the mock's .step-row default opacity treatment. */
.tmb-card-status.is-empty ~ * .tmb-step,
.tmb-order-card:has(.tmb-card-status.is-empty) .tmb-step {
  opacity: 0.38;
  pointer-events: none;
}

/* ----- sub-steps ----- */
.tmb-substeps {
  margin: 0;
  padding: 0 0 11px 40px;
  list-style: none;
  display: grid;
  gap: 8px;
}

.tmb-substep {
  display: flex;
  align-items: baseline;
  gap: 10px;
  cursor: pointer;
}

.tmb-substep::before {
  content: "";
  flex: 0 0 auto;
  align-self: flex-start;
  width: 6px;
  height: 6px;
  margin-top: 5px;
  border-radius: 50%;
  background: #c8ccd4;
}

.tmb-substep.is-done::before {
  background: var(--tmb-green);
}

.tmb-substep-label {
  flex: 1 1 auto;
  color: var(--tmb-secondary);
  font-size: 14px;
  font-weight: 500;
}

.tmb-substep-value {
  flex: 0 1 auto;
  min-width: 0;
  color: var(--tmb-ink);
  font-size: 12px;
  font-weight: 500;
  text-align: right;
  overflow-wrap: anywhere;
}

.tmb-substep.is-optional .tmb-substep-value {
  color: var(--tmb-placeholder);
  font-weight: 400;
}

.tmb-substep:focus-visible {
  outline: 2px solid var(--tmb-blue);
  outline-offset: 2px;
  border-radius: 6px;
}

/* ----- estimate ----- */
.tmb-card-estimate {
  margin-top: 14px;
  padding: 9px 13px;
  background: #eaf2ff;
  border-radius: var(--tmb-radius-md);
}

/* CD confirmation round 2026-07-13: the resolved (total) estimate keeps the
   same #eaf2ff panel as the range state - the old bare-text override was an
   ORDERCARD-3-era misread. The total block inherits the shared panel above. */

.tmb-card-estimate:empty {
  display: none;
}

.tmb-estimate-kicker {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin: 0 0 6px;
  padding: 0;
  background: transparent;
  color: #006A96;
  font-size: 10px;
  font-weight: 700;
  letter-spacing: 0.12em;
  text-transform: uppercase;
}

.tmb-estimate-kicker::before {
  content: "";
  width: 6px;
  height: 6px;
  border-radius: 999px;
  background: #0081B6;
}

.tmb-estimate-amount {
  margin: 0;
  color: #1d1e22;
  font: 800 30px/1.1 var(--tmb-font-head);
  letter-spacing: -0.01em;
}

.tmb-estimate-amount span {
  margin-left: 8px;
  font-family: var(--tmb-font-body);
  font-size: 13px;
  font-weight: 500;
  color: #585c62;
}

/* Screen 0 pricing box: a bold heading over bulleted rate lines. */
.tmb-estimate-title {
  margin: 0 0 6px;
  color: var(--tmb-ink);
  font-size: 14.5px;
  font-weight: 700;
  letter-spacing: -0.005em;
}

.tmb-estimate-range-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 10px;
}

.tmb-estimate-compact-range {
  display: none;
  flex: 0 0 auto;
  color: var(--tmb-muted);
  font-size: 11.5px;
  font-weight: 500;
  white-space: nowrap;
}

.tmb-estimate-rates {
  margin: 0;
  padding: 0;
  list-style: none;
  display: flex;
  flex-direction: column;
  gap: 4px;
  color: var(--tmb-muted);
  font-size: 12.5px;
  font-weight: 500;
}

.tmb-estimate-rates li {
  position: relative;
  padding-left: 13px;
}

.tmb-estimate-rates li::before {
  content: '';
  position: absolute;
  left: 2px;
  top: 0.58em;
  width: 3px;
  height: 3px;
  border-radius: 50%;
  background: currentColor;
}

.tmb-estimate-note {
  margin: 6px 0 0;
  color: #585c62;
  font-size: 12.5px;
  line-height: 1.5;
}

.tmb-card-cta {
  display: flex;
  align-items: center;
  justify-content: center;
  margin-top: 16px;
  padding: 15px 20px;
  border-radius: 999px;
  background: #0081B6;
  color: #fff;
  text-decoration: none;
  /* CTATYPE-1 REVERTED (Cliff, 2026-07-29): owner overruled the 19px/700
     type step - the CTA returns to its pre-ruling size. */
  font-size: 15px;
  line-height: 1.3;
  font-weight: 600;
  text-align: center;
  box-shadow: none;
  transition: filter 0.14s ease;
}

.tmb-card-cta:hover {
  filter: brightness(0.94);
}

.tmb-card-cta.is-disabled {
  background: #f3f4f8;
  color: #8b8f97;
  pointer-events: none;
  box-shadow: none;
}

@media (min-width: 901px) {
  .tmb-page:has(.tmb-order-card:not([hidden])) {
    --tmb-desktop-bottom-gap: 32px;
  }

  /* Desktop layout (CD scroll-pattern, 2026-05-27):
   * Document-scroll model. The page scrolls as one continuous column - no
   * inner scrollbar on the chat thread. The topbar is sticky at the top of
   * the viewport (handled in the .tmb-topbar block above). The Order Card
   * right rail is sticky too, pinned 24px from the viewport top, so it
   * stays in view as the user reads the conversation. The hero (h1) is
   * treated as content and scrolls away naturally; only the chrome
   * (topbar + Order Card) stays pinned.
   * Replaces the prior app-shell flex-column pattern, which caused mobile
   * clipping and didn't match CD's reference.
   */
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-layout {
    align-items: start; /* required for sticky to work inside the grid */
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-hero h1 {
    font-size: clamp(40px, 5vw, 72px);
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-hero p:last-child {
    margin-top: 12px;
  }

  /* Chat-area fills the viewport vertically when content is short so the
   * composer anchors near the bottom of the visible area (matching CD's
   * mockup State A). When content grows past the viewport, the chat-area
   * expands naturally and the page scrolls. The log flex-fills so the
   * composer always sits at the bottom of the chat-area.
   * Without this, a short conversation leaves a tall empty gap under the
   * composer because the right-rail Order Card is taller than the chat
   * content.
   */
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-chat-area {
    display: flex;
    flex-direction: column;
    /* Fill exactly the space left by the chrome so a short conversation does NOT
       make the page scroll (page only scrolls when the thread overflows).
       Chrome = fixed header + 16px top gap + CD's 32px bottom gap. */
    min-height: calc(100vh - var(--tmb-topbar-h) - 16px - var(--tmb-desktop-bottom-gap));
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-hero {
    flex: 0 0 auto;
  }

  /* Keep the transcript at its natural height. Free space belongs between the
     transcript and the tray, while a long transcript grows the page and uses
     the document scrollbar. */
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-log {
    flex: 0 0 auto;
    min-height: 0;
    max-height: none;
    overflow-y: visible;
    margin-bottom: 16px;
    padding: 4px 2px 0;
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-log:empty {
    margin-bottom: 16px;
    padding: 0;
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-composer {
    flex: 0 0 auto;
    /* The tray and composer are adjacent flow blocks. Their coordinated sticky
       offsets hold the controls at the bottom only after their natural slots
       enter the viewport; the natural-height log above cannot shrink or paint
       underneath them. */
    position: sticky;
    bottom: var(--tmb-desktop-bottom-gap);
    z-index: 5;
  }

  /* The apron covers only the gap below the composer's own flow slot. */
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-composer::after {
    content: '';
    position: absolute;
    left: 0;
    right: 0;
    top: calc(100% + 1px);
    height: calc(var(--tmb-desktop-bottom-gap) - 1px);
    background: var(--tmb-page);
    pointer-events: none;
  }

  /* Match the composer's sticky offset so it rests flush where it pins. */
  .tmb-page:has(.tmb-order-card:not([hidden])) {
    padding-bottom: var(--tmb-desktop-bottom-gap);
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-chips {
    flex: 0 0 auto;
    min-height: 48px;
    margin: auto 0 12px;
    position: sticky;
    bottom: calc(var(--tmb-desktop-bottom-gap) + var(--tmb-composer-h, 64px) + 12px);
    z-index: 4;
  }

  /* Opaque dock backdrop (Cliff 2026-07-13): when chips are up, content
     scrolled behind the sticky tray must disappear under it, not show in
     the pill gaps or the 12px band down to the composer. Page colour so
     the pills still read as sitting on the page. */
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-chips:not(:empty)::before {
    content: '';
    position: absolute;
    inset: 0 0 -12px 0;
    background: var(--tmb-page);
    z-index: -1;
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-chips:empty {
    display: flex;
    visibility: hidden;
  }

  /* CD "Sticky Header (Spec)": the Order Card docks at top = header-height + 16px
   * so it sits just below the fixed header and never slides under it (matches the
   * page's top offset, so the card aligns with the hero at rest). align-self:start
   * keeps it at content height.
   *
   * CD Variation A pinned treatment (blind-QA B10-052 P1, "Order Card (no
   * sub-steps flow)" adaptive demo): when the card would overflow the rail,
   * the WHOLE card must not scroll (that put price + Place order below the
   * fold on 768px-class laptops with no way to reach them short of releasing
   * the sticky). Instead the card becomes a flex column capped at the rail
   * height: header, price strip and Place order stay PINNED on screen at
   * every viewport height, and only the STEP LIST scrolls internally
   * (.tmb-card-steps below). On a normal window the card fits and nothing
   * scrolls - the internal scroller only engages on overflow. */
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-order-card {
    position: sticky;
    top: calc(var(--tmb-topbar-h) + 16px);
    align-self: start;
    max-height: calc(100vh - var(--tmb-topbar-h) - 48px);
    overflow: hidden;
    display: flex;
    flex-direction: column;
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-card-inner {
    display: flex;
    flex-direction: column;
    flex: 1 1 auto;
    min-height: 0;
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-card-header,
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-card-estimate,
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-card-cta {
    flex: 0 0 auto;
  }

  /* B10-052: the step list is the ONLY internal scroller - price + CTA never
     leave the screen. scrollbar-gutter keeps rows from shifting when the
     scrollbar appears. */
  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-card-steps {
    flex: 0 1 auto;
    min-height: 0;
    overflow-y: auto;
    scrollbar-gutter: stable;
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-order-card.is-measuring-size {
    max-height: none;
  }

  .tmb-page:has(.tmb-order-card:not([hidden])) .tmb-order-card.is-measuring-size .tmb-card-steps {
    overflow-y: visible;
  }
}

.tmb-order-card.is-compact .tmb-card-inner {
  padding: 18px 14px;
}

.tmb-order-card.is-compact .tmb-card-header {
  margin-bottom: 14px;
}

.tmb-order-card.is-compact .tmb-card-header h2 {
  font-size: 19px;
}

.tmb-order-card.is-compact .tmb-step-head {
  padding: 8px 0;
}

/* COMPACTPENCIL-1: the compact shorthand above must not remove the lane that
   keeps a done row's right-aligned value clear of its hover pencil. */
.tmb-order-card.is-compact .tmb-step.is-done .tmb-step-head {
  padding-right: 26px;
}

/* CD compact stacked rhythm: name-to-value gap 2px, body gap 2px, and the
   note keeps the compact row's 8px bottom padding before the divider. */
.tmb-order-card.is-compact .tmb-step[data-step="pickup_location"] .tmb-step-head {
  row-gap: 2px;
}

.tmb-order-card.is-compact .tmb-step.has-note .tmb-step-head {
  padding-bottom: 2px;
}

.tmb-order-card.is-compact .tmb-estimate-rates,
.tmb-order-card.is-compact .tmb-estimate-note,
.tmb-order-card.is-compact .tmb-estimate-kicker {
  display: none;
}

.tmb-order-card.is-compact .tmb-estimate-compact-range {
  display: inline;
}

.tmb-order-card.is-compact .tmb-card-estimate[data-mode="total"] {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 10px;
}

.tmb-order-card.is-compact .tmb-estimate-amount {
  display: flex;
  flex: 1 1 auto;
  align-items: baseline;
  justify-content: space-between;
  gap: 10px;
  font-size: 20px;
}

.tmb-order-card.is-compact .tmb-card-cta {
  margin-top: 12px;
}

@media (max-width: 900px) {
  .tmb-page {
    /* The fixed mobile stack is the live composer plus the Order Card peek.
       Keep one shared clearance token for flow padding and chip scrolling so
       every chip state stays reachable as the composer grows. */
    --tmb-mobile-dock-clearance: calc(var(--tmb-composer-h, 82px) + 102px);
    /* Top padding clears the now-fixed mobile header (CD: header-height + 16px).
       MOB-1 REOPENED: bottom clearance belongs to .tmb-log below. Padding this
       height-clamped page did not increase the document scroll range, so inline
       offer chips still flowed behind the fixed Order Card peek. */
    padding-top: calc(var(--tmb-topbar-h) + 16px);
    padding-bottom: 0;
  }

  /* scrollIntoView can't see fixed overlays: give the chip tray a scroll
     margin equal to the fixed stack so the I10 render-time scroll actually
     clears the Order Card bar + composer (MOB-1, 2026-07-10). */
  [data-quick-chips] {
    scroll-margin-bottom: calc(var(--tmb-mobile-dock-clearance, 184px) + 8px);
  }

  /* When the card is hidden on mobile, only the fixed composer needs clearing. */
  .tmb-page:has(.tmb-order-card[hidden]) {
    --tmb-mobile-dock-clearance: calc(var(--tmb-composer-h, 82px) + 28px);
  }

  /* Header logo + gutter are set by the CD-breakpoint tiers (1024/768) above;
     this block only handles the mobile LAYOUT mode (single-column, fixed
     composer + peek card). The header is fixed on all viewports now. */

  .tmb-layout {
    display: block;
    padding: 0 16px;
  }

  .tmb-hero {
    margin: 0 0 20px;
  }

  .tmb-hero h1 {
    font-size: 36px;
    line-height: 1.1;
  }

  .tmb-hero p:last-child {
    font-size: 16px;
  }

  .tmb-log {
    max-height: none;
    overflow-y: visible;
    /* The chip tray is relocated into this flow container on mobile. Reserving
       the fixed-stack height here makes both short and long logs genuinely
       scrollable, allowing the tray's scroll margin to lift its last row above
       the Order Card peek instead of merely painting into page padding. */
    padding-bottom: var(--tmb-mobile-dock-clearance);
  }

  /* B16-016 (JC-ruled): on mobile the chip row is relocated INTO the thread,
     inline under the asking bot bubble (chat.js placeChipsSlot). The log's
     own 14px flex gap spaces it; drop the desktop tray margins so the chips
     hug their question instead of floating mid-void. */
  .tmb-log .tmb-chips {
    margin: 0;
    scroll-margin-bottom: var(--tmb-mobile-dock-clearance);
  }

  /* Mobile Order Card pattern: M5 bottom sheet (CD "Order Card (Mobile)",
   * Cliff 2026-07-05). Two snap points only:
   *  - PEEK: this fixed bar (grip + icon + title/pill + live sub + chevron),
   *    docked directly above the composer. ALWAYS present during an active
   *    order - dragging down from peek is a no-op, never a dismissal.
   *  - EXPANDED: the separate .tmb-sheet element rises from the bottom over
   *    the scrim (max-height 82%). .tmb-card-inner (the desktop card body) is
   *    never shown on mobile anymore - the sheet replaces the old
   *    peek-reveals-inner pattern.
   * The card element itself goes chromeless here; the toggle carries the
   * peek's surface so the grip can overhang its rounded top. */
  .tmb-order-card {
    position: fixed;
    left: 12px;
    right: 12px;
    /* R13-09 / R14-06: sit clear of the fixed composer. The composer height is
       dynamic - the textarea auto-grows to 2-3 rows - so a fixed offset
       re-overlapped the collapsed card toggle once the composer grew. chat.js
       publishes the measured composer height as --tmb-composer-h; this offset
       tracks it (composer's 12px bottom inset + its height + an 8px gap). */
    bottom: calc(var(--tmb-composer-h, 82px) + 20px);
    top: auto;
    z-index: 20;
    background: transparent;
    box-shadow: none;
    overflow: visible;
  }

  /* CARDPANEL-1 (CD ProgressChip.Mobile, finalised 2026-08-21) supersedes the
     M5 full-screen scrim: the card drops from under the header and STOPS
     ABOVE THE DOCK, so the dim covers only the thread between topbar and
     dock - Place order stays visible and live behind the open card, and
     tapping the dimmed thread closes it. touch-action/overscroll-behavior
     stop the page behind from scrolling through; body scroll is locked. */
  .tmb-card-scrim.is-visible {
    display: block;
    position: fixed;
    left: 0;
    right: 0;
    top: var(--tmb-topbar-h);
    /* CARDPANEL-2 (Cliff 2026-08-22): the scrim dims EVERYTHING under the
       bar - thread AND dock - a lit dock under an open panel read as a
       broken modal. Only the bar stays crisp: the chip is the toggle. Tap
       the dim anywhere, including over the dock, to close. Blur stays. */
    bottom: 0;
    z-index: 45;
    /* CD picture verdict 2026-08-21: 28% read as a dead grey slab over a short
       thread; 15% still reads as the dimmed thread. */
    background: rgba(15, 14, 26, 0.15);
    backdrop-filter: blur(2px);
    -webkit-backdrop-filter: blur(2px);
    touch-action: none;
    overscroll-behavior: contain;
    animation: tmb-overlay-fade 150ms ease-out;
  }

  body.tmb-card-open-mobile {
    overflow: hidden;
  }

  /* R13-09: the composer is pinned to the bottom; the peek bar docks directly
     above it (the card's fixed offset tracks the live composer height), so
     the composer never moves when the peek updates or the sheet opens. */
  .tmb-composer {
    position: fixed;
    left: 12px;
    right: 12px;
    bottom: 12px;
    z-index: 40;
  }

  /* PROGCHIP-1 (CD ProgressChip.Mobile, ruled 2026-08-20/21): the M5 peek bar
     is RETIRED - the order's status lives in the header chip and in the card
     it opens, and the dock holds one object (the composer). This wrapper
     survives only as the dock host of the Ready-state Place order button
     (CTASTACK-1): chromeless, and shown only while that button is. */
  .tmb-card-mobile-toggle {
    display: none;
    width: 100%;
    border: 0;
    background: transparent;
    box-shadow: none;
    padding: 0;
    position: relative;
  }
  .tmb-order-card.has-dock-cta .tmb-card-mobile-toggle {
    display: block;
  }
  /* Before Ready the card has nothing to show in the dock; an empty aside
     would still claim the dock's 8px flex gap. The dock holds one object. */
  .tmb-mobile-dock .tmb-order-card:not(.has-dock-cta) {
    display: none;
  }
  .tmb-card-mobile-toggle .tmb-card-mobile-main {
    display: none;
  }

  /* Peek state dressing (blind-QA B11-001/B11-002, 2026-07-06;
     PEEKRING-1, 2026-08-05): the blank-slate bar recedes at reduced opacity.
     Active and open states keep the prototype's neutral border and shadow. */
  .tmb-card-mobile-toggle.is-ghost {
    opacity: 0.7;
  }

  .tmb-pk-grip {
    position: absolute;
    top: 5px;
    left: 50%;
    transform: translateX(-50%);
    width: 34px;
    height: 4px;
    border-radius: 3px;
    background: #d6dae2;
  }
  .tmb-pk-icon {
    flex: 0 0 auto;
    width: 32px;
    height: 32px;
    border-radius: 8px;
    background: var(--tmb-blue-soft);
    color: var(--tmb-blue-pressed);
    display: inline-flex;
    align-items: center;
    justify-content: center;
  }
  .tmb-pk-body {
    flex: 1 1 auto;
    min-width: 0;
    display: flex;
    flex-direction: column;
    align-items: flex-start;
    gap: 1px;
    text-align: left;
  }
  .tmb-pk-title {
    display: inline-flex;
    align-items: center;
    gap: 8px;
    font-size: 13px;
    font-weight: 700;
    letter-spacing: -0.005em;
    color: var(--tmb-ink);
    line-height: 1.2;
  }
  .tmb-pk-pill {
    font-size: 10px;
    font-weight: 700;
    padding: 2px 8px;
    border-radius: 999px;
    background: var(--tmb-blue-soft);
    color: var(--tmb-blue-pressed);
    letter-spacing: 0.04em;
    text-transform: uppercase;
    white-space: nowrap;
  }
  .tmb-pk-pill.is-ready {
    background: rgba(0,168,107,.14);
    color: #047857;
  }
  .tmb-pk-pill.is-editing {
    background: rgba(255,134,66,.16);
    color: #b4550f;
  }
  .tmb-pk-pill.is-empty {
    background: #f3f4f8;
    color: var(--tmb-secondary);
  }
  .tmb-pk-pill.is-out_of_service {
    background: var(--tmb-red-soft);
    color: var(--tmb-red);
  }
  .tmb-pk-sub {
    max-width: 100%;
    font-size: 12px;
    color: var(--tmb-muted);
    margin-top: 1px;
    line-height: 1.3;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
  }
  .tmb-pk-chev {
    flex: 0 0 auto;
    display: inline-flex;
    color: #9aa0a8;
  }

  /* The desktop card body never renders on mobile - the M5 sheet replaces it. */
  .tmb-card-inner {
    display: none;
  }

  .tmb-card-header {
    display: none;
  }

  /* ----- M5 expanded sheet (CD .m-sheet) ----- */
  /* CARDPANEL-1 (CD ProgressChip.Mobile, finalised 2026-08-21): the card is a
     DROP from under the header - opened and closed by the chip (chevron
     flipped), by the dimmed thread, or by Escape. It stops above the dock so
     Place order stays live behind it. 200ms cubic-bezier(.2,.7,.3,1) on the
     transform, 150ms on opacity; no drag handle, no close X. */
  .tmb-sheet {
    display: flex;
    flex-direction: column;
    position: fixed;
    left: 0;
    right: 0;
    top: var(--tmb-topbar-h);
    bottom: auto;
    background: #fff;
    border-radius: 0 0 20px 20px;
    box-shadow: 0 14px 34px rgba(6,6,22,.18);
    padding: 6px 0 14px;
    z-index: 46;
    max-height: calc(100vh - var(--tmb-topbar-h) - var(--tmb-mobile-dock-h, 71px) - 8px);
    max-height: calc(100dvh - var(--tmb-topbar-h) - var(--tmb-mobile-dock-h, 71px) - 8px);
    /* Closed at rest: parked above the header and hidden from AT/tab order.
       The visibility delay keeps it visible for the 200ms slide-up. */
    transform: translateY(-102%);
    opacity: 0;
    transition: transform 200ms cubic-bezier(.2,.7,.3,1), opacity 150ms ease-out, visibility 0s linear 200ms;
    visibility: hidden;
    outline: none;
  }
  .tmb-sheet.is-open {
    transform: translateY(0);
    opacity: 1;
    visibility: visible;
    transition: transform 200ms cubic-bezier(.2,.7,.3,1), opacity 150ms ease-out;
  }
  .tmb-sheet.is-dragging {
    transition: none;
    visibility: visible;
  }

  .tmb-sheet-drag,
  .tmb-sheet-handle {
    display: none;
  }
  /* CARDPANEL-1 head (CD .p-head): "Your order" 15px/700, the status pill
     beside it (10px/700 uppercase, grey; Ready green; Editing amber - the
     pill is where the word belongs, the chip carries no colour), and the
     kebab at the far right with the same single Start over as desktop. */
  .tmb-sheet-head {
    display: flex;
    align-items: center;
    gap: 10px;
    margin: 0;
    padding: 12px 18px;
    flex-shrink: 0;
  }
  .tmb-sheet-actions {
    display: contents;
  }
  .tmb-sheet-menu-slot {
    margin-left: auto;
  }
  /* CD picture verdict 2026-08-21: over the white card the popover's 30px
     shadow landed as a hard bar across the row behind it - the kebab menu
     inside the drop wears the standard small-card shadow instead. */
  .tmb-sheet .tmb-card-menu {
    box-shadow: 0 1px 2px rgba(20,30,60,.05), 0 0 0 1px #DEE2E6;
  }
  .tmb-sheet-eyebrow {
    display: none;
  }
  .tmb-sheet-title {
    margin: 0;
    font-size: 15px;
    font-family: var(--tmb-font-body);
    font-weight: 700;
    letter-spacing: -0.01em;
    color: var(--tmb-ink);
  }
  .tmb-sheet-status {
    display: inline-flex;
    align-items: center;
    font-size: 10px;
    font-weight: 700;
    padding: 2px 8px;
    border-radius: 999px;
    background: #eef0f4;
    color: #6d717a;
    letter-spacing: 0.04em;
    text-transform: uppercase;
    white-space: nowrap;
  }
  .tmb-sheet-status .dot {
    display: none;
    width: 6px;
    height: 6px;
    border-radius: 999px;
    background: var(--tmb-blue);
  }
  .tmb-sheet-status.is-ready {
    background: rgba(0,168,107,.12);
    color: #1f7a52;
  }
  .tmb-sheet-status.is-ready .dot {
    width: 7px;
    height: 7px;
    background: #00a86b;
    box-shadow: 0 0 0 3px rgba(0,168,107,.18);
  }
  .tmb-sheet-status.is-editing {
    background: rgba(255,134,66,.16);
    color: #b4550f;
  }
  .tmb-sheet-status.is-editing .dot {
    background: #b4550f;
  }
  .tmb-sheet-status.is-empty {
    background: #f3f4f8;
    color: var(--tmb-secondary);
  }
  .tmb-sheet-status.is-empty .dot {
    background: #c8ccd4;
  }
  .tmb-sheet-status.is-out_of_service {
    background: var(--tmb-red-soft);
    color: var(--tmb-red);
  }
  .tmb-sheet-status.is-out_of_service .dot {
    background: var(--tmb-red);
  }

  /* Only the step list scrolls; header above and pricing/CTA below stay put.
     overscroll-behavior keeps its scroll from chaining to the locked body. */
  .tmb-sheet-inner {
    flex: 1 1 auto;
    min-height: 0;
    padding: 0 20px;
    overflow-y: auto;
    overscroll-behavior: contain;
  }
  .tmb-sheet-foot {
    flex-shrink: 0;
    padding: 0 20px;
  }

  .tmb-sheet-steps {
    display: flex;
    flex-direction: column;
    margin-bottom: 14px;
  }
  .tmb-sheet-step {
    display: flex;
    align-items: flex-start;
    gap: 14px;
    padding: 14px 0;
    border-bottom: 1px solid #DEE2E6;
    position: relative;
    opacity: 0.38;
    transition: opacity .15s ease;
  }
  .tmb-sheet-step:last-child {
    border-bottom: 0;
  }
  .tmb-sheet-step.is-current {
    opacity: 1;
  }
  .tmb-sheet-badge {
    width: 26px;
    height: 26px;
    border-radius: 999px;
    background: transparent;
    color: #8b8f97;
    box-shadow: none;
    font-size: 12px;
    font-weight: 700;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex-shrink: 0;
    margin-top: 1px;
  }
  .tmb-sheet-step.is-done {
    opacity: 1;
  }
  .tmb-sheet-step.is-done .tmb-sheet-badge {
    width: 24px;
    height: 24px;
    border: 0;
    border-radius: 999px;
    background: #eaf2ff;
    color: #006A96;
    box-shadow: none;
    font-size: 12px;
    font-weight: 700;
  }
  .tmb-sheet-step.is-pending .tmb-sheet-badge {
    width: 24px;
    height: 24px;
    background: #eef0f4;
    color: #8b8f97;
    box-shadow: none;
  }
  .tmb-sheet-step.is-current .tmb-sheet-badge {
    background: #0081B6;
    color: #fff;
    box-shadow: 0 0 0 4px rgba(0,129,182,0.18);
  }
  .tmb-sheet-step-body {
    flex: 1 1 auto;
    min-width: 0;
  }
  .tmb-sheet-step-name {
    font-size: 15px;
    font-weight: 500;
    color: #585c62;
  }
  .tmb-sheet-step-val {
    font-size: 13px;
    font-weight: 500;
    color: #9298a0;
    margin-top: 3px;
    line-height: 1.45;
  }
  .tmb-sheet-step.is-done .tmb-sheet-step-name {
    color: #8b8f97;
    font-weight: 500;
  }
  .tmb-sheet-step.is-done .tmb-sheet-step-val {
    color: #1d1e22;
    font-size: 12px;
    font-weight: 600;
  }
  .tmb-sheet-line {
    display: block;
  }
  .tmb-sheet-line.sub {
    color: var(--tmb-muted);
    margin-top: 2px;
  }
  .tmb-sheet-step.is-done:focus-within {
    opacity: 1;
  }
  .tmb-sheet-step-current {
    font-size: 12.5px;
    font-weight: 600;
    color: #006A96;
    margin-top: 3px;
  }

  /* Persistent pencil on every done row (no hover on mobile): 13px icon in a
     44px tap target; negative margins keep the row compact (CD .m-edit). */
  .tmb-sheet-edit {
    flex-shrink: 0;
    align-self: center;
    width: 44px;
    height: 44px;
    margin: -10px -10px -10px 0;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    background: transparent;
    border: 0;
    cursor: pointer;
    color: #b6bac1;
    /* EDITTAP-1, CD Transitions.EditStep act 1 beat 0 (RULED): the Edit press
       answers at t=0, concurrent with everything else the tap starts. This is
       the mobile route's actual Edit control (sheet -> row -> pencil), so the
       press lives on it rather than on the row. */
    transition: transform 0.15s ease-out, filter 0.15s ease-out;
  }

  .tmb-sheet-edit:active {
    transform: scale(0.98);
    filter: brightness(0.94);
  }

  /* Reduced motion drops the scale and keeps the brightness, exactly as the
     address row press does - the press is still acknowledged, it just does not
     move. Overriding only the :active rule (never re-declaring the base
     selector) keeps .tmb-sheet-edit's single source of geometry: the
     DONEROWS-1 and NOTEPENCIL-1 locks read the LAST block of that selector. */
  @media (prefers-reduced-motion: reduce) {
    .tmb-sheet-edit:active {
      transform: none;
    }
  }

  /* CARDPANEL-1 rows (CD ProgressChip.Mobile cardHTML): 44px rows and the
     WHOLE answered row is the tap target, the circled pencil inside it the
     affordance; name 11px/600 muted, value 14px/600 ink, sub 12px muted, one
     line each. The live row carries "Asking now", an edited row the Editing
     pill (FullFlow's .step-editing, pencil ahead of the word). Badges keep
     the DONEROWS-1 geometry above. */
  .tmb-sheet-steps {
    margin-bottom: 8px;
  }
  .tmb-sheet-step {
    gap: 11px;
    padding: 9px 0;
    min-height: 44px;
    border-bottom: 0;
    border-radius: 10px;
    align-items: flex-start;
    /* The base row fade still stands (ORDERCARD-3): pending rows fade, done
       and current rows lift to full opacity (the rules above; DONEROWS-1 is
       the done-row full-opacity rule, not the fade). */
    opacity: 0.38;
    transition: opacity .15s ease;
  }
  .tmb-sheet-step.is-done {
    opacity: 1;
    cursor: pointer;
    -webkit-tap-highlight-color: transparent;
  }
  .tmb-sheet-step.is-done:active {
    background: #f5f6fa;
  }
  .tmb-sheet-step.is-done:focus-visible {
    outline: none;
    box-shadow: var(--tmb-focus);
  }
  .tmb-sheet-step-name {
    font-size: 11px;
    font-weight: 600;
    color: #585c62;
  }
  .tmb-sheet-step.is-done .tmb-sheet-step-name {
    color: #8b8f97;
    font-weight: 600;
  }
  .tmb-sheet-step-val {
    margin-top: 1px;
    line-height: 1.35;
  }
  .tmb-sheet-step.is-done .tmb-sheet-step-val {
    font-size: 14px;
    font-weight: 600;
    color: #1d1e22;
  }
  /* CARDPANEL-1a (CD round-two verdict 2026-08-21): the value wraps to two
     lines like the conversation does - the card is the thing people check -
     while the muted sub-line stays a single clamped line. */
  .tmb-sheet-step-val .tmb-sheet-line {
    display: -webkit-box;
    -webkit-box-orient: vertical;
    -webkit-line-clamp: 2;
    overflow: hidden;
    white-space: normal;
  }
  .tmb-sheet-step-val .tmb-sheet-line.sub {
    display: block;
    text-overflow: ellipsis;
    white-space: nowrap;
  }
  .tmb-sheet-step.is-done .tmb-sheet-line.sub {
    font-size: 12px;
    font-weight: 500;
    color: var(--tmb-muted);
    margin-top: 2px;
  }
  .tmb-sheet-step-tail {
    flex-shrink: 0;
    display: inline-flex;
    align-items: center;
    align-self: flex-start;
    margin-top: 2px;
  }
  .tmb-sheet-step-current {
    margin: 0;
    font-size: 10px;
    font-weight: 700;
    padding: 3px 8px;
    border-radius: 999px;
    background: var(--tmb-blue-soft);
    color: #006A96;
    letter-spacing: 0.04em;
    text-transform: uppercase;
    white-space: nowrap;
  }
  .tmb-sheet-step-current.is-editing {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    padding: 4px 10px;
    font-size: 11.5px;
    font-weight: 600;
    letter-spacing: 0.03em;
    text-transform: none;
  }
  .tmb-sheet-step-tail .tmb-sheet-edit {
    align-self: center;
    margin: -9px -9px -9px 0;
    color: #006A96;
  }
  .tmb-sheet-edit-circle {
    width: 26px;
    height: 26px;
    border-radius: 999px;
    background: var(--tmb-blue-soft);
    color: #006A96;
    display: inline-flex;
    align-items: center;
    justify-content: center;
  }
  /* CARDPANEL-1a: rows locked behind an open edit - greyed pencil, no pointer. */
  .tmb-sheet-step.is-locked {
    cursor: default;
  }
  .tmb-sheet-step.is-locked:active {
    background: transparent;
  }
  .tmb-sheet-step-tail .tmb-sheet-edit--locked {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 44px;
    height: 44px;
    margin: -9px -9px -9px 0;
    pointer-events: none;
  }
  .tmb-sheet-step.is-locked .tmb-sheet-edit-circle {
    opacity: 0.4;
  }
  .tmb-sheet-pricing {
    background: #eaf2ff;
    border-radius: 12px;
    padding: 9px 13px;
    margin-bottom: 14px;
  }
  .tmb-sheet-pr-kicker {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    margin: 0 0 6px;
    color: #006A96;
    font-size: 10px;
    font-weight: 700;
    letter-spacing: 0.12em;
    text-transform: uppercase;
  }
  .tmb-sheet-pr-kicker::before {
    content: '';
    width: 6px;
    height: 6px;
    border-radius: 999px;
    background: #0081B6;
  }
  .tmb-sheet-pr-amount {
    margin: 0;
    color: #1d1e22;
    font: 800 30px/1.1 var(--tmb-font-head);
  }
  .tmb-sheet-pr-amount span {
    margin-left: 8px;
    color: #585c62;
    font: 500 13px/1.4 var(--tmb-font-body);
  }
  .tmb-sheet-pr-title {
    margin: 0 0 6px;
    font-size: 11px;
    font-weight: 700;
    color: var(--tmb-blue-pressed);
    letter-spacing: 0.06em;
    text-transform: uppercase;
  }
  .tmb-sheet-pr-range {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 10px;
  }
  .tmb-sheet-pr-range .tmb-sheet-pr-title {
    margin-bottom: 0;
  }
  .tmb-sheet-pr-range > span {
    color: var(--tmb-muted);
    font-size: 11.5px;
    white-space: nowrap;
  }
  .tmb-sheet.is-compact .tmb-sheet-pr-rates {
    display: none;
  }
  .tmb-sheet.is-compact .tmb-sheet-pricing[data-mode="total"] {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 10px;
  }
  .tmb-sheet.is-compact .tmb-sheet-pr-kicker,
  .tmb-sheet.is-compact .tmb-sheet-pr-fine {
    display: none;
  }
  .tmb-sheet.is-compact .tmb-sheet-pr-amount {
    display: flex;
    flex: 1 1 auto;
    align-items: baseline;
    justify-content: space-between;
    gap: 10px;
    font-size: 20px;
  }
  .tmb-sheet.is-measuring-size {
    max-height: none;
  }
  .tmb-sheet.is-measuring-size .tmb-sheet-inner {
    flex: 0 0 auto;
    overflow-y: visible;
  }
  .tmb-sheet.is-compact .tmb-sheet-head,
  .tmb-sheet.is-compact .tmb-sheet-inner,
  .tmb-sheet.is-compact .tmb-sheet-foot {
    padding-left: 14px;
    padding-right: 14px;
  }
  .tmb-sheet.is-compact .tmb-sheet-title {
    font-size: 15px;
  }
  .tmb-sheet.is-compact .tmb-sheet-step {
    padding: 8px 0;
  }
  .tmb-sheet-pr-row {
    display: flex;
    justify-content: space-between;
    align-items: baseline;
    font-size: 13px;
    color: var(--tmb-ink);
    gap: 10px;
  }
  .tmb-sheet-pr-row .amt {
    font-weight: 700;
  }
  .tmb-sheet-pr-rate {
    margin: 0 0 2px;
    font-size: 13px;
    color: var(--tmb-ink);
  }
  .tmb-sheet-pr-fine {
    margin: 6px 0 0;
    font-size: 12.5px;
    color: #585c62;
    line-height: 1.5;
  }

  .tmb-sheet-cta {
    width: 100%;
    border-radius: 999px;
    background: #0081B6;
    color: #fff;
    border: 0;
    padding: 15px 20px;
    font-weight: 600;
    font-size: 15px;
    box-shadow: none;
    transition: filter 0.14s ease;
  }
  .tmb-sheet-cta:not(:disabled):hover {
    filter: brightness(0.94);
  }
  .tmb-sheet-cta:disabled {
    background: #d8dce5;
    color: #fff;
    box-shadow: none;
    cursor: not-allowed;
  }

  /* When the conversation is short (chat.js adds .tmb-log-is-short to
     .tmb-page), the chat column fills the viewport so the bottom-fixed Order
     Card / composer bar sit at the true bottom. Per Claude Design's mobile
     screens, the quick-reply chips stay directly beneath the most recent
     message (NOT pushed to the bottom) - the log keeps its content height and
     the spare space falls below the chips. */
  .tmb-page.tmb-log-is-short {
    height: auto;
    min-height: 100dvh;
    display: flex;
    flex-direction: column;
    padding-bottom: 0;
  }

  .tmb-page.tmb-log-is-short .tmb-layout,
  .tmb-page.tmb-log-is-short .tmb-chat-area {
    flex: 1 1 auto;
    min-height: 0;
    display: flex;
    flex-direction: column;
  }

  .tmb-page.tmb-log-is-short .tmb-log {
    flex: 0 1 auto;
    min-height: 0;
    max-height: none;
  }
}

/* MOBILE-3 (2026-07-14): CD FullFlow mobile contract. All overrides are
   capability-scoped so desktop and compact fine-pointer rendering stay on
   their existing source rules. */
/* MOBILE3FIX contract block (RO-065 2026-07-20: width-only, no coarse gate) */
@media (max-width: 900px) {
  /* MOBILE3FIX (2026-07-14): CD round-1 M3a overrules fix 7. The opaque
     page-colour seal prevents conversation content painting through.
     BARWHITE-1 (Cliff 2026-08-23) amends the flat half: at rest the bar is
     the seamless page colour, but once content scrolls under it it lifts
     to the white bar + seal shadow - one recipe on every header. */
  .tmb-topbar {
    background: var(--tmb-page-bg);
    box-shadow: none;
  }
  .tmb-topbar.is-scrolled {
    background: #fff;
    box-shadow: 0 6px 16px rgba(6, 6, 22, 0.05);
  }

  /* Fix 8: the populated first-name label remains visible in the account pill. */
  .tmb-account-label {
    display: inline;
    max-width: 92px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
  }

  .tmb-account-chip {
    gap: 7px;
    padding: 0 10px 0 5px;
  }

  /* Fixes 1-2: one 52px composer row and the 36px FullFlow send tile. */
  .tmb-mobile-dock .tmb-composer {
    --tmb-composer-inline-pad: 18px;
    grid-template-columns: minmax(0, 1fr) 36px;
    gap: 8px;
    width: 100%;
    height: 52px;
    min-height: 52px;
    max-height: 52px;
    padding: 8px 8px 8px 18px;
    border-radius: 14px;
  }

  .tmb-mobile-dock .tmb-input {
    height: 36px;
    min-height: 36px;
    max-height: 36px;
    padding: 7px 8px 7px 0;
    overflow-x: auto;
    overflow-y: hidden;
    white-space: nowrap;
    font-weight: 500;
    line-height: 20px;
  }

  .tmb-mobile-dock .tmb-input:placeholder-shown {
    height: 36px;
    min-height: 36px;
    max-height: 36px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
  }

  .tmb-mobile-dock .tmb-input::placeholder {
    color: #6f747d;
    font-weight: 500;
  }

  .tmb-mobile-dock .tmb-send,
  .tmb-mobile-dock .tmb-send.is-ready,
  .tmb-mobile-dock .tmb-send.is-ready:hover {
    width: 36px;
    height: 36px;
    border-radius: 10px;
    background: #eaf2ff;
    color: #6f747d;
  }

  .tmb-mobile-dock .tmb-composer.tmb-composer--dimmed .tmb-send {
    background: #eaf2ff;
    color: #71727A;
  }

  /* Keep the implementation-superior padlock and grey locked-composer state. */
  .tmb-mobile-dock .tmb-composer:has(.tmb-input.is-locked) .tmb-send {
    background: #eef0f4;
    color: #b3b8c0;
  }

  /* Fix 3: phone chips use the FullFlow type scale and wrapping row. */
  .tmb-chips {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
  }

  .tmb-chips button {
    min-height: 44px;
    padding: 10px 16px;
    border-radius: 999px;
    background: #fff;
    color: #0081B6;
    box-shadow: inset 0 0 0 1.5px #0081B6;
  }

  .tmb-chips button.is-primary {
    background: #0081B6;
    color: #fff;
    box-shadow: none;
  }

  /* Fixes 5-6 and 26: collapsed peek anatomy and READY inline action.
     PROGCHIP-1 (2026-08-21): the peek is retired and the wrapper only hosts
     the stacked Place order bar, so it carries no padding - CD measured the
     old 10px/14px as 12px of unexplained dock height at Ready. */
  .tmb-card-mobile-toggle {
    gap: 10px;
    padding: 0;
  }

  .tmb-card-mobile-toggle.is-ready {
    gap: 12px;
  }

  .tmb-card-mobile-main {
    flex: 1 1 auto;
    min-width: 0;
    display: flex;
    align-items: center;
    gap: 10px;
    padding: 0;
    border: 0;
    background: transparent;
    color: inherit;
    text-align: left;
    touch-action: none;
  }

  .tmb-pk-icon {
    width: 32px;
    height: 32px;
    border-radius: 8px;
  }

  .tmb-pk-title {
    font-size: 13px;
    font-weight: 700;
  }

  .tmb-pk-pill {
    padding: 2px 8px;
    font-size: 10px;
    font-weight: 700;
  }

  .tmb-pk-pill.is-editing {
    background: rgba(255,134,66,.16);
    color: #b4550f;
  }

  .tmb-pk-sub {
    font-size: 12px;
  }

  /* CTASTACK-1 (Cliff 2026-08-21, CD ProgressChip.Mobile .place): at Ready the
     Place order button is a full-width 48px bar stacked ABOVE the ghost
     composer - the typing surface never leaves the screen ("swapped in" was
     rendered and rejected). Replaces the 40px READY peek pill of MOBILE-3. */
  .tmb-pk-cta {
    display: block;
    width: 100%;
    height: 48px;
    padding: 0 16px;
    border: 0;
    border-radius: 999px;
    background: #0081B6;
    color: #fff;
    box-shadow: none;
    font-family: var(--tmb-font-body);
    font-size: 16px;
    font-weight: 700;
    white-space: nowrap;
  }

  .tmb-pk-cta[hidden] {
    display: none;
  }

  .tmb-card-mobile-toggle.is-ready .tmb-pk-chev {
    display: none;
  }

  /* Fixes 14-16: expanded sheet scale, menu, pricing, and CTA.
     CARDPANEL-1 (2026-08-21): the sheet's 78% cap, its handle and its 20px
     title belonged to the bottom sheet; the drop sizes itself to the room
     above the dock (see the .tmb-sheet rule), has no handle, and reads
     "Your order" at 15px/700. The menu/pricing/CTA fixes below still apply. */
  .tmb-sheet-title,
  .tmb-sheet.is-compact .tmb-sheet-title {
    font-size: 15px;
  }

  .tmb-sheet-actions {
    display: contents;
  }

  .tmb-sheet-menu-slot {
    flex: 0 0 auto;
  }

  .tmb-sheet-menu-slot:empty {
    display: none;
  }

  .tmb-sheet-menu-slot .tmb-card-menu-btn {
    width: 40px;
    height: 40px;
    color: #6f747d;
  }

  .tmb-sheet-step-name {
    font-size: 17px;
  }

  .tmb-sheet-pr-kicker::before {
    display: none;
  }

  .tmb-sheet .tmb-sheet-pricing[data-mode="total"],
  .tmb-sheet.is-compact .tmb-sheet-pricing[data-mode="total"] {
    display: grid;
    grid-template-columns: minmax(0, 1fr) auto;
    align-items: center;
    gap: 4px 12px;
  }

  .tmb-sheet.is-compact .tmb-sheet-pr-kicker {
    display: block;
  }

  .tmb-sheet-pr-kicker {
    margin: 0;
  }

  .tmb-sheet-pr-amount,
  .tmb-sheet.is-compact .tmb-sheet-pr-amount {
    display: block;
    margin: 0;
    color: #1d1e22;
    font: 700 20px/1.2 var(--tmb-font-head);
    text-align: right;
  }

  .tmb-sheet-pr-amount span {
    display: block;
    margin: 1px 0 0;
    font-size: 11px;
  }

  .tmb-sheet-pr-fine {
    grid-column: 1 / -1;
  }

  .tmb-sheet-cta {
    height: 44px;
    padding: 0 20px;
  }

  /* Fixes 17-20: compact address field and full-width suggestion rows. */
  .ifc-head {
    color: #1d1e22;
  }

  .ifc-input {
    height: 46px;
    border-radius: 12px;
  }

  .ifc-clear {
    top: 16px;
  }

  .addr-pred {
    margin: 8px -18px -16px;
    border-radius: 0 0 16px 16px;
    box-shadow: none;
    border-top: 1px solid #DEE2E6;
  }

  .addr-pred-item {
    border-bottom: 1px solid #DEE2E6;
  }

  .inline-form-card .pc-foot {
    padding-top: 22px;
  }

  /* Mobile auth scale, clear scrim, and OTP halo. */
  .tmb-auth-overlay {
    backdrop-filter: none;
    -webkit-backdrop-filter: none;
  }

  .tmb-auth-card {
    padding: 20px;
  }

  .tmb-auth-provider,
  .tmb-auth-submit {
    height: 48px;
  }

  .tmb-auth-submit {
    margin-top: 20px;
  }

  .tmb-otp-cell:focus {
    box-shadow: inset 0 0 0 2px var(--tmb-blue), 0 0 0 4px rgba(0,129,182,.15);
  }

  /* Fix 13: safety acknowledgement becomes a full-width bottom sheet. */
  .tmb-safety-overlay {
    align-items: flex-end;
    padding: 0;
  }

  .tmb-safety-card {
    width: 100%;
    max-width: none;
    max-height: 92dvh;
    overflow-y: auto;
    border-radius: 28px 28px 0 0;
    padding: 12px 20px calc(24px + env(safe-area-inset-bottom, 0px));
    box-shadow: 0 -10px 40px -10px rgba(20,30,60,.25);
  }

  .tmb-safety-card::before {
    content: '';
    display: block;
    width: 40px;
    height: 4px;
    margin: 0 auto 16px;
    border-radius: 3px;
    background: #d6dae2;
  }

  .tmb-safety-close {
    display: none;
  }

  .tmb-safety-title {
    padding-right: 0;
  }
}

/* MOBILE-2, CD touch contract (2026-07-14). This is deliberately narrower
   than the mobile layout breakpoint: compact fine-pointer windows keep the
   existing document-scroll model, and every desktop rule above stays inert.
   On a touch layout the shell owns the viewport, .tmb-chat-area is the one
   conversation scroller, and the complete peek + composer stack is sealed by
   one dock surface. */
/* MOBILE-2 touch shell contract block (RO-065 2026-07-20: width-only, no coarse gate) */
@media (max-width: 900px) {
  html,
  body {
    /* PAGEBG-1 (Cliff 2026-08-23, "desktop wins", CD on side): one page
       colour on every shell - the value below is the desktop page token,
       superseding the MOBILE-2 contract's lighter mobile token; CD moves
       its mobile artboard token on its side. (TOPFADE-1's one-source rule:
       no hex names in prose here - the token is the single source.) */
    --tmb-page-bg: #f8f9fe;
    width: 100%;
    height: 100%;
    overflow: hidden;
    overscroll-behavior: none;
  }

  body {
    position: fixed;
    inset: 0;
    width: 100%;
    height: 100%;
    min-height: 0;
    overflow: hidden;
    background: var(--tmb-page-bg);
  }

  .tmb-page,
  .tmb-page.tmb-log-is-short {
    position: relative;
    width: 100%;
    height: min(100dvh, var(--tmb-touch-viewport-h, 100dvh));
    min-height: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    overflow: hidden;
    overscroll-behavior: none;
    background: var(--tmb-page-bg);
  }

  .tmb-topbar {
    position: relative;
    top: auto;
    left: auto;
    right: auto;
    /* TOPBARSEAL-1 / CARDPANEL-2: above the dock (40), the scrim (45) and
       the card panel (46) so the panel slides down from behind the bar and
       the seal shadow paints over the dimmed thread. */
    z-index: 48;
    flex: 0 0 var(--tmb-topbar-h);
    background: var(--tmb-page-bg);
    box-shadow: 0 6px 16px rgba(6, 6, 22, 0);
    transition: background 150ms ease-out, box-shadow 150ms ease-out;
  }

  /* TOPBARSEAL-1 (CD Transitions.WashProsAfterSignIn, 2026-08-18; Cliff
     2026-08-22 "the blur/fade beneath header is replaced with sharper
     cut-off / shadow"): the scroll cue is the BAR - an opaque page-token bar
     plus a seal shadow, the mirror of the dock's 0 -6px 16px (DOCKGROUP-1).
     Content clips hard at the bar's bottom edge; it is never tinted,
     blurred or faded below it. The TOPFADE-1 gradient is retired; the
     has-topfade class (chatArea.scrollTop > 0, TOPFADE-1's gate) now drives
     the seal. The bar sits above the dock, the scrim and the card panel
     (CARDPANEL-2: the panel slides down from BEHIND the bar). */
  .tmb-topbar::after {
    content: none;
  }

  /* BARWHITE-1 (Cliff 2026-08-23: "header colour should be white... so
     there's some contrast between header and scrolling thread. Pretty sure
     this is what CD says"): the sealed touch bar takes the desktop sticky
     header's lift - white once content scrolls under it, seamless page
     colour at rest (RO-037 no-banner unchanged). One recipe on every
     header (CD alignment note, 2026-08-22). */
  .tmb-topbar.has-topfade {
    background: #fff;
    box-shadow: 0 6px 16px rgba(6, 6, 22, 0.05);
  }

  .tmb-layout,
  .tmb-page.tmb-log-is-short .tmb-layout {
    flex: 1 1 auto;
    min-height: 0;
    width: 100%;
    margin: 0;
    padding: 0 12px;
    display: block;
    overflow: hidden;
  }

  /* The hero, eyebrow, bubbles, inline chips, and structured editors all live
     in this one scroll region. Dock-height padding leaves the final Confirm
     control fully reachable above the sealed overlay.

     TAILVOID-1: `none`, not `contain`. Both stop scroll chaining to the locked
     body, but `contain` deliberately KEEPS the local bounce - and at the end of
     the conversation that bounce drags the last message up off the dock and
     exposes the page behind it. Measured with a real touch swipe: 151px of
     overscroll and 151px of visible emptiness on the simulator, 130px on
     Cliff's physical iPhone 16 in Chrome. At rest the layout is correct, which
     is why this reads as a flash of white rather than a permanent gap and why
     it survived every headless rig - Chromium has no rubber-band at all.
     RED/GREEN: qa/ios-sim/overscroll_probe.py. */
  .tmb-chat-area,
  .tmb-page.tmb-log-is-short .tmb-chat-area {
    height: 100%;
    min-height: 0;
    padding: 16px 0 var(--tmb-mobile-dock-h, 220px);
    display: block;
    overflow-y: auto;
    overflow-anchor: none;
    overscroll-behavior: none;
    -webkit-overflow-scrolling: touch;
  }

  .tmb-chat-area {
    scrollbar-width: none;
  }

  .tmb-chat-area::-webkit-scrollbar {
    display: none;
  }

  .tmb-log,
  .tmb-page.tmb-log-is-short .tmb-log {
    flex: none;
    min-height: 0;
    max-height: none;
    overflow: visible;
    padding-bottom: 0;
  }

  /* One dock, one seal. The children keep their normal card/composer styling;
     the opaque page-coloured group owns safe-area coverage and occlusion. */
  .tmb-mobile-dock {
    position: absolute;
    left: 0;
    right: 0;
    bottom: 0;
    z-index: 40;
    display: flex;
    flex-direction: column;
    gap: 8px;
    background: var(--tmb-page-bg);
    padding: 8px 12px calc(10px + env(safe-area-inset-bottom));
    box-shadow: 0 -6px 16px rgba(6,6,22,.05);
    transition: transform 180ms cubic-bezier(.33,1,.68,1), opacity 140ms ease-out;
    will-change: transform;
  }

  /* KEYDOCK-1, CD KEYBOARD-1 (2026-07-15): structured field focus owns the
     visible strip. The peek and locked composer slide out as one sealed dock;
     the shell itself is never translated. */
  .tmb-mobile-dock.is-keyboard-hidden {
    transform: translateY(calc(100% + env(safe-area-inset-bottom)));
    opacity: 0;
    pointer-events: none;
  }

  /* KEYRIDE-3 drawn ride (stage opt-in ?keyride=ride; JC-059): while the
     picture rides, the shell lets the frozen keyboard-down band paint past
     its keyboard-up box, the real dock waits unseen at its keyboard-up rect
     (no fade - the stand-in is pixel-identical on top of it), and the
     stand-in carries a page-coloured apron below itself so a curve
     mismatch at the keyboard's edge never shows the thread. */
  .tmb-page.tmb-ride-open {
    overflow: visible;
  }

  .tmb-page.tmb-ride-active .tmb-mobile-dock {
    opacity: 0;
    transition: none;
  }

  .tmb-mobile-dock-ride {
    pointer-events: none;
    will-change: transform;
  }

  .tmb-mobile-dock-ride::after {
    content: '';
    position: absolute;
    top: 100%;
    left: 0;
    right: 0;
    height: 480px;
    background: var(--tmb-page-bg);
  }

  .tmb-page.tmb-keyboard-editing {
    --tmb-mobile-dock-clearance: 0px;
  }

  /* SPECMATCH-1 Stage 5: the keyboard-editing smooth scroll rule is gone -
     it was a hidden second writer animating raw scrollTop assignments under
     the explicit owner motion (the CHANGE-1 root-cause class). */
  .tmb-page.tmb-keyboard-editing .tmb-chat-area {
    padding-bottom: 0;
  }

  /* ACT3 caveat 1 (design-specs/cd-address-pick-act3.md): the editor plus its
     reserved suggestion room must fit the budget above the keyboard, and when
     it cannot the list SHEDS ROWS (3 to 2 to 1) - it never scrolls. chat.js
     (shedAddressSuggestionRows) drops rows from the bottom against measured
     geometry, so the old 196px scroller is gone: a scrolling suggestion list
     was the clipped third row on SE3. */
  .tmb-page.tmb-touch-shell .addr-pred {
    max-height: none;
    overflow: hidden;
    overscroll-behavior: contain;
  }

  .tmb-mobile-dock .tmb-order-card {
    position: static;
    inset: auto;
    width: 100%;
    z-index: auto;
  }

  .tmb-mobile-dock .tmb-composer {
    position: relative;
    inset: auto;
    width: 100%;
    z-index: auto;
  }

}

@media (max-width: 900px) and (prefers-reduced-motion: reduce) {
  .tmb-mobile-dock {
    transition: none;
  }
}

/* Phase 2: returning-user one-tap confirm overlay */
.tmb-confirm-overlay {
  position: fixed;
  inset: 0;
  background: rgba(15, 23, 42, 0.45);
  backdrop-filter: blur(2px);
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 100;
  padding: 16px;
  animation: tmb-overlay-fade 200ms ease-out;
}

.tmb-confirm-overlay[hidden] {
  display: none;
}

@keyframes tmb-overlay-fade {
  from { opacity: 0; }
  to { opacity: 1; }
}

.tmb-confirm-card {
  background: var(--tmb-surface);
  border-radius: var(--tmb-radius-lg);
  box-shadow: var(--tmb-shadow-lg);
  padding: 28px;
  width: min(440px, 100%);
  text-align: left;
}

.tmb-confirm-eyebrow {
  margin: 0 0 8px;
  color: var(--tmb-blue);
  text-transform: uppercase;
  font-size: 11px;
  letter-spacing: 0.12em;
  font-weight: 700;
}

.tmb-confirm-card h2 {
  margin: 0 0 8px;
  font: 600 22px/1.25 var(--tmb-font-head);
  letter-spacing: -0.005em;
  color: var(--tmb-ink);
}

.tmb-confirm-summary {
  margin: 0 0 18px;
  color: var(--tmb-muted);
  font-size: 14px;
  line-height: 1.5;
}

.tmb-confirm-summary:empty {
  display: none;
}

.tmb-confirm-progress {
  height: 4px;
  background: var(--tmb-divider);
  border-radius: 9999px;
  overflow: hidden;
  margin-bottom: 12px;
}

.tmb-confirm-progress-bar {
  height: 100%;
  background: var(--tmb-blue);
  width: 0%;
  transition: width 100ms linear;
}

.tmb-confirm-counter {
  margin: 0 0 18px;
  color: var(--tmb-secondary);
  font-size: 13px;
}

.tmb-confirm-counter span {
  font-weight: 700;
  color: var(--tmb-ink);
}

.tmb-confirm-actions {
  display: flex;
  justify-content: flex-end;
}

.tmb-confirm-cancel {
  background: transparent;
  border: 1px solid var(--tmb-border);
  border-radius: var(--tmb-radius-full);
  padding: 8px 16px;
  font-size: 13px;
  font-weight: 600;
  color: var(--tmb-ink);
}

.tmb-confirm-cancel:hover {
  background: var(--tmb-surface-light);
  border-color: var(--tmb-blue);
  color: var(--tmb-blue-dark);
}

/* Inline auth modal (OTP / password). Shares overlay style with confirm; the
   card adds form-specific layout. */
.tmb-auth-overlay {
  position: fixed;
  inset: 0;
  background: rgba(15, 23, 42, 0.45);
  backdrop-filter: blur(2px);
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 100;
  padding: 16px;
  animation: tmb-overlay-fade 200ms ease-out;
}
.tmb-auth-overlay[hidden] { display: none; }

.tmb-auth-card {
  background: var(--tmb-surface);
  border-radius: var(--tmb-radius-lg);
  box-shadow: var(--tmb-shadow-lg);
  padding: 28px;
  width: min(440px, 100%);
}

.tmb-auth-eyebrow {
  margin: 0 0 8px;
  color: var(--tmb-blue);
  text-transform: uppercase;
  font-size: 11px;
  letter-spacing: 0.12em;
  font-weight: 700;
}

.tmb-auth-title {
  margin: 0 0 8px;
  font: 600 22px/1.25 var(--tmb-font-head);
  letter-spacing: -0.005em;
  color: var(--tmb-ink);
}

.tmb-auth-subtitle {
  margin: 0 0 20px;
  color: var(--tmb-muted);
  font-size: 14px;
  line-height: 1.5;
}
.tmb-auth-subtitle:empty { display: none; }

.tmb-auth-form { margin: 0; }

.tmb-auth-input-area { margin-bottom: 16px; }

.tmb-autofill-username {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  border: 0;
  overflow: hidden;
  clip: rect(0 0 0 0);
  clip-path: inset(50%);
  white-space: nowrap;
}

.tmb-reset-group {
  display: grid;
  gap: 8px;
}
.tmb-reset-group + .tmb-reset-group { margin-top: 14px; }

.tmb-field-label {
  /* CD superseded the uppercase/tracked label-above-the-input. Until the reset
     fields migrate to the DS notched floating label, this is at least sentence
     case, weight 500, no tracking (not uppercase/600/tracked). */
  font-size: 12px;
  font-weight: 500;
  color: var(--tmb-muted);
  text-transform: none;
}

.tmb-otp-cells {
  display: flex;
  gap: 8px;
  justify-content: flex-start;
}
.tmb-auth-input-area > .tmb-otp-cells { justify-content: center; }

.tmb-otp-cell {
  flex: 0 0 52px;
  width: 52px;
  height: 56px;
  text-align: center;
  font-size: 22px;
  font-weight: 600;
  border: 1px solid var(--tmb-border);
  border-radius: var(--tmb-radius-md);
  background: var(--tmb-surface);
  color: var(--tmb-ink);
  font-family: var(--tmb-font-head);
  -moz-appearance: textfield;
}
.tmb-otp-cell::-webkit-outer-spin-button,
.tmb-otp-cell::-webkit-inner-spin-button {
  -webkit-appearance: none;
  margin: 0;
}
.tmb-otp-cell:focus {
  outline: none;
  /* CD invariant 2: 2px inset primary ring, no outer glow. */
  border-color: var(--tmb-blue-dark);
  box-shadow: inset 0 0 0 2px var(--tmb-blue-dark);
}

.tmb-password-input {
  width: 100%;
  /* CD DS Text Field: 56px tall, 100px pill radius. (Notched floating label is
     applied when the reset-screen markup migrates to the DS field.) */
  height: 56px;
  padding: 0 18px;
  font-size: 16px;
  border: 1px solid var(--tmb-border);
  border-radius: 100px;
  background: var(--tmb-surface);
  color: var(--tmb-ink);
  font-family: var(--tmb-font-body);
  box-sizing: border-box;
}
.tmb-password-input:focus {
  outline: none;
  /* CD invariant 2: 2px inset primary ring, no outer glow. */
  border-color: var(--tmb-blue-dark);
  box-shadow: inset 0 0 0 2px var(--tmb-blue-dark);
}

.tmb-auth-consents {
  display: grid;
  gap: 10px;
  margin-top: 12px;
}

.tmb-auth-check {
  display: grid;
  grid-template-columns: 18px 1fr;
  gap: 10px;
  align-items: start;
  padding: 10px;
  border: 1px solid var(--tmb-border);
  border-radius: var(--tmb-radius-sm);
  background: var(--tmb-surface-light);
  color: var(--tmb-muted);
  font-size: 12px;
  line-height: 1.45;
}

.tmb-auth-check input {
  width: 16px;
  height: 16px;
  margin: 1px 0 0;
  accent-color: var(--tmb-blue);
}

.tmb-auth-submit {
  width: 100%;
  height: 48px;
  border: none;
  border-radius: var(--tmb-radius-md);
  background: var(--tmb-cta-bg);
  color: white;
  font-size: 15px;
  font-weight: 600;
  font-family: var(--tmb-font-body);
  cursor: pointer;
  transition: background 120ms ease;
}
.tmb-auth-submit:hover:not(:disabled) { background: var(--tmb-cta-bg-hover); }
.tmb-auth-submit:disabled { opacity: 0.6; cursor: not-allowed; }

.tmb-auth-message {
  margin: 12px 0 0;
  font-size: 13px;
  /* Wave 7 F-06: CD's error token is crimson #C41E3A (Text Field spec) - the
     old amber shade was off-system. */
  color: #C41E3A;
  min-height: 1em;
}
.tmb-auth-message:empty { display: none; }

.tmb-auth-message--info {
  color: var(--tmb-secondary);
  background: var(--tmb-surface-light);
  border-radius: var(--tmb-radius-sm);
  padding: 8px 10px;
  font-size: 12px;
}

.tmb-auth-secondary-link {
  display: inline-block;
  margin-top: 12px;
  font-size: 13px;
  color: var(--tmb-blue-dark);
  text-decoration: underline;
  cursor: pointer;
}
.tmb-auth-secondary-link:hover { color: var(--tmb-ink); }

.tmb-auth-footer {
  margin-top: 16px;
  text-align: center;
}
.tmb-auth-fallback {
  font-size: 13px;
  color: var(--tmb-muted);
  text-decoration: underline;
}

.tmb-auth-actions {
  margin-top: 12px;
  display: flex;
  justify-content: flex-end;
}

.tmb-auth-cancel {
  background: transparent;
  border: 1px solid var(--tmb-border);
  border-radius: var(--tmb-radius-full);
  padding: 6px 14px;
  font-size: 12px;
  font-weight: 600;
  color: var(--tmb-ink);
  cursor: pointer;
}
.tmb-auth-cancel:hover {
  background: var(--tmb-surface-light);
  border-color: var(--tmb-blue);
  color: var(--tmb-blue-dark);
}

@media (max-width: 520px) {
  /* Header gutter stays at the CD mobile spec (20px, set in the <=767px tier);
     no tighter override here so the header gutter is consistent across mobile. */

  .tmb-layout {
    padding: 0 12px;
  }

  .tmb-domain {
    display: none;
  }

  .tmb-account-label {
    display: none;
  }

  .tmb-account-chip {
    padding: 0 8px 0 4px;
    gap: 4px;
  }

  .tmb-account-menu {
    min-width: 220px;
  }

  .tmb-hero h1 {
    font-size: 32px;
  }

  .tmb-composer {
    --tmb-composer-inline-pad: 10px;
    grid-template-columns: minmax(0, 1fr) 48px;
    padding: 10px;
  }

  /* MOBILE3FIX (2026-07-14): CD round-1 requires the same one-line hint on
     compact fine-pointer layouts as every other composer. */
  .tmb-input:placeholder-shown {
    min-height: 36px;
    max-height: 36px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
  }

  .tmb-send {
    width: 48px;
    height: 48px;
  }

}

/* ============================================================
   Redesign 2026-05-20 - claude.ai/design "Rapid Order (Official)".
   Sign-in modal (0a/0b/0c) + WashPros safety modal (9a).
   Design-aligned; appended so the cascade wins over base rules.
   ============================================================ */

.tmb-auth-overlay {
  background: rgba(20, 30, 60, 0.42);
}

/* Sign-in modal shell (design .signin-modal) */
.tmb-auth-card {
  width: 440px;
  max-width: 100%;
  border-radius: 18px;
  padding: 36px 36px 28px;
  box-shadow: 0 30px 80px -20px rgba(20, 30, 60, 0.35), 0 4px 12px rgba(20, 30, 60, 0.08);
  position: relative;
}

.tmb-auth-eyebrow {
  margin: 0 0 10px;
  letter-spacing: 0.14em;
  font-size: 11px;
}

.tmb-auth-title {
  margin: 0 0 10px;
  /* Only Regular and Semibold are loaded. Use the real Semibold face so Chrome
     does not synthesize an over-heavy 800 weight. */
  font: 600 34px/1.05 var(--tmb-font-head);
  letter-spacing: -0.025em;
}

.tmb-auth-subtitle {
  margin: 0 0 26px;
  font-size: 14.5px;
  line-height: 1.5;
  overflow-wrap: anywhere;
  word-break: break-word;
}

/* The submit button carries the full field-to-button gap (28px), so the
   dynamic input area no longer needs its own bottom margin. */
.tmb-auth-input-area { margin-bottom: 0; }

/* X close button, top-right (design .signin-close) */
.tmb-auth-close {
  position: absolute;
  top: 12px;
  right: 12px;
  /* Touch target: 44x44 per WCAG 2.5.5 / Apple HIG. The 32x32 visual disc
   * is preserved via background-clip / inset shadow so the visible button
   * still looks like 32x32 but the tap surface is 44x44. */
  width: 44px;
  height: 44px;
  border-radius: var(--tmb-radius-full);
  border: 0;
  background: radial-gradient(circle, #f3f4f8 0 16px, transparent 16px);
  color: #6f747d;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
  transition: background 0.14s ease, color 0.14s ease;
}
/* A08: mock has no hover state on the close button - removed hover rule to match */
.tmb-auth-close svg { display: block; }

/* Provider buttons (Continue with Google / Apple) */
.tmb-auth-provider {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10px;
  width: 100%;
  height: 56px;
  padding: 0 12px;
  border-radius: var(--tmb-radius-full);
  background: #fff;
  color: #1f1f1f;
  border: 1px solid #747775;
  box-shadow: none;
  /* Deliberate guideline deviation: Tumbil keeps Poppins here instead of Google Sans. */
  font-family: var(--tmb-font-body);
  font-weight: 600;
  font-size: 14px;
  line-height: 20px;
  letter-spacing: 0;
  cursor: pointer;
  margin-bottom: 10px;
  transition: border-color 0.14s ease, background 0.14s ease;
}
.tmb-auth-provider:hover:not(:disabled) {
  border-color: #5f6368;
  background: #f8fafd;
}
.tmb-auth-provider-icon,
.tmb-auth-provider-spinner {
  display: inline-flex;
  flex: 0 0 18px;
  width: 18px;
  height: 18px;
  align-items: center;
  justify-content: center;
}
.tmb-auth-provider svg { display: block; flex: 0 0 auto; }
.tmb-auth-provider-label {
  display: inline-block;
  min-width: 0;
}
.tmb-auth-provider-spinner {
  width: 16px;
  height: 16px;
  flex-basis: 16px;
  border-radius: 50%;
  border: 2px solid rgba(31, 31, 31, 0.24);
  border-top-color: #1f1f1f;
  animation: tmb-auth-provider-spin 0.7s linear infinite;
}
@keyframes tmb-auth-provider-spin {
  to { transform: rotate(360deg); }
}

/* "or with email" divider */
.tmb-auth-divider {
  display: flex;
  align-items: center;
  gap: 14px;
  margin: 18px 0 22px;
  color: #aab0b8;
  font-size: 11.5px;
  text-transform: uppercase;
  letter-spacing: 0.12em;
  /* CD .signin-divider: 600. */
  font-weight: 600;
}
.tmb-auth-divider::before,
.tmb-auth-divider::after {
  content: "";
  flex: 1;
  height: 1px;
  background: var(--tmb-divider);
}

/* Outlined pill text field - Tumbil DS (56h, 100r, notched floating label).
   Scoped to .tmb-auth-field so the standalone .tmb-password-input on the
   password-reset screen keeps its plain bordered style. */
.tmb-auth-fields {
  display: flex;
  flex-direction: column;
  gap: 20px;
}
.tmb-auth-row2 {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 12px;
}
.tmb-auth-field {
  position: relative;
  height: 56px;
  border-radius: 100px;
  background: var(--tmb-surface);
  box-shadow: inset 0 0 0 1px #dee2e6;
  transition: box-shadow 0.12s ease;
}
.tmb-auth-field:hover {
  box-shadow: inset 0 0 0 1px var(--tmb-placeholder);
}
.tmb-auth-field:focus-within {
  box-shadow: inset 0 0 0 2px var(--tmb-blue-dark);
}
.tmb-auth-field.has-error {
  box-shadow: inset 0 0 0 1px var(--tmb-red);
}
.tmb-auth-field > label {
  position: absolute;
  top: -8px;
  left: 16px;
  padding: 0 4px;
  background: var(--tmb-surface);
  font-family: var(--tmb-font-body);
  font-weight: 400;
  font-size: 12px;
  line-height: 16px;
  /* CD notched label tracking. */
  letter-spacing: 0.4px;
  text-transform: none;
  color: var(--tmb-muted);
  pointer-events: none;
  z-index: 1;
}
.tmb-auth-field:hover > label { color: var(--tmb-ink); }
.tmb-auth-field:focus-within > label { color: var(--tmb-blue-dark); }
.tmb-auth-field.has-error > label { color: var(--tmb-red); }
.tmb-auth-field input {
  width: 100%;
  height: 100%;
  padding: 0 16px;
  border: 0;
  border-radius: 100px;
  background: transparent;
  font-family: var(--tmb-font-body);
  font-size: 16px;
  line-height: 24px;
  /* CD DS input text tracking. */
  letter-spacing: 0.5px;
  color: var(--tmb-ink);
  outline: none;
  box-sizing: border-box;
}
.tmb-auth-field input::placeholder { color: var(--tmb-placeholder); }
/* The autofill fill below is painted by the INPUT and covers the parent
 * .tmb-auth-field's inset border ring. Re-paint the 1px ring on top of the
 * fill so the pill stroke stays visible when Chrome autofills. The hover /
 * focus-within parent variants mirror the live border colours above. */
.tmb-auth-field input:-webkit-autofill,
.tmb-auth-field input:-webkit-autofill:hover,
.tmb-auth-field input:-webkit-autofill:focus {
  -webkit-text-fill-color: var(--tmb-ink);
  -webkit-box-shadow: inset 0 0 0 1px #dee2e6, inset 0 0 0 1000px var(--tmb-surface);
  caret-color: var(--tmb-ink);
  transition: background-color 5000s ease-in-out 0s;
}
.tmb-auth-field:hover input:-webkit-autofill,
.tmb-auth-field:hover input:-webkit-autofill:hover,
.tmb-auth-field:hover input:-webkit-autofill:focus {
  -webkit-box-shadow: inset 0 0 0 1px var(--tmb-placeholder), inset 0 0 0 1000px var(--tmb-surface);
}
.tmb-auth-field:focus-within input:-webkit-autofill,
.tmb-auth-field:focus-within input:-webkit-autofill:hover,
.tmb-auth-field:focus-within input:-webkit-autofill:focus {
  -webkit-box-shadow: inset 0 0 0 2px var(--tmb-blue-dark), inset 0 0 0 1000px var(--tmb-surface);
}
.tmb-auth-field.has-error input:-webkit-autofill,
.tmb-auth-field.has-error input:-webkit-autofill:hover,
.tmb-auth-field.has-error input:-webkit-autofill:focus {
  -webkit-box-shadow: inset 0 0 0 1px var(--tmb-red), inset 0 0 0 1000px var(--tmb-surface);
}
/* PHONEDUP-1 (Cliff 2026-08-11): the phone input spans only PART of its
 * pill (the +1 prefix sits beside it), so the ring repaint above lands
 * around the input's own rect - a second rectangle nested inside the pill
 * whenever Chrome autofills the number. The parent ring is never covered
 * here (the input does not reach the pill edges), so paint only the fill,
 * in every parent variant. */
.tmb-auth-field .tmb-auth-phone input:-webkit-autofill,
.tmb-auth-field .tmb-auth-phone input:-webkit-autofill:hover,
.tmb-auth-field .tmb-auth-phone input:-webkit-autofill:focus,
.tmb-auth-field:hover .tmb-auth-phone input:-webkit-autofill,
.tmb-auth-field:hover .tmb-auth-phone input:-webkit-autofill:hover,
.tmb-auth-field:hover .tmb-auth-phone input:-webkit-autofill:focus,
.tmb-auth-field:focus-within .tmb-auth-phone input:-webkit-autofill,
.tmb-auth-field:focus-within .tmb-auth-phone input:-webkit-autofill:hover,
.tmb-auth-field:focus-within .tmb-auth-phone input:-webkit-autofill:focus,
.tmb-auth-field.has-error .tmb-auth-phone input:-webkit-autofill,
.tmb-auth-field.has-error .tmb-auth-phone input:-webkit-autofill:hover,
.tmb-auth-field.has-error .tmb-auth-phone input:-webkit-autofill:focus {
  -webkit-box-shadow: inset 0 0 0 1000px var(--tmb-surface);
}

/* Phone field - fixed +1 Canada prefix, no country picker. */
.tmb-auth-phone {
  display: flex;
  align-items: center;
  width: 100%;
  height: 100%;
  padding: 0 18px 0 14px;
}
.tmb-auth-phone-prefix {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  flex-shrink: 0;
  margin-right: 10px;
  padding: 0 10px 0 6px;
  background: #f3f4f8;
  border-radius: 999px;
  color: var(--tmb-ink);
  font-size: 16px;
  line-height: 24px;
}
.tmb-auth-phone-flag {
  display: block;
  width: 22px;
  height: 22px;
  border-radius: 50%;
  overflow: hidden;
  flex-shrink: 0;
}
.tmb-auth-phone-flag svg { display: block; width: 100%; height: 100%; }
.tmb-auth-phone input {
  flex: 1;
  min-width: 0;
  width: auto;
  height: 100%;
  padding: 0;
  border: 0;
  background: transparent;
  font-family: var(--tmb-font-body);
  font-size: 16px;
  line-height: 24px;
  color: var(--tmb-ink);
  outline: none;
}
.tmb-auth-phone input::placeholder { color: var(--tmb-placeholder); }

/* Forgot-password link - sits between the password field and Sign in (0b). */
.tmb-auth-forgot {
  margin-top: 14px;
  font-size: 13px;
}
.tmb-auth-forgot a {
  /* CD --primary-pressed (#006A96), intentionally distinct from --primary. */
  color: var(--tmb-blue-pressed);
  font-weight: 600;
  text-decoration: none;
  cursor: pointer;
}
.tmb-auth-forgot a:hover { text-decoration: underline; }

/* Transactional consent row - gates Continue on the account-setup screen. */
.tmb-auth-consent {
  display: flex;
  gap: 12px;
  align-items: flex-start;
  margin-top: 18px;
  padding-top: 16px;
  border-top: 1px solid var(--tmb-divider);
  cursor: pointer;
}
.tmb-auth-consent-box {
  width: 22px;
  height: 22px;
  flex-shrink: 0;
  margin-top: 1px;
  border-radius: 6px;
  /* CD .signin-consent .box unchecked border: #c8ccd4 (cooler/lighter gray). */
  box-shadow: inset 0 0 0 1.5px #c8ccd4;
  background: var(--tmb-surface);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  transition: background 0.12s ease, box-shadow 0.12s ease;
}
.tmb-auth-consent-box svg { display: none; }
.tmb-auth-consent.is-checked .tmb-auth-consent-box {
  background: var(--tmb-blue);
  box-shadow: none;
}
.tmb-auth-consent.is-checked .tmb-auth-consent-box svg { display: block; }
.tmb-auth-consent:focus-visible {
  outline: 2px solid var(--tmb-blue);
  outline-offset: 2px;
  border-radius: 8px;
}
.tmb-auth-consent-text {
  font-size: 13px;
  line-height: 1.5;
  color: var(--tmb-muted);
  letter-spacing: -0.005em;
}
.tmb-auth-consent-text a {
  /* CD .signin-consent .text a -> --primary-pressed (#006A96). */
  color: var(--tmb-blue-pressed);
  font-weight: 600;
  text-decoration: none;
}
.tmb-auth-consent-text a:hover { text-decoration: underline; }

/* OTP cells -> 4-col grid (design .otp-cells / .otp-cell) */
.tmb-otp-cells {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 12px;
  margin-bottom: 22px;
}
.tmb-auth-input-area > .tmb-otp-cells { justify-content: stretch; }
.tmb-otp-cell {
  flex: none;
  width: 100%;
  height: 64px;
  border-radius: var(--tmb-radius-md);
  background: #f5f6fa;
  border: 0;
  box-shadow: inset 0 0 0 1.5px var(--tmb-divider);
  text-align: center;
  font-family: var(--tmb-font-head);
  font-weight: 800;
  font-size: 28px;
  color: var(--tmb-ink);
  letter-spacing: -0.01em;
  font-variant-numeric: tabular-nums;
}
.tmb-otp-cell:focus {
  outline: none;
  background: var(--tmb-surface);
  /* CD invariant 2: 2px inset primary ring only, no outer glow. */
  box-shadow: inset 0 0 0 2px var(--tmb-blue);
}

/* OTP actions row + secure note */
.tmb-otp-actions {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-top: 14px;
  font-size: 13px;
}
.tmb-otp-resend { color: var(--tmb-muted); }
.tmb-otp-switch {
  color: var(--tmb-blue-dark);
  font-weight: 600;
  text-decoration: none;
  cursor: pointer;
}
.tmb-otp-switch:hover { text-decoration: underline; }
.tmb-auth-secure {
  margin-top: 20px;
  padding-top: 14px;
  border-top: 1px solid var(--tmb-divider);
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 12px;
  color: #8b8f97;
}
.tmb-auth-secure svg { display: block; flex: 0 0 auto; }

/* Submit -> 56px pill (design .signin-submit).
 * Background is the CD primary (--tmb-blue = #0081B6); hover is the CD pressed
 * blue (--tmb-blue-pressed = #006A96). (The old note about a brighter shade is
 * obsolete: the whole surface moved to CD's darker primary, invariant 1.) */
.tmb-auth-submit {
  height: 56px;
  padding: 0 22px;
  border-radius: var(--tmb-radius-full);
  margin-top: 28px;
  background: var(--tmb-blue);
  box-shadow: 0 8px 22px -10px rgba(0, 129, 182, 0.6);
}
.tmb-auth-submit:hover:not(:disabled) { background: var(--tmb-blue-pressed); }
/* Disabled submit - matches the design's grey "not ready" pill, not a faded
   blue. Overrides the base .tmb-auth-submit:disabled opacity rule. */
.tmb-auth-submit:disabled,
.tmb-auth-submit.is-disabled {
  background: #f3f4f8;
  color: #8b8f97;
  box-shadow: none;
  opacity: 1;
  cursor: not-allowed;
}

/* Later auth-step fallback footer. */
.tmb-auth-footer {
  font-size: 13px;
  color: var(--tmb-muted);
  text-align: center;
  margin-top: 18px;
}
.tmb-auth-fallback {
  color: var(--tmb-blue-pressed);
  font-weight: 600;
  text-decoration: none;
}

.tmb-auth-legal {
  margin: 18px 0 0;
  color: #585C62;
  font-size: 13px;
  line-height: 1.5;
  text-align: center;
}
.tmb-auth-legal[hidden] { display: none; }
.tmb-auth-legal a {
  color: #006A96;
  font-weight: 600;
  text-decoration: none;
}
.tmb-auth-legal a:hover { text-decoration: underline; }

/* ============ WashPros safety modal (design screen 9a) ============ */
.tmb-safety-overlay {
  position: fixed;
  inset: 0;
  background: rgba(20, 30, 60, 0.42);
  backdrop-filter: blur(2px);
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 100;
  padding: 16px;
  animation: tmb-overlay-fade 200ms ease-out;
}
.tmb-safety-overlay[hidden] { display: none; }
/* SAFEWAIT-1 fade-out: the modal beneath fades 150ms while the placement
   scrim fades in (CD entry contract). */
.tmb-safety-overlay.is-leaving {
  animation: tmb-placewait-out 150ms ease-out forwards;
  pointer-events: none;
}

/* SAFEWAIT-1 placement scrim (CD ruling 2026-07-21, cd-safewait-1.md).
   Scrim: rgba(15,20,35,.45) + blur(2px) - the one project scrim vocabulary.
   Chip: white 64px circle, DS shadow-md. Ring: 28px, 3px stroke, track
   #E9EAEB, arc #0081B6, 360deg at 0.9s linear infinite. z 110 translates
   CD's "clears every in-page overlay" intent into THIS stacking context
   (safety + auth overlays sit at 100); browser chrome is unaffected by
   in-page z. Entry fade 150ms; exit only on failure via .is-leaving
   (200ms) - success persists until the redirect unloads the page. */
.tmb-placewait-overlay {
  position: fixed;
  inset: 0;
  z-index: 110;
  display: flex;
  align-items: center;
  justify-content: center;
  background: rgba(15, 20, 35, 0.45);
  backdrop-filter: blur(2px);
  touch-action: none;
  overscroll-behavior: contain;
  animation: tmb-overlay-fade 150ms ease-out;
}
.tmb-placewait-overlay[hidden] { display: none; }
.tmb-placewait-overlay.is-leaving {
  animation: tmb-placewait-out 200ms ease-out forwards;
  pointer-events: none;
}
.tmb-placewait-chip {
  width: 64px;
  height: 64px;
  border-radius: 999px;
  background: #fff;
  box-shadow: 0 8px 24px rgba(6, 6, 22, .08);
  display: flex;
  align-items: center;
  justify-content: center;
}
.tmb-placewait-ring {
  width: 28px;
  height: 28px;
  animation: tmb-placewait-spin 0.9s linear infinite;
}
@keyframes tmb-placewait-spin { to { transform: rotate(360deg); } }
@keyframes tmb-placewait-out { to { opacity: 0; } }
@media (prefers-reduced-motion: reduce) {
  /* CD: scrim appears/leaves without fade; the spinner KEEPS rotating -
     it is the status signal, not decoration. */
  .tmb-placewait-overlay { animation: none; }
  .tmb-placewait-overlay.is-leaving { animation: none; opacity: 0; }
  .tmb-safety-overlay.is-leaving { animation: none; opacity: 0; }
}
.tmb-safety-card {
  position: relative;
  width: 480px;
  max-width: 100%;
  background: var(--tmb-surface);
  border-radius: 18px;
  padding: 32px 36px 28px;
  box-shadow: 0 30px 80px -20px rgba(20, 30, 60, 0.35), 0 4px 12px rgba(20, 30, 60, 0.08);
}
.tmb-safety-close {
  position: absolute;
  top: 12px;
  right: 12px;
  /* Touch target: 44x44 per WCAG 2.5.5. */
  width: 44px;
  height: 44px;
  border-radius: var(--tmb-radius-full);
  border: 0;
  background: transparent;
  color: var(--tmb-ink);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
}
.tmb-safety-close:hover { background: var(--tmb-surface-light); }
.tmb-safety-close svg { display: block; }
.tmb-safety-title {
  margin: 0 0 12px;
  padding-right: 36px;
  font: 800 24px/1.2 var(--tmb-font-head);
  letter-spacing: -0.015em;
  color: var(--tmb-ink);
}
.tmb-safety-sub {
  margin: 0 0 20px;
  font-size: 14.5px;
  color: var(--tmb-muted);
  line-height: 1.55;
}
.tmb-safety-list {
  display: flex;
  flex-direction: column;
  gap: 14px;
  margin-bottom: 18px;
}
.tmb-safety-row {
  display: flex;
  align-items: flex-start;
  gap: 14px;
  padding: 4px 0;
  cursor: pointer;
  background: none;
  border: 0;
  text-align: left;
  width: 100%;
  font-family: var(--tmb-font-body);
}
.tmb-safety-check {
  width: 26px;
  height: 26px;
  border-radius: var(--tmb-radius-sm);
  box-shadow: inset 0 0 0 1.5px var(--tmb-border);
  background: var(--tmb-surface);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
  margin-top: 1px;
  transition: background 0.12s ease, box-shadow 0.12s ease;
}
.tmb-safety-row.is-checked .tmb-safety-check {
  background: var(--tmb-blue);
  box-shadow: none;
}
.tmb-safety-check svg { display: none; color: #fff; }
.tmb-safety-row.is-checked .tmb-safety-check svg { display: block; }
.tmb-safety-row.is-checked .tmb-safety-check path { stroke: #fff; }
.tmb-safety-row:focus-visible {
  outline: 2px solid var(--tmb-blue);
  outline-offset: 2px;
  border-radius: 6px;
}
.tmb-safety-label {
  font-size: 14.5px;
  line-height: 1.45;
  color: var(--tmb-ink);
  font-weight: 500;
  letter-spacing: -0.005em;
  padding-top: 3px;
}
.tmb-safety-warn {
  margin: 0 0 18px;
  padding: 14px 0 4px;
  border-top: 1px solid var(--tmb-divider);
  font-size: 13px;
  color: var(--tmb-muted);
  line-height: 1.55;
}
.tmb-safety-confirm {
  width: 100%;
  padding: 16px 20px;
  border-radius: var(--tmb-radius-full);
  background: #f3f4f8;
  color: #8b8f97;
  font-family: var(--tmb-font-body);
  font-weight: 600;
  font-size: 15px;
  border: 0;
  text-align: center;
  cursor: not-allowed;
}
.tmb-safety-confirm.is-ready {
  background: var(--tmb-cta-bg);
  color: #fff;
  cursor: pointer;
  box-shadow: 0 8px 22px -10px rgba(0, 129, 182, 0.6);
}
.tmb-safety-confirm.is-ready:hover { background: var(--tmb-cta-bg-hover); }

/* ============ Order Card kebab menu + Start over (design 5b/5c) ============ */
/* Header right-side column: status pill + kebab share one row. */
.tmb-card-actions {
  flex: 0 0 auto;
  display: flex;
  align-items: center;
  gap: 8px;
}
.tmb-card-menu-wrap { position: relative; }
.tmb-card-menu-btn {
  /* Touch target: 44x44 per WCAG 2.5.5 / Apple HIG. Visual chevron remains the
   * 16x16 SVG inside; the wider tap surface keeps the kebab usable on touch. */
  width: 44px;
  height: 44px;
  border-radius: var(--tmb-radius-sm);
  border: 0;
  background: transparent;
  color: var(--tmb-placeholder);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: 0;
  cursor: pointer;
  transition: background 0.14s ease, color 0.14s ease;
}
.tmb-card-menu-btn[hidden] { display: none; }
.tmb-card-menu-btn:hover,
.tmb-card-menu-btn[aria-expanded="true"] {
  background: var(--tmb-surface-light);
  color: var(--tmb-ink);
}
.tmb-card-menu-btn svg { display: block; }
.tmb-card-menu {
  position: absolute;
  top: calc(100% + 6px);
  right: 0;
  min-width: 200px;
  padding: 6px;
  background: var(--tmb-surface);
  border-radius: var(--tmb-radius-md);
  box-shadow: 0 12px 30px -10px rgba(20, 30, 60, 0.25), 0 0 0 1px var(--tmb-divider);
  z-index: 30;
}
.tmb-card-menu[hidden] { display: none; }
.tmb-card-menu-item {
  display: flex;
  align-items: center;
  gap: 10px;
  width: 100%;
  padding: 10px 12px;
  border: 0;
  border-radius: var(--tmb-radius-sm);
  background: transparent;
  color: var(--tmb-ink);
  font-family: var(--tmb-font-body);
  font-weight: 500;
  font-size: 14px;
  text-align: left;
  cursor: pointer;
}
.tmb-card-menu-item:hover { background: var(--tmb-surface-light); }
.tmb-card-menu-item svg { display: block; flex: 0 0 auto; color: var(--tmb-secondary); }
.tmb-card-menu-item.is-danger,
.tmb-card-menu-item.is-danger svg { color: var(--tmb-red); }

/* Start-over confirm modal (design screen 5c). */
.tmb-startover-overlay {
  position: fixed;
  inset: 0;
  background: rgba(20, 30, 60, 0.42);
  backdrop-filter: blur(2px);
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 110;
  padding: 16px;
  animation: tmb-overlay-fade 200ms ease-out;
}
.tmb-startover-overlay[hidden] { display: none; }
.tmb-startover-card {
  width: 420px;
  max-width: 100%;
  background: var(--tmb-surface);
  border-radius: 18px;
  padding: 32px 32px 24px;
  box-shadow: 0 30px 80px -20px rgba(20, 30, 60, 0.35), 0 4px 12px rgba(20, 30, 60, 0.08);
}
.tmb-startover-title {
  margin: 0 0 8px;
  font: 800 22px/1.2 var(--tmb-font-head);
  letter-spacing: -0.015em;
  color: var(--tmb-ink);
}
.tmb-startover-sub {
  margin: 0 0 22px;
  font-size: 14.5px;
  line-height: 1.5;
  color: var(--tmb-muted);
}
.tmb-startover-actions {
  display: flex;
  gap: 10px;
  justify-content: flex-end;
}
.tmb-startover-cancel,
.tmb-startover-confirm {
  padding: 12px 22px;
  border-radius: var(--tmb-radius-full);
  border: 0;
  font-family: var(--tmb-font-body);
  font-weight: 600;
  font-size: 14px;
  cursor: pointer;
}
.tmb-startover-cancel {
  background: #f3f4f8;
  color: var(--tmb-ink);
}
.tmb-startover-cancel:hover { background: var(--tmb-divider); }
.tmb-startover-confirm {
  background: var(--tmb-ink);
  color: #fff;
}
.tmb-startover-confirm:hover { background: #000; }

/* ============ Skip-to-main accessibility link (UA-09) ============
 * Visually hidden until focused via Tab, then renders as a top-left button.
 * Targets #tmb-main so keyboard users can skip the header in one tap. */
.tmb-skip-to-main {
  position: absolute;
  top: 0;
  left: 0;
  padding: 10px 16px;
  background: var(--tmb-blue);
  color: #fff;
  font-weight: 600;
  font-size: 14px;
  text-decoration: none;
  border-radius: 0 0 var(--tmb-radius-md) 0;
  transform: translateY(-110%);
  transition: transform 0.16s ease;
  z-index: 1000;
}
.tmb-skip-to-main:focus {
  transform: translateY(0);
  outline: 2px solid var(--tmb-ink);
  outline-offset: 2px;
}

/* ============ WashPros selector (design screen 5a) ============
   Inline card rendered under the bot's preferred-WashPros question for
   returning customers. Tap-to-toggle, max 3, auto-priority by tap order.
   No drag-rank in v1 - tap order is the priority. */
.tmb-washpros-msg {
  background: transparent !important;
  padding: 0 !important;
  margin-left: 0 !important;
  max-width: 100% !important;
}
.tmb-washpros-selector {
  background: var(--tmb-surface);
  /* CD .washpro-selector: 18px radius with a 6px top-left bot-bubble tail, a soft
     shadow + hairline ring (no flat border). */
  border: 0;
  border-radius: 18px;
  border-top-left-radius: 6px;
  box-shadow: 0 1px 2px rgba(20, 30, 60, 0.05), 0 0 0 1px var(--tmb-divider);
  padding: 18px 18px 16px;
  display: flex;
  flex-direction: column;
  gap: 10px;
  font-family: var(--tmb-font-body);
}

.tmb-ws-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 12px;
}
.tmb-ws-title {
  font-family: var(--tmb-font-head);
  font-size: 16px;
  font-weight: 700;
  color: var(--tmb-ink);
}
.tmb-ws-counter {
  font-size: 12.5px;
  font-weight: 600;
  /* CD muted text = #585C62 (= --tmb-muted), not --tmb-secondary. */
  color: var(--tmb-muted);
  font-variant-numeric: tabular-nums;
}
.tmb-ws-explainer {
  font-size: 13.5px;
  color: var(--tmb-muted);
  line-height: 1.45;
  margin: 0;
}
.tmb-ws-opt {
  /* CD: the "(Optional)" tag is emphasized ink, not muted. */
  color: var(--tmb-ink);
  font-weight: 600;
}

.tmb-ws-list {
  list-style: none;
  padding: 0;
  margin: 4px 0 6px;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.tmb-ws-row {
  display: grid;
  grid-template-columns: 20px 1fr 28px;
  align-items: center;
  /* CD .ws-row: gap 14px, padding 12px 16px, radius 14px. */
  gap: 14px;
  padding: 12px 16px;
  border-radius: 14px;
  background: var(--tmb-surface-light);
  border: 1px solid var(--tmb-divider);
  cursor: pointer;
  user-select: none;
  transition: background 120ms ease, border-color 120ms ease;
}
.tmb-ws-row:hover { background: #eef0f5; }
.tmb-ws-row:focus-visible {
  outline: none;
  box-shadow: var(--tmb-focus);
}
.tmb-ws-row.is-selected {
  /* CD: selected = #eaf2ff fill, NO border (keep the row border transparent so
     it never draws a visible outline). */
  background: var(--tmb-blue-soft);
  border-color: transparent;
}
.tmb-ws-row.is-unavailable {
  /* CD: don't fade the whole row - keep it at full opacity and only gray the
     name + date + tag text (rules below). */
  background: var(--tmb-surface);
  cursor: not-allowed;
}
.tmb-ws-row.is-unavailable .tmb-ws-name,
.tmb-ws-row.is-unavailable .tmb-ws-date,
.tmb-ws-row.is-unavailable .tmb-ws-tag,
.tmb-ws-row.is-unavailable .tmb-ws-reason {
  color: #B3B6BB;
}
.tmb-ws-handle {
  /* B09-010 (verify wave): CD "Preferred WashPros" - drag handle 6-dot grid
     is #C8CCD4 on every row, NOT the muted text token. */
  color: #c8ccd4;
  display: inline-flex;
  align-items: center;
  justify-content: center;
}
.tmb-ws-row.is-selected .tmb-ws-handle {
  cursor: grab;
  touch-action: none;
}
.tmb-ws-row.is-dragging {
  z-index: 5;
  box-shadow: 0 10px 24px rgba(13, 18, 32, 0.18);
  opacity: 0.96;
  transition: none;
}
.tmb-ws-row.is-dragging .tmb-ws-handle { cursor: grabbing; }
.tmb-ws-meta {
  display: flex;
  flex-direction: column;
  gap: 2px;
  min-width: 0;
}
.tmb-ws-name {
  /* CD .ws-name: 15px. */
  font-size: 15px;
  font-weight: 600;
  color: var(--tmb-ink);
  letter-spacing: -0.005em;
}
.tmb-ws-tag {
  font-size: 12px;
  font-weight: 500;
  color: var(--tmb-muted);
  margin-left: 4px;
}
.tmb-ws-date {
  /* CD .ws-date: 13px, muted #585C62. */
  font-size: 13px;
  color: var(--tmb-muted);
}
.tmb-ws-reason {
  font-size: 12.5px;
  color: var(--tmb-muted);
}
.tmb-ws-checkbox {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  /* CD .ws-check: 24x24, radius 6px, idle inset 1.5px #C8CCD4 ring. */
  width: 24px;
  height: 24px;
  border-radius: 6px;
  border: 0;
  box-shadow: inset 0 0 0 1.5px #C8CCD4;
  background: #fff;
  box-sizing: border-box;
  transition: background 120ms ease, box-shadow 120ms ease, opacity 120ms ease;
}
.tmb-ws-row.is-selected .tmb-ws-checkbox {
  background: var(--tmb-blue);
  box-shadow: none;
}
.tmb-ws-row.is-cb-disabled:not(.is-selected) .tmb-ws-checkbox {
  opacity: 0.4;
}
.tmb-ws-handle.is-hidden { visibility: hidden; }

.tmb-ws-actions {
  display: flex;
  gap: 8px;
  justify-content: flex-end;
  margin-top: 6px;
}
.tmb-ws-skip,
.tmb-ws-continue {
  font: inherit;
  cursor: pointer;
  padding: 8px 16px;
  border-radius: var(--tmb-radius-md);
  font-size: 13.5px;
  font-weight: 600;
  border: 1px solid transparent;
}
.tmb-ws-skip {
  background: transparent;
  color: var(--tmb-secondary);
  border-color: var(--tmb-divider);
}
.tmb-ws-skip:hover { background: var(--tmb-surface-light); color: var(--tmb-ink); }
.tmb-ws-continue {
  background: var(--tmb-cta-bg);
  color: #fff;
  /* CD .ws-continue: a full pill - padding 12px 28px, radius 999px, 14px. */
  padding: 12px 28px;
  border-radius: 999px;
  font-size: 14px;
}
.tmb-ws-continue:hover { background: var(--tmb-cta-bg-hover); }
.tmb-ws-continue:disabled,
.tmb-ws-skip:disabled { opacity: 0.6; cursor: default; }

/* ============================================================
   Inline form card (CD spec, 2026-05-27).
   Rendered inside the chat thread for structured sub-step input.
   First use: pickup-address. The card carries its own input and
   Google Places predictions; the bottom composer stays available
   for ad-hoc chat but the card is the primary input target while
   the sub-step is active.
   ============================================================ */

.inline-form-card {
  width: 100%;
  max-width: min(540px, 92%);
  margin: 0;
  padding: 0;
  background: var(--tmb-surface);
  /* CD .inline-form-card / .ifc: a tight elevation + hairline ring (no separate
     CSS border, no heavy drop shadow). */
  border: 0;
  border-radius: var(--tmb-radius-lg);
  box-shadow: 0 1px 2px rgba(20, 30, 60, 0.05), 0 0 0 1px var(--tmb-divider);
  overflow: visible;
  position: relative;
}

.inline-form-card.is-filled {
  background: var(--tmb-surface-light);
}

.ifc-head {
  display: flex;
  align-items: center;
  gap: 10px;
  /* CD .ifc-head eyebrow: 12px / 700 / 0.06em, padding 14px 18px 0. */
  padding: 14px 18px 0;
  font-size: 12px;
  font-weight: 700;
  color: var(--tmb-secondary);
  letter-spacing: 0.06em;
  text-transform: uppercase;
}

.ifc-pin {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 20px;
  height: 20px;
  background: transparent;
  color: var(--tmb-blue-dark);
  flex-shrink: 0;
}

.ifc-pin svg {
  width: 13px;
  height: 13px;
}

.ifc-body {
  padding: 4px 18px 16px;
  position: relative;
}

.ifc-input {
  width: 100%;
  /* CD DS Text Field pill: 56px tall, 100px radius, 16px input text, idle inset
     1px #DEE2E6 ring (no border), hover 1px #A2A4A8. */
  height: 56px;
  padding: 0 18px;
  font-family: inherit;
  font-size: 16px;
  line-height: 24px;
  color: var(--tmb-ink);
  background: var(--tmb-surface);
  border: 0;
  border-radius: 100px;
  box-shadow: inset 0 0 0 1px var(--tmb-divider);
  outline: 0;
  transition: box-shadow 120ms ease;
}

.ifc-input:hover {
  box-shadow: inset 0 0 0 1px #A2A4A8;
}

.ifc-input:focus,
.inline-form-card:not(.is-filled):focus-within .ifc-input {
  /* CD invariant 2: 2px inset primary ring, no outer glow. */
  border-color: transparent;
  box-shadow: inset 0 0 0 2px #0081B6;
}

/* R17-06 free-typed check + B04-050 street-level gate. CD DS Text Field
   error treatment: 2px inset #C41E3A ring + support text in the same red. */
.ifc-input.is-invalid {
  box-shadow: inset 0 0 0 2px #C41E3A;
}

.ifc-hint {
  margin-top: 8px;
  padding: 0 18px;
  font-size: 13px;
  line-height: 18px;
  color: #C41E3A;
}

.ifc-input::placeholder {
  color: var(--tmb-placeholder);
}

/* CD picker X-clear (Pickup Location Variation / Pickup Out of Coverage,
   blind-QA B05-021): 22px round button inside the field's right edge, shown
   only while there is text ([hidden] otherwise). Clears text + predictions
   and keeps focus in the input. */
.ifc-clear {
  position: absolute;
  top: 21px; /* body pad 4px + (56px field - 22px button) / 2 */
  right: 34px;
  width: 22px;
  height: 22px;
  border-radius: 999px;
  border: 0;
  padding: 0;
  background: #eef0f4;
  color: #8b8f97;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
}

.ifc-clear[hidden] {
  display: none;
}

.ifc-clear:hover {
  color: var(--tmb-ink);
}

/* Keep typed text clear of the X button. */
.ifc-input {
  padding-right: 64px;
}

.inline-form-card.is-filled .ifc-input {
  background: transparent;
  border-color: transparent;
  box-shadow: none;
  height: auto;
  padding-left: 0;
  font-weight: 500;
  cursor: default;
}

.ifc-edit {
  position: absolute;
  top: 12px;
  right: 12px;
  background: transparent;
  border: 0;
  color: var(--tmb-blue);
  font-size: 13px;
  font-weight: 600;
  cursor: pointer;
  padding: 4px 8px;
  border-radius: var(--tmb-radius-sm);
}

.ifc-edit:hover {
  background: var(--tmb-blue-soft);
}

.ifc-edit[hidden] {
  display: none;
}

.addr-pred {
  margin-top: 8px;
  /* CD .preds: tighter elevation + hairline ring, 16px radius (no flat border). */
  border: 0;
  border-radius: 16px;
  background: var(--tmb-surface);
  box-shadow: 0 14px 32px -16px rgba(20, 30, 60, 0.22), 0 0 0 1px var(--tmb-divider);
  overflow: hidden;
}

.addr-pred[hidden] {
  display: none;
}

.addr-pred-item {
  /* CD .pred row anatomy (B04-007): pin badge + text column, 13px gap,
     12px/15px padding. */
  display: flex;
  align-items: center;
  gap: 13px;
  width: 100%;
  padding: 12px 15px;
  border: 0;
  border-bottom: 1px solid var(--tmb-divider);
  background: var(--tmb-surface);
  color: var(--tmb-ink);
  text-align: left;
  font-size: 14px;
  line-height: 1.3;
  cursor: pointer;
}

.addr-pred-item:last-child {
  border-bottom: 0;
}

/* ACT3 row press (design-specs/cd-address-pick-act3.md), verbatim:
   "Row press feedback. 98% scale, brightness .94, 150ms ease-out, concurrent -
   nothing waits on it, same as a chip. The press IS the acknowledgement: no
   tick, no flash, no selected state on a row that is about to leave." */
.addr-pred-item {
  transition: transform 0.15s ease-out, filter 0.15s ease-out;
}

.addr-pred-item:active {
  transform: scale(0.98);
  filter: brightness(0.94);
}

@media (prefers-reduced-motion: reduce) {
  .addr-pred-item {
    transition: filter 0.15s ease-out;
  }

  .addr-pred-item:active {
    transform: none;
  }
}

.addr-pred-item:hover,
.addr-pred-item:focus,
.addr-pred-item.is-active {
  /* CD .pred:hover/.focus: soft full-row tint only (#f3f9fd), no left accent bar. */
  outline: 0;
  background: #f3f9fd;
}

/* CD .pred .pin: 28px circle badge, tinted primary on the hover/focus row. */
.addr-pred-pin {
  width: 28px;
  height: 28px;
  border-radius: 999px;
  background: #f3f4f8;
  color: #6f747d;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
}

.addr-pred-item:hover .addr-pred-pin,
.addr-pred-item:focus .addr-pred-pin,
.addr-pred-item.is-active .addr-pred-pin {
  background: rgba(0, 129, 182, 0.12);
  color: var(--tmb-blue-dark);
}

.addr-pred-txt {
  flex: 1;
  min-width: 0;
}

/* CD .pred .main with the matched-query emphasis (B04-008): main line 600,
   matched portion bold + primary via <b>. */
.addr-pred-main {
  display: block;
  font-size: 14.5px;
  font-weight: 600;
  color: var(--tmb-ink);
  letter-spacing: -0.005em;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

.addr-pred-main b {
  color: var(--tmb-blue-dark);
  font-weight: 700;
}

.addr-pred-item small {
  display: block;
  color: var(--tmb-muted);
  font-size: 12px;
  line-height: 1.35;
  margin-top: 2px;
}

/* CD Variation empty state (B04-014): quiet muted line under the field. */
.addr-empty {
  padding: 10px 18px 0;
  font-size: 13px;
  color: var(--tmb-muted);
}

.addr-empty[hidden] {
  display: none;
}

.addr-pred-foot {
  padding: 8px 13px;
  font-size: 11px;
  color: var(--tmb-muted);
  background: var(--tmb-surface-light);
  border-top: 1px solid var(--tmb-divider);
}

@media (max-width: 520px) {
  .inline-form-card {
    max-width: 100%;
  }
}

/* ============ Laundry Care (Option D) inline picker ============ */
/* Reuses .inline-form-card for the shell. Detergent = single-select radio
 * rows; Extras = multi-select checkbox rows. Helper text shows only under the
 * active/checked row. Maps Option D's palette to the chat's --tmb-* tokens. */

.tmb-care-msg {
  /* Standalone wrapper - no .tmb-message bubble classes (see renderLaundry-
     CareSelector). Direct child of .tmb-log (flex column, gap 14px,
     align-items:flex-start), so it sits left-aligned and spaced like the other
     turns. The card inside carries its own border/radius/bg and sizes to
     content. */
  width: 100%;
  max-width: min(540px, 92%);
}

.tmb-care-selector {
  width: 100%;
  max-width: min(540px, 92%);
  overflow: hidden;
  /* Hug content height and pack children to the top. Without this the card was
     rendering ~98px taller than its content, leaving an empty band above the
     Confirm button (the sizing drift Cliff flagged). align-self:flex-start
     stops it stretching to the chat column's cross size as a flex item. */
  display: flex;
  flex-direction: column;
  height: auto;
  align-self: flex-start;
}

/* When the detergent dropdown is open its menu must escape the card, so the
   card switches from clipping (overflow:hidden) to overflow:visible. */
.tmb-care-selector.menuopen {
  overflow: visible;
}

.tmb-care-pad,
.tmb-care-foot {
  flex: 0 0 auto;
}

.tmb-care-pad {
  padding: 24px 18px 16px;
  display: flex;
  flex-direction: column;
  gap: 22px;
}

.tmb-care-group {
  display: flex;
  flex-direction: column;
}

/* ===== Detergent dropdown (Option B) ===== */
.tmb-cs-wrap {
  position: relative;
}

.tmb-cs-field {
  position: relative;
  height: 56px;
  box-sizing: border-box;
  border: 1px solid var(--tmb-divider);
  border-radius: var(--tmb-radius-full);
  padding: 0 22px;
  display: flex;
  align-items: center;
  gap: 12px;
  justify-content: space-between;
  cursor: pointer;
  background: var(--tmb-surface);
}

.tmb-cs-field.is-open {
  border: 2px solid var(--tmb-blue-dark);
  /* -1px padding offsets the +1px border so the label/value don't shift on open */
  padding: 0 21px;
}

.tmb-cs-field:focus-visible {
  outline: 0;
  box-shadow: var(--tmb-focus);
}

.tmb-cs-flabel {
  position: absolute;
  top: -8px;
  left: 18px;
  background: var(--tmb-surface);
  padding: 0 5px;
  /* CD notched floating label: Poppins 400, 12/16, letter-spacing 0.4px. */
  font-size: 12px;
  font-weight: 400;
  letter-spacing: 0.4px;
  color: var(--tmb-muted);
}

.tmb-cs-field.is-open .tmb-cs-flabel {
  color: var(--tmb-blue-dark);
}

.tmb-cs-value {
  flex: 1;
  min-width: 0;
  font-size: 16px;
  font-weight: 500;
  color: var(--tmb-ink);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

.tmb-cs-caret {
  width: 20px;
  height: 20px;
  flex: 0 0 20px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  color: var(--tmb-muted);
  transition: transform 150ms ease;
}

.tmb-cs-field.is-open .tmb-cs-caret {
  color: var(--tmb-blue-dark);
  transform: rotate(180deg);
}

.tmb-cs-menu {
  position: absolute;
  top: calc(100% + 8px);
  left: 0;
  right: 0;
  z-index: 5;
  background: var(--tmb-surface);
  border: 1px solid #e9eaeb;
  border-radius: 20px;
  box-shadow: 0 10px 28px rgba(6, 6, 22, 0.12);
  padding: 8px;
}

.tmb-cs-mi {
  display: flex;
  align-items: center;
  justify-content: flex-start;
  gap: 10px;
  padding: 12px 16px;
  border-radius: var(--tmb-radius-full);
  cursor: pointer;
  font-size: 15px;
  color: var(--tmb-ink);
  background: transparent;
  border: 0;
  width: 100%;
  text-align: left;
  font-family: inherit;
  transition: background 120ms ease;
}

.tmb-cs-mi:hover {
  background: var(--tmb-blue-soft);
}

.tmb-cs-mi.is-sel {
  color: var(--tmb-blue-dark);
  font-weight: 500;
}

.tmb-cs-ck {
  width: 18px;
  height: 18px;
  flex: 0 0 18px;
  color: var(--tmb-blue-dark);
  display: inline-flex;
  align-items: center;
  justify-content: center;
}

/* ===== Extras (Option B): tappable cards ===== */
.tmb-b-head {
  font-size: 13.5px;
  font-weight: 600;
  /* CD .b-head colour. */
  color: #6a6e76;
  padding: 0 2px 10px;
}

.tmb-b-opts {
  display: flex;
  flex-direction: column;
  gap: 12px;
}

.tmb-b-opt {
  display: flex;
  align-items: center;
  gap: 14px;
  border: 1.5px solid #e7eaef;
  border-radius: 14px;
  padding: 13px 16px;
  cursor: pointer;
  background: var(--tmb-surface);
  width: 100%;
  text-align: left;
  font-family: inherit;
  transition: background 140ms ease, border-color 140ms ease;
}

.tmb-b-opt:focus { outline: 0; }
.tmb-b-opt:focus-visible {
  /* CD: no outer glow on the extras cards (invariant 2). Keyboard focus uses a
     2px inset primary ring instead of the old 3px outer glow. */
  outline: 0;
  box-shadow: inset 0 0 0 2px var(--tmb-blue-dark);
}

.tmb-b-box {
  width: 24px;
  height: 24px;
  border-radius: 7px;
  flex-shrink: 0;
  box-shadow: inset 0 0 0 1.5px #ccd2da;
  color: #fff;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  transition: background 140ms ease, box-shadow 140ms ease;
}

.tmb-b-box svg {
  opacity: 0;
  display: block;
}

.tmb-b-body {
  flex: 1;
  min-width: 0;
}

.tmb-b-name {
  display: block;
  font-size: 15px;
  font-weight: 500;
  color: #6f747d;
}

.tmb-b-sub {
  display: none;
  font-size: 12.5px;
  color: var(--tmb-muted);
  line-height: 1.45;
  margin-top: 6px;
}

.tmb-b-opt.is-active {
  align-items: flex-start;
  background: var(--tmb-blue-soft);
  border-color: transparent;
  border-radius: 16px;
}

.tmb-b-opt.is-active .tmb-b-box {
  background: var(--tmb-blue-dark);
  box-shadow: inset 0 0 0 1.5px var(--tmb-blue-dark);
}

.tmb-b-opt.is-active .tmb-b-box svg {
  opacity: 1;
}

.tmb-b-opt.is-active .tmb-b-name {
  color: var(--tmb-ink);
  font-weight: 600;
}

.tmb-b-opt.is-active .tmb-b-sub {
  display: block;
}

/* Additional-instructions note: grid-rows 0fr->1fr reveal so the Confirm button
   glides down rather than snapping (CD v1282). The keyframe fires on the
   .tmb-anim class, which chat.js adds only on the open tap - so unrelated
   re-renders (ticking another extra, opening the dropdown) hold the open state
   without replaying the slide. Collapsed state reserves 0 height. */
@keyframes tmbBNoteReveal {
  from { grid-template-rows: 0fr; opacity: 0; margin-top: 0; }
  to { grid-template-rows: 1fr; opacity: 1; margin-top: 10px; }
}

.tmb-b-note-wrap {
  display: grid;
  grid-template-rows: 0fr;
  opacity: 0;
  margin-top: 0;
}

.tmb-b-opt.is-active .tmb-b-note-wrap {
  grid-template-rows: 1fr;
  opacity: 1;
  margin-top: 10px;
}

.tmb-b-opt.is-active .tmb-b-note-wrap.tmb-anim {
  animation: tmbBNoteReveal 0.26s ease both;
}

.tmb-b-note-inner {
  overflow: hidden;
  min-height: 0;
}

.tmb-b-note {
  display: block;
  width: 100%;
  box-sizing: border-box;
  border: 1px solid var(--tmb-divider);
  border-radius: 12px;
  background: var(--tmb-surface);
  padding: 11px 13px;
  font-family: inherit;
  font-size: 16px;
  color: var(--tmb-ink);
  resize: none;
  line-height: 1.5;
}

.tmb-b-note::placeholder {
  color: var(--tmb-placeholder);
}

/* Focus = brand-blue inset edge (CD v1282). This also satisfies RO-044's intent
   (no OS-default green ring; brand-blue, consistent with the open dropdown's
   brand-blue border) - v1282 swapped the old soft 0.12 outer glow for the inset. */
.tmb-b-note:focus,
.tmb-b-note:focus-visible {
  outline: none;
  border-color: var(--tmb-blue-dark);
  box-shadow: inset 0 0 0 1px var(--tmb-blue-dark);
}

/* CD Option B state 4 (.b-tip): guidance line under the note field. */
.tmb-b-tip {
  display: block;
  margin-top: 7px;
  font-size: 12px;
  color: var(--tmb-muted);
  line-height: 1.4;
}

/* B08-013/JC-048: neither CD source draws a counter - it stays hidden until
   the customer nears the 800-char cap (chat.js CARE_NOTE_COUNT_SHOW_AT). */
.tmb-b-count {
  display: none;
  font-size: 11.5px;
  color: var(--tmb-placeholder);
  text-align: right;
  margin-top: 4px;
}

.tmb-b-count.is-visible {
  display: block;
}

@media (prefers-reduced-motion: reduce) {
  .tmb-b-opt.is-active .tmb-b-note-wrap.tmb-anim {
    animation: none;
  }
}

.tmb-care-foot {
  padding: 6px 18px 18px;
}

.tmb-care-confirm {
  width: 100%;
  border: 0;
  background: var(--tmb-cta-bg);
  color: #fff;
  font-family: inherit;
  font-weight: 700;
  font-size: 15px;
  /* CD .care-confirm: 14px. */
  padding: 14px;
  border-radius: var(--tmb-radius-full);
  letter-spacing: -0.005em;
  cursor: pointer;
  transition: background 120ms ease;
}

.tmb-care-confirm:hover {
  background: var(--tmb-cta-bg-hover);
}

.tmb-care-confirm:disabled {
  background: #e4e6eb;
  color: #b3b7bf;
  cursor: default;
}

/* Confirmed recap (Option D state 3): green check + resolved value. */
.tmb-care-selector.tmb-care-done {
  padding: 16px 18px;
}

/* ---- Completed inline-card recap (CD state 5) ----
   Laundry-care keeps its own .tmb-care-* classes (referenced by its verifiers);
   the generic .tmb-donecard family shares the exact same rules so the address
   and WashPros cards collapse to an identical compact row when done. */
.tmb-care-donecard,
.tmb-donecard {
  display: flex;
  align-items: center;
  gap: 14px;
}

/* Host padding for the address + WashPros wraps when they hold a recap (the
   care selector already sets this via .tmb-care-done). */
.inline-form-card.tmb-donecard-host {
  padding: 16px 18px;
  background: var(--tmb-surface-light);
  box-shadow: 0 0 0 1px var(--tmb-divider);
  opacity: 1;
}

.tmb-care-doneico,
.tmb-donecard-ico {
  /* CD .dc-ico: 32x32, bg rgba(0,168,107,.12), colour --ready #00a86b. */
  width: 32px;
  height: 32px;
  border-radius: 999px;
  flex-shrink: 0;
  background: rgba(0, 168, 107, 0.12);
  color: var(--tmb-green);
  display: inline-flex;
  align-items: center;
  justify-content: center;
}

.tmb-care-donebody,
.tmb-donecard-body {
  flex: 1;
  min-width: 0;
  display: flex;
  flex-direction: column;
}

.tmb-care-donelabel,
.tmb-donecard-label {
  /* CD .dc-label: 11px, colour --muted #585c62. */
  font-size: 11px;
  font-weight: 700;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--tmb-muted);
}

.tmb-care-doneval,
.tmb-donecard-val {
  /* CD .dc-val: 14.5px / 600 (no extra letter-spacing). */
  font-size: 14.5px;
  font-weight: 600;
  color: var(--tmb-ink);
  margin-top: 2px;
}

/* Apt / delivery-notes subline under the address recap value. */
.tmb-donecard-sub {
  font-size: 12.5px;
  font-weight: 500;
  color: var(--tmb-muted);
  margin-top: 3px;
  line-height: 1.35;
}

@media (max-width: 520px) {
  .tmb-care-selector {
    max-width: 100%;
  }
}

/* CD Screen 1b - pickup address confirmation card (.pc-*). Ported from
   Rapid Order (Official).html (_official.css .pc-* rules) so the confirm step
   matches CD; CD tokens mapped to impl tokens (--soft-surface -> --tmb-blue-soft,
   --primary -> --tmb-blue-dark which is now #0081B6, etc). */
.inline-form-card .pc-addr { display: flex; align-items: flex-start; gap: 12px; padding: 14px 16px 12px; }
.inline-form-card .pc-pin { width: 36px; height: 36px; border-radius: 11px; background: var(--tmb-blue-soft); color: var(--tmb-blue-dark); display: inline-flex; align-items: center; justify-content: center; flex-shrink: 0; }
.inline-form-card .pc-pin svg { width: 18px; height: 18px; }
.inline-form-card .pc-addr-text { flex: 1 1 auto; min-width: 0; }
.inline-form-card .pc-a { font-size: 15.5px; font-weight: 600; color: var(--tmb-ink); letter-spacing: -0.01em; line-height: 1.3; }
.inline-form-card .pc-sub { font-size: 12.5px; color: var(--tmb-muted); margin-top: 2px; }
.inline-form-card .pc-change { margin-left: auto; border: 0; background: transparent; color: var(--tmb-blue-dark); font-family: var(--tmb-font-body); font-weight: 600; font-size: 13px; cursor: pointer; padding: 4px; flex-shrink: 0; }
.inline-form-card .pc-fields { display: flex; flex-direction: column; gap: 12px; padding: 0 16px; }
.inline-form-card .pc-field { display: flex; flex-direction: column; }
.inline-form-card .pc-label { font-size: 12px; font-weight: 600; color: #71727a; margin-bottom: 6px; }
.inline-form-card .pc-label .opt { font-size: 11px; font-weight: 500; color: #a2a4a8; margin-left: 6px; }
.inline-form-card .pc-input { border: 0; box-shadow: inset 0 0 0 1px var(--tmb-divider); border-radius: 100px; background: #fff; height: 52px; padding: 0 18px; font-family: var(--tmb-font-body); font-size: 16px; font-weight: 400; color: var(--tmb-ink); transition: box-shadow .15s ease; width: 100%; }
.inline-form-card textarea.pc-input { border-radius: 20px; height: auto; min-height: 72px; padding: 12px 16px; line-height: 1.5; resize: none; }
.inline-form-card .pc-input::placeholder { color: #a2a4a8; }
.inline-form-card .pc-input:hover { box-shadow: inset 0 0 0 1px #A2A4A8; }
.inline-form-card .pc-input:focus { outline: 0; box-shadow: inset 0 0 0 2px var(--tmb-blue-dark); }
/* Selection-time coverage precheck interim state (blind-QA B05-001): the
   chosen address + Change, with a quiet status line - no fields, no Use. */
.inline-form-card .pc-checking { padding: 0 16px 16px; font-size: 13.5px; color: var(--tmb-muted); }
.inline-form-card .pc-foot { padding: 12px 16px 16px; }
.inline-form-card .pc-use { width: 100%; border: 0; background: var(--tmb-cta-bg); color: #fff; font-family: var(--tmb-font-body); font-weight: 600; font-size: 15px; height: 52px; border-radius: 999px; cursor: pointer; letter-spacing: -0.005em; transition: background .15s ease, transform 150ms ease-out, filter 150ms ease-out; }
.inline-form-card .pc-use:hover { background: var(--tmb-cta-bg-hover); }
.inline-form-card .pc-use:active { transform: scale(0.98); filter: brightness(0.94); }

/* CD "Pickup Out of Coverage" (2026-06-15): the out-of-area notice rendered
   inside the pickup card - the chosen address with a Change pencil, then an
   alert box linking the Service Coverage Area help article. No "Use this
   address", no waitlist; the composer stays locked. Ported from CD's
   Pickup Out of Coverage.html (.cov-* family). */
.inline-form-card[data-stage="coverage"] {
  /* COVERAGEFORMAT-1: contain the alert's final 16px margin so the approved
     bottom inset stays inside the rounded card during prior-step editing. */
  display: flow-root;
}
.inline-form-card .cov-head { display: flex; align-items: flex-start; gap: 12px; padding: 16px 16px 12px; }
.inline-form-card .cov-pin { width: 38px; height: 38px; border-radius: 11px; background: var(--tmb-blue-soft); color: var(--tmb-blue-dark); display: inline-flex; align-items: center; justify-content: center; flex-shrink: 0; }
.inline-form-card .cov-pin svg { width: 20px; height: 20px; }
.inline-form-card .cov-addr { flex: 1 1 auto; min-width: 0; font-size: 16px; font-weight: 600; color: var(--tmb-ink); letter-spacing: -0.01em; line-height: 1.3; }
.inline-form-card .cov-change { margin-left: auto; width: 34px; height: 34px; border-radius: 999px; border: 0; background: var(--tmb-blue-soft); color: var(--tmb-blue-dark); display: inline-flex; align-items: center; justify-content: center; cursor: pointer; flex-shrink: 0; transition: filter .15s ease; }
.inline-form-card .cov-change svg { width: 15px; height: 15px; }
.inline-form-card .cov-change:hover { filter: brightness(0.96); }
.inline-form-card .cov-alert { margin: 0 16px 16px; background: var(--tmb-page); border-radius: 12px; box-shadow: inset 0 0 0 1px var(--tmb-divider); padding: 16px; display: flex; gap: 12px; align-items: flex-start; }
.inline-form-card .cov-alert-ico { color: var(--tmb-secondary); flex-shrink: 0; margin-top: 1px; display: inline-flex; }
.inline-form-card .cov-alert-ico svg { width: 18px; height: 18px; }
.inline-form-card .cov-alert p { margin: 0; font-size: 14px; font-weight: 400; color: var(--tmb-muted); line-height: 1.55; }
.inline-form-card .cov-alert a { color: var(--tmb-blue-dark); font-weight: 600; text-decoration: underline; text-underline-offset: 2px; }

/* ORDERCARD-1: notes are plain muted text, never boxes, icons, or quoted
   sub-rows. Large clamps to two lines; Compact clamps to one. */
.tmb-step-note {
  padding: 0 0 14px 40px;
}

.tmb-step-note-text {
  display: -webkit-box;
  overflow: hidden;
  font-size: 12.5px;
  color: #585c62;
  line-height: 1.5;
  overflow-wrap: anywhere;
  -webkit-box-orient: vertical;
  -webkit-line-clamp: 2;
}

.tmb-step-note.is-expanded .tmb-step-note-text {
  display: block;
  overflow: visible;
  -webkit-line-clamp: unset;
}

.tmb-step-note-toggle {
  display: none;
  margin: 3px 0 0;
  padding: 0;
  border: 0;
  background: transparent;
  font-size: 12px;
  font-weight: 600;
  color: #0081B6;
  cursor: pointer;
}

.tmb-step-note.is-overflowing .tmb-step-note-toggle,
.tmb-step-note.is-expanded .tmb-step-note-toggle {
  display: inline;
}

.tmb-order-card.is-compact .tmb-step-note {
  display: flex;
  align-items: baseline;
  gap: 4px;
  padding-bottom: 7px;
}

.tmb-order-card.is-compact .tmb-step-note-text {
  display: block;
  min-width: 0;
  overflow: hidden;
  font-size: 12px;
  white-space: nowrap;
  text-overflow: ellipsis;
}

.tmb-order-card.is-compact .tmb-step-note.is-expanded {
  display: block;
}

.tmb-order-card.is-compact .tmb-step-note.is-expanded .tmb-step-note-text {
  white-space: normal;
  overflow: visible;
}

.tmb-sheet .tmb-step-note {
  padding: 3px 0 0;
}

.tmb-sheet.is-compact .tmb-step-note {
  display: flex;
  align-items: baseline;
  gap: 4px;
}

.tmb-sheet.is-compact .tmb-step-note-text {
  display: block;
  min-width: 0;
  overflow: hidden;
  font-size: 12px;
  white-space: nowrap;
  text-overflow: ellipsis;
}

.tmb-sheet.is-compact .tmb-step-note.is-expanded {
  display: block;
}

.tmb-sheet.is-compact .tmb-step-note.is-expanded .tmb-step-note-text {
  white-space: normal;
  overflow: visible;
}

/* Pre sign-in entry (CD adopted 2026-07-07, implemented 2026-07-09): quiet
 * sign-in line on blank-slate screens only (0, 0a-0d, M0), never signed-in.
 * Desktop: under the FB-01 bubble (in-log element). Mobile: after the inline
 * chips (post-chips element). One line, not a bubble or chip. */
.tmb-quiet-signin {
  margin: 14px 2px 0;
  color: var(--tmb-muted);
  font-size: 13.5px;
}
.tmb-quiet-signin-link {
  padding: 0;
  border: 0;
  background: none;
  color: var(--tmb-blue);
  font: inherit;
  font-weight: 600;
  cursor: pointer;
  text-decoration: none;
}
.tmb-quiet-signin-link:hover {
  color: var(--tmb-blue-pressed);
  text-decoration: underline;
}
[data-signin-quiet-mobile] { display: none; }
@media (max-width: 900px) {
  [data-signin-quiet] { display: none; }
  [data-signin-quiet-mobile] {
    display: block;
    /* SIGNINSPOT-1b ruling (b), CD 2026-07-22: the chip-to-line distance is
     * 10px TOTAL rect-to-rect. The log's 14px flex gap participates, so the
     * margin compensates: 14 - 4 = 10. Canon states totals now, not
     * margins, so gap-vs-margin composition can't drift again. */
    margin: -4px 2px 0;
    font-size: 12.5px;
  }
  .tmb-quiet-signin-link:hover { text-decoration: none; color: var(--tmb-blue); }
  /* SIGNINSPOT-1b round (CD, 2026-07-22): mobile eyebrow RENDERS sentence
   * case - CD explicitly corrected the earlier "uppercase render" reading
   * of its 2026-07-07 decision record. Desktop stays uppercase. */
  .tmb-eyebrow {
    font-size: 10px;
    font-weight: 700;
    letter-spacing: 0.18em;
    margin-bottom: 10px;
    text-transform: none;
  }
}

/* MOBILE-3 late-cascade companions for components whose base definitions
   intentionally live after the primary mobile contract block. */
/* MOBILE-3 late-cascade block (RO-065 2026-07-20: width-only, no coarse gate) */
@media (max-width: 900px) {
  .tmb-account-label {
    display: inline;
    max-width: 92px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
  }

  .tmb-account-chip {
    gap: 7px;
    padding: 0 10px 0 5px;
  }

  /* MOBILEGIB-1: mobile geometry keeps the shared bubble type scale. */
  .tmb-message {
    max-width: 306px;
    padding: 12px 16px;
    border-radius: 18px;
  }

  .tmb-message-bot {
    border-radius: 18px;
    border-top-left-radius: 6px;
  }

  .tmb-message-user {
    border-radius: 18px;
    border-top-right-radius: 6px;
  }

  /* SENDTIME-1 no-jank amendment: tappable reply controls enter without a
     geometry transform, so a fast tap cannot chase a moving target. */
  .tmb-chips button {
    animation-name: tmb-chip-in-opacity;
  }

  .ifc-head {
    color: #1d1e22;
  }

  .ifc-input {
    height: 46px;
    border-radius: 12px;
  }

  .ifc-clear {
    top: 16px;
  }

  .addr-pred {
    margin: 8px -18px -16px;
    border-radius: 0 0 16px 16px;
    box-shadow: none;
    border-top: 1px solid #DEE2E6;
  }

  .addr-pred-item {
    border-bottom: 1px solid #DEE2E6;
  }

  .inline-form-card .pc-foot {
    padding-top: 22px;
  }

  .tmb-auth-overlay {
    backdrop-filter: none;
    -webkit-backdrop-filter: none;
  }

  .tmb-auth-card {
    padding: 20px;
  }

  .tmb-auth-provider,
  .tmb-auth-submit {
    height: 48px;
  }

  .tmb-auth-submit {
    margin-top: 20px;
  }

  .tmb-otp-cell:focus {
    box-shadow: inset 0 0 0 2px var(--tmb-blue), 0 0 0 4px rgba(0,129,182,.15);
  }

  .tmb-safety-overlay {
    align-items: flex-end;
    padding: 0;
  }

  .tmb-safety-card {
    width: 100%;
    max-width: none;
    max-height: 92dvh;
    overflow-y: auto;
    border-radius: 28px 28px 0 0;
    padding: 12px 20px calc(24px + env(safe-area-inset-bottom, 0px));
    box-shadow: 0 -10px 40px -10px rgba(20,30,60,.25);
  }

  .tmb-safety-card::before {
    content: '';
    display: block;
    width: 40px;
    height: 4px;
    margin: 0 auto 16px;
    border-radius: 3px;
    background: #d6dae2;
  }

  .tmb-safety-close {
    display: none;
  }

  .tmb-safety-title {
    padding-right: 0;
  }
}

/* ===== PROGCHIP-1: the header progress chip (CD ProgressChip.Mobile, ruled
   2026-08-20; CHIPTONE-1 and CTASTACK-1, Cliff 2026-08-21). Mobile only - the
   desktop card is unchanged and the chip never renders there. ===== */
.tmb-progress-chip {
  display: none;
}
@media (max-width: 900px) {
  /* The chip: 30px painted, 44px touched (::after - the same fix the composer
     send got, so "zero added height" survives the touch floor), sized to its
     content, left of Help. One treatment in every state: blue ring, ink
     label, white pill - no green at Ready, no amber while editing; the ring
     closing is the whole Ready signal. */
  .tmb-progress-chip {
    display: inline-flex;
    align-items: center;
    gap: 7px;
    height: 30px;
    padding: 0 10px;
    border: 0;
    border-radius: 999px;
    background: #fff;
    box-shadow: 0 1px 2px rgba(20,30,60,.04), 0 0 0 1px #DEE2E6;
    color: var(--tmb-ink);
    font-family: var(--tmb-font-body);
    font-size: 12.5px;
    font-weight: 700;
    letter-spacing: -0.005em;
    line-height: 1;
    white-space: nowrap;
    position: relative;
    cursor: pointer;
    flex-shrink: 0;
    -webkit-tap-highlight-color: transparent;
    /* CD verdict 2026-08-21 on the device measurement: two 44px targets need
       their centres 44px apart, so the painted gap to Help is 14px (the
       header's own 6px plus 8px here), and Help gets a 44px target too. */
    margin-right: 8px;
  }
  .tmb-progress-chip[hidden] {
    display: none;
  }
  .tmb-progress-chip::after {
    content: "";
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    width: calc(100% + 14px);
    height: 44px;
    border-radius: 999px;
  }
  .tmb-progress-chip:focus-visible {
    outline: none;
    box-shadow: 0 1px 2px rgba(20,30,60,.04), 0 0 0 1px #DEE2E6, var(--tmb-focus);
  }
  .tmb-progress-chip-ring {
    width: 20px;
    height: 20px;
    display: block;
    flex-shrink: 0;
  }
  .tmb-progress-chip-arc {
    transition: stroke-dashoffset 200ms cubic-bezier(.2,.7,.3,1);
  }
  .tmb-progress-chip-ct {
    font-variant-numeric: tabular-nums;
  }
  .tmb-progress-chip-ct:empty {
    display: none;
  }
  .tmb-progress-chip-chev {
    color: #9aa0a8;
    flex-shrink: 0;
    transition: transform 200ms cubic-bezier(.2,.7,.3,1);
  }
  .tmb-progress-chip[aria-expanded="true"] .tmb-progress-chip-chev {
    transform: rotate(180deg);
  }

  /* CTASTACK-1: while Place order sits above it, the composer goes ghost -
     transparent, hairline ring, muted placeholder and send - so Ready still
     has exactly one solid action (locked #11). Specificity matches the
     touch-shell idle composer chain above; source order settles the tie. */
  .tmb-page.tmb-touch-shell .tmb-mobile-dock .tmb-composer.is-ghost[data-chat-form] {
    background: transparent;
    box-shadow: inset 0 0 0 1px #DEE2E6;
  }
  .tmb-page.tmb-touch-shell .tmb-mobile-dock .tmb-composer.is-ghost[data-chat-form] .tmb-input[data-chat-input]::placeholder {
    color: #71727A;
  }
  .tmb-page.tmb-touch-shell .tmb-mobile-dock .tmb-composer.is-ghost[data-chat-form] .tmb-input[data-chat-input] {
    color: #71727A;
  }
  .tmb-page.tmb-touch-shell .tmb-mobile-dock .tmb-composer.is-ghost[data-chat-form] .tmb-send {
    background: #eaf2ff;
    color: #a7abb3;
  }
  .tmb-page.tmb-touch-shell .tmb-mobile-dock .tmb-composer.is-ghost[data-chat-form] .tmb-caret {
    display: none;
  }
}
@media (prefers-reduced-motion: reduce) {
  .tmb-progress-chip-chev,
  .tmb-progress-chip-arc {
    transition: none;
  }
}

/* Act 4 (CD Transitions.WashProsAfterSignIn 12a, 2026-08-20): Place order
   means "take me to checkout", and checkout arrives as a 200ms crossfade in
   which the header does not move - the logo, Help and the account chip
   persist at their pixels while only the region below changes. No push, no
   parallax; checkout opens at its own top. Cross-document view transitions
   do exactly that for the same-origin chat -> /checkout navigation (and the
   Edit return): the old page's last frame, placing scrim included, fades
   into the new page over 200ms ease-out, and the three named bar elements
   are matched across the two documents and hold still (both pages load this
   sheet and both bars carry the same markup). Browsers without
   cross-document transitions cut as they always did. */
@view-transition {
  navigation: auto;
}
::view-transition-old(root),
::view-transition-new(root) {
  animation-duration: 200ms;
  animation-timing-function: ease-out;
}
.tmb-brand-logo {
  view-transition-name: tmb-brand-logo;
}
.tmb-topbar-actions > .tmb-help,
.tmb-checkout-topbar-actions > .tmb-help {
  view-transition-name: tmb-help;
}
.tmb-account {
  view-transition-name: tmb-account;
}
::view-transition-group(tmb-brand-logo),
::view-transition-group(tmb-help),
::view-transition-group(tmb-account),
::view-transition-old(tmb-brand-logo),
::view-transition-new(tmb-brand-logo),
::view-transition-old(tmb-help),
::view-transition-new(tmb-help),
::view-transition-old(tmb-account),
::view-transition-new(tmb-account) {
  animation-duration: 0s;
}
@media (prefers-reduced-motion: reduce) {
  ::view-transition-group(*),
  ::view-transition-old(*),
  ::view-transition-new(*) {
    animation: none !important;
  }
}

/* TOPBARFIT-1 (2026-08-21, wired iPhone 15, signed in): with the progress
   chip, Help and the account chip all in the 393px bar, the actions row ran
   266px wide and the chip sat over the logo ("Tumb" clipped at 107 against a
   logo that ends at 120). The brand never shrinks (an image overflows instead
   of giving), so the actions row must: the chip and Help hold their size and
   the account label gives way first, ellipsizing, so nothing ever overlaps
   the logo. Desktop and the signed-out bar are untouched. Seen only signed in
   - every PROGCHIP-1 device walk ran signed out. */
@media (max-width: 767px) {
  .tmb-topbar-inner > .tmb-brand {
    flex: 0 0 auto;
  }
  .tmb-topbar-actions,
  .tmb-checkout-topbar-actions {
    flex: 1 1 auto;
    min-width: 0;
  }
  .tmb-account {
    min-width: 0;
  }
  .tmb-account-chip {
    max-width: 100%;
  }
  .tmb-account-label {
    flex: 1 1 auto;
    min-width: 0;
  }
}

/* BARNAME-1 (Cliff 2026-08-22, CD Transitions.WashProsAfterSignIn .acct.pill)
   supersedes BARFIT-1's avatar-only chip on phones: the signed-in control is
   a WHITE PILL - avatar, first name, caret - 34px tall, 2px 10px 2px 3px
   padding, 999 radius, a 1px #E9EAEB ring, a 26px avatar, the caret in
   #9aa0a8; the same menu on tap; the 44px tap target stays (34 + 5 + 5).
   The full logo stays (Cliff, BARFIT-1). The action group is still
   [progress chip] 14 [Help 38] 14 [pill], so the name is CLAMPED (max 64px,
   ellipsis) - the bar's geometry must not depend on how long a name is
   (BARFIT-1's reason), and a 393px bar at Ready ("$43" chip) keeps a few
   pixels between the logo and the chip with a short name. The 6px actions
   gap plus this 8px margin is the ruled 14px between Help and the pill. */
@media (max-width: 479px) {
  .tmb-account {
    margin-left: 8px;
  }
  .tmb-account-chip {
    position: relative;
    height: 34px;
    min-width: 34px;
    max-width: 140px;
    padding: 2px 10px 2px 3px;
    gap: 7px;
    border: 0;
    border-radius: var(--tmb-radius-full);
    background: #fff;
    box-shadow: 0 0 0 1px #E9EAEB;
    justify-content: center;
  }
  .tmb-account-chip::after {
    content: '';
    position: absolute;
    inset: -5px;
    border-radius: var(--tmb-radius-full);
  }
  .tmb-account-chip:hover,
  .tmb-account-chip[aria-expanded="true"] {
    background: #fff;
    border-color: transparent;
  }
  /* BARSPEC-1 (CD 2026-08-22): avatar 28 (not 26), name 13/600 clamped at
     96px with an ellipsis as a long-name guard only, caret 10 never drops. */
  .tmb-account-avatar {
    flex: 0 0 28px;
    width: 28px;
    height: 28px;
    font-size: 14px;
  }
  /* BARCROSS-1 (CD ruling 2026-08-22, design-specs/cd/CLAUDE.md): with the
     icon mark alone on the phone bar (MARKONLY-1) the full first name fits -
     the account pill is 118px at 393 and 375, the same width on the chat and
     on checkout so nothing re-lays out through the arrival crossfade; the
     ellipsis stays only as a guard for long names, pill max 140px. (The
     interim BARNAME-1b avatar-only pill is retired with the word mark.) */
  .tmb-account-label {
    display: inline-block;
    min-width: 0;
    max-width: 96px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
    font-size: 13px;
    font-weight: 600;
    color: var(--tmb-ink);
  }
  .tmb-account-caret {
    display: inline-flex;
    color: #9aa0a8;
    flex-shrink: 0;
  }
}

/* BARFIT-1b / 1c (CD confirmation rounds 2026-08-21): on a phone the account
   menu's edge cut straight through the bubble behind it and the two read as
   one shape. It takes the kebab menu's soft drop - the Order Card's
   .tmb-card-menu shadow, a 12px/30px drop at 25% plus the divider ring. The
   sheet kebab's hairline (round 1b) was not enough separation over a bubble. */
@media (max-width: 767px) {
  .tmb-account-menu {
    box-shadow: 0 12px 30px -10px rgba(20, 30, 60, 0.25), 0 0 0 1px var(--tmb-divider);
  }
}
