/* ============================================================
   Buildtron Trip Tickets — components.css
   Strict BEM naming. All values reference design tokens.
   ============================================================ */

/* ------------------------------------------------------------
   Design tokens
   ------------------------------------------------------------ */
:root {
  /* Brand */
  --brand-red: #E10600;
  --brand-red-deep: #B80500;
  --brand-red-soft: #FF1F19;
  --brand-red-tint: #FFF1F0;
  --brand-red-line: #FBD7D5;
  --brand-ink: #0E1116;

  --primary: var(--brand-red);
  --primary-hover: var(--brand-red-deep);
  --primary-bright: var(--brand-red-soft);
  --primary-tint: var(--brand-red-tint);
  --primary-line: var(--brand-red-line);

  /* Neutrals */
  --ink:   #0E1116;
  --ink-2: #1B2129;
  --ink-3: #2C333D;
  --ink-4: #4A525E;

  --canvas: #F5F6F8;
  --surface: #FFFFFF;
  --surface-alt: #F8F9FB;
  --surface-2: #F1F3F6;
  --border: #E6E8EC;
  --border-strong: #D5D9DF;
  --border-soft: #EEF0F3;

  --text: #0E1116;
  --text-2: #586374;
  --text-3: #8A93A2;

  /* Status taxonomy */
  --st-draft: #6B7585;
  --st-approval: #C58A04;
  --st-approval-bg: #FFF8E6;
  --st-approved: #137A3F;
  --st-approved-bg: #E8F5EE;
  --st-rejected: #C2161A;
  --st-rejected-bg: #FCEAEA;
  --st-printed: #0C5BB4;
  --st-printed-bg: #E7F0FB;
  --st-awaiting: #0B6E73;
  --st-awaiting-bg: #E4F2F2;
  --st-closed: #4A525E;
  --st-closed-bg: #EEF0F3;
  --st-reprint: #5B3DCB;
  --st-reprint-bg: #EEEAFB;
  /* Cancelled — a managerial void, deliberately NOT the rejection red: mulberry
     reads "terminated by authority", distinct from a pipeline "no". */
  --st-cancelled: #93264F;
  --st-cancelled-bg: #FAE7EE;
  /* "For Approval" — the viewer's own call to action; hotter than the ambient
     In-Approval amber so actionable rows pop out of the inbox list. */
  --st-mine: #9A4D00;
  --st-mine-bg: #FFEFD9;
  --warning: #C58A04;

  /* Type */
  --f-head: "Barlow Semi Condensed", "Archivo", sans-serif;
  --f-body: "Inter", system-ui, sans-serif;
  --f-mono: "JetBrains Mono", ui-monospace, monospace;

  /* Radii */
  --r-xs: 4px;
  --r-sm: 6px;
  --r-md: 8px;
  --r-lg: 12px;
  --r-xl: 16px;

  /* Shadows */
  --shadow-xs: 0 1px 1px rgba(14,17,22,0.04);
  --shadow-sm: 0 1px 2px rgba(14,17,22,0.05), 0 1px 3px rgba(14,17,22,0.04);
  --shadow-md: 0 2px 4px rgba(14,17,22,0.04), 0 8px 24px rgba(14,17,22,0.06);
  --shadow-lg: 0 4px 12px rgba(14,17,22,0.06), 0 24px 48px rgba(14,17,22,0.10);
  --shadow-ring: 0 0 0 3px rgba(225,6,0,0.16);

  /* Motion */
  --ease-out: cubic-bezier(0.22, 1, 0.36, 1);
  --dur-fast: 120ms;
  --dur-med: 200ms;

  /* Scrollbar — the visible line, its hover weight, and the brand-red
     drag state. Dark surfaces re-declare the three colors (see the
     .nav-rail override in the Scrollbars section below). */
  --scrollbar-thumb: rgba(74, 82, 94, 0.38);       /* --ink-4 @ 38% */
  --scrollbar-thumb-hover: rgba(74, 82, 94, 0.58);
  --scrollbar-thumb-drag: rgba(225, 6, 0, 0.62);   /* --brand-red */

  /* Layer scale — every fixed/floating surface picks a slot here instead of
     inventing a z-index. dropdown < drawer < modal < menu < toast. */
  --z-dropdown: 50;   /* in-flow dropdowns (top-bar user menu) */
  --z-drawer: 60;     /* mobile nav rail */
  --z-modal: 100;     /* modal overlay + dialog */
  --z-menu: 150;      /* body-portaled context menus (above modals) */
  --z-mapfs: 180;     /* full-screen map stage (above modals, below toasts) */
  --z-toast: 200;     /* toast notifications (above everything) */

  /* App shell geometry — the rail's two widths and the top-bar height.
     The shell grid (components.css) consumes these; the Responsive and
     App-shell-glue sections below are the only places the values move,
     so the rail can never be sized from two competing rules again. */
  --rail-w-max: 248px;
  --rail-w-min: 68px;
  --rail-w: var(--rail-w-max);
  --topbar-h: 60px;
}

