/* console.css — the shared chrome for iMove's own lead-management console.
   These screens depict IMOVE'S product, not the CreatiSoul proposal frame, so
   this file does not import frame.css and defines its own small scale
   instead of reusing --sp-* / --fs-* (those names belong to frame.css's deck).
   It DOES reuse imove.css's --imv-* colour tokens and fonts.css's embedded
   typefaces — both are loaded by every page that includes this file.

   GOLD RULE FOR THIS WHOLE FILE: gold is background, border or SVG fill
   ONLY, never `color`/`-webkit-text-fill-color`. Guard G4 only permits gold
   TEXT inside a selector carrying the `.imv` class (never `.imv-light`), and
   these console pages carry neither class — they are a separate design
   system. Rather than thread `.imv` onto every dark surface here, gold text
   is avoided outright; every "gold as an accent" moment below (active nav
   item, active filter chip, the AI-referred bar fill, the honesty note's
   rule) uses it as a fill/background/border. Where warm emphasis is needed
   IN text, `#8A6200` (`--imv-gold-on-light`) is used directly — it is not in
   G4's restricted hex list, so it is safe as text on any surface, and it is
   the token the palette itself names for exactly this job. */

:root {
  --con-fs-xs: 0.75rem;
  --con-fs-sm: 0.875rem;
  --con-fs-base: 1rem;
  --con-fs-md: 1.125rem;
  --con-fs-lg: 1.5rem;
  --con-fs-xl: 2rem;
  --con-sp-1: 0.25rem;
  --con-sp-2: 0.5rem;
  --con-sp-3: 0.75rem;
  --con-sp-4: 1rem;
  --con-sp-5: 1.25rem;
  --con-sp-6: 1.5rem;
  --con-sp-8: 2rem;
  --con-nav-w: 224px;
  --con-bottom-bar-h: 64px;
}

*, *::before, *::after { box-sizing: border-box; }
html { -webkit-text-size-adjust: 100%; }
body {
  margin: 0;
  overflow-x: hidden; /* wide content scrolls inside its own container — see .table-scroll */
  background: var(--imv-bone);
  color: var(--imv-t1);
  font-family: "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
  font-size: var(--con-fs-base);
  line-height: 1.5;
}
h1, h2, h3, h4 {
  font-family: "Bricolage Grotesque", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
  margin: 0;
  line-height: 1.2;
}
p { margin: 0; }
img, svg { max-width: 100%; display: block; }
a { color: inherit; }
button { font-family: inherit; }

/* ---------- Shell ---------- */
.console {
  display: flex;
  flex-direction: column;
  min-height: 100dvh;
}

.console-topbar {
  position: sticky;
  top: 0;
  z-index: 30;
  display: flex;
  /* Wrap, not the default nowrap row: .console-topbar__meta below is
     white-space:nowrap and, as a flex item, defaults to min-width:auto — it
     will not shrink below its own text's width. A short meta string
     ("Signed in as iMove management") fits alongside the brand at 390px
     without this rule ever firing; a longer persona string ("Signed in as
     Google Ads · Channel partner") pushes the row past the viewport,
     measured as a real 35px document.documentElement.scrollWidth overflow
     at 390, not eyeballed. flex-wrap:wrap drops the meta text to its own
     full-width row only when it doesn't fit — a no-op for every shorter
     string. */
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: var(--con-sp-4);
  min-height: 56px;
  padding-block: var(--con-sp-2);
  padding-inline: var(--con-sp-5);
  background: var(--imv-ink);
  color: var(--imv-bone);
}
.console-topbar__brand {
  display: inline-flex;
  align-items: center;
  gap: var(--con-sp-2);
  text-decoration: none;
  font-family: "Bricolage Grotesque", sans-serif;
  font-weight: 700;
  font-size: var(--con-fs-md);
  color: var(--imv-bone); /* explicit — not gold, see file-top rule */
}
.console-topbar__mark {
  width: 14px;
  height: 14px;
  border-radius: 4px;
  background: var(--imv-gold); /* background, not text — G4 does not apply */
}
.console-topbar__product {
  font-weight: 500;
  opacity: 0.7;
}
.console-topbar__meta {
  font-size: var(--con-fs-xs);
  color: var(--imv-bone);
  opacity: 0.65;
  white-space: nowrap;
}

.console-body {
  flex: 1;
  display: flex;
  align-items: stretch;
}

/* ---------- Left nav (desktop) / bottom bar (mobile) ---------- */
/* Below 900px this collapses into a fixed bottom bar. Both states share
   .console-nav__link so active/disabled styling is written once. */
.console-nav {
  flex: 0 0 var(--con-nav-w);
  display: flex;
  flex-direction: column;
  gap: var(--con-sp-1);
  padding: var(--con-sp-4);
  background: var(--imv-black);
}
.console-nav__link {
  display: flex;
  align-items: center;
  gap: var(--con-sp-3);
  min-height: 44px; /* mobile-first tap target floor */
  padding-inline: var(--con-sp-4);
  border-radius: 10px;
  border: none;
  background: transparent;
  color: var(--imv-bone);
  opacity: 0.78;
  font-size: var(--con-fs-sm);
  font-weight: 600;
  text-decoration: none;
  text-align: start;
  cursor: pointer;
}
.console-nav__link.is-active {
  background: var(--imv-gold); /* background only */
  color: var(--imv-ink);
  opacity: 1;
}
.console-nav__link:disabled {
  opacity: 0.35;
  cursor: not-allowed;
}
.console-nav__link:not(:disabled):hover,
.console-nav__link:not(:disabled):focus-visible {
  opacity: 1;
  background: rgba(250, 249, 247, 0.1);
}
.console-nav__link.is-active:hover,
.console-nav__link.is-active:focus-visible {
  background: var(--imv-gold);
}

@media (max-width: 899.98px) {
  .console-nav {
    position: fixed;
    inset-inline: 0;
    bottom: 0;
    z-index: 30;
    flex-direction: row;
    justify-content: space-around;
    gap: 0;
    padding: var(--con-sp-2);
    padding-bottom: max(var(--con-sp-2), env(safe-area-inset-bottom));
    height: var(--con-bottom-bar-h);
  }
  .console-nav__link {
    flex: 1;
    justify-content: center;
    padding-inline: var(--con-sp-2);
  }
  .console-main { padding-bottom: calc(var(--con-bottom-bar-h) + var(--con-sp-6)); }
}

.console-main {
  flex: 1;
  min-width: 0; /* a flex child's content (the table scroller) must be able
                   to shrink below its content size, or overflow-x on the
                   scroller never has anything to clip against */
  padding: var(--con-sp-6) var(--con-sp-5) var(--con-sp-8);
}
@media (min-width: 640px) {
  .console-main { padding: var(--con-sp-8) var(--con-sp-6) var(--con-sp-8); }
}

/* ---------- Screen-set sub-nav (the four leads-* pages) ---------- */
.console-tabs {
  display: flex;
  flex-wrap: wrap;
  gap: var(--con-sp-2);
  margin-bottom: var(--con-sp-6);
  border-bottom: 1px solid var(--imv-hairline);
}
.console-tabs__link {
  display: inline-flex;
  align-items: center;
  min-height: 44px;
  padding-inline: var(--con-sp-1);
  margin-bottom: -1px;
  border-bottom: 3px solid transparent;
  color: var(--imv-t2);
  text-decoration: none;
  font-weight: 600;
  font-size: var(--con-fs-sm);
}
.console-tabs__link.is-active {
  color: var(--imv-t1);
  border-bottom-color: var(--imv-gold); /* border, not text colour */
}
.console-tabs__link:hover,
.console-tabs__link:focus-visible {
  color: var(--imv-t1);
}