* { box-sizing: border-box; }

html, body {
  margin: 0;
  padding: 0;
  font-family: var(--f-body);
  font-size: 15px;
  color: var(--text);
  background: var(--canvas);
  -webkit-font-smoothing: antialiased;
}

::selection { background: rgba(225,6,0,0.18); color: var(--ink); }

/* The hidden attribute must always remove an element from layout. Component
   classes set explicit display values (flex/grid/inline-flex), and ANY author
   rule outranks the UA's [hidden] { display: none } — which is why screens
   kept re-fixing this one class at a time (.alert-banner[hidden],
   .modal-overlay[hidden], .wizard__footer .btn[hidden], …). One global guard
   ends the bug class: JS `el.hidden = true` always wins. */
[hidden] { display: none !important; }

/* ------------------------------------------------------------
   Scrollbars — slim machined groove
   The OS scrollbar (17px track + arrow buttons on Windows) is replaced
   app-wide by a 4px pill floating in a 10px transparent gutter: the
   gutter keeps a grabbable pointer target while the *visible* line
   stays thin. Hover thickens the pill to 6px by shrinking the inset
   border — the gutter never changes, so nothing shifts. While dragging,
   the pill takes the brand red, matching the active-state language of
   the rail edge, badges, and focus ring.
   ------------------------------------------------------------ */
::-webkit-scrollbar { width: 10px; height: 10px; }
::-webkit-scrollbar-track { background: transparent; }
::-webkit-scrollbar-corner { background: transparent; } /* no white block where both axes meet */
::-webkit-scrollbar-button { display: none; width: 0; height: 0; }
::-webkit-scrollbar-thumb {
  background-color: var(--scrollbar-thumb);
  border: 3px solid transparent;   /* 10px gutter − 2×3px inset = 4px line */
  border-radius: 999px;
  background-clip: content-box;
}
::-webkit-scrollbar-thumb:hover  { background-color: var(--scrollbar-thumb-hover); border-width: 2px; }
::-webkit-scrollbar-thumb:active { background-color: var(--scrollbar-thumb-drag);  border-width: 2px; }

/* Dark-surface variant: the nav rail scrolls on --ink, where an
   ink-alpha pill would vanish — ghost white instead, and the brighter
   red (--brand-red-soft) for the drag state so it pops on ink. Any
   future dark scroll container can re-declare the same three tokens. */
.nav-rail {
  --scrollbar-thumb: rgba(255, 255, 255, 0.16);
  --scrollbar-thumb-hover: rgba(255, 255, 255, 0.30);
  --scrollbar-thumb-drag: rgba(255, 31, 25, 0.66);
}

/* Firefox has no ::-webkit-scrollbar; give it the standard properties.
   These MUST stay scoped to non-WebKit engines: per spec, an element
   with scrollbar-color/scrollbar-width set ignores ::-webkit-scrollbar
   styling entirely (Chromium 121+ enforces this), so declaring both
   globally would silently revert Chrome/Edge to the flat UA thin bar.
   Declared on * rather than html because var() resolves where the
   property is *specified* — inheritance passes along the resolved
   color, so an html-level declaration would bake in the light thumb
   and the .nav-rail token override above could never take effect. */
@supports (not selector(::-webkit-scrollbar)) {
  * { scrollbar-width: thin; scrollbar-color: var(--scrollbar-thumb) transparent; }
}

/* ------------------------------------------------------------
   Utilities
   ------------------------------------------------------------ */
.text-2     { color: var(--text-2); }
.text-mono  { font-family: var(--f-mono); }
.text-sm    { font-size: 13px; }
.text-xs    { font-size: 12px; }
.font-head  { font-family: var(--f-head); }
.font-bold  { font-weight: 700; }
.mt-2 { margin-top: 8px; }
.mt-3 { margin-top: 12px; }
.mt-4 { margin-top: 16px; }
.mb-3 { margin-bottom: 12px; }
.divider { height: 1px; background: var(--border); margin: 16px 0; border: 0; }

/* ------------------------------------------------------------
   Page wrapper
   ------------------------------------------------------------ */
.page {
  padding: 28px 32px;
  max-width: none;
  margin: 0 auto;
}
.page--narrow      { max-width: 900px; }
.page--with-sticky { padding-bottom: 88px; }