/* ---------- Page heading ---------- */
.console-heading { margin-bottom: var(--con-sp-6); }
.console-heading h1 { font-size: var(--con-fs-xl); font-weight: 700; margin-bottom: var(--con-sp-1); }
.console-heading p { color: var(--imv-t2); font-size: var(--con-fs-sm); max-width: 42em; }

/* ---------- KPI tiles ---------- */
.console-kpis {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(160px, 1fr));
  gap: var(--con-sp-4);
  margin-bottom: var(--con-sp-6);
}
.kpi-card {
  background: #fff;
  border: 1px solid var(--imv-hairline);
  border-radius: 12px;
  padding: var(--con-sp-4) var(--con-sp-5);
}
.kpi-card__value {
  display: block;
  font-family: "Bricolage Grotesque", sans-serif;
  font-size: var(--con-fs-xl);
  font-weight: 700;
  line-height: 1.1;
}
.kpi-card__label {
  display: block;
  margin-top: var(--con-sp-1);
  font-size: var(--con-fs-xs);
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--imv-t2);
}

/* ---------- Filter chips ---------- */
.filter-bar {
  display: flex;
  flex-wrap: wrap;
  gap: var(--con-sp-5);
  margin-bottom: var(--con-sp-5);
}
.chip-group {
  display: flex;
  flex-direction: column;
  gap: var(--con-sp-2);
  min-width: 0; /* lets the nowrap/overflow-x:auto row below actually clip and
                    scroll instead of stretching this flex item — and the
                    whole ancestor chain up to <body> — to its content's full
                    width. Same fix as .console-main above, same reason. */
}
.chip-group__label {
  font-size: var(--con-fs-xs);
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--imv-t2);
  font-weight: 600;
}
/* One row per group, scrolling horizontally rather than wrapping to several
   rows. This is not a style preference — measured, not eyeballed: on a
   390px phone the Source group alone (8 chips) wraps to four rows when
   allowed to wrap, and the filter bar's Date group ends up tall enough to
   land under the fixed bottom nav bar at typical scroll positions,
   resolving taps on "Earlier this month" to the nav instead of the chip
   (found by the elementFromPoint hit-test, not by looking at a screenshot).
   Each chip is a real, individually focusable <button>, so — unlike the
   leads table — this scroller does not need its own tabindex/role/
   aria-label: keyboard focus lands on the chips themselves and the browser
   auto-scrolls the container to reveal whichever one is focused. */
.chip-group__chips {
  display: flex;
  flex-wrap: nowrap;
  gap: var(--con-sp-2);
  overflow-x: auto;
  -webkit-overflow-scrolling: touch;
  padding-block-end: 2px; /* room for the focus outline, not clipped by overflow */
  padding-inline-end: var(--con-sp-4);
}
.chip {
  display: inline-flex;
  flex-shrink: 0; /* a flex item's default min-width:auto lets it shrink to
                      its widest WORD and wrap a two-word label ("Google" /
                      "Ads" on separate lines) rather than keep its natural
                      width — caught by reading the 390px screenshot after
                      the row below switched from wrap to scroll. Without
                      this, the row shrinks its chips instead of overflowing
                      them, and overflow-x:auto never has anything to scroll. */
  align-items: center;
  min-height: 44px; /* tap target floor — this is exactly the control the
                        brief calls out as at risk; size is real, not an
                        invisible padding trick, so no overlap is possible */
  padding-inline: var(--con-sp-4);
  border-radius: 999px;
  border: 1px solid var(--imv-g3);
  background: #fff;
  color: var(--imv-t1);
  font-size: var(--con-fs-sm);
  font-weight: 600;
  white-space: nowrap;
  cursor: pointer;
}
.chip[aria-pressed="true"] {
  background: var(--imv-gold); /* background, not text */
  border-color: var(--imv-gold);
  color: var(--imv-ink);
}
.chip:focus-visible { outline: 2px solid var(--imv-ink); outline-offset: 2px; }