.page-header {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 16px;
  margin-bottom: 22px;
}
.page-header__actions { display: flex; gap: 8px; flex-wrap: wrap; }
.page-header__crumb {
  display: flex; align-items: center; gap: 10px; margin-bottom: 6px;
}
.page-header__step { font-size: 13px; color: var(--text-2); font-family: var(--f-mono); }
.page-header__draft-code { font-size: 13px; color: var(--text-2); font-family: var(--f-mono); }
.page-title {
  font-family: var(--f-head);
  font-size: 28px;
  font-weight: 700;
  letter-spacing: -0.02em;
  margin: 0;
  line-height: 1.1;
  color: var(--ink);
}
.page-title--mono { font-family: var(--f-mono); font-size: 22px; }
.page-title__mono { font-family: var(--f-mono); }
.page-subtitle {
  color: var(--text-2);
  font-size: 14px;
  margin-top: 6px;
  line-height: 1.5;
}
.page-eyebrow {
  font-family: var(--f-head);
  font-size: 11px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--primary);
  margin-bottom: 4px;
}

/* ------------------------------------------------------------
   Responsive
   Shell sizing moves ONLY through the :root tokens here — never by
   re-declaring .app-shell, whose one grid rule (components.css)
   consumes the tokens. (Re-declaring it is how the old breakpoint
   rules silently died: equal specificity, earlier stylesheet.)
   ------------------------------------------------------------ */
@media (max-width: 1279px) {
  :root { --rail-w: var(--rail-w-min); }   /* rail condenses to icons by default */
}
@media (max-width: 767px) {
  :root { --topbar-h: 56px; }              /* --rail-w is already the 68px strip */
  .page { padding: 16px; }
}

/* Component & screen responsive overrides live BESIDE their base rules, not
   here. A media override only wins when it follows its base in source order
   (equal specificity, media queries add none), and core/site.css loads
   before components.css and every per-page sheet — so re-declaring them here
   is exactly how they silently died. Relocated to sit after their bases:
     · .kpi-grid · .stepper · .printable__sigs · .top-bar (phone)  → components.css
     · .detail__split · .return__split                            → pages/tickets/site.css
     · .config__split                                             → pages/configuration/site.css
     · .dashboard__split · .dashboard__quick-grid                 → pages/dashboard/site.css
   Already correct in their own sheets: .queue__* · .inbox__split (≤1100) ·
   .pipeline__board (≤767), all in pages/tickets. Dropped: .new-request__grid
   — the New Request screen is the wizard now, no such element exists. */

/* ------------------------------------------------------------
   App shell glue (scoped-structure additions)
   The rail chevron is the ONE nav toggle at every size. CSS owns the
   per-band default (expanded ≥1280, icon rail below — see Responsive);
   .nav-rail--collapsed / .nav-rail--expanded are the user's explicit
   override of that default, set by the chevron and cleared on band
   crossings (js/core/site.js), so a choice made at one viewport can
   never wedge the rail at another.
   ------------------------------------------------------------ */
.app-main { grid-column: 2 / 3; grid-row: 2 / 3; overflow-y: auto; min-width: 0; }

/* Pre-paint persistence hint. The inline <head> script (js contract in
   _Layout) stamps these on <html> from localStorage so the shell loads at
   the user's last rail width with NO flash — they mirror the :has(.nav-rail--*)
   rules below. site.js then transfers the choice onto the rail itself and
   removes these on load, so the two paths resolve to the same --rail-w. */
.nav-pref-collapsed .app-shell { --rail-w: var(--rail-w-min); }
@media (min-width: 768px) {
  .nav-pref-expanded .app-shell { --rail-w: var(--rail-w-max); }
}

.app-shell:has(.nav-rail--collapsed) { --rail-w: var(--rail-w-min); }
@media (min-width: 768px) {
  .app-shell:has(.nav-rail--expanded) { --rail-w: var(--rail-w-max); }
}

/* Phone: the rail stays in-flow as the 68px icon strip; expanding lifts
   it over the content as a fixed flyout instead of widening the track,
   so the strip's space stays reserved and nothing beneath reflows. */
@media (max-width: 767px) {
  .nav-rail--expanded {
    position: fixed;
    top: 0; bottom: 0; left: 0;
    width: var(--rail-w-max);
    z-index: var(--z-drawer);
    box-shadow: var(--shadow-lg);
  }
}

/* ------------------------------------------------------------
   Inline icon default sizing
   Icons render as <svg><use href="#icon-..."></svg> with no
   intrinsic size; class-sized icons (.btn__icon etc.) override.
   ------------------------------------------------------------ */
svg { width: 1em; height: 1em; flex-shrink: 0; }
/* ApexCharts sizes its chart <svg> via width/height *attributes*; the 1em rule
   above overrides those and collapses every chart to ~16px. Its legend/tooltip
   are HTML so they still showed — only the plot appeared to vanish. Exempt the
   chart svg so its attribute-driven size stands (legend-marker svgs stay 1em). */
.apexcharts-svg { width: auto; height: auto; }
.map-view__road { width: 100%; height: 100%; }
.nav-rail__mark img, .printable__logo img, .login__logo img { width: 100%; height: 100%; object-fit: contain; }