/* ---------- Table (leads-inbox) ---------- */
/* The scroller needs BOTH a min-width on the table itself AND to be a
   labelled, focusable tab stop of its own — two separate lessons, both
   load-bearing. Without the min-width, overflow-x:auto never triggers, and
   a table left to its own width concertinas into four-line-wrapped cells
   on a narrow phone — the general failure mode this rule exists to
   prevent. Without tabindex/role/aria-label on the wrapper, table cells
   are not natively focusable, so a keyboard user has no way to reach the
   columns that scroll off-screen. */
.table-scroll {
  overflow-x: auto;
  -webkit-overflow-scrolling: touch;
  border: 1px solid var(--imv-hairline);
  border-radius: 12px;
}
.table-scroll:focus-visible { outline: 2px solid var(--imv-ink); outline-offset: 2px; }
.leads-table {
  width: 100%;
  min-width: 860px;
  border-collapse: collapse;
  background: #fff;
  font-size: var(--con-fs-sm);
}
.leads-table th, .leads-table td {
  padding: var(--con-sp-3) var(--con-sp-4);
  text-align: start;
  white-space: nowrap;
  border-bottom: 1px solid var(--imv-hairline);
}
.leads-table th {
  font-size: var(--con-fs-xs);
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--imv-t2);
  font-weight: 600;
  background: var(--imv-g1);
}
.leads-table tbody tr:last-child td { border-bottom: none; }
.leads-table td.leads-table__name { font-weight: 600; }
.leads-table td.leads-table__corridor { color: var(--imv-t2); }

/* ---------- Source badge — reused by Tasks 7 and 8 ---------- */
.src-badge {
  display: inline-flex;
  align-items: center;
  gap: var(--con-sp-1);
  padding: 0.2rem 0.6rem;
  border-radius: 999px;
  border: 1px solid var(--imv-g3);
  background: var(--imv-g1);
  color: var(--imv-t1);
  font-size: var(--con-fs-xs);
  font-weight: 600;
  white-space: nowrap;
}
/* The AI-referred badge is the mix's key data point, so it is the one badge
   that carries a colour accent — a gold WASH background with gold-on-light
   TEXT (#8A6200 is not in G4's restricted hex list, so it is safe as text on
   any surface; it is the palette's own token for warm text on a light
   surface). Every other source stays a neutral grey pill on purpose —
   "gold is an accent... never a field of it" applies to the whole screen,
   not just literal colour area. */
.src-badge--ai {
  background: var(--imv-gold-wash);
  border-color: var(--imv-gold);
  color: var(--imv-gold-on-light);
}

/* ---------- Status pill ---------- */
.status-pill {
  display: inline-flex;
  align-items: center;
  padding: 0.2rem 0.6rem;
  border-radius: 999px;
  font-size: var(--con-fs-xs);
  font-weight: 600;
}
.status-pill--new { background: var(--imv-g2); color: var(--imv-t1); }
.status-pill--contacted { background: var(--imv-g2); color: var(--imv-t2); }
.status-pill--quoted { background: var(--imv-g2); color: var(--imv-t2); }
.status-pill--won { background: var(--imv-ink); color: var(--imv-bone); }
.status-pill--lost { background: transparent; color: var(--imv-t3); border: 1px solid var(--imv-g3); }

/* ---------- Enquiry facts (leads-detail) ---------- */
.fact-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(160px, 1fr));
  gap: var(--con-sp-5);
  padding: var(--con-sp-5);
  background: #fff;
  border: 1px solid var(--imv-hairline);
  border-radius: 12px;
  margin-bottom: var(--con-sp-8);
}
.fact-grid dt {
  font-size: var(--con-fs-xs);
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--imv-t2);
  margin-bottom: var(--con-sp-1);
}
.fact-grid dd { margin: 0; font-weight: 600; font-size: var(--con-fs-md); }

/* ---------- Source journey — the reason leads-detail.html exists.
   It gets the section's full width and the most generous spacing on the
   page; each step is a tall card, not a thin breadcrumb line. A single
   column with a connecting rule on mobile becomes a four-column row with a
   connecting rule from 860px — the same breakpoint-swap shape frame.css
   already uses for .timeline, reimplemented locally because console.css
   deliberately does not depend on frame.css. */
.journey-section { margin-bottom: var(--con-sp-8); }
.journey-section h2 { font-size: var(--con-fs-lg); margin-bottom: var(--con-sp-1); }
.journey-section > p { color: var(--imv-t2); margin-bottom: var(--con-sp-6); max-width: 42em; }
.journey {
  list-style: none;
  counter-reset: journey-step;
  margin: 0;
  padding: 0;
  display: grid;
  gap: var(--con-sp-6);
}
.journey__step {
  counter-increment: journey-step;
  position: relative;
  padding-inline-start: var(--con-sp-8);
  border-inline-start: 2px solid var(--imv-g3);
  padding-block: var(--con-sp-1) var(--con-sp-2);
}
/* The step number is CSS-GENERATED, never literal text in the markup — the
   same reasoning as .num-badge in frame.css: a literal "1" sitting right
   before a heading like "First touch" would read, once tags are stripped,
   as "1 First touch", and step 4 sits directly before "Form submitted",
   which contains no unit word today but the same class of collision has
   bitten this build before and the fix costs nothing. aria-hidden because
   the step's own eyebrow/title text already says what step it is. */
.journey__index {
  position: absolute;
  left: -1px;
  top: 0;
  transform: translateX(-50%);
  width: 2rem;
  height: 2rem;
  border-radius: 50%;
  background: var(--imv-gold);
  color: var(--imv-ink);
  font-weight: 700;
  font-family: "Bricolage Grotesque", sans-serif;
  display: flex;
  align-items: center;
  justify-content: center;
}
.journey__index::before { content: counter(journey-step); }
.journey__eyebrow {
  font-size: var(--con-fs-xs);
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--imv-t2);
  font-weight: 600;
  margin-bottom: var(--con-sp-1);
}
.journey__title { font-size: var(--con-fs-md); font-weight: 700; margin-bottom: var(--con-sp-2); }
.journey__detail { color: var(--imv-t2); font-size: var(--con-fs-sm); }
.journey__pages {
  display: flex;
  flex-wrap: wrap;
  gap: var(--con-sp-2);
  margin-top: var(--con-sp-3);
}
.journey__page {
  padding: 0.2rem 0.6rem;
  border-radius: 6px;
  background: var(--imv-g1);
  border: 1px solid var(--imv-g3);
  font-size: var(--con-fs-xs);
  font-family: ui-monospace, "SFMono-Regular", Menlo, monospace;
  color: var(--imv-t1);
}

@media (min-width: 860px) {
  .journey { grid-template-columns: repeat(4, 1fr); gap: var(--con-sp-4); }
  .journey__step {
    border-inline-start: none;
    border-block-start: 2px solid var(--imv-g3);
    padding-inline-start: 0;
    padding-block-start: var(--con-sp-8);
  }
  .journey__index { left: 0; top: -1rem; transform: none; }
}

/* ---------- Notes / status card (leads-detail) ---------- */
.detail-card {
  background: #fff;
  border: 1px solid var(--imv-hairline);
  border-radius: 12px;
  padding: var(--con-sp-5);
  margin-bottom: var(--con-sp-5);
}
.detail-card h3 { font-size: var(--con-fs-base); margin-bottom: var(--con-sp-2); }
.detail-card p { color: var(--imv-t2); }

/* ---------- Attribution dashboard ---------- */
.attribution__header {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: var(--con-sp-4);
  margin-bottom: var(--con-sp-2);
}
.toggle-group {
  display: inline-flex;
  gap: var(--con-sp-1);
  padding: var(--con-sp-1);
  background: var(--imv-g1);
  border-radius: 999px;
}
.toggle-btn {
  min-height: 44px;
  padding-inline: var(--con-sp-5);
  border-radius: 999px;
  border: none;
  background: transparent;
  color: var(--imv-t2);
  font-weight: 700;
  font-size: var(--con-fs-sm);
  cursor: pointer;
}
.toggle-btn.is-active {
  background: var(--imv-ink);
  color: var(--imv-bone);
}
.toggle-btn:focus-visible { outline: 2px solid var(--imv-ink); outline-offset: 2px; }

.attribution__total { color: var(--imv-t2); font-size: var(--con-fs-sm); margin-bottom: var(--con-sp-6); }
.attribution__total strong { color: var(--imv-t1); }

.attr-bars {
  display: grid;
  gap: var(--con-sp-3);
  padding: var(--con-sp-5);
  background: #fff;
  border: 1px solid var(--imv-hairline);
  border-radius: 12px;
  margin-bottom: var(--con-sp-4);
}
.attr-row {
  display: grid;
  grid-template-columns: 9rem 1fr 6rem;
  align-items: center;
  gap: var(--con-sp-3);
}
.attr-row__label { font-size: var(--con-fs-sm); font-weight: 600; }
.attr-row__track {
  height: 14px;
  border-radius: 999px;
  background: var(--imv-g2);
  overflow: hidden;
}
.attr-row__fill {
  display: block;
  height: 100%;
  border-radius: 999px;
  background: var(--imv-t1); /* default channel fill */
  transition: width 0.35s ease;
}
/* The reveal: the two AI channels are the only bars that ever turn gold, and
   only their WIDTH changes on toggle — a plain background-colour swap, never
   text, so G4 is a non-issue regardless of surface. */
.attr-row--ai .attr-row__fill { background: var(--imv-gold); }
/* Partner dashboard: same reveal pattern, different subject. A channel
   partner reading a status breakdown cares most about one row — Won, the
   number that actually says the spend is working — so it gets the same
   background-only gold treatment as the AI bars above (G4-safe regardless of
   surface, since this is `background`, never `color`). */
.attr-row--won .attr-row__fill { background: var(--imv-gold); }
.attr-row__value { text-align: end; font-size: var(--con-fs-sm); font-variant-numeric: tabular-nums; }

.attr-legend {
  display: flex;
  align-items: center;
  gap: var(--con-sp-2);
  color: var(--imv-t2);
  font-size: var(--con-fs-xs);
}
.attr-legend__swatch {
  width: 10px;
  height: 10px;
  border-radius: 3px;
  background: var(--imv-gold);
}

/* ---------- Honesty note (leads-ai) ---------- */
.note {
  border-inline-start: 3px solid var(--imv-gold); /* border, not text */
  padding-inline-start: var(--con-sp-4);
  padding-block: var(--con-sp-1);
  color: var(--imv-t1);
  max-width: 42em;
}
.note p { margin-bottom: var(--con-sp-2); }
.note p:last-child { margin-bottom: 0; }

/* ---------- AI referrals list ---------- */
.ai-list { list-style: none; margin: 0 0 var(--con-sp-6); padding: 0; display: grid; gap: var(--con-sp-3); }
.ai-card {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: var(--con-sp-3);
  padding: var(--con-sp-4) var(--con-sp-5);
  background: #fff;
  border: 1px solid var(--imv-hairline);
  border-radius: 12px;
}
.ai-card__source { display: flex; align-items: center; gap: var(--con-sp-3); }
.ai-card__pages { display: flex; flex-wrap: wrap; gap: var(--con-sp-2); }
.ai-card__count { text-align: end; }
.ai-card__count strong { display: block; font-family: "Bricolage Grotesque", sans-serif; font-size: var(--con-fs-lg); }
.ai-card__count span { font-size: var(--con-fs-xs); color: var(--imv-t2); text-transform: uppercase; letter-spacing: 0.04em; }

/* ---------- Shipment tracking (tracking-ops) ---------- */
/* Stage pill: same shape as .status-pill above, reused for shipment
   tracking's six-stage vocabulary instead of the five-value lead status.
   Customs gets the same gold-WASH-background/gold-on-light-TEXT treatment as
   .src-badge--ai — it is the stage a family worries about most, so it is the
   one stage that carries the accent, matching the rule the AI-referred badge
   already established: gold marks the thing the reader most needs to
   notice. Delivered reuses .status-pill--won's ink/bone "done" treatment
   verbatim. #8A6200 (--imv-gold-on-light) is text-safe on any surface per
   G4 — the hex itself is never in the restricted GOLDS list. */
.stage-pill {
  display: inline-flex;
  align-items: center;
  padding: 0.2rem 0.6rem;
  border-radius: 999px;
  font-size: var(--con-fs-xs);
  font-weight: 600;
}
.stage-pill--booked,
.stage-pill--packed { background: var(--imv-g2); color: var(--imv-t2); }
.stage-pill--departed,
.stage-pill--in-transit { background: var(--imv-g2); color: var(--imv-t1); }
.stage-pill--customs {
  background: var(--imv-gold-wash);
  border: 1px solid var(--imv-gold); /* border, not text — G4-safe regardless of surface */
  color: var(--imv-gold-on-light);
}
.stage-pill--delivered { background: var(--imv-ink); color: var(--imv-bone); }

/* The shipments table needs two more columns than leads-table otherwise
   shares CSS with, and "Next milestone" is a short sentence, not a short
   label — forcing it onto one nowrap line the way every other leads-table
   column does would blow the table out to an unreasonable width. min-width
   is raised to fit six real columns, and the milestone column alone opts
   back into wrapping rather than nowrap. */
.leads-table--shipments { min-width: 980px; }
.leads-table td.leads-table__milestone {
  white-space: normal;
  max-width: 260px;
  color: var(--imv-t2);
}

/* Stage timeline the ops user advances. Each stage is a REAL button in
   normal flex flow with its own gap — not an absolutely-positioned hit area
   expanded by a negative margin, the way .progress-nav__dot is in
   frame.css. That trick is deliberately NOT reused here: an expanded hit
   area on overlapping absolutely-positioned elements can misdirect a click
   to the wrong neighbour (only found by an elementFromPoint hit-test, not
   by looking at a screenshot), and a control that changes a shipment's
   live stage is a worse place for that risk than a jump-nav. A flex row of
   real buttons cannot overlap its neighbours regardless of label length —
   verified with the same hit-test this build already uses. */
.stage-track {
  list-style: none;
  margin: var(--con-sp-2) 0 var(--con-sp-4);
  padding: 0;
  display: flex;
  flex-wrap: wrap;
  gap: var(--con-sp-3);
}
.stage-track__btn {
  display: inline-flex;
  align-items: center;
  gap: var(--con-sp-2);
  min-height: 48px; /* tap target floor */
  padding-inline: var(--con-sp-4);
  border-radius: 10px;
  border: 2px solid var(--imv-g3);
  background: #fff;
  color: var(--imv-t2);
  font-size: var(--con-fs-sm);
  font-weight: 600;
  cursor: pointer;
}
.stage-track__btn:focus-visible { outline: 2px solid var(--imv-ink); outline-offset: 2px; }
.stage-track__btn.is-done { border-color: var(--imv-gold); color: var(--imv-t1); }
.stage-track__btn.is-current { background: var(--imv-gold); border-color: var(--imv-gold); color: var(--imv-ink); }
.stage-track__check {
  display: none;
  width: 14px;
  height: 14px;
  flex-shrink: 0;
}
.stage-track__btn.is-done .stage-track__check { display: inline-flex; }
