:root {
  --brand: #d92218;
  --brand-dark: #b3160e;
  --brand-tint: #fff1f0;
  --brand-tint-border: #ffccc7;
  --navy: #0e1b2e;
  --navy-mid: #162842;
  --navy-light: #1f385c;
  --bg: #f4f6f9;
  --card: #ffffff;
  --card-subtle: #f8fafc;
  --border: #e2e8f0;
  --border-light: #edf2f7;
  --text: #0f172a;
  --ink: #0f172a;
  --muted: #64748b;
  --label: #475569;
  --ok: #059669;
  --ok-bg: #ecfdf5;
  --ok-border: #a7f3d0;
  --warn: #dc2626;
  --warn-bg: #fef2f2;
  --warn-border: #fecaca;
  --pending: #d97706;
  --pending-bg: #fffbeb;
  --pending-border: #fde68a;

  --neutral-bg: #f1f5f9;
  --neutral-fg: #334155;

  --accent-teal: #0d9488;
  --accent-teal-dark: #0f766e;
  --accent-blue: #2563eb;
  --accent-blue-dark: #1d4ed8;

  --shadow-sm: 0 1px 2px 0 rgba(15, 23, 42, 0.05);
  --shadow: 0 1px 3px 0 rgba(15, 23, 42, 0.06), 0 1px 2px -1px rgba(15, 23, 42, 0.04);
  --shadow-md: 0 4px 6px -1px rgba(15, 23, 42, 0.07), 0 2px 4px -2px rgba(15, 23, 42, 0.05);
  --shadow-lg: 0 10px 15px -3px rgba(15, 23, 42, 0.08), 0 4px 6px -4px rgba(15, 23, 42, 0.03);

  --radius: 6px;
  --radius-lg: 10px;
  --radius-sm: 4px;
  --radius-full: 9999px;

  /* ---- Sidebar surface scale ----
     The navigation used to paint its own colours inline, including a red
     gradient wash behind the active item. A gradient is decoration on a
     control whose only job is to answer "where am I", and at 12.5px over a
     dark ground it reads as a smear rather than a state. These four values
     replace it: one flat ground, and three levels of white lifted off it
     for rest / hover / current. Flat surfaces at fixed opacities stay
     legible at every size, are trivially checkable for contrast, and give
     the whole rail one visual system instead of three inline exceptions.

     The brand red survives as the 3px indicator on the current item and
     nowhere else in here -- an accent that marks one thing is an accent;
     an accent behind every state is wallpaper. */
  --sidebar-bg: #0f1c2f;
  --sidebar-line: rgba(255, 255, 255, 0.07);
  --sidebar-hover: rgba(255, 255, 255, 0.055);
  --sidebar-active: rgba(255, 255, 255, 0.10);
  --sidebar-text: #c3cfe0;
  --sidebar-text-dim: #8b9bb2;
  --sidebar-text-strong: #ffffff;

  /* Width is a variable so the shell, the collapse transition and the
     content max-width below all read the same number. */
  --sidebar-w: 244px;
  --sidebar-w-rail: 68px;
  --main-max: 1280px;

  /* One motion vocabulary for the whole chrome. Two durations, because
     there are two kinds of movement here: a state changing under the
     cursor, and a panel travelling across the screen. */
  --ease-out: cubic-bezier(0.22, 0.61, 0.36, 1);
  --dur-fast: 0.16s;
  --dur-panel: 0.26s;

  --font-sans: 'IBM Plex Sans', -apple-system, Segoe UI, Roboto, Arial, sans-serif;
  --font-display: 'IBM Plex Sans Condensed', 'IBM Plex Sans', -apple-system, sans-serif;
  --font-mono: 'IBM Plex Mono', ui-monospace, Consolas, monospace;
}

* { box-sizing: border-box; }

body {
  margin: 0;
  font-family: var(--font-sans);
  background: var(--bg);
  color: var(--text);
  -webkit-font-smoothing: antialiased;
}

.mono { font-family: var(--font-mono); }

#login-screen,
#boot-screen {
  min-height: 100vh;
  display: flex;
  align-items: center;
  justify-content: center;
  background: radial-gradient(circle at top, #162842 0%, #0e1b2e 100%);
}

#boot-screen {
  flex-direction: column;
  gap: 8px;
}
#boot-screen .sub { color: #94a3b8; font-size: 13px; margin: 0; font-weight: 500; }

.login-card {
  background: var(--card);
  border: 1px solid rgba(255, 255, 255, 0.1);
  border-radius: 12px;
  padding: 36px 32px;
  width: 340px;
  max-width: 90vw;
  box-shadow: 0 20px 25px -5px rgba(0, 0, 0, 0.3), 0 8px 10px -6px rgba(0, 0, 0, 0.2);
}

.login-card h1 {
  font-family: var(--font-display);
  font-size: 24px;
  font-weight: 700;
  letter-spacing: -0.01em;
  margin: 0 0 4px;
  color: var(--ink);
  text-align: center;
}

.login-card p.sub {
  margin: 0 0 24px;
  color: var(--muted);
  font-size: 13px;
  text-align: center;
}

.brand-mark {
  width: 36px;
  height: 36px;
  border-radius: var(--radius);
  /* Flat brand red, no gradient and no glow. The mark is an identifier,
     not a button -- lighting it from within made it the loudest object in
     a navigation rail whose job is to be quiet. */
  background: var(--brand);
  display: flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
  color: #fff;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: 16px;
  letter-spacing: .3px;
}

.brand-mark.lg {
  width: 60px;
  height: 60px;
  margin: 0 auto 16px;
  font-size: 24px;
  border-radius: var(--radius-lg);
}

input, select, textarea {
  width: 100%;
  padding: 9px 12px;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  font-size: 13.5px;
  margin-bottom: 12px;
  font-family: inherit;
  background: #ffffff;
  color: var(--ink);
  transition: border-color 0.15s ease, box-shadow 0.15s ease;
}

input:focus, select:focus, textarea:focus {
  outline: none;
  border-color: var(--brand);
  box-shadow: 0 0 0 3px rgba(217, 34, 24, 0.12);
}

label {
  display: block;
  font-size: 11px;
  color: var(--label);
  margin-bottom: 6px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .04em;
}

label span.muted { text-transform: none; font-weight: 400; letter-spacing: normal; }

button {
  cursor: pointer;
  border: none;
  border-radius: var(--radius);
  padding: 9px 16px;
  font-size: 13.5px;
  font-weight: 600;
  background: linear-gradient(180deg, #e5281f 0%, #cf1d15 100%);
  color: #fff;
  border: 1px solid #b31710;
  box-shadow: 0 1px 2px rgba(207, 29, 21, 0.2), inset 0 1px 0 rgba(255, 255, 255, 0.15);
  transition: all 0.15s ease;
}

button:hover {
  background: linear-gradient(180deg, #d32018 0%, #b81710 100%);
  box-shadow: 0 2px 4px rgba(207, 29, 21, 0.25);
}

button:active {
  transform: translateY(1px);
  box-shadow: 0 1px 2px rgba(207, 29, 21, 0.2);
}

button.secondary {
  background: #ffffff;
  color: var(--ink);
  border: 1px solid var(--border);
  box-shadow: 0 1px 2px rgba(0, 0, 0, 0.04);
}

button.secondary:hover {
  background: #f8fafc;
  border-color: #cbd5e1;
  color: var(--ink);
}

button:disabled, button[disabled] {
  cursor: not-allowed;
  background: #f1f5f9;
  border-color: var(--border);
  color: var(--muted);
  box-shadow: none;
  transform: none;
}
button:disabled:hover, button[disabled]:hover { background: #f1f5f9; }
button.secondary:disabled, button.secondary[disabled] {
  background: #f8fafc;
  color: #94a3b8;
  border-color: var(--border);
  box-shadow: none;
}
button.secondary:disabled:hover, button.secondary[disabled]:hover { background: #f8fafc; }

.error-text { color: var(--warn); font-size: 13px; margin: -4px 0 12px; font-weight: 500; }

/* ---------- App shell: sidebar + main column ---------- */

.app-shell {
  display: flex;
  min-height: 100vh;
  align-items: flex-start;
}

.sidebar {
  width: var(--sidebar-w);
  flex-shrink: 0;
  background: var(--sidebar-bg);
  display: flex;
  flex-direction: column;
  height: 100vh;
  position: sticky;
  top: 0;
  border-right: 1px solid var(--sidebar-line);
  /* No drop shadow. A 1px line already separates the rail from the page;
     a shadow on top of it is the same edge drawn twice. */
  transition: width var(--dur-panel) var(--ease-out);
}

.brand {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 16px 18px;
  border-bottom: 1px solid var(--sidebar-line);
  background: transparent;
  min-height: 69px;
}

.brand-name {
  font-family: var(--font-display);
  font-weight: 700;
  font-size: 15px;
  color: #ffffff;
  line-height: 1.2;
  letter-spacing: .3px;
}
.brand-sub {
  font-size: 10px;
  color: #94a3b8;
  text-transform: uppercase;
  letter-spacing: .06em;
  font-weight: 500;
  margin-top: 1px;
}

.side-nav-label {
  padding: 14px 18px 6px;
  font-size: 10px;
  letter-spacing: .08em;
  color: var(--sidebar-text-dim);
  text-transform: uppercase;
  font-weight: 700;
}

.side-nav { flex: 1; overflow-y: auto; padding-bottom: 12px; }

.side-link, .side-group-toggle {
  position: relative;
  width: calc(100% - 16px);
  display: flex;
  align-items: center;
  gap: 10px;
  /* 34px tall including padding. Not the 44px touch minimum, because at
     this width the whole row is the target and a 44px row would put six
     items on a laptop screen; the mobile drawer, where fingers are
     actually used, gets the taller rows in its own media query. */
  padding: 8px 12px;
  margin: 2px 8px;
  border-radius: var(--radius);
  /* The group toggles are <button>s, so the app-wide button rule was
     drawing a 1px solid #b31710 around each of them -- a red rectangle on
     three sides of "Sales" and "Supply Chain" that nobody had asked for
     (the old `border-left: none` removed exactly one of the four). The
     rail's own hover and active surfaces are the state; a border is a
     second, contradicting answer. */
  border: none;
  background: transparent;
  color: var(--sidebar-text);
  font-weight: 500;
  font-size: 12.5px;
  text-align: left;
  margin-bottom: 0;
  text-decoration: none;
  cursor: pointer;
  box-sizing: border-box;
  /* Named properties, not `all`: `all` also transitions width, which turns
     the collapse into two animations fighting over the same 260ms. */
  transition: background-color var(--dur-fast) var(--ease-out),
              color var(--dur-fast) var(--ease-out);
}

/* The current-page indicator. A pseudo-element rather than border-left,
   which is what it used to be -- a border adds 3px of box, so becoming
   the active item nudged its own label sideways and every other row
   stayed put. This occupies no layout at all and scales up from nothing,
   so the mark arrives without moving a single character. */
.side-link::before, .side-sublink::before {
  content: '';
  position: absolute;
  left: 0;
  top: 50%;
  width: 3px;
  height: 18px;
  border-radius: 0 2px 2px 0;
  background: var(--brand);
  transform: translateY(-50%) scaleX(0);
  transform-origin: left center;
  transition: transform var(--dur-fast) var(--ease-out);
}
.side-link.active::before, .side-sublink.active::before { transform: translateY(-50%) scaleX(1); }

.side-link:hover, .side-group-toggle:hover {
  background: var(--sidebar-hover);
  color: var(--sidebar-text-strong);
}

/* Keyboard users get the same answer the mouse gets, plus a real ring.
   :focus-visible, so clicking a nav item doesn't leave a ring behind. */
.side-link:focus-visible,
.side-group-toggle:focus-visible,
.side-sublink:focus-visible {
  outline: 2px solid #7dd3fc;
  outline-offset: -2px;
  background: var(--sidebar-hover);
  color: var(--sidebar-text-strong);
}

.side-link.active {
  background: var(--sidebar-active);
  color: var(--sidebar-text-strong);
  font-weight: 600;
}
.side-link.active .side-icon { opacity: 1; }

.side-icon { width: 18px; height: 18px; flex-shrink: 0; display: flex; align-items: center; justify-content: center; color: inherit; opacity: .85; }
.side-icon svg { width: 18px; height: 18px; }

.side-group-toggle .chevron {
  margin-left: auto;
  width: 14px;
  height: 14px;
  color: var(--sidebar-text-dim);
  transition: transform var(--dur-panel) var(--ease-out);
}
.side-group-toggle .chevron svg { width: 14px; height: 14px; }
.side-group.open .side-group-toggle .chevron { transform: rotate(180deg); }
.side-group.open > .side-group-toggle { color: var(--sidebar-text-strong); }

.side-submenu {
  display: none;
  padding-left: 0;
  margin: 2px 0 4px;
}

/* display:none cannot be transitioned, so opening is animated by the items
   themselves rather than by measuring a height nobody can predict (Supply
   Chain has sixteen children and four section labels). Cheap, exact, and
   it cannot desync from the real content height. */
.side-group.open .side-submenu {
  display: block;
  animation: submenuIn var(--dur-panel) var(--ease-out);
}

@keyframes submenuIn {
  from { opacity: 0; transform: translateY(-4px); }
  to   { opacity: 1; transform: none; }
}

.side-sublink {
  position: relative;
  display: flex;
  align-items: center;
  width: calc(100% - 16px);
  text-align: left;
  background: transparent;
  color: var(--sidebar-text-dim);
  font-weight: 400;
  font-size: 12px;
  padding: 6px 12px 6px 36px;
  margin: 1px 8px;
  border-radius: var(--radius);
  border-left: none;
  margin-bottom: 0;
  text-decoration: none;
  cursor: pointer;
  box-sizing: border-box;
  transition: background-color var(--dur-fast) var(--ease-out),
              color var(--dur-fast) var(--ease-out);
}

.side-sublink:hover {
  background: var(--sidebar-hover);
  color: #eef4fb;
}
.side-sublink.active {
  background: var(--sidebar-active);
  color: var(--sidebar-text-strong);
  font-weight: 600;
}
.side-sublink.disabled { color: #475569; cursor: default; }

.sidebar-footer {
  border-top: 1px solid var(--sidebar-line);
  padding: 14px 16px;
  background: rgba(0, 0, 0, 0.16);
}

.user-chip {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 12px;
  background: rgba(255, 255, 255, 0.04);
  border: 1px solid rgba(255, 255, 255, 0.08);
  border-radius: var(--radius);
  padding: 8px 10px;
}

.user-avatar {
  width: 32px;
  height: 32px;
  border-radius: var(--radius);
  background: #1e3a8a;
  border: 1px solid rgba(255, 255, 255, 0.15);
  color: #fff;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 12px;
  font-weight: 700;
  flex-shrink: 0;
  box-shadow: var(--shadow-sm);
}

.user-name { font-size: 12.5px; font-weight: 600; color: #fff; line-height: 1.2; }
.sidebar-footer .role-badge {
  background: rgba(255, 255, 255, 0.1);
  color: #94a3b8;
  margin-right: 0;
  font-size: 10px;
  padding: 1px 6px;
  border-radius: 4px;
}

.sidebar-footer button.secondary {
  width: 100%;
  background: rgba(255, 255, 255, 0.08);
  border: 1px solid rgba(255, 255, 255, 0.12);
  color: #e2e8f0;
  font-weight: 500;
  font-size: 12px;
}
.sidebar-footer button.secondary:hover {
  background: rgba(255, 255, 255, 0.14);
  color: #ffffff;
}

.main-col { flex: 1; min-width: 0; }

.topbar-crumb {
  background: #ffffff;
  border-bottom: 1px solid var(--border);
  padding: 0 28px;
  display: flex;
  align-items: center;
  justify-content: space-between;
  height: 50px;
  flex-shrink: 0;
  font-size: 12.5px;
  color: var(--muted);
  box-shadow: 0 1px 2px rgba(0, 0, 0, 0.02);
}

.topbar-crumb-left { display: flex; align-items: center; gap: 8px; min-width: 0; font-weight: 500; }
.topbar-crumb-left #breadcrumb-text { min-width: 0; overflow-wrap: break-word; color: var(--ink); font-weight: 600; }

/* The right-hand group is now a container for two things -- the bell and
   the status pill -- so the pill's own chrome moved onto the pill. It had
   been on the group, which would have drawn a border around the bell too. */
.topbar-crumb-right {
  display: flex;
  align-items: center;
  gap: 10px;
  flex-shrink: 0;
}

.status-pill {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  font-size: 12px;
  color: var(--ink);
  font-weight: 600;
  white-space: nowrap;
  background: #f8fafc;
  border: 1px solid var(--border);
  padding: 4px 10px;
  border-radius: var(--radius-full);
}

/* Below the drawer breakpoint the bar already wraps and the topbar is
   tight; the status pill is reassurance, not information, so it is the
   first thing to give up its space. */
@media (max-width: 640px) {
  .status-pill:not(.presence-pill) { display: none; }
}

.status-dot {
  width: 8px;
  height: 8px;
  border-radius: 50%;
  background: var(--ok);
  display: inline-block;
  box-shadow: 0 0 0 3px rgba(5, 150, 105, 0.2);
  animation: pulseStatusDot 2.5s infinite;
}

@keyframes pulseStatusDot {
  0%, 100% { transform: scale(1); opacity: 1; }
  50% { transform: scale(1.1); opacity: 0.85; }
}

.page-header {
  background: #ffffff;
  border-bottom: 1px solid var(--border);
  padding: 20px 28px;
  display: flex;
  align-items: flex-end;
  justify-content: space-between;
  flex-shrink: 0;
  flex-wrap: wrap;
  gap: 14px;
}

.page-eyebrow {
  font-size: 10px;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--brand);
  font-weight: 700;
  margin-bottom: 4px;
  display: inline-block;
}
.page-eyebrow:empty { display: none; }

.page-header h1 {
  font-family: var(--font-display);
  font-size: 26px;
  font-weight: 700;
  letter-spacing: -0.01em;
  color: #0f172a;
  margin: 0;
  min-width: 0;
  overflow-wrap: break-word;
}

/* The content follows the rail. Collapsing the navigation frees 176px, and
   a fixed 1280px measure would have simply parked it as extra margin --
   the page would look identical either side of a control the user just
   pressed, which reads as a broken button. Widening the measure instead
   means the space actually goes to the tables that wanted it. */
main {
  padding: 24px 28px;
  max-width: var(--main-max);
  margin: 0 auto;
  transition: max-width var(--dur-panel) var(--ease-out);
}

.hamburger-btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: transparent;
  border: none;
  padding: 6px;
  border-radius: 6px;
  cursor: pointer;
  flex-shrink: 0;
  color: var(--ink);
}
.hamburger-btn:hover { background: var(--bg); }
.hamburger-btn svg { width: 22px; height: 22px; display: block; }

.sidebar-backdrop { display: none; }

/* ---------- Module rail + flyout (desktop) ---------- */
/*
   Modelled on an inventory ERP's main menu (Cin7 Core / DEAR): a slim dark
   rail of MODULES, icon over label, and pressing one opens a light flyout
   panel beside it listing that module's pages by section, with "+"
   shortcuts to start a new document.

   Why this over the 244px accordion it replaces: the accordion spent a
   quarter of a laptop screen on navigation all day to be used for a second
   at a time, and a department with sixteen pages pushed every other
   department below the fold. The rail costs 84px permanently; the flyout
   floats over the page only while it is being used.

   Same markup as the phone drawer (below 861px), which keeps the accordion.
   Every rule here is scoped to the desktop query for that reason.
*/
.side-flyout-head { display: none; }
.side-quick svg { width: 14px; height: 14px; }
/* The module toggles are <button>s, and the app-wide button rule gives every
   button a red drop shadow and a white inset highlight -- drawn here as a
   faint box around each module. Same leak the border reset above fixed. */
.side-group-toggle, .side-group-toggle:hover, .side-group-toggle:active { box-shadow: none; transform: none; }
.side-row { display: flex; align-items: center; }
.side-row > .side-sublink:not(.side-quick) { flex: 1; min-width: 0; }

@media (min-width: 861px) {
  .app-shell { --sidebar-w: 84px; --main-max: 1420px; }

  .sidebar { z-index: 50; }
  /* On a desktop the menu button hides the rail outright (core.js
     setNavHidden), and the content then takes the full width. */
  .app-shell.nav-hidden .sidebar { display: none; }
  .app-shell.nav-hidden { --main-max: 100%; }

  .brand { padding: 14px 0; justify-content: center; min-height: 64px; }
  .brand-text { display: none; }

  .side-nav { padding: 6px 0 10px; overflow-x: hidden; scrollbar-width: thin; scrollbar-color: #2b3d5c transparent; }

  .side-link,
  .side-group-toggle {
    flex-direction: column;
    justify-content: center;
    gap: 5px;
    width: calc(100% - 12px);
    margin: 2px 6px;
    padding: 9px 2px 8px;
    font-size: 10.5px;
    font-weight: 600;
    line-height: 1.15;
    letter-spacing: .01em;
    text-align: center;
  }
  .side-icon { width: 20px; height: 20px; }
  .side-icon svg { width: 20px; height: 20px; }
  .side-group-toggle .chevron { display: none; }

  /* The module that owns the current page carries the red mark -- page
     links are out of sight until a flyout opens, so this is the only
     "you are here" the rail can show. */
  .side-group.has-active > .side-group-toggle {
    background: var(--sidebar-active);
    color: var(--sidebar-text-strong);
  }
  .side-group.has-active > .side-group-toggle::before {
    content: '';
    position: absolute;
    left: -6px;
    top: 50%;
    width: 3px;
    height: 26px;
    border-radius: 0 2px 2px 0;
    background: var(--brand);
    transform: translateY(-50%);
  }
  .side-link::before { left: -6px; height: 26px; }
  .side-group.open > .side-group-toggle {
    background: rgba(255, 255, 255, 0.14);
    color: var(--sidebar-text-strong);
  }

  /* The flyout. Fixed beside the rail, full height, over the page. */
  .side-submenu {
    display: none;
    position: fixed;
    top: 0;
    bottom: 0;
    left: var(--sidebar-w);
    width: 296px;
    margin: 0;
    padding: 0 0 18px;
    overflow-y: auto;
    background: #ffffff;
    border-right: 1px solid var(--border);
    box-shadow: 18px 0 40px -18px rgba(15, 23, 42, 0.35);
    z-index: 45;
  }
  .side-group.open .side-submenu {
    display: block;
    animation: flyoutIn var(--dur-fast) var(--ease-out);
  }

  .side-flyout-head {
    display: block;
    padding: 20px 20px 14px;
    margin-bottom: 4px;
    border-bottom: 1px solid var(--border-light);
    background: linear-gradient(180deg, #ffffff 0%, #f8fafc 100%);
  }
  .side-flyout-head strong {
    display: block;
    font-family: var(--font-display);
    font-size: 18px;
    font-weight: 700;
    color: var(--ink);
    letter-spacing: -0.005em;
  }
  .side-flyout-head span { display: block; margin-top: 3px; font-size: 12px; color: var(--muted); line-height: 1.4; }

  .side-submenu .side-section-label {
    padding: 14px 20px 5px;
    font-size: 10px;
    color: var(--muted);
  }
  .side-submenu > .side-flyout-head + .side-section-label { padding-top: 10px; }

  .side-submenu .side-sublink {
    width: calc(100% - 16px);
    margin: 1px 8px;
    padding: 8px 12px;
    font-size: 13px;
    font-weight: 500;
    color: var(--ink);
  }
  .side-submenu .side-sublink:hover { background: var(--bg); color: var(--ink); }
  .side-submenu .side-sublink.active {
    background: var(--brand-tint);
    color: var(--brand-dark);
    font-weight: 600;
  }
  .side-submenu .side-sublink:focus-visible {
    outline: 2px solid var(--brand);
    outline-offset: -2px;
    background: var(--bg);
    color: var(--ink);
  }
  .side-submenu .side-soon { color: var(--muted); border-color: var(--border); }

  .side-submenu .side-row { margin-right: 10px; }
  .side-submenu .side-row > .side-sublink:not(.side-quick) { margin-right: 6px; }
  .side-submenu .side-sublink.side-quick {
    flex: 0 0 30px;
    width: 30px;
    height: 30px;
    margin: 0;
    padding: 0;
    justify-content: center;
    border: 1px solid var(--border);
    border-radius: var(--radius);
    color: var(--label);
    background: #ffffff;
  }
  .side-submenu .side-sublink.side-quick::before { display: none; }
  .side-submenu .side-sublink.side-quick:hover {
    background: var(--brand);
    border-color: var(--brand);
    color: #ffffff;
  }

  .sidebar-footer { padding: 12px 8px; }
  .user-chip { justify-content: center; padding: 6px; gap: 0; margin-bottom: 8px; }
  .user-chip > div { display: none; }
  .sidebar-footer button.secondary { padding: 8px 0; font-size: 11px; }
}

@keyframes flyoutIn {
  from { opacity: 0; transform: translateX(-8px); }
  to   { opacity: 1; transform: none; }
}

@media (prefers-reduced-motion: reduce) {
  .side-group.open .side-submenu { animation: none; }
}

@media (max-width: 860px) {
  .side-row > .side-sublink.side-quick {
    flex: 0 0 auto;
    width: 44px;
    padding: 12px 0;
    margin: 1px 8px 1px 0;
    justify-content: center;
    color: var(--sidebar-text);
  }
  .side-row > .side-sublink.side-quick::before { display: none; }
}

@media (max-width: 960px) {
  .topbar-crumb { flex-wrap: wrap; height: auto; padding: 8px 16px; gap: 8px; }
  .page-header { padding: 14px 16px; }
  main { padding: 16px; }
}

@media (max-width: 860px) {
  .app-shell { display: block; }
  .hamburger-btn { display: inline-flex; align-items: center; justify-content: center; }

  .sidebar {
    position: fixed;
    top: 0;
    left: 0;
    bottom: 0;
    width: min(280px, 84vw);
    height: 100vh;
    z-index: 40;
    transform: translateX(-100%);
    transition: transform 0.22s ease;
    box-shadow: 2px 0 18px rgba(0, 0, 0, 0.18);
  }
  .sidebar.mobile-open { transform: translateX(0); }

  .sidebar-backdrop {
    display: block;
    position: fixed;
    inset: 0;
    background: rgba(20, 24, 30, 0.45);
    z-index: 30;
    opacity: 0;
    pointer-events: none;
    transition: opacity 0.22s ease;
  }
  .sidebar-backdrop.visible { opacity: 1; pointer-events: auto; }

  .main-col { width: 100%; }
}

@media (max-width: 520px) {
  .cards { grid-template-columns: 1fr 1fr; }
  .form-grid { grid-template-columns: 1fr; }
  .panel { padding: 14px; }
  .page-header h1 { font-size: 17px; }
  .date-picker { flex-wrap: wrap; }
  .panel-head-row { flex-wrap: wrap; gap: 8px; }
}

.comingsoon-panel {
  text-align: center;
  padding: 56px 32px;
  max-width: 460px;
  margin: 24px auto;
}

.comingsoon-icon {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 52px;
  height: 52px;
  border-radius: 50%;
  background: var(--brand-tint);
  color: var(--brand);
  margin-bottom: 14px;
}

.comingsoon-icon svg { width: 26px; height: 26px; }

.comingsoon-badge {
  display: inline-block;
  padding: 3px 10px;
  border-radius: 999px;
  background: var(--bg);
  color: var(--muted);
  font-size: 11px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.03em;
  margin-bottom: 10px;
}

.comingsoon-panel h2 { margin: 0 0 8px; }
.comingsoon-panel p { font-size: 13.5px; line-height: 1.5; }

.hidden { display: none !important; }

.dashboard-section-title {
  font-size: 13px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.04em;
  color: var(--muted);
  margin: 0 0 12px;
}

.cards {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(190px, 1fr));
  gap: 14px;
  margin-bottom: 24px;
}

.card {
  display: flex;
  /* Top-aligned, not centred: every KPI now carries a label and a sub-line,
     so the text block has real height and a vertically centred icon floats
     away from the number it belongs to. */
  align-items: flex-start;
  gap: 14px;
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  padding: 16px 18px;
}

.card-icon {
  flex-shrink: 0;
  width: 36px;
  height: 36px;
  border-radius: var(--radius);
  display: flex;
  align-items: center;
  justify-content: center;
  /* Neutral by default. This used to be brand-tint red on every card,
     which meant a card reporting "0 problems" looked exactly as alarming
     as one reporting a real discrepancy -- the tone modifiers below are
     what earn a colour. */
  background: var(--neutral-bg);
  color: var(--neutral-fg);
}

.card-icon svg { width: 19px; height: 19px; }

.card .num { font-family: var(--font-display); font-size: 28px; font-weight: 700; letter-spacing: -0.01em; color: var(--ink); line-height: 1.1; font-variant-numeric: tabular-nums; }
.card .label { font-size: 12.5px; font-weight: 600; color: var(--label); margin-top: 3px; line-height: 1.35; }
.card.flag .num { color: var(--warn); }
.card.flag .card-icon { background: var(--warn-bg); color: var(--warn); }
.card.attention .num { color: var(--pending); }
.card.attention .card-icon { background: var(--pending-bg); color: var(--pending); }
/* "Good" is the one tone that deliberately doesn't recolor the number:
   nothing is wrong, so the value stays plain ink and only the supporting
   line carries the green -- reserving strong color for exceptions is the
   same rule the flag/attention tones follow in the other direction. */
.card.good .card-icon { background: var(--ok-bg); color: var(--ok); }

/* .cell-sub is a table cell helper (nowrap, so a column can't be forced
   wide by one long value) -- inside a card the sub-line is a full sentence
   and has to wrap instead. */
.card .cell-sub { white-space: normal; font-size: 11.5px; line-height: 1.4; margin-top: 3px; }
.card .cell-sub.sub-ok { color: var(--ok); }
.card .cell-sub.sub-warn { color: var(--warn); }
.card .cell-sub.sub-pending { color: var(--pending); }

/* Clickable dashboard KPI cards -- real <button> elements (keyboard/
   screen-reader accessible) reset back to look like the plain .card they
   extend, with a hover/focus affordance signaling "this jumps somewhere". */
.card-clickable {
  width: 100%;
  text-align: left;
  font: inherit;
  cursor: pointer;
  transition: border-color .12s ease, box-shadow .12s ease, transform .12s ease;
}
.card-clickable:hover, .card-clickable:focus-visible {
  /* Explicit background reset -- .card-clickable is a real <button>, and
     without this it silently inherits the generic button:hover's brand-red
     fill (still the only rule declaring `background` for this state), which
     read as a broken/unreadable red card rather than a hover affordance. */
  background: var(--card);
  border-color: #c3cbd6;
  box-shadow: 0 6px 16px rgba(19, 35, 57, .10);
  transform: translateY(-2px);
}
.card-clickable:active { transform: translateY(0); }
.card-body { min-width: 0; }

/* The dashboard's eight KPIs sit in a deliberate 4x2 block rather than the
   generic .cards auto-fit, which reflows them into a leftover 3/3/2. The
   strip reads as one unit that way, and each card keeps the same position
   from one visit to the next -- which is most of what makes a KPI strip
   scannable rather than re-read every time. Other .cards users (the dip
   preview, for one) still want auto-fit, so this is scoped to the strip. */
#summary-cards { grid-template-columns: repeat(4, minmax(0, 1fr)); }
@media (max-width: 1100px) { #summary-cards { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
@media (max-width: 560px) { #summary-cards { grid-template-columns: 1fr; } }

.dashboard-hero { margin-bottom: 14px; }
.dashboard-hero .dashboard-section-title { margin-bottom: 4px; }
.dashboard-hero p { margin: 0; font-size: 12.5px; }

/* Historical-date banner. Amber rather than red: looking at a past date is
   an ordinary thing to do, not a fault -- it only needs to be impossible to
   miss, so the live cards beside it aren't misread as history. */
.dash-datemode {
  display: flex;
  align-items: center;
  gap: 12px;
  flex-wrap: wrap;
  padding: 10px 14px;
  margin-bottom: 16px;
  background: var(--pending-bg);
  border: 1px solid var(--pending-border);
  border-radius: var(--radius);
}

.dash-datemode-pill {
  font-size: 12px;
  font-weight: 700;
  color: #7a4f0f;
  background: #ffffff;
  border: 1px solid var(--pending-border);
  border-radius: var(--radius-full);
  padding: 3px 10px;
  white-space: nowrap;
}

.dash-datemode-text {
  flex: 1;
  min-width: 220px;
  font-size: 12px;
  line-height: 1.4;
  color: #7a4f0f;
}

.dash-datemode button.secondary {
  padding: 6px 12px;
  font-size: 12.5px;
  white-space: nowrap;
}

.dashboard-chart-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 16px;
  margin-bottom: 20px;
}
@media (max-width: 900px) {
  .dashboard-chart-grid { grid-template-columns: 1fr; }
}

.trend-chart-wrap { position: relative; }
.trend-chart { width: 100%; height: auto; display: block; overflow: visible; }
.trend-bar { fill: var(--brand); }
.trend-bar:hover { fill: var(--brand-dark); }
.trend-bar-zero { fill: var(--border); }
.chart-baseline { stroke: var(--border); stroke-width: 1; }
.chart-axis-label { font-size: 9px; fill: var(--muted); }

/* Smooth area/line variant of the trend chart -- same data, headline and
   hover-tooltip mechanics as the bar version above, just a curved line with
   a soft gradient fill under it instead of discrete bars. Each of the two
   dashboard trend panels gets its own hue (teal for Production, blue for
   Dispatch) purely to tell the two charts apart at a glance; scoped by the
   chart's own container id so it can't leak into other .trend-chart users. */
.trend-area-line { fill: none; stroke-width: 2.5; stroke-linecap: round; stroke-linejoin: round; }
.trend-area-fill { stroke: none; }
.trend-area-dot { fill: var(--card); stroke-width: 2; r: 3; }
.trend-area-hit { fill: transparent; cursor: pointer; }

#chart-production .trend-area-line, #chart-production .trend-area-dot { stroke: var(--accent-teal); }
#chart-dispatch .trend-area-line, #chart-dispatch .trend-area-dot { stroke: var(--accent-blue); }
.chart-tooltip {
  position: absolute;
  pointer-events: none;
  background: var(--navy);
  color: #fff;
  font-size: 11px;
  font-weight: 600;
  padding: 4px 8px;
  border-radius: 2px;
  white-space: nowrap;
  opacity: 0;
  transition: opacity .1s ease;
  z-index: 5;
}
.chart-tooltip.visible { opacity: 1; }

/* Dispatch Performance report -- dual-series (Dispatched bars + Planned
   target line) and status-colored (on/under target) chart variants,
   extending the single-hue trend-bar pattern above. Always paired with a
   legend once there's more than one series, per the dataviz rule that
   identity is never color-alone. */
.chart-legend { display: flex; gap: 18px; flex-wrap: wrap; margin-top: 10px; font-size: 12px; color: var(--muted); }
.chart-legend-item { display: flex; align-items: center; gap: 6px; }
.chart-legend-swatch { width: 10px; height: 10px; border-radius: 2px; display: inline-block; flex-shrink: 0; }
.chart-legend-line { width: 14px; height: 2px; display: inline-block; flex-shrink: 0; }

.trend-line-planned { fill: none; stroke: var(--navy); stroke-width: 2; }
.trend-line-marker { fill: var(--navy); cursor: pointer; }
.trend-line-marker:hover { fill: var(--navy-light); }

.trend-bar-attained-ok { fill: var(--ok); }
.trend-bar-attained-ok:hover { fill: #16673f; }
.trend-bar-attained-under { fill: var(--warn); }
.trend-bar-attained-under:hover { fill: #8f1a11; }

.pct-bar-track { background: var(--bg); border-radius: 3px; height: 6px; overflow: hidden; min-width: 60px; }
.pct-bar-fill { height: 100%; border-radius: 3px; }
.pct-bar-fill.ok { background: var(--ok); }
.pct-bar-fill.under { background: var(--warn); }
.pct-bar-fill.high { background: var(--warn); }
.pct-bar-fill.low { background: var(--pending); }

/* Fill % rendered as bar-plus-number in a table cell: the bar is what makes
   nine tanks comparable at a glance, the number is what someone actually
   writes down -- neither alone is enough, and the bar is never the only
   carrier of "this one is nearly full" (the Status column says so in
   words). */
.fill-cell { display: flex; align-items: center; gap: 8px; }
.fill-cell .pct-bar-track { flex: 1; min-width: 34px; }
.fill-cell .fill-value { width: 42px; flex-shrink: 0; text-align: right; font-family: var(--font-mono); font-size: 12px; font-weight: 600; }

/* The headline above a trend chart: the period total, and whether that's up
   or down on the period before it. A 14-bar chart shows a shape well and a
   magnitude badly -- without this you can see dispatch is lumpy but not
   whether the fortnight was actually better than the last one. */
.chart-headline {
  display: flex;
  align-items: baseline;
  gap: 10px;
  flex-wrap: wrap;
  margin: -6px 0 12px;
}
.chart-headline .chart-headline-total { font-family: var(--font-mono); font-size: 19px; font-weight: 600; color: var(--ink); line-height: 1.2; }
.chart-headline .chart-headline-delta { font-size: 12px; font-weight: 600; color: var(--muted); }
.chart-headline .chart-headline-delta.up { color: var(--ok); }
.chart-headline .chart-headline-delta.down { color: var(--warn); }
.chart-headline .chart-headline-delta.idle { color: var(--pending); }

.kpi-badge { font-size: 11px; font-weight: 600; padding: 1px 7px; border-radius: var(--radius-sm); margin-left: 6px; }
.kpi-badge.ok { background: var(--ok-bg); color: var(--ok); }
.kpi-badge.under { background: var(--warn-bg); color: var(--warn); }

#rdp-sku-table tbody tr.totals-row { font-weight: 700; border-top: 2px solid var(--border); }

.panel {
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  padding: 20px;
  margin-bottom: 20px;
}

.panel h2 { font-size: 15px; margin: 0 0 14px; color: var(--ink); }

/* Numbered section header (Truck Loading's Log a Truck / Trucks / Loading
   Authorization / Register cards) -- bleeds to the panel's edges via
   negative margin rather than restructuring .panel itself, so every other
   page's plain .panel/h2 pattern is untouched. */
.panel-section-head {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 14px 20px;
  margin: -20px -20px 20px;
  border-bottom: 1px solid var(--border-light);
  background: linear-gradient(180deg, #ffffff 0%, #f8fafc 100%);
}
.panel-section-num {
  width: 24px;
  height: 24px;
  border-radius: var(--radius);
  background: linear-gradient(135deg, #e5281f 0%, #b3160e 100%);
  color: #fff;
  font-size: 11px;
  font-weight: 700;
  display: flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
  box-shadow: 0 1px 3px rgba(217, 34, 24, 0.25);
}
.panel-section-num.neutral {
  background: linear-gradient(135deg, #334155 0%, #0f172a 100%);
  box-shadow: 0 1px 3px rgba(15, 23, 42, 0.2);
}
.panel-section-title {
  font-size: 14px;
  font-weight: 700;
  color: #0f172a;
  letter-spacing: 0.01em;
  flex: 1;
}
.panel-section-sub {
  font-size: 11.5px;
  color: var(--muted);
  font-weight: 400;
  margin-top: 2px;
  display: block;
}
.panel-section-count {
  font-size: 12px;
  color: var(--label);
  font-weight: 600;
  background: #f1f5f9;
  padding: 3px 10px;
  border-radius: var(--radius-full);
  border: 1px solid var(--border);
  white-space: nowrap;
  min-width: 0;
}
/* On a phone the head has no room to keep a count on one line beside the
   title -- let it wrap rather than push the whole page sideways. */
@media (max-width: 720px) {
  .panel-section-count { white-space: normal; overflow-wrap: break-word; }
}
.panel-section-intro { padding: 0 0 4px; font-size: 12px; color: var(--muted); }

.callout-note {
  font-size: 12px;
  color: var(--muted);
  padding: 10px 14px;
  background: #fdf6ec;
  border: 1px solid #f0dfb8;
  border-radius: var(--radius-lg);
  display: flex;
  gap: 8px;
}
.callout-note strong { color: #a3720c; font-weight: 700; }
/* Same shape, raised voice -- for a note that accompanies something the
   operator is about to do anyway rather than merely being told about. */
.callout-note-warn { background: var(--warn-bg); border-color: #f3c3bd; }
.callout-note-warn strong { color: var(--warn); }

/* Truck Loading's stock-availability banner -- amber when a planned SKU
   is only sitting on the production floor (transfer it to a location
   before loading), red when there's no stock recorded for it anywhere.
   Deliberately just a colored note, same shape as .callout-note, not a
   blocking modal -- the real block happens server-side at submit time. */
.stock-banner {
  font-size: 13px;
  padding: 12px 16px;
  border-radius: var(--radius-lg);
  margin-bottom: 14px;
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.stock-banner strong { font-weight: 700; }
.stock-banner.stock-banner-warn { background: var(--pending-bg); color: #7a4f0f; border: 1px solid #e9c98a; }
.stock-banner.stock-banner-critical { background: var(--warn-bg); color: var(--warn); border: 1px solid #f0b8b2; }

.dr-total-row td { background: var(--bg); border-top: 2px solid var(--border); }

.table-responsive {
  width: 100%;
  overflow-x: auto;
  -webkit-overflow-scrolling: touch;
}

/* Admin lookup tables (Products, Customers, FG SKUs, Locations, Stock
   Items) sit side-by-side in a grid -- without a capped height, a long
   list (e.g. 40+ customers) stretches its whole column and pushes every
   other lookup panel far down the page. Capped height + sticky header
   keeps each panel a fixed, professional size regardless of row count. */
.table-responsive-tall {
  max-height: 280px;
  overflow-y: auto;
}

.table-responsive-tall thead th {
  position: sticky;
  top: 0;
  background: #f1f3f6;
  z-index: 1;
}

/* Same capped-height + sticky-header pattern as .table-responsive-tall,
   but roomier -- for date-ranged registers (Loading History, and anywhere
   else picking "This Year" or "All Time" can return hundreds of rows).
   Without this, a wide date range just makes the whole page longer and
   longer instead of staying a fixed, scannable size. */
.table-scroll-register {
  max-height: 520px;
  overflow-y: auto;
}

.table-scroll-register thead th {
  position: sticky;
  top: 0;
  background: #f1f3f6;
  z-index: 1;
}

/* Same capped-height idea for a non-table list of cards (Truck Loading
   Register) -- keeps a page with many trucks currently in the yard from
   growing unbounded, still fully scrollable within its own panel. */
.scroll-panel-tall {
  max-height: 640px;
  overflow-y: auto;
  padding-right: 4px; /* keep the scrollbar off the card content */
}

table {
  width: 100%;
  border-collapse: collapse;
  font-size: 13px;
}

/* Data tables with a fixed column plan (colgroup below) -- keeps columns
   proportioned to their actual content instead of the browser's auto-layout
   dumping leftover width into whichever column happens to catch it. */
#trips-table, #dips-table, #dispatch-table, #gatepass-table,
#additives-table, #users-table, #tanks-table {
  table-layout: fixed;
  min-width: 720px; /* below this, .table-responsive scrolls instead of squeezing */
}

th, td {
  text-align: left;
  padding: 8px 10px;
  border: 1px solid var(--border);
  white-space: normal;
  overflow-wrap: break-word;
}

th { color: var(--label); font-weight: 700; font-size: 10.5px; letter-spacing: .3px; text-transform: uppercase; background: #f1f3f6; }

.cell-sub { color: var(--muted); font-size: 11px; white-space: nowrap; }

/* ---------- Free-text notes in a table (see noteCell() in core.js) ---------- */

/* Every remark / reason / comment / observation in the app renders through
   this one treatment, so a paragraph an operator typed can never redraw a
   register's column plan. The cap is a measure, not a pixel width: it is
   about how much prose a person can take in while scanning a row, and it
   stays the same measure on every screen so the registers read as one
   system. Two lines, then the reader asks for the rest. */
.note {
  max-width: 34ch;
  min-width: 0;
  color: var(--muted);
  font-size: 11.5px;
  line-height: 1.45;
  white-space: normal;
}

.note-body {
  display: -webkit-box;
  -webkit-box-orient: vertical;
  -webkit-line-clamp: 2;
  line-clamp: 2;
  overflow: hidden;
  /* anywhere, not break-word: a pasted URL or a batch code with no spaces
     is still one unbreakable token to break-word, and one of those is all
     it takes to blow the cap. */
  overflow-wrap: anywhere;
}

/* Opened, the note stops being a glance and becomes something to read, so
   it also claims a floor -- without one, a note opened inside a squeezed
   scrolling table degrades to one word per line. */
.note.is-open { min-width: 20ch; }
.note.is-open .note-body { -webkit-line-clamp: unset; line-clamp: unset; }

/* Borrows the table header's micro-label voice rather than inventing a
   fourth text style -- it reads as part of the table's own furniture. Only
   shown once the note has actually been measured as overflowing, so a
   two-word remark carries no control at all. */
.note-toggle {
  display: none;
  margin-top: 3px;
  padding: 0;
  border: 0;
  background: none;
  font-family: inherit;
  font-size: 10px;
  font-weight: 700;
  letter-spacing: .3px;
  text-transform: uppercase;
  color: var(--label);
  cursor: pointer;
}
.note.is-clamped .note-toggle { display: inline-block; }
.note-toggle:hover { color: var(--brand); }
.note-toggle:focus-visible { outline: 2px solid var(--brand); outline-offset: 2px; border-radius: var(--radius-sm); }

/* Paper has no "More" button, so a printed register carries the whole
   remark and drops the control. */
@media print {
  .note { max-width: none; }
  .note-body { display: block; overflow: visible; }
  .note-toggle { display: none !important; }
}

.badge {
  display: inline-block;
  padding: 3px 8px;
  border-radius: var(--radius-sm);
  font-size: 10.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .02em;
}

.badge.ok, .badge.used, .badge.received { color: var(--ok); background: var(--ok-bg); }
.badge.flagged, .badge.missing, .badge.unaccounted, .badge.critical, .badge.out_of_stock { color: var(--warn); background: var(--warn-bg); }
.badge.awaiting_plant, .badge.damaged, .badge.at_risk, .badge.partially_received, .badge.open { color: var(--pending); background: var(--pending-bg); }
.badge.voided, .badge.neutral { color: var(--muted); background: var(--bg); }

/* Stock Coverage risk rows -- two tiers so "below threshold but weeks away"
   reads differently from "critical / already out of stock" at a glance,
   not just via the text in the Coverage cell. */
.stock-row-at-risk { background: var(--pending-bg); }
.stock-row-critical { background: var(--warn-bg); }

.prod-hour-losses-list { display: flex; flex-wrap: wrap; gap: 4px; margin-top: 4px; }
.loss-chip {
  display: inline-flex; align-items: center; gap: 4px;
  padding: 2px 6px; border-radius: var(--radius-sm); font-size: 11px;
  background: var(--warn-bg); color: var(--warn); white-space: nowrap;
}
.loss-chip-remove { background: none; border: none; cursor: pointer; color: inherit; font-size: 13px; line-height: 1; padding: 0; }

.panel-head-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  flex-wrap: wrap;
  margin-bottom: 14px;
}
.panel-head-row h2 { margin: 0; }

/* Compact square icon button for a table row that needs several actions
   in a narrow, fixed-width cell (Users' Edit/Permissions/Roles/Status,
   the down-time picker's "add a new reason") -- four full-text
   .secondary buttons stacked in a 36%-wide table-layout:fixed column
   either wrapped onto several lines or ran off the row. One glyph, one
   tooltip (the `title` attribute), same neutral chrome as .secondary so
   it still reads as "an action on this row" rather than a fifth new
   visual language. `.icon-btn-danger`/`.icon-btn-ok` are for the one
   action per row whose direction (turning access off vs. back on)
   is worth a colour hint on hover -- everything else stays neutral so
   colour keeps meaning "this one is different", not decoration. */
.icon-btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 30px;
  height: 30px;
  padding: 0;
  flex-shrink: 0;
  background: #fff;
  color: var(--label);
  border: 1px solid var(--border);
  border-radius: var(--radius-sm);
}
.icon-btn svg { width: 15px; height: 15px; }
.icon-btn:hover { background: var(--bg); color: var(--ink); }
.icon-btn:focus-visible { outline: 2px solid var(--brand); outline-offset: 1px; }
.icon-btn.icon-btn-danger:hover { background: var(--warn-bg); color: var(--warn); border-color: var(--warn); }
.icon-btn.icon-btn-ok:hover { background: var(--ok-bg); color: var(--ok); border-color: var(--ok); }
.icon-btn.icon-btn-sm { width: 26px; height: 26px; }
.icon-btn.icon-btn-sm svg { width: 13px; height: 13px; }

.row-actions { display: flex; gap: 6px; flex-wrap: wrap; }

.btn-link {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  text-decoration: none;
  padding: 7px 14px;
  font-size: 13px;
  font-weight: 600;
  border-radius: var(--radius);
  border: 1px solid var(--ok);
  color: var(--ok);
  background: var(--ok-bg);
  white-space: nowrap;
  transition: background-color 0.12s ease, box-shadow 0.12s ease;
}

.btn-link svg { width: 15px; height: 15px; flex-shrink: 0; }

.btn-link:hover {
  background: var(--ok);
  color: #fff;
  box-shadow: 0 1px 4px rgba(0,0,0,0.12);
}

.form-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));
  gap: 4px 16px;
}

/* A repeating checklist-style sub-record within a form (e.g. one filling
   QC observation) -- labeled fields in a grid, not a wide table row. */
.obs-block {
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  padding: 14px 16px;
  margin-bottom: 14px;
  background: var(--bg);
}
.obs-block-head {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 8px;
}
.obs-block-head strong { font-size: 13px; color: var(--muted); text-transform: uppercase; letter-spacing: .03em; }
.obs-block h4 { font-size: 12px; text-transform: uppercase; letter-spacing: .03em; color: var(--muted); margin: 12px 0 4px; }

.two-col {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 20px;
}

.two-col + .two-col { margin-top: 20px; }

/* Lets a wide/many-column panel (e.g. Admin -> Products & Lookups' Stock
   Coverage Items, with 7 columns and long free-text item names) break out
   of the half-width column instead of being squeezed illegible. */
.two-col-full { grid-column: 1 / -1; }

@media (max-width: 720px) {
  .two-col { grid-template-columns: 1fr; }
}

.date-picker { display: flex; align-items: center; gap: 8px; margin: 0; }
.date-picker input[type=date], .date-picker select { width: auto; margin-bottom: 0; }

.toast {
  position: fixed;
  bottom: 20px;
  right: 20px;
  background: var(--ink);
  color: #fff;
  padding: 10px 16px;
  border-radius: 8px;
  font-size: 13px;
  box-shadow: 0 4px 16px rgba(0,0,0,0.15);
}

.toast.error { background: var(--warn); }
/* Succeeded, with something worth reading -- deliberately not the failure
   red. The darker amber is the readable-on-white --pending token dropped
   onto a dark chip, so it stays distinct from both the plain ink toast
   and the error one. */
.toast.warn { background: #8a5a0b; }
/* Idle-logout countdown (core.js). Top-centre and persistent, unlike a
   toast, because it has to be noticed by someone who has walked away. */
.idle-warning {
  position: fixed;
  top: 12px;
  left: 50%;
  transform: translateX(-50%);
  z-index: 10000;
  max-width: calc(100vw - 32px);
  background: #8a5a0b;
  color: #fff;
  padding: 10px 16px;
  border-radius: 8px;
  font-size: 13px;
  box-shadow: 0 4px 16px rgba(0,0,0,0.2);
}
.muted { color: var(--muted); font-size: 12px; }

.role-badge {
  display: inline-block;
  padding: 2px 8px;
  border-radius: var(--radius-sm);
  background: var(--bg);
  color: var(--muted);
  font-size: 11px;
  text-transform: capitalize;
  margin-right: 8px;
}

/* Admin > Users, Role column. A user can hold several roles, and the
   extra ones are what open up extra menus, so the register lists them
   all rather than only users.role. The primary reads solid and the
   additional ones outlined, so "which one is the main job" survives at a
   glance without a second column or a legend. */
.user-roles-cell { display: flex; flex-wrap: wrap; gap: 4px; }

.role-pill {
  display: inline-block;
  padding: 2px 7px;
  border-radius: var(--radius-sm);
  font-size: 11px;
  line-height: 1.5;
  border: 1px solid var(--border);
  background: #fff;
  color: var(--muted);
  white-space: nowrap;
}

.role-pill.role-pill-primary {
  background: var(--bg);
  border-color: var(--border);
  color: var(--label);
  font-weight: 600;
}

.select-with-icon {
  display: flex;
  align-items: center;
  gap: 8px;
}

.select-with-icon select { margin-bottom: 0; flex: 1; }

.icon-preview {
  flex-shrink: 0;
  width: 32px;
  height: 32px;
  display: flex;
  align-items: center;
  justify-content: center;
}

.icon-cell {
  display: inline-flex;
  align-items: center;
  gap: 8px;
}

.icon-cell svg { flex-shrink: 0; }

table svg { display: block; }

.inline-form {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  margin-bottom: 16px;
  align-items: flex-start;
}

.inline-form input { margin-bottom: 0; }

.view-loading {
  padding: 40px 0;
  text-align: center;
  color: var(--muted);
  font-size: 14px;
}

/* Date-range filter bar (Goods Receipt register): quick presets + a manual
   From/To fallback, same idea as most SaaS date pickers. */
.date-range-bar {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 12px;
  margin-bottom: 8px;
}

.date-range-presets {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
}

.chip {
  border: 1px solid var(--border);
  background: var(--card);
  color: var(--label);
  border-radius: var(--radius);
  padding: 7px 14px;
  font-size: 12px;
  font-weight: 600;
  cursor: pointer;
}

.chip:hover { background: var(--bg); }

.chip.active {
  background: var(--brand);
  border-color: var(--brand);
  color: #fff;
}

/* Dashboard's combined Stock at Risk / FG Stock Discrepancies / Tank Dip
   Status card -- one panel, three pill tabs switching which table shows,
   instead of three separate full-width panels stacked one after another.
   Panel-switching is pure CSS visibility (.hidden), so none of the three
   sections' own JS (dips.js's filter chips, etc.) needs to know it's now
   living inside a tab. */
.dash-tabs {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  margin-bottom: 16px;
}

.dash-tab-btn {
  border: 1px solid var(--border);
  background: var(--card);
  color: var(--label);
  border-radius: 999px;
  padding: 8px 16px;
  font-size: 12.5px;
  font-weight: 600;
  cursor: pointer;
}

.dash-tab-btn:hover { background: var(--bg); }

.dash-tab-btn.active {
  background: var(--navy);
  border-color: var(--navy);
  color: #fff;
}

.dash-tab-panel.hidden { display: none; }

/* Marks the register row whose record is currently loaded into the form
   above it. GRN-specific name, app-wide use -- around twenty modules apply
   it (admin, maintenance, QC, production, tank-qc, truck-loading, ...), so
   it is not GRN's to remove. The grouped .docket-edit-group does the same
   job for registers whose rows come in groups. */
.grn-edit-row { background: var(--brand-tint); }

.inline-form button { flex-shrink: 0; }

/* Units of Measure modal (Admin -> Stock Items -> Units), matching the
   per-item unit configuration screens the user modeled this on. */
.modal-backdrop {
  position: fixed;
  inset: 0;
  background: rgba(28, 39, 51, 0.5);
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 1000;
  padding: 20px;
}

.modal-box {
  background: var(--card);
  border-radius: var(--radius-lg);
  max-width: 560px;
  width: 100%;
  max-height: 85vh;
  overflow-y: auto;
  padding: 20px;
  box-shadow: 0 12px 32px rgba(28, 39, 51, 0.25);
}

/* A modal that has to show a table -- the payment history behind an
   authorization decision. 560px forces a six-column table into a scroll
   bar on a desktop, which is the one place the reader must not have to
   work to see the figures they are deciding on. */
.modal-box-wide { max-width: 780px; }
/* The order-viewer popup: it carries the full printable document (.po-doc
   caps at 940px, see the "what shows here is exactly what prints" comments
   in customer-orders.js), so it needs more room than any other modal in the
   app -- 780px would force that document to shrink or scroll horizontally,
   which a printable sheet must never do. */
.modal-box-xwide { max-width: 1000px; }

/* The review checklist: one line per thing confirmed, tick or cross first
   so the eye can run down the column rather than read three sentences. */
.co-review-checklist {
  display: flex;
  flex-direction: column;
  gap: 6px;
  margin: 10px 0;
}
.co-review-line {
  display: flex;
  align-items: baseline;
  gap: 8px;
  flex-wrap: wrap;
}
.co-review-line-label { font-weight: 600; }

.co-doc-list { margin: 8px 0; padding-left: 18px; }
.co-doc-list li { margin-bottom: 6px; }

.modal-head-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 14px;
}

.modal-head-row h2 { margin: 0; }

.modal-close-btn {
  background: none;
  border: none;
  font-size: 20px;
  line-height: 1;
  cursor: pointer;
  color: var(--muted);
  padding: 4px;
}

.modal-close-btn:hover { color: var(--ink); }

/* Choose Unit of Measure popup (GRN row) -- tiles for each configured unit,
   matching the reference POS's "pick a tile, click OK" pattern. */
.unit-choice-tiles {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
}

.unit-choice-tile {
  padding: 14px 18px;
  border-radius: 8px;
  border: 2px solid var(--border);
  background: var(--bg);
  color: var(--ink);
  font-weight: 600;
  cursor: pointer;
  min-width: 90px;
}

.unit-choice-tile:hover { border-color: var(--brand); }
.unit-choice-tile.selected { border-color: var(--brand); background: var(--brand-tint); }

/* Reports -> Production down-time bar charts. Plain flex bars rather than
   SVG/canvas: one measure (minutes lost) ranked across a handful of
   categories, so a single flat hue (navy -- kept distinct from the brand
   red used everywhere for interactive chrome) with a direct value label
   reads cleanly without needing a legend. */
.report-bar-row {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 5px 0;
}

.report-bar-label {
  width: 220px;
  flex-shrink: 0;
  font-size: 13px;
  color: var(--ink);
  text-align: right;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.report-bar-track {
  flex: 1;
  min-width: 40px;
  background: var(--bg);
  border-radius: 4px;
  height: 20px;
  position: relative;
}

.report-bar-fill {
  height: 100%;
  min-width: 3px;
  background: var(--navy);
  border-radius: 0 4px 4px 0;
  transition: background 0.15s;
}

.report-bar-row:hover .report-bar-fill { background: var(--navy-light); }

/* Dashboard's two category-breakdown panels (Dispatch by SKU / Production
   by Line) reuse the report-bar pattern above but each keep the trend
   chart's own hue (blue / teal) they're grouped with, scoped by container
   id so the Reports pages' own bars are untouched. */
#chart-dispatch-by-sku .report-bar-fill { background: var(--accent-blue); }
#chart-dispatch-by-sku .report-bar-row:hover .report-bar-fill { background: var(--accent-blue-dark); }
#chart-production-by-line .report-bar-fill { background: var(--accent-teal); }
#chart-production-by-line .report-bar-row:hover .report-bar-fill { background: var(--accent-teal-dark); }

.report-bar-value {
  width: 90px;
  flex-shrink: 0;
  font-family: var(--font-mono);
  font-size: 12.5px;
  font-weight: 600;
  color: var(--muted);
}

@media (max-width: 640px) {
  .report-bar-label { width: 120px; font-size: 12px; }
  .report-bar-value { width: 70px; }
}

/* ==================== Truck Loading ====================

   The screen follows one truck from Sales' plan to the gate, and two
   components carry it.

   (1) The yard rail (.tl-rail): the four stages in the order a truck
       actually passes through them, drawn as joined segments so the page
       opens on the shape of the journey rather than on four unrelated
       KPI tiles. The sequence is not decoration -- a truck cannot load
       before it is authorized, or leave before it is loaded -- and every
       segment is also the filter for that stage, so the overview and the
       work are the same control. The last segment is the way out, to
       Loading History.

   (2) A register of one line per truck (.tl-band / .tl-row / .tl-drawer),
       grouped under the gate pass release that authorized it. The release
       band carries the three authorization gates once; each truck is a
       single line with a load gauge; the load form lives in a drawer that
       is built only when opened, one at a time. A yard with twenty trucks
       costs twenty lines rather than twenty open forms. */

/* Process Flow Rail */
.tl-rail {
  margin-bottom: 20px;
}

/* View Switcher Tabs */
.tl-view-nav {
  display: flex;
  align-items: center;
  gap: 6px;
  background: #ffffff;
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  padding: 4px;
  margin-bottom: 20px;
  box-shadow: var(--shadow-sm);
  overflow-x: auto;
  -webkit-overflow-scrolling: touch;
}

.tl-view-btn {
  flex: 1;
  min-width: 140px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  padding: 9px 14px;
  border-radius: var(--radius);
  border: 1px solid transparent;
  background: transparent;
  color: var(--label);
  font-size: 13px;
  font-weight: 600;
  cursor: pointer;
  transition: all 0.15s ease;
  white-space: nowrap;
}

.tl-view-btn svg {
  width: 16px;
  height: 16px;
  opacity: 0.8;
}

.tl-view-btn:hover {
  background: #f8fafc;
  color: var(--ink);
}

.tl-view-btn.active {
  background: #ffffff;
  color: var(--brand);
  border-color: var(--border);
  box-shadow: var(--shadow-sm);
  font-weight: 700;
}

.tl-view-btn.active svg {
  opacity: 1;
  stroke: var(--brand);
}

.tl-tab-badge {
  font-size: 11px;
  font-weight: 700;
  padding: 2px 7px;
  border-radius: var(--radius-full);
  background: #f1f5f9;
  color: var(--label);
  line-height: 1;
}

.tl-view-btn.active .tl-tab-badge {
  background: var(--brand-tint);
  color: var(--brand);
}

/* Operation Grid & Search Controls */
.tl-ops-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 20px;
  margin-bottom: 20px;
}

/* The grid holds two panels, and the view switcher shows one of them at a
   time -- so in Check-in and in Sales Loading Plan the second column stayed
   reserved and empty, pinning the visible panel to half the page while the
   other half sat blank. Set by tlSwitchView() from how many panels are
   actually visible, rather than :has(), so the rule is stated where the
   view is decided. */
.tl-ops-grid.tl-ops-grid-single {
  grid-template-columns: 1fr;
}

.lu-search-box {
  position: relative;
  display: flex;
  align-items: center;
  margin-bottom: 16px;
}

.lu-search-icon {
  position: absolute;
  left: 12px;
  width: 16px;
  height: 16px;
  color: var(--muted);
  pointer-events: none;
  display: flex;
  align-items: center;
  justify-content: center;
}
.lu-search-icon svg {
  width: 16px;
  height: 16px;
}

.lu-search-input {
  width: 100%;
  padding: 9px 12px 9px 36px !important;
  margin-bottom: 0 !important;
  border-radius: var(--radius) !important;
  background: #ffffff !important;
  font-size: 13.5px !important;
}

/* Register Groups, Bands, and Truck Rows */
:root {
  --tl-q-w: 64px;
}

/* The register widens the queue gutter over the 64px default. Verified in a
   browser on 2026-08-22 at 76px across the band and every plate, at both
   1280px and 375px -- the load-order numeral is the one column that never
   collapses, so it is sized for the numeral rather than inherited. */
.tl-register-groups {
  --tl-q-w: 76px;
}

.tl-group {
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  margin-bottom: 16px;
  box-shadow: var(--shadow-sm);
  overflow: hidden;
  transition: border-color 0.15s ease, box-shadow 0.15s ease;
}

.tl-group:hover {
  border-color: #cbd5e1;
  box-shadow: var(--shadow);
}

.tl-band {
  display: grid;
  grid-template-columns: var(--tl-q-w) 1.6fr 1fr auto;
  gap: 14px;
  align-items: center;
  padding: 14px 18px;
  background: #f8fafc;
  border-bottom: 1px solid var(--border-light);
}

.tl-band-id {
  min-width: 0;
}

.tl-band-header-line {
  display: flex;
  align-items: center;
  gap: 10px;
  flex-wrap: wrap;
  margin-bottom: 4px;
}

.tl-band-cust {
  font-size: 14.5px;
  font-weight: 700;
  color: #0f172a;
  letter-spacing: -0.01em;
}

.tl-truck-count-pill {
  font-size: 11px;
  font-weight: 600;
  background: #e2e8f0;
  color: #334155;
  padding: 2px 8px;
  border-radius: var(--radius-full);
}

.tl-ref {
  display: inline-flex;
  align-items: baseline;
  gap: 5px;
  min-width: 0;
}

.tl-ref-k {
  font-size: 9px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .06em;
  color: var(--muted);
}

.tl-ref-v {
  font-family: var(--font-mono);
  font-size: 12px;
  font-weight: 600;
  color: var(--ink);
}

.tl-ref-gp {
  background: #ffffff;
  border: 1px solid var(--border);
  padding: 2px 8px;
  border-radius: 4px;
  box-shadow: 0 1px 2px rgba(0, 0, 0, 0.02);
}

.tl-ref-ticket {
  background: #f1f5f9;
  border: 1px solid var(--border);
  padding: 2px 8px;
  border-radius: 4px;
}

/* The loading authorization a truck is moving on. Toned green because it
   is the one chip on the row that means "this may proceed"; an override
   basis is amber, so the rows resting on somebody's signature rather than
   on arithmetic are the ones the eye lands on first. */
.tl-ref-auth {
  background: #ecfdf5;
  border: 1px solid #a7f3d0;
  padding: 2px 8px;
  border-radius: 4px;
}

.tl-ref-auth .tl-ref-k { color: #047857; }
.tl-ref-auth .tl-ref-v { color: #065f46; }

.tl-ref-auth-override {
  background: #fffbeb;
  border-color: #fde68a;
}

.tl-ref-auth-override .tl-ref-k { color: #b45309; }
.tl-ref-auth-override .tl-ref-v { color: #92400e; }

.tl-auth {
  display: flex;
  flex-direction: column;
  gap: 3px;
  min-width: 0;
}

.tl-auth-verdict {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-size: 12px;
  font-weight: 700;
  padding: 3px 9px;
  border-radius: var(--radius-full);
  width: fit-content;
}

.tl-auth-ok {
  background: var(--ok-bg);
  color: var(--ok);
  border: 1px solid var(--ok-border);
}

.tl-auth-blocked {
  background: var(--warn-bg);
  color: var(--warn);
  border: 1px solid var(--warn-border);
}

.tl-auth-dot {
  width: 6px;
  height: 6px;
  border-radius: 50%;
  background: currentColor;
}

.tl-auth-fine {
  font-size: 11px;
  color: var(--muted);
  line-height: 1.3;
}

.tl-fine-sep {
  color: #cbd5e1;
  padding: 0 4px;
}

.tl-band-actions {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
  justify-content: flex-end;
}

.tl-band-actions button.secondary {
  padding: 6px 12px;
  font-size: 12.5px;
}

/* Truck Row */
.tl-row {
  display: grid;
  grid-template-columns: var(--tl-q-w) 1fr auto;
  gap: 14px;
  align-items: center;
  padding: 12px 18px;
  background: #ffffff;
  border-bottom: 1px solid var(--border-light);
  transition: background 0.15s ease;
}

.tl-row:last-of-type {
  border-bottom: none;
}

.tl-row:hover {
  background: #f8fafc;
}

.tl-row-next {
  background: #f0fdf4 !important;
  border-left: 3px solid var(--ok);
}

.tl-row-closed {
  opacity: 0.7;
  background: #fbfcfe;
}

.tl-row-closed:hover {
  opacity: 0.95;
}

.tl-row-highlight {
  animation: tlRowPulse 2.4s ease-out;
}

@keyframes tlRowPulse {
  0% { background: rgba(217, 34, 24, 0.2); }
  100% { background: #ffffff; }
}

/* Queue position pill */
/* Truck Information in Row */
.tl-row-main {
  min-width: 0;
  display: flex;
  flex-direction: column;
  gap: 6px;
}

.tl-row-id {
  display: flex;
  align-items: center;
  gap: 10px;
  flex-wrap: wrap;
}

.tl-truck-plate {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 3px 8px;
  background: #ffffff;
  border: 1.5px solid #1e293b;
  border-radius: 4px;
  box-shadow: 0 1px 2px rgba(0, 0, 0, 0.06);
  font-family: var(--font-mono);
  font-weight: 700;
  font-size: 13px;
  letter-spacing: 0.04em;
  color: #0f172a;
}

.tl-truck-plate-icon {
  font-size: 13px;
  line-height: 1;
}

.tl-truck-no {
  letter-spacing: 0.04em;
}

.tl-row-step {
  font-size: 12px;
  color: var(--muted);
  font-weight: 500;
}

.tl-row-step-go {
  color: var(--ok);
  font-weight: 600;
}

.tl-row-closed-note {
  font-size: 11.5px;
  color: var(--muted);
}

.tl-row-actions {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
  justify-content: flex-end;
}

/* "Log load" while its drawer is open. Without this the button that opened
   the drawer looks identical to the one that would open it, and with one
   drawer allowed at a time there is nothing else on the row saying which
   truck the open form belongs to. aria-expanded already carries this for
   assistive tech; this is the visible half. */
.tl-drawer-toggle.is-open {
  background: var(--navy);
  border-color: var(--navy);
  color: #ffffff;
}

.tl-drawer-toggle.is-open:hover {
  background: var(--navy-mid);
  border-color: var(--navy-mid);
}

/* Filter matched nothing -- sits inside the register list, so it needs its
   own padding rather than the group spacing it would otherwise inherit. */
.tl-empty-filter {
  padding: 16px 4px 4px;
}

.tl-row-actions button {
  padding: 7px 14px;
  font-size: 12.5px;
}

/* Quantity Meter */
.tl-row-meter {
  max-width: 480px;
}

.qty-meter {
  display: flex;
  align-items: center;
  gap: 10px;
}

.qty-meter-track {
  flex: 1;
  height: 8px;
  background: #e2e8f0;
  border-radius: var(--radius-full);
  overflow: hidden;
  position: relative;
}

.qty-meter-fill {
  height: 100%;
  border-radius: var(--radius-full);
  background: var(--brand);
  transition: width 0.3s ease;
}

.qty-meter-fill.is-full {
  background: var(--ok);
}

.qty-meter-label {
  font-family: var(--font-mono);
  font-size: 12px;
  font-weight: 600;
  color: var(--ink);
  white-space: nowrap;
}

/* Expanded Drawer (Load Form) */
.tl-drawer {
  background: #f8fafc;
  border-top: 1px solid var(--border);
  padding: 20px 24px;
  box-shadow: inset 0 2px 4px rgba(0, 0, 0, 0.02);
}

.tl-drawer-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 16px;
  padding-bottom: 12px;
  border-bottom: 1px solid var(--border-light);
}

.tl-drawer-title {
  font-size: 14px;
  font-weight: 700;
  color: #0f172a;
}

.tl-drawer-close {
  background: transparent;
  border: none;
  color: var(--muted);
  font-size: 18px;
  padding: 4px 8px;
  cursor: pointer;
}
.tl-drawer-close:hover {
  color: var(--ink);
}

.tl-load-panel-fields {
  display: flex;
  gap: 16px;
  margin-bottom: 14px;
}

.tl-planned-load-block {
  display: block;
}
.tl-planned-load-block label {
  margin-top: 10px;
}

/* --- Truck Loading: missing classes restored below --- */

/* Stock-availability banners at the top of the register, one per SKU that
   has an issue. Critical = zero stock anywhere; warn = only on the
   production floor, not yet in a warehouse location. */
.stock-banner {
  padding: 10px 16px;
  border-radius: var(--radius);
  font-size: 13px;
  line-height: 1.45;
  margin-bottom: 10px;
  font-weight: 500;
}
.stock-banner strong { font-weight: 700; }

.stock-banner-critical {
  background: var(--warn-bg);
  border: 1px solid var(--warn-border);
  color: #7f1d1d;
}

.stock-banner-warn {
  background: var(--pending-bg);
  border: 1px solid var(--pending-border);
  color: #78350f;
}

/* Reuses the same banner shape for a positive result -- the GRN QC
   clearance check (grn.js) is the first caller that needs to say "this is
   fine", not just warn or block. */
.stock-banner-ok {
  background: var(--ok-bg);
  border: 1px solid var(--ok-border);
  color: #065f46;
}

/* Planned-by-Sales group and band: visually distinct from yard-resident
   groups so the register reads as two clear sections. */
.tl-group-plan {
  border-style: dashed;
  border-color: #cbd5e1;
  background: #fcfcfe;
}
.tl-group-plan:hover {
  border-color: #94a3b8;
}

.tl-band-plan {
  background: #f1f5f9;
  border-bottom-style: dashed;
}

/* Ghost rows: Sales-planned trucks not yet logged into the yard. They are
   real plan entries and need to be visible, but dimmed to show they are
   not physically here yet. */
.tl-row-ghost {
  background: #fafbfd;
  opacity: 0.72;
  border-bottom-style: dashed;
}
.tl-row-ghost:hover {
  opacity: 0.92;
  background: #f5f7fa;
}

/* Band being edited -- gentle highlight so the operator sees which
   release the check-in form below is updating. */
.tl-band-editing {
  outline: 2px solid var(--brand);
  outline-offset: -2px;
  background: var(--brand-tint);
}

/* Authorization verdict: idle state (planned-by-Sales, not in the yard).
   Neutral tone alongside the existing ok/blocked variants. */
.tl-auth-idle {
  background: var(--neutral-bg);
  color: var(--neutral-fg);
  border: 1px solid var(--border);
}

/* CEO approval note beneath the auth verdict -- free-text so it wraps. */
.tl-auth-note {
  margin-top: 4px;
  max-width: 360px;
}

/* Step guidance notes on each truck row -- the one-line sentence beneath
   the meter telling the operator what happens next. Four tones:
   - default (muted): informational, no action
   - go (green): ready, next action named
   - wait (amber): queue-blocked, name the blocker
   - blocked (red): authorization-blocked */
.tl-row-step {
  font-size: 12px;
  color: var(--muted);
  font-weight: 500;
  line-height: 1.4;
}

.tl-row-step-go {
  color: var(--ok);
  font-weight: 600;
}

.tl-row-step-wait {
  color: var(--pending);
  font-weight: 600;
}

.tl-row-step-blocked {
  color: var(--warn);
  font-weight: 600;
}

/* Remarks: why Finance asked, why the CEO answered -- on the truck's own
   row. Deliberately quieter than stepNote above it: stepNote is what to do
   right now, this is why, and the two must not compete for the eye. */
.tl-row-remark {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 6px;
  margin-top: 4px;
  font-size: 12px;
}
.tl-row-remark-tag {
  font-weight: 600;
  color: var(--label);
  white-space: nowrap;
}
.tl-row-remark .note { font-size: 12px; }

/* The inline "Show it" jump link inside a step-wait note. Styled as a
   subtle inline link-button, not a full action button. */
.tl-step-jump {
  display: inline;
  background: none;
  border: none;
  box-shadow: none;
  color: var(--accent-blue);
  font-size: 12px;
  font-weight: 600;
  padding: 0 2px;
  margin-left: 4px;
  text-decoration: underline;
  text-underline-offset: 2px;
  cursor: pointer;
}
.tl-step-jump:hover {
  color: var(--accent-blue-dark);
  background: none;
  box-shadow: none;
}

/* SKU name and plain-text labels beside the quantity meter. */
.tl-row-sku {
  font-size: 12px;
  color: var(--muted);
  font-weight: 500;
  margin-left: 2px;
}

.tl-row-plain {
  font-size: 13px;
  color: var(--label);
  font-weight: 500;
}

/* "Clear" button in the register's filter label -- inline link, not a
   full primary button. */
.tl-clear-filter {
  display: inline;
  background: none;
  border: none;
  box-shadow: none;
  color: var(--brand);
  font-size: 12px;
  font-weight: 700;
  padding: 0 4px;
  margin-left: 6px;
  text-decoration: underline;
  text-underline-offset: 2px;
  cursor: pointer;
}
.tl-clear-filter:hover {
  color: var(--brand-dark);
  background: none;
  box-shadow: none;
}

/* Small truck number in plan table and history table rows -- mono,
   compact, same face as the .tl-truck-plate but without the plate
   border treatment. */
.tl-truck-no-sm {
  font-family: var(--font-mono);
  font-size: 12.5px;
  font-weight: 700;
  letter-spacing: 0.03em;
  color: var(--ink);
}

/* Zero-stock row in the location-availability mini-table shown when a
   location is picked during check-in. */
.stock-row-critical {
  color: var(--warn);
  font-weight: 600;
}

/* Compact availability table inside the planned-load picker. */
.tl-loc-avail-table {
  font-size: 12px;
  border-collapse: collapse;
}
.tl-loc-avail-table th {
  font-size: 10px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .04em;
  color: var(--muted);
  border-bottom: 1px solid var(--border);
  padding: 4px 8px;
  text-align: left;
}
.tl-loc-avail-table td {
  padding: 4px 8px;
  border-bottom: 1px solid var(--border-light);
}

/* "All Panels" button in the view switcher -- slightly more muted than
   the main tabs so it reads as a utility, not a fifth view. */
.tl-view-btn-all {
  flex: 0 0 auto;
  min-width: 110px;
  border-left: 1px solid var(--border-light);
}

/* Grouped field block in the check-in form -- gives the customer picker
   its own quiet card so the form scans as distinct steps. */
.form-group-card {
  background: #f8fafc;
  border: 1px solid var(--border-light);
  border-radius: var(--radius);
  padding: 12px 14px;
  margin-bottom: 4px;
}
.form-group-card > label { margin-top: 0; }
.form-group-card > select,
.form-group-card > input { margin-bottom: 0; }

/* The register is the operational centre of the screen -- a left accent
   marks it out from the plan / check-in / history panels around it. */
.tl-panel-active {
  border-left: 3px solid var(--brand);
}

/* Trucks-in-this-group header row above the truck cards in check-in. */
.tl-trucks-header-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
  margin-top: 16px;
  margin-bottom: 4px;
}

/* --- Load Drawer: fields, locked-SKU, shortfall panel --- */

.tl-load-panel-title {
  font-size: 14px;
  font-weight: 700;
  color: var(--ink);
  margin-bottom: 12px;
  letter-spacing: -0.01em;
}

.tl-load-field {
  min-width: 0;
  flex: 1 1 160px;
}
.tl-load-field label {
  margin-bottom: 6px;
}

/* Read-only locked SKU/ticket readout in the drawer — looks like a filled
   input that can't be changed. */
.tl-load-locked-sku {
  font-size: 13.5px;
  font-weight: 600;
  color: var(--ink);
  padding: 8px 12px;
  background: #f1f5f9;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  margin-bottom: 4px;
}

/* Location row inside the load form drawer. */
.tl-load-loc-controls {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-bottom: 4px;
}

/* Per-location stock availability note — sits right below its row. */
.tl-load-loc-avail {
  font-size: 11.5px;
  line-height: 1.3;
  margin-bottom: 8px;
  min-height: 16px;
}

/* Row separation is carried by the availability note's own margin above,
   so the wrapper adds none -- restoring the old 10px here on top of it
   would double-space the bays. Only the trailing gap under the last row
   needs removing, which is what the old :last-child rule did. */
.tl-load-loc-row:last-child .tl-load-loc-avail {
  margin-bottom: 0;
}

/* Red "X short of this load" variant of the availability note. */
.tl-avail-short {
  color: var(--warn);
  font-weight: 600;
}

/* Allocation note for Sales-locked trucks -- matches/mismatches the
   planned total. Switches to error-text class when over/under. */
.tl-load-alloc-note {
  font-size: 12px;
  color: var(--muted);
  font-weight: 500;
}

/* Shortfall acknowledgment panel -- revealed when a location has less
   stock on record than this load asks for. Styled as a cautionary box,
   not an error: loading past a low record is allowed with a reason. */
.tl-load-shortfall {
  background: var(--pending-bg);
  border: 1px solid var(--pending-border);
  border-radius: var(--radius);
  padding: 14px 16px;
  margin-top: 14px;
}

.tl-load-shortfall-head {
  font-size: 13px;
  font-weight: 600;
  color: #78350f;
  margin-bottom: 10px;
  line-height: 1.4;
}

.tl-load-shortfall-check {
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 13px;
  font-weight: 500;
  color: var(--ink);
  margin-bottom: 8px;
  text-transform: none;
  letter-spacing: normal;
}
.tl-load-shortfall-check input[type="checkbox"] {
  width: auto;
  margin: 0;
}

.tl-load-shortfall-reason {
  width: 100%;
  margin-bottom: 0;
}

/* --- Planned Load cell states (check-in form) --- */

/* The toggle link when collapsed -- and the "has existing plan" variant
   that summarizes what was already entered. */
.tl-plan-toggle {
  background: none;
  border: 1px dashed var(--border);
  border-radius: var(--radius);
  padding: 8px 14px;
  width: 100%;
  text-align: left;
  font-size: 12.5px;
  font-weight: 500;
  color: var(--muted);
  cursor: pointer;
  box-shadow: none;
  margin-top: 10px;
  transition: all 0.15s ease;
}
.tl-plan-toggle:hover {
  background: #f8fafc;
  border-color: #94a3b8;
  color: var(--label);
  box-shadow: none;
}

.tl-plan-toggle.has-plan {
  border-style: solid;
  border-color: var(--ok-border);
  background: var(--ok-bg);
  color: var(--ok);
  font-weight: 600;
}
.tl-plan-toggle.has-plan:hover {
  background: #d1fae5;
}

/* Locked state: Sales-plan-matched. Shows the SKU and quantity as a chip
   with only the location to pick. */
.tl-plan-locked-chip {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
  background: var(--ok-bg);
  border: 1px solid var(--ok-border);
  border-radius: var(--radius);
  padding: 8px 12px;
  margin-top: 10px;
}

.tl-plan-locked-label {
  font-size: 10px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .06em;
  color: var(--ok);
  background: rgba(5, 150, 105, 0.12);
  padding: 2px 8px;
  border-radius: var(--radius-full);
}

.tl-plan-locked-sku {
  font-size: 13px;
  font-weight: 700;
  color: var(--ink);
}

.tl-plan-locked-loc {
  margin-top: 8px;
}

/* Open state: free-entry picker for ad-hoc planned loads. */
.tl-plan-open-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
}

.tl-plan-collapse-btn {
  background: none;
  border: none;
  box-shadow: none;
  font-size: 12px;
  font-weight: 600;
  color: var(--muted);
  padding: 4px 8px;
  cursor: pointer;
}
.tl-plan-collapse-btn:hover {
  color: var(--ink);
  background: none;
  box-shadow: none;
}

/* --- FG Loading Plan table helpers --- */

/* Sequence number cell -- gauge-cut mono numeral. */
.tl-plan-seq {
  font-family: var(--font-display);
  font-size: 16px;
  font-weight: 700;
  color: var(--ink);
}

/* Stage column -- flex container for badge + jump button. */
.tl-plan-stage {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
}

/* "Show in register" jump button inside the plan table. */
.tl-plan-jump {
  font-size: 11.5px;
  padding: 4px 10px;
}

/* Responsive Rules for Truck Loading */
@media (max-width: 960px) {
  .tl-ops-grid {
    grid-template-columns: 1fr;
  }
}

@media (max-width: 820px) {
  .tl-band, .tl-row {
    grid-template-columns: var(--tl-q-w) 1fr;
  }
  .tl-auth, .tl-band-actions, .tl-row-actions {
    grid-column: 2;
    justify-content: flex-start;
  }
  .tl-load-panel-fields {
    flex-direction: column;
  }
}

/* Trucks flow across the width instead of stacking. A customer bringing
   five trucks used to mean five full-width cards and a page you had to
   scroll to reach the signature; the same five now fill the row first.
   auto-fill rather than auto-fit on purpose -- with one truck logged, a
   card that stretched to the full 1400px would give two short codes
   absurdly wide inputs. align-items:start so a card whose sales-plan
   block is open doesn't drag its neighbours' height with it. */
.tl-trucks-list {
  margin-top: 6px;
  display: grid;
  /* min() and not a bare 360px: minmax()'s minimum is a hard floor, so on a
     375px phone the track stayed 360px wide inside a narrower container and
     pushed the card into horizontal overflow. Measured at 13px over before
     this. */
  grid-template-columns: repeat(auto-fill, minmax(min(360px, 100%), 1fr));
  gap: 12px;
  align-items: start;
}

.tl-add-truck-card {
  border: 1px solid var(--border);
  border-radius: var(--radius);
  background: #f8fafc;
  padding: 14px 16px;
  box-shadow: var(--shadow-sm);
  transition: all 0.15s ease;
}

.tl-add-truck-card:hover {
  border-color: #cbd5e1;
  background: #ffffff;
}

.tl-add-truck-card-head {
  display: flex;
  align-items: flex-end;
  gap: 12px;
}

.tl-add-truck-card-index {
  width: 28px;
  height: 28px;
  border-radius: var(--radius-sm);
  background: #e2e8f0;
  color: #334155;
  font-family: var(--font-display);
  font-size: 13px;
  font-weight: 700;
  display: flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
  margin-bottom: 12px;
}

/* 44px square: this is used on a tablet at the bay, and the button sat at
   roughly 30px -- under the minimum touch target, next to the two inputs
   it would destroy if mis-tapped. */
.tl-add-truck-card-head .tl-truck-remove-btn {
  min-width: 44px;
  min-height: 44px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: 0;
  font-size: 14px;
  line-height: 1;
  flex-shrink: 0;
  margin-bottom: 4px;
}

@media (max-width: 480px) {
  .tl-add-truck-card-head { flex-wrap: wrap; }
  .tl-add-truck-card-head .tl-truck-remove-btn { margin-left: auto; }
}

/* Phone-friendly data tables: below the breakpoint, the FG Loading Plan
   and Loading History tables stop being tables at all -- each row becomes
   its own stacked card with the column name as a label in front of the
   value, same pattern used by most responsive-table implementations.
   Requires each <td> to carry data-label (set in truck-loading.js). */
@media (max-width: 700px) {
  #tl-plan-table, #tl-history-table { border: 0; }
  #tl-plan-table colgroup, #tl-history-table colgroup { display: none; }
  #tl-plan-table thead, #tl-history-table thead { display: none; }
  #tl-plan-table tbody tr, #tl-history-table tbody tr {
    display: block;
    border: 1px solid var(--border);
    border-radius: var(--radius-lg);
    margin-bottom: 10px;
    padding: 4px 12px;
    background: var(--card);
  }
  #tl-plan-table td, #tl-history-table td {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    border: none;
    border-bottom: 1px solid var(--border-light);
    padding: 8px 0;
    text-align: right;
    white-space: normal;
  }
  #tl-plan-table td:last-child, #tl-history-table td:last-child { border-bottom: none; }
  #tl-plan-table td::before, #tl-history-table td::before {
    content: attr(data-label);
    font-weight: 700;
    color: var(--label);
    text-align: left;
    text-transform: uppercase;
    font-size: 10.5px;
    letter-spacing: .3px;
    flex-shrink: 0;
  }
  #tl-plan-table td[data-label=""], #tl-history-table td[data-label=""] {
    justify-content: center;
    padding: 10px 0 2px;
  }
  #tl-plan-table td[data-label=""]::before, #tl-history-table td[data-label=""]::before { content: none; }
  #tl-plan-table td[data-label=""] button, #tl-history-table td[data-label=""] button { width: 100%; }
}

/* The page box, declared once for the whole application.

   Every printable thing here -- purchase order, customer order, invoice,
   receipt, the FG Loading Plan, a register -- prints through the single
   .print-area helper below, so the paper it lands on is described here
   rather than four times over.

   There was no @page rule at all before this, which is why printed
   documents did not fit the sheet: with no declared size or margin the
   browser applies its own (typically ~10mm, and Chrome adds its own
   header/footer band on top), while .po-doc is capped at 940px -- wider
   than A4's ~794px printable width at 96dpi. The right-hand column of
   every document table was therefore either clipped off the sheet or the
   whole page was silently scaled down to fit, which is what made the
   figures small and the sheet look wrong.

   Slightly deeper bottom margin than top: the signature strip sits at the
   foot of a purchase order and an invoice, and a rule with no air under
   it reads as though the page was cut short. */
@page {
  size: A4;
  margin: 14mm 13mm 16mm;
}

/* Paper-only heading, hidden on screen; shown by the .print-only rule
   inside @media print below. */
.print-only { display: none; }

/* Generic "print just this one element" helper -- mark the element to
   keep with class="print-area", everything else on the page is hidden.
   Reusable by any future print button, not just the loading plan. */
@media print {
  body * { visibility: hidden; }
  .print-area, .print-area * { visibility: visible; }
  .print-area { position: absolute; top: 0; left: 0; width: 100%; }

  /* The app background is a tint that belongs to the screen; paper is
     paper. Stated explicitly because .po-doc below drops its own card
     background along with the rest of the card. */
  html, body { background: #fff; }

  /* Controls that only make sense on screen. Marked up as .no-print in
     several views already, which until now relied entirely on the
     body-wide hide above -- so the class did nothing for anything that
     sat inside a .print-area. display, not visibility, so a hidden
     control does not leave its own gap on the page. */
  .no-print { display: none !important; }

  /* Counterpart to .no-print: a heading duplicated for paper only, where
     the screen version sits inside a .panel-head-row full of buttons that
     .no-print hides -- the printed page still needs its own title. */
  .print-only { display: block !important; }

  /* A button is never part of a document. Registers mix row actions (reorder
     arrows, Edit, Cancel, Log this truck) into their cells, and those were
     printing onto the sheet the dock follows. */
  .print-area button,
  .print-area .icon-btn { display: none !important; }

  /* Release the capped-height registers. A scrolling panel prints as
     whichever 520px the reader happened to be looking at and silently
     drops the rest -- and the FG Loading Plan is printed specifically to
     be carried to the dock and followed in full. */
  .print-area.table-scroll-register,
  .print-area .table-scroll-register,
  .print-area.scroll-panel-tall,
  .print-area .scroll-panel-tall {
    max-height: none;
    overflow: visible;
  }

  /* A .table-responsive wrapper scrolls sideways on a narrow screen. On
     paper it cannot scroll, so leaving it clipped means the columns it
     was scrolling to reach simply do not exist on the printout -- and
     nothing on the sheet says they are missing. */
  .print-area .table-responsive {
    overflow: visible;
    max-width: none;
  }

  /* Documents fill the page box rather than their on-screen card width.
     The border, shadow, radius, padding and 940px cap are all the card
     the document floats in, not the document -- and the cap is what was
     pushing content off the right edge of the sheet. Purchase Orders had
     a local version of this rule; it now covers the customer order, the
     invoice and the receipt too, which never had one. */
  .print-area.po-doc,
  .print-area .po-doc {
    max-width: none;
    padding: 0;
    border: none;
    border-radius: 0;
    box-shadow: none;
    background: #fff;
  }

  /* Tables take the width of the page rather than of their content, and
     a long free-text cell (an item description, a note, a reference the
     customer chose) wraps instead of widening the table past the paper.
     Deliberately NOT table-layout: fixed -- the purchase order and
     customer order document tables declare their own column widths, but
     the receipt and invoice tables do not, and fixed layout would give
     those equal-width columns and a worse sheet than the one being
     fixed. */
  .print-area table {
    width: 100%;
    border-collapse: collapse;
  }
  .print-area th,
  .print-area td {
    overflow-wrap: anywhere;
  }

  /* Where a document runs to a second sheet: repeat the table head, never
     split a row or a list item down the middle, and never leave a heading
     stranded at the foot of a page with its content overleaf. */
  .print-area thead { display: table-header-group; }
  .print-area tr,
  .print-area li { break-inside: avoid; }
  .print-area h3 { break-after: avoid; }

  /* Blocks that only make sense read whole. The totals and the signature
     strip in particular: a page break through either produces a sheet
     that looks like the document was tampered with. */
  .print-area .po-doc-masthead,
  .print-area .po-doc-totals,
  .print-area .po-doc-sign,
  .print-area .po-doc-parties,
  .print-area .po-receipt,
  .print-area .co-receipt-figure {
    break-inside: avoid;
  }
}

/* ---------- Admin -> Products & Lookups: grouped, searchable catalogs ----------
   Deliberately its own class namespace (.lu-*) rather than reusing .two-col/
   .two-col-full -- those two classes are also used by tanker-register.html
   and trips.html, and this page's layout must not be able to affect either. */

.lu-intro { margin-bottom: 18px; }
.lu-intro p { margin: 0; }


.lu-group { margin-bottom: 30px; }
.lu-group:last-child { margin-bottom: 0; }

.lu-group-head {
  display: flex;
  align-items: center;
  gap: 12px;
  padding-bottom: 10px;
  margin-bottom: 16px;
  border-bottom: 2px solid var(--border-light);
}

.lu-group-icon {
  width: 34px;
  height: 34px;
  border-radius: var(--radius);
  display: flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
}
.lu-group-icon svg { width: 18px; height: 18px; }

.lu-group-head h3 { margin: 0; font-family: var(--font-display); font-size: 16px; font-weight: 700; color: var(--ink); letter-spacing: -0.01em; }
.lu-group-head p { margin: 2px 0 0; font-size: 12px; color: var(--muted); }

/* Each domain group borrows an existing hue rather than introducing a new
   color token -- blue/teal already mean "Sales/Dispatch" and "Production" on
   the dashboard's own trend charts, so this extends a meaning the app
   already teaches instead of inventing a fourth, unrelated one. */
.lu-group-sales .lu-group-icon { background: rgba(59, 111, 160, 0.12); color: var(--accent-blue); }
.lu-group-sales .lu-panel-icon { color: var(--accent-blue); }
.lu-group-sales .lookup-panel { border-top-color: var(--accent-blue); }

.lu-group-supply .lu-group-icon { background: rgba(19, 35, 57, 0.08); color: var(--navy); }
.lu-group-supply .lu-panel-icon { color: var(--navy); }
.lu-group-supply .lookup-panel { border-top-color: var(--navy); }

.lu-group-production .lu-group-icon { background: rgba(31, 138, 114, 0.12); color: var(--accent-teal); }
.lu-group-production .lu-panel-icon { color: var(--accent-teal); }
.lu-group-production .lookup-panel { border-top-color: var(--accent-teal); }

/* Flexbox, not CSS Grid -- a grid's auto-fit tracks are sized before it
   knows how many items will actually land in a row, so a group with a
   single narrow panel (e.g. Sales & Distribution's lone Customers card next
   to full-width FG SKUs) was leaving two empty phantom columns of dead
   space beside it instead of the panel growing to fill the row. Flex-grow
   fills leftover row space with whatever *is* there, whether that's one
   panel or four. */
.lu-grid {
  display: flex;
  flex-wrap: wrap;
  gap: 20px;
  align-items: stretch;
}

.lookup-panel {
  flex: 1 1 300px;
  min-width: 0;
  /* Caps how far a lone panel can flex-grow when it wraps onto a row by
     itself (e.g. a 4th half-width card after three already filled the row
     above) -- without this it stretches to the entire remaining row width,
     which looks sparse for a simple two-column name list. Full-width
     catalog panels below are exempt via the compound selector. */
  max-width: 560px;
  border-top-width: 3px;
  border-top-color: var(--border);
  /* So a jump-nav chip's scrollIntoView doesn't land the panel flush against
     the viewport edge. */
  scroll-margin-top: 16px;
}

/* Compound selector for specificity, not source order -- guarantees this
   wins over .lookup-panel's flex-basis regardless of where either rule
   ends up in the stylesheet later. */
.lookup-panel.lookup-panel-full { flex-basis: 100%; max-width: none; }

.lu-panel-head { margin-bottom: 12px; }
.lu-panel-title { display: flex; align-items: center; gap: 9px; min-width: 0; }
.lu-panel-title h2 { margin: 0; }
.lu-panel-icon { display: flex; flex-shrink: 0; color: var(--muted); }
.lu-panel-icon svg { width: 17px; height: 17px; }

.lu-count-badge {
  font-size: 11px;
  font-weight: 700;
  color: var(--muted);
  background: var(--bg);
  border-radius: 999px;
  padding: 2px 10px;
  flex-shrink: 0;
  white-space: nowrap;
}

.lu-add-box {
  background: var(--bg);
  border: 1px solid var(--border-light);
  border-radius: var(--radius);
  padding: 12px 14px 4px;
  margin-bottom: 12px;
}
.lu-add-box .inline-form { margin-bottom: 10px; }

.lu-add-label {
  display: flex;
  align-items: center;
  gap: 5px;
  font-size: 10.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .4px;
  color: var(--muted);
  margin-bottom: 8px;
}
.lu-add-label svg { width: 13px; height: 13px; color: var(--brand); }

.lu-search-row { margin-bottom: 10px; }
.lu-search-box { position: relative; }
.lu-search-box svg {
  position: absolute;
  left: 10px;
  top: 50%;
  transform: translateY(-50%);
  width: 14px;
  height: 14px;
  color: var(--muted);
  pointer-events: none;
}
.lu-search-input { padding-left: 30px; margin-bottom: 0; }

/* Client-side row filter for the longer catalogs (Stock Coverage Items in
   particular runs to dozens of long raw-material names) -- toggled by
   admin.js, never touches the underlying data. */
.lu-row-filtered { display: none; }

/* ---------- Products & Lookups: rail + stage ----------
   Nine catalogs stacked down one page measured 4,540px tall at 1280px, and
   the shape of that page was the problem: three of the nine rows carried a
   single 560px card against 688px of empty row, while the data itself was
   crammed into a 280px porthole you had to scroll *inside* after scrolling
   the page to reach it. Wide and empty, tall and cramped, at the same time.

   One catalog at a time fixes both halves with the same move -- the rail
   spends the narrow left column on navigation that used to be a row of
   chips scrolled past and forgotten, and the chosen catalog gets the entire
   remaining width and a table window sized to the viewport instead of a
   fixed 280px. */

.lu-workbench {
  display: grid;
  grid-template-columns: 236px minmax(0, 1fr);
  gap: 20px;
  align-items: start;
}
/* "Hide catalog list" (admin.js) gives the open catalog the whole width. */
.lu-workbench.rail-hidden { grid-template-columns: minmax(0, 1fr); }
.lu-workbench.rail-hidden .lu-rail { display: none; }
.lu-intro-actions { display: flex; gap: 8px; flex-wrap: wrap; align-items: center; }
.lu-rail-toggle svg { width: 15px; height: 15px; vertical-align: -3px; margin-right: 4px; }

/* Sticky so switching catalogs never requires scrolling back up -- the rail
   is the page's primary navigation now, not a one-time jump list. */
.lu-rail {
  position: sticky;
  top: 16px;
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  padding: 10px 8px;
  box-shadow: var(--shadow-sm);
}

.lu-rail-section + .lu-rail-section { margin-top: 14px; }

.lu-rail-section-label {
  font-size: 10.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .5px;
  color: var(--muted);
  padding: 0 8px 6px;
}

.lu-rail-item {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  width: 100%;
  /* 44px floor -- these are the page's main controls and are tapped on the
     plant's touch terminals, not only clicked with a mouse. */
  min-height: 44px;
  padding: 8px 10px;
  text-align: left;
  background: transparent;
  color: var(--label);
  border: 0;
  /* Transparent until active so selecting a catalog doesn't shift the label
     sideways by the width of the accent bar. */
  border-left: 3px solid transparent;
  /* The global button rule carries the brand-red drop shadow that belongs to
     a primary action. These are navigation, and nine red-edged boxes read as
     nine Add buttons. */
  box-shadow: none;
  border-radius: var(--radius-sm);
  font-family: inherit;
  font-size: 13px;
  font-weight: 500;
  cursor: pointer;
  transition: background-color .12s ease, color .12s ease;
}

.lu-rail-item:hover { background: var(--bg); color: var(--ink); }
.lu-rail-item:focus-visible { outline: 2px solid var(--brand); outline-offset: -2px; }

.lu-rail-item.active {
  background: var(--bg);
  color: var(--ink);
  font-weight: 700;
}

/* The accent already assigned to each group elsewhere on this page, reused
   so the rail and the panel it opens read as the same thing. */
.lu-rail-section.lu-group-sales .lu-rail-item.active { border-left-color: var(--accent-blue); }
.lu-rail-section.lu-group-supply .lu-rail-item.active { border-left-color: var(--navy); }
.lu-rail-section.lu-group-production .lu-rail-item.active { border-left-color: var(--accent-teal); }

.lu-rail-name { min-width: 0; overflow-wrap: anywhere; }

.lu-rail-count {
  flex-shrink: 0;
  font-size: 11px;
  font-weight: 700;
  font-variant-numeric: tabular-nums;
  color: var(--muted);
  background: var(--bg);
  border-radius: var(--radius-full);
  padding: 1px 8px;
}
.lu-rail-item.active .lu-rail-count { background: var(--card); color: var(--label); }

/* The stage holds one catalog, so the width cap that stopped a lone card
   from stretching across a shared row is exactly wrong here. */
.lu-stage .lu-group { margin-bottom: 0; }
.lu-stage .lookup-panel { flex-basis: 100%; max-width: none; }

/* Giving a catalog the full width creates a second kind of dead space in
   the narrow ones: Customers is a single "Name" column, and stretched to
   ~900px it is a hairline of text beside nothing. So for those, the add
   form and its note move out of the stack and into that space -- the list
   is what you read, adding one is a single field, and side by side they
   cost one screen instead of two. The wide catalogs (FG SKUs, Stock
   Coverage Items, Production Lines) are exempt: their tables want every
   pixel and their forms are five fields wide, so those stay stacked. */
.lu-stage .lookup-panel:not(.lookup-panel-full) {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 300px;
  grid-template-areas:
    "head   head"
    "search add"
    "table  add"
    "table  note";
  column-gap: 20px;
  align-content: start;
}
.lu-stage .lookup-panel:not(.lookup-panel-full) > .panel-head-row { grid-area: head; }
.lu-stage .lookup-panel:not(.lookup-panel-full) > .lu-search-row { grid-area: search; }
.lu-stage .lookup-panel:not(.lookup-panel-full) > .table-responsive { grid-area: table; }
.lu-stage .lookup-panel:not(.lookup-panel-full) > .lu-add-box {
  grid-area: add;
  align-self: start;
  margin-bottom: 0;
}
.lu-stage .lookup-panel:not(.lookup-panel-full) > p.muted {
  grid-area: note;
  align-self: start;
  margin: 12px 0 0;
}

@media (max-width: 1100px) {
  /* Two content columns inside a panel that is itself already beside the
     rail -- below this the aside squeezes the table, so it goes back to
     the plain stack. */
  .lu-stage .lookup-panel:not(.lookup-panel-full) {
    display: block;
  }
  .lu-stage .lookup-panel:not(.lookup-panel-full) > .lu-add-box { margin-bottom: 12px; }
  .lu-stage .lookup-panel:not(.lookup-panel-full) > p.muted { margin: 0 0 10px; }
}

/* A table window scaled to the viewport rather than a fixed 280px. The page
   itself no longer scrolls far, so this is the only scroll on screen --
   dvh, not vh, so a phone's collapsing address bar doesn't clip it. */
.lu-stage .table-responsive-tall {
  max-height: clamp(320px, calc(100vh - 380px), 760px);
  max-height: clamp(320px, calc(100dvh - 380px), 760px);
}

@media (max-width: 900px) {
  /* Below this the two columns would starve each other, so the rail becomes
     a wrapping band above the stage -- still every catalog, still one tap,
     just no longer beside the content. */
  .lu-workbench { grid-template-columns: minmax(0, 1fr); }
  .lu-rail { position: static; }
  .lu-rail-section { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; }
  .lu-rail-section + .lu-rail-section { margin-top: 8px; }
  .lu-rail-section-label { flex-basis: 100%; padding: 4px 4px 2px; }
  .lu-rail-item { width: auto; }
}

/* Small colored icon tile -- reused on Settings' three domain cards (each
   one is really a mini version of a Products & Lookups group, not a plain
   catalog panel, so it gets the group's tiled treatment instead of a bare
   icon). Generic enough to reuse anywhere else a "this belongs to domain X"
   icon is needed later. */
.icon-tile {
  width: 26px;
  height: 26px;
  border-radius: var(--radius-sm);
  display: flex;
  align-items: center;
  justify-content: center;
  flex-shrink: 0;
}
.icon-tile svg { width: 14px; height: 14px; }
.icon-tile-navy { background: rgba(19, 35, 57, 0.08); color: var(--navy); }
.icon-tile-ok { background: var(--ok-bg); color: var(--ok); }
.icon-tile-neutral { background: var(--bg); color: var(--label); }

@media (max-width: 520px) {
  .lu-group-head { align-items: flex-start; }
}

/* ---------- Supply Chain -> Purchase Orders (.po-* namespace) ----------
   Own namespace rather than extending .lu-* or .two-col, for the same
   reason .lu-* has one: nothing here may leak into the other screens that
   share the generic layout classes.

   Two ideas carry this screen. (1) The drawdown gauge (.qty-meter-*, below
   -- shared with Raw Material Receiving, see core.js's qtyMeter()): a PO's
   whole story is how much of what was committed has actually arrived,
   drawn down partially over time, so received-vs-ordered is one gauge
   rather than two adjacent numbers. (2) The detail view is drawn as the
   document a PO actually is, and that same sheet is what class="print-area"
   prints -- no separate print layout that can drift from the screen. */

.po-fieldset {
  border: 0;
  padding: 0;
  margin: 0 0 18px;
}

.po-fieldset > legend {
  padding: 0;
  font-size: 10.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .08em;
  color: var(--muted);
  margin-bottom: 8px;
}

.po-edit-banner {
  border: 1px solid #e9c98a;
  background: var(--pending-bg);
  border-radius: var(--radius);
  padding: 12px 14px;
  margin-bottom: 16px;
}

.po-edit-banner p { margin: 0 0 10px; color: #7a4f0f; font-size: 12.5px; }
.po-edit-banner .form-grid { margin: 0; }
.po-edit-banner input { margin-bottom: 0; }

/* Quantities and money are read down a column, never across -- tabular
   mono for every figure cell in both the draft table and the document. */
#po-items-table input.po-item-qty,
#po-items-table input.po-item-price {
  font-family: var(--font-mono);
  text-align: right;
}

#po-items-table .po-item-line-total,
#po-doc .po-fig {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  text-align: right;
  white-space: nowrap;
}

/* The draft's running total is drawn as the same totals block the saved
   document uses, so the form reads as a draft of the sheet it becomes. */
.po-draft-total {
  display: flex;
  justify-content: flex-end;
  margin-top: 12px;
}

.po-total-block {
  min-width: 260px;
  border-top: 2px solid var(--navy);
  padding-top: 8px;
}

.po-total-row {
  display: flex;
  justify-content: space-between;
  gap: 20px;
  font-size: 12.5px;
  padding: 3px 0;
  color: var(--label);
}

.po-total-row span:last-child {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  color: var(--ink);
}

.po-total-row.po-total-grand {
  border-top: 1px solid var(--border);
  margin-top: 5px;
  padding-top: 7px;
  font-weight: 700;
  font-size: 13px;
  color: var(--ink);
}

.po-total-row.po-total-grand span:last-child {
  font-family: var(--font-display);
  font-size: 18px;
  font-weight: 700;
  letter-spacing: -0.01em;
}

/* ---------- Received-vs-ordered gauge (shared, not PO-only) ----------
   Rendered by core.js's qtyMeter(); used by Purchase Orders and by Raw
   Material Receiving. Over-receipt is a permitted soft check in this app
   (see business-rules.md), so the gauge shows the overshoot instead of
   clamping to a full bar -- a clamped bar hides the one case worth
   noticing. */

.qty-meter { display: flex; align-items: center; gap: 8px; min-width: 0; }

.qty-meter-track {
  position: relative;
  flex: 1;
  min-width: 40px;
  height: 8px;
  background: var(--bg);
  border: 1px solid var(--border-light);
  border-radius: 2px;
}

.qty-meter-fill {
  position: absolute;
  left: 0;
  top: 0;
  bottom: 0;
  border-radius: 1px;
}

.qty-meter-fill.qty-meter-partial { background: var(--pending); }
.qty-meter-fill.qty-meter-done { background: var(--ok); }
.qty-meter-fill.qty-meter-void { background: var(--border); }

/* The over-received segment, drawn past the ordered mark. Its left border
   is that mark: everything left of it was ordered, everything right of it
   is delivery that ran over the paperwork. Positioned inside the track so
   it can never reach across into the figures beside the gauge. */
.qty-meter-over {
  position: absolute;
  top: 0;
  bottom: 0;
  background: var(--warn);
  border-left: 1px solid var(--card);
  border-radius: 0 1px 1px 0;
}

.qty-meter-value {
  flex-shrink: 0;
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: 11.5px;
  font-weight: 600;
  color: var(--ink);
  white-space: nowrap;
}

.qty-meter-value .qty-meter-of { color: var(--muted); font-weight: 400; }

.po-overdue {
  display: block;
  margin-top: 2px;
  font-size: 10.5px;
  font-weight: 700;
  color: var(--warn);
  text-transform: uppercase;
  letter-spacing: .04em;
}

/* ---------- The purchase order document ---------- */

.po-doc-actions { display: flex; gap: 8px; flex-wrap: wrap; }

.po-doc {
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  box-shadow: 0 1px 3px rgba(28, 39, 51, 0.06);
  padding: 30px 32px 26px;
  max-width: 940px;
  print-color-adjust: exact;
  -webkit-print-color-adjust: exact;
}

.po-doc-masthead {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 24px;
  flex-wrap: wrap;
  border-bottom: 2px solid var(--navy);
  padding-bottom: 14px;
}

.po-doc-issuer { display: flex; align-items: center; gap: 11px; }

.po-doc-mark {
  width: 36px;
  height: 36px;
  flex-shrink: 0;
  border-radius: var(--radius);
  background: var(--brand);
  color: #fff;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: 16px;
  display: flex;
  align-items: center;
  justify-content: center;
}

.po-doc-issuer-name { font-weight: 700; font-size: 14px; color: var(--ink); line-height: 1.25; }
.po-doc-issuer-sub { font-size: 11px; color: var(--muted); }

.po-doc-ident { text-align: right; }

.po-doc-no {
  font-family: var(--font-display);
  font-size: 27px;
  font-weight: 700;
  letter-spacing: -0.01em;
  line-height: 1.1;
  color: var(--ink);
}

.po-doc-label {
  font-size: 10px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .09em;
  color: var(--muted);
  margin-bottom: 3px;
}

.po-doc-parties {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 24px;
  padding: 18px 0;
  border-bottom: 1px solid var(--border-light);
}

.po-party-name { font-size: 14px; font-weight: 600; color: var(--ink); }
.po-party-line { font-size: 12.5px; color: var(--label); margin-top: 2px; }

.po-doc-terms {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: 18px;
  padding: 14px 0 18px;
  border-bottom: 1px solid var(--border-light);
}

.po-term-value { font-size: 13px; color: var(--ink); font-weight: 600; }

.po-doc h3 {
  font-size: 10.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .09em;
  color: var(--muted);
  margin: 22px 0 8px;
}

#po-doc table { width: 100%; border-collapse: collapse; }

#po-doc thead th {
  font-size: 10.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .05em;
  color: var(--muted);
  text-align: left;
  padding: 6px 8px;
  border-bottom: 1px solid var(--border);
  background: none;
}

#po-doc thead th.po-fig { text-align: right; }

#po-doc tbody td {
  padding: 9px 8px;
  border-bottom: 1px solid var(--border-light);
  font-size: 13px;
  vertical-align: top;
}

#po-doc tbody tr:last-child td { border-bottom: 1px solid var(--border); }

.po-doc-totals { display: flex; justify-content: flex-end; margin-top: 14px; }

.po-doc-note {
  margin-top: 18px;
  font-size: 12.5px;
  color: var(--label);
  line-height: 1.5;
}

.po-doc-cancelled {
  margin-top: 18px;
  border: 1px solid #f0b8b2;
  background: var(--warn-bg);
  border-radius: var(--radius);
  padding: 11px 13px;
  color: var(--warn);
  font-size: 12.5px;
}

.po-receipt {
  border-left: 2px solid var(--border);
  padding: 2px 0 2px 12px;
  margin-top: 12px;
}

.po-receipt-head { font-size: 12.5px; color: var(--ink); font-weight: 600; }
.po-receipt-meta { font-size: 11.5px; color: var(--muted); margin-top: 1px; }
.po-receipt ul { margin: 6px 0 0; padding-left: 17px; font-size: 12.5px; color: var(--label); }
.po-receipt li { margin-bottom: 2px; }

/* Wet-signature strip: this app already treats a signature as the thing
   that makes a record real (includes/signature.php), and a printed PO gets
   counter-signed on paper before it goes out to the supplier. */
.po-doc-sign {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 40px;
  margin-top: 34px;
}

.po-sign-rule {
  border-top: 1px solid var(--ink);
  padding-top: 5px;
  font-size: 11px;
  color: var(--muted);
}

.po-sign-rule strong { display: block; font-size: 12.5px; color: var(--ink); font-weight: 600; margin-bottom: 1px; }

@media (max-width: 720px) {
  .po-doc { padding: 20px 18px; }
  .po-doc-parties, .po-doc-sign { grid-template-columns: 1fr; gap: 16px; }
  .po-doc-terms { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .po-doc-ident { text-align: left; }
}

/* What's on screen is what prints -- the sheet just drops the chrome that
   only makes sense as a card floating on the app background.

   Dropping that chrome (border, shadow, radius, padding, the 940px cap)
   now happens once in the shared .print-area block near the top of this
   file, so it applies to the customer order, the invoice and the receipt
   as well -- all three are .po-doc sheets that never had this rule. What
   is left here is only the spacing this particular document wants on
   paper, which the shared rule has no business knowing about. */
@media print {
  .po-doc h3 { margin-top: 18px; }
  .po-doc-sign { margin-top: 28px; }
}

/* ---------- The docket: a grouped register for event-shaped records ----
   Used by Raw Material Receiving and Issue to Production, both of which
   record an *event* -- one truck / one issuance to one department, at a
   moment, carrying several items. Both registers used to flatten that into
   one flat row per item, repeating six to eight identity columns on every
   line of every event (Issue to Production went as far as blanking those
   cells out on every row but the first, which is the flat layout admitting
   it wanted to be grouped).

   A docket is a full-width band carrying the event's identity once, then
   its item lines beneath. The papers (gate pass, weighbridge ticket, PO,
   request time) are set as small mono stubs because that is what they
   physically are at the gate -- and two of them are the numbers this app
   claims transactionally through includes/number_registry.php.

   Grouped rows mean core.js's per-row initGlobalTableSearch() would hide a
   docket's header while leaving its matching line orphaned, so both
   screens omit data-filter-target and own a group-aware filter instead
   (grn.js's filterGrnRegister / material-requests.js's filterMrRegister). */

.docket-row > td {
  padding: 0;
  border-bottom: none;
  background: #f8f9fb;
  border-top: 2px solid var(--navy);
  border-left: 2px solid var(--navy);
}

/* Groups after the first need air above them, so consecutive dockets don't
   read as one long event. */
.docket-row:not(:first-child) > td { box-shadow: 0 -10px 0 var(--card); }

.docket {
  display: flex;
  align-items: flex-start;
  gap: 18px;
  flex-wrap: wrap;
  padding: 11px 14px;
}

.docket-id { min-width: 0; flex: 1 1 200px; }

.docket-title {
  font-size: 14px;
  font-weight: 700;
  color: var(--ink);
  line-height: 1.25;
  overflow-wrap: break-word;
}

.docket-when {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: 11.5px;
  color: var(--muted);
  margin-top: 2px;
}

/* The event's papers. Label above, number below in mono -- a stub, read
   the way an operator reads the physical slips. */
.docket-papers { display: flex; gap: 16px; flex-wrap: wrap; }

.docket-paper { min-width: 0; }

.docket-paper-label {
  display: block;
  font-size: 9.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .07em;
  color: var(--muted);
}

.docket-paper-no {
  display: block;
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: 13px;
  font-weight: 600;
  color: var(--ink);
  overflow-wrap: break-word;
}

.docket-paper-no.docket-paper-none { color: var(--border); font-weight: 400; }

.docket-side {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-left: auto;
  flex-shrink: 0;
}

/* What the delivery landed at, on the docket band. Reads as a figure
   rather than a badge because it is a measured amount, not a state -- and
   it is absent entirely, not blanked, for a reader without
   stock.view_cost. */
.docket-value {
  font-variant-numeric: tabular-nums;
  font-weight: 600;
  font-size: 12.5px;
  color: var(--ink);
  white-space: nowrap;
}

.docket-value.muted { font-weight: 400; color: var(--muted); }

/* .cell-sub.sub-warn was scoped to .card only; a warning under a table
   cell needs it too -- an unpriced line in a costed delivery is exactly
   the case that must not read as ordinary grey supporting text. */
.cell-sub.sub-warn { color: var(--warn); }

/* The 48-hour deposit clock (migration 081): amber while it runs, bold red
   once it has passed. */
.cell-sub.sub-pending { color: var(--pending); }
.cell-sub.sub-overdue { color: var(--warn); font-weight: 600; }

/* Raw Material Receiving's cost column and charges panel, hidden as one
   unit by grn.js when the reader lacks stock.view_cost. The rule exists so
   the class is greppable from the CSS as well as the JS -- the visibility
   itself is .hidden, and the server withholds the data regardless. */
.grn-cost-col { /* no styling of its own; toggled via .hidden */ }

#grn-cost-summary { margin-top: 12px; max-width: 420px; }

/* Raw Material Ledger: the opening -> movements -> closing strip. Reads
   left to right as the sentence the page is making, with the closing
   balance set apart because it is the answer and the rest is the working.
   Wraps to one column on a phone rather than squeezing five figures. */
.rl-summary {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
  gap: 10px;
  margin-bottom: 14px;
}

.rl-stat {
  border: 1px solid var(--border);
  border-radius: 8px;
  padding: 10px 12px;
  background: var(--panel);
}

.rl-stat-label {
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: .04em;
  color: var(--muted);
  margin-bottom: 4px;
}

.rl-stat-value {
  font-size: 18px;
  font-weight: 600;
  font-variant-numeric: tabular-nums;
  color: var(--ink);
}

.rl-stat.rl-stat-grand { border-color: var(--ink); }
.rl-stat.rl-stat-grand .rl-stat-value { font-size: 20px; }

/* In and out are read at a glance in a column of movements, so they carry
   the same colours the rest of the app uses for gained and lost stock. */
.rl-in { color: var(--ok, #167c3c); font-variant-numeric: tabular-nums; }
.rl-out { color: var(--warn); font-variant-numeric: tabular-nums; }

/* Named people attest to every one of these records -- that roll call is
   the record's authority, so it sits on its own rule rather than becoming
   three or four more columns. */
.docket-sign {
  flex-basis: 100%;
  font-size: 11.5px;
  color: var(--muted);
  border-top: 1px solid var(--border-light);
  padding-top: 7px;
}

.docket-sign strong { color: var(--label); font-weight: 600; }

.docket-corrected { color: var(--pending); font-weight: 600; }

.docket-line-row > td:first-child { border-left: 2px solid var(--border); }
.docket-line-row > td { font-size: 13px; }

.docket-line-no {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  color: var(--muted);
}

/* How the goods were actually counted: a pack unit and its multiplier, or
   Direct. Both screens record this and neither used to show it. */
.docket-counted {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: 12.5px;
  color: var(--ink);
}

.docket-counted-direct { font-family: var(--font-sans); color: var(--muted); }

.docket-qty-plain {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: 13px;
  font-weight: 600;
  color: var(--ink);
}

/* Highlights every row of the event currently loaded into the form above,
   not just its first line. */
.docket-edit-group > td { background: var(--brand-tint); }

@media (max-width: 720px) {
  .docket { gap: 12px; }
  .docket-side { margin-left: 0; flex-basis: 100%; }
  .docket-papers { gap: 12px; }
}

/* ---------- Variance against a tolerance band ----------
   Stock Take (expected vs counted) and FG Receipts (what production
   reported vs what the warehouse actually took in) both ask the same
   question, and it is not the one qtyMeter() answers: here *both*
   directions are a problem, and there is a tolerance band inside which a
   difference is simply normal. So this reads as a signed difference judged
   against that band, not as a fill level. Rendered by core.js's
   varianceTag(). */

.variance {
  display: inline-flex;
  align-items: baseline;
  gap: 6px;
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}

.variance-figure { font-size: 13px; font-weight: 600; }

.variance-pct { font-size: 11px; }

.variance-none .variance-figure { color: var(--muted); font-weight: 400; }
.variance-ok .variance-figure, .variance-ok .variance-pct { color: var(--ok); }
.variance-flagged .variance-figure, .variance-flagged .variance-pct { color: var(--warn); }

.variance-tag {
  font-family: var(--font-sans);
  font-size: 9.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .05em;
  padding: 1px 5px;
  border-radius: var(--radius-sm);
}

.variance-ok .variance-tag { color: var(--ok); background: var(--ok-bg); }
.variance-flagged .variance-tag { color: var(--warn); background: var(--warn-bg); }

/* ---------- Shared form furniture ---------- */

/* A fieldset's default min-width is min-content, which overrides a
   .table-responsive child's ability to shrink and scroll -- that pushed
   the whole page sideways on a phone once already (Purchase Orders,
   2026-08-18). Set app-wide rather than per screen so the next form that
   groups a wide table in a fieldset doesn't rediscover it. */
fieldset { min-width: 0; }

.form-help {
  font-size: 12px;
  color: var(--muted);
  margin: 8px 0 0;
  max-width: 70ch;
  line-height: 1.5;
}

/* ---------- Receive FG from Production ---------- */

/* Pallets / cartons / pcs are three readings of one quantity, so they reuse
   the docket's label-over-figure stub, just tighter. */
.fgr-triple { gap: 12px; }

/* ---------- Production shift report: material ledger ---------- */

/* The Issuance column is an entry field with a provenance line under it,
   not a prose column -- so its note runs to a tighter measure than a
   register's, and the Material column is given a floor so the ledger keeps
   reading as a ledger no matter how many requests fed one row. */
.prod-material-source-note { margin-top: 4px; }
.prod-material-source-note .note { max-width: 24ch; }
#prod-materials-table .prod-material-name { min-width: 160px; }

/* ---------- Stock Take count sheet ---------- */

/* Its own class, deliberately not .grn-edit-row: that tint means "this
   record is loaded into the form above" everywhere else in the app, and
   borrowing it here made one colour mean two different things on one
   screen. */
.stocktake-row-flagged > td { background: var(--warn-bg); }

.stocktake-flagged-count { color: var(--warn); font-weight: 700; }

#stocktake-lines-table .stocktake-variance-display { white-space: nowrap; }

/* ---------- Stock Coverage: the runway ----------
   Coverage days, threshold days and extended coverage used to be three
   separate numeric columns, leaving the reader to answer the only question
   this screen exists for: will this item run out before the resupply
   lands? The runway draws it -- the filled segment is cover from stock on
   hand, the hatched segment is what transit + PO placed adds on top, and
   the rule is the threshold those two are judged against. Unlike
   qtyMeter(), this is a horizon rather than a ratio: the track is time. */

.runway { display: flex; align-items: center; gap: 10px; min-width: 0; }

.runway-track {
  position: relative;
  flex: 1;
  min-width: 60px;
  height: 10px;
  background: var(--bg);
  border: 1px solid var(--border-light);
  border-radius: 2px;
  overflow: hidden;
}

.runway-fill {
  position: absolute;
  left: 0;
  top: 0;
  bottom: 0;
  border-radius: 1px;
}

.runway-fill.runway-ok { background: var(--ok); }
.runway-fill.runway-at-risk { background: var(--pending); }
.runway-fill.runway-critical { background: var(--warn); }

/* Incoming stock is a promise, not stock -- hatched so it never reads as
   the same kind of certainty as what is physically on hand. */
.runway-incoming {
  position: absolute;
  top: 0;
  bottom: 0;
  background: repeating-linear-gradient(
    45deg,
    var(--accent-blue) 0 3px,
    transparent 3px 6px
  );
  border-left: 1px solid var(--card);
}

/* The threshold these are judged against, drawn where it actually falls. */
.runway-threshold {
  position: absolute;
  top: -2px;
  bottom: -2px;
  width: 1px;
  background: var(--navy);
}

.runway-value {
  flex-shrink: 0;
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: 12px;
  font-weight: 600;
  color: var(--ink);
  white-space: nowrap;
}

.runway-value .runway-ext { color: var(--accent-blue); font-weight: 600; }

.runway-sub {
  font-size: 11px;
  color: var(--muted);
  white-space: nowrap;
  margin-top: 2px;
}

/* ---------- Production: hourly attainment ----------
   A filling line hour has a target (the set speed) and an actual. The
   hourly grid recorded both and showed neither against the other, so a
   shift's shape -- which hours ran, which stalled -- was invisible without
   reading every row. */

.prod-hour-attain { display: flex; align-items: center; gap: 8px; }

.prod-hour-track {
  position: relative;
  flex: 1;
  min-width: 36px;
  height: 8px;
  background: var(--bg);
  border: 1px solid var(--border-light);
  border-radius: 2px;
  overflow: hidden;
}

.prod-hour-fill { position: absolute; left: 0; top: 0; bottom: 0; }
.prod-hour-fill.prod-hour-met { background: var(--ok); }
.prod-hour-fill.prod-hour-under { background: var(--pending); }
.prod-hour-fill.prod-hour-stalled { background: var(--warn); }

.prod-hour-value {
  flex-shrink: 0;
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: 11.5px;
  font-weight: 600;
  white-space: nowrap;
}

.prod-downtime-figure {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-weight: 600;
}

.prod-downtime-figure.prod-downtime-high { color: var(--warn); }

/* ---------- Dashboard annunciator ----------
   A weighbridge/tank-farm control room doesn't open with a wall of figures;
   it opens with an annunciator panel that is dark until something needs a
   person. This dashboard had eight equally-weighted KPI cards and three
   tabbed exception tables, so answering "is anything wrong right now?"
   meant reading all of them. The annunciator answers it in one line, from
   data already in dashboard/summary.php, and each lit flag is the button
   that takes you to the thing that lit it.

   Quiet when clear is the point -- if it shouted all the time it would be
   ignored, which is exactly what a real annunciator panel is designed to
   avoid. */

.annunciator {
  display: flex;
  align-items: center;
  gap: 18px;
  flex-wrap: wrap;
  background: var(--card);
  border: 1px solid var(--border);
  border-left: 4px solid var(--ok);
  border-radius: var(--radius-lg);
  padding: 14px 18px;
  margin-bottom: 18px;
}

.annunciator.is-watch { border-left-color: var(--pending); }
.annunciator.is-alert { border-left-color: var(--warn); }

.annunciator-lamp {
  width: 11px;
  height: 11px;
  border-radius: 50%;
  flex-shrink: 0;
  background: var(--ok);
  box-shadow: 0 0 0 3px var(--ok-bg);
}

.annunciator.is-watch .annunciator-lamp { background: var(--pending); box-shadow: 0 0 0 3px var(--pending-bg); }
.annunciator.is-alert .annunciator-lamp { background: var(--warn); box-shadow: 0 0 0 3px var(--warn-bg); }

/* The one piece of motion on this page, and only while something is
   actually wrong -- a lamp that pulses when everything is fine is just
   decoration, and trains people to ignore it. */
@media (prefers-reduced-motion: no-preference) {
  .annunciator.is-alert .annunciator-lamp { animation: annunciator-pulse 2s ease-in-out infinite; }
}

@keyframes annunciator-pulse {
  0%, 100% { box-shadow: 0 0 0 3px var(--warn-bg); }
  50% { box-shadow: 0 0 0 7px var(--warn-bg); }
}

.annunciator-main { min-width: 0; flex: 1 1 260px; }

.annunciator-headline {
  font-family: var(--font-display);
  font-size: 19px;
  font-weight: 700;
  letter-spacing: -0.01em;
  color: var(--ink);
  line-height: 1.2;
}

.annunciator-sub {
  font-size: 12px;
  color: var(--muted);
  margin-top: 2px;
}

.annunciator-flags {
  display: flex;
  gap: 8px;
  flex-wrap: wrap;
  margin-left: auto;
}

/* Each flag is the route to whatever lit it -- naming the count and the
   thing ("3 stock items at risk"), never a bare number needing a legend. */
.annunciator-flag {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  background: var(--bg);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 6px 11px;
  font-size: 12.5px;
  font-weight: 600;
  color: var(--ink);
  cursor: pointer;
  font-family: inherit;
}

.annunciator-flag:hover { background: var(--card); border-color: var(--brand); }
.annunciator-flag:focus-visible { outline: 2px solid var(--brand); outline-offset: 2px; }

.annunciator-flag-count {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-weight: 700;
}

.annunciator-flag.flag-alert { border-color: #f0b8b2; background: var(--warn-bg); }
.annunciator-flag.flag-alert .annunciator-flag-count { color: var(--warn); }
.annunciator-flag.flag-watch { border-color: #e9c98a; background: var(--pending-bg); }
.annunciator-flag.flag-watch .annunciator-flag-count { color: #7a4f0f; }

@media (max-width: 720px) {
  .annunciator-flags { margin-left: 0; flex-basis: 100%; }
}

/* ---------- Sidebar: sections inside an oversized department ----------
   Supply Chain owns twelve screens -- far past the point where a flat list
   of siblings can be scanned -- and they were in no discernible order:
   inbound (Purchase Orders, Raw Material Receiving) sat *after* outbound
   (Truck Loading, Gate Pass Register).

   The sections put them in the order material actually moves through this
   plant: bought, received, stored, drawn to the line, finished, shipped.
   That is the one place in this app where sequence genuinely carries
   information the reader needs -- it is the physical path of the goods, not
   a decorative numbering -- so it is worth spending structure on. Applied
   only to this group: Quality Control's nine items share a naming pattern
   and scan fine, and adding labels there would be chrome. */

.side-section-label {
  padding: 11px 16px 3px 28px;
  font-size: 9.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .09em;
  color: #5f6f88;
  user-select: none;
}

.side-submenu > .side-section-label:first-child { padding-top: 4px; }

/* Roadmap placeholders in Reports -- kept visible on purpose (they're a
   statement of intent, not dead links), but marked so nobody clicks one
   expecting a report. */
.side-soon {
  margin-left: auto;
  font-size: 9px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .07em;
  color: #5f6f88;
  border: 1px solid #2b3d5c;
  border-radius: var(--radius-sm);
  padding: 1px 5px;
}

/* ---------- Two-factor authentication ---------- */
/* The login screen's second step, its enrolment card, and the one-time
   recovery-code display. Sized wider than .login-card because the enrolment
   card carries a QR plus instructions, which do not read at 320px. */

.login-card-wide {
  width: 420px;
}

.mfa-alt {
  margin-top: 14px;
  display: flex;
  flex-direction: column;
  gap: 8px;
  align-items: center;
}

/* A button that reads as a link -- these are alternate paths (use a recovery
   code, go back), not actions competing with the card's primary button. */
.linklike {
  background: none;
  border: none;
  padding: 0;
  width: auto;
  color: var(--muted);
  font-size: 12.5px;
  text-decoration: underline;
  cursor: pointer;
}

.linklike:hover {
  color: var(--ink);
}

.mfa-steps {
  margin: 0 0 18px;
  padding-left: 20px;
  color: var(--ink);
  font-size: 13px;
  line-height: 1.55;
}

.mfa-steps > li + li {
  margin-top: 14px;
}

.mfa-steps input {
  margin-top: 8px;
}

.mfa-qr {
  margin: 10px 0;
  padding: 12px;
  background: #fff;              /* QR contrast must not depend on the theme */
  border: 1px solid var(--border);
  border-radius: 8px;
  display: flex;
  justify-content: center;
}

.mfa-qr svg {
  display: block;
  width: 200px;
  height: 200px;
}

.mfa-manual {
  font-size: 12px;
  color: var(--muted);
}

.mfa-manual code {
  display: block;
  margin-top: 6px;
  padding: 8px 10px;
  background: var(--bg);
  border: 1px solid var(--border);
  border-radius: 6px;
  font-family: var(--font-mono);
  font-size: 13px;
  letter-spacing: .08em;
  color: var(--ink);
  word-break: break-all;
  /* Typed by hand off the screen, so it must be selectable in one go. */
  user-select: all;
}

.mfa-codes {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 8px;
  margin: 4px 0 16px;
}

.mfa-codes code {
  padding: 8px;
  background: var(--bg);
  border: 1px solid var(--border);
  border-radius: 6px;
  font-family: var(--font-mono);
  font-size: 13px;
  text-align: center;
  color: var(--ink);
  user-select: all;
}

.mfa-codes-actions {
  flex-direction: row;
  justify-content: center;
  gap: 10px;
  margin-bottom: 14px;
}

.mfa-codes-actions button {
  width: auto;
  padding: 7px 14px;
  font-size: 12.5px;
}

.mfa-ack {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-bottom: 12px;
  font-size: 12.5px;
  color: var(--muted);
  cursor: pointer;
}

.mfa-ack input {
  width: auto;
  margin: 0;
}

/* The recovery codes are meant to be printed and put somewhere safe, so the
   print view drops everything except the codes themselves. */
@media print {
  body * { visibility: hidden; }
  #mfa-codes-card, #mfa-codes-card * { visibility: visible; }
  #mfa-codes-card {
    position: absolute;
    top: 0; left: 0;
    width: 100%;
    border: none;
    box-shadow: none;
  }
  .mfa-codes-actions, .mfa-ack, #mfa-codes-done { display: none; }
}

/* Admin > Users: the actionable state is "required but not enrolled", so it
   is the one that gets the alarm colour. */
.mfa-badge {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  font-size: 11.5px;
  white-space: nowrap;
}

/* Settings > Security: the role picker for mfa_required_roles. */
.mfa-role-picker {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(160px, 1fr));
  gap: 6px 12px;
  margin-bottom: 10px;
}

.mfa-role-option {
  display: flex;
  align-items: center;
  gap: 7px;
  font-size: 12.5px;
  color: var(--ink);
  cursor: pointer;
}

.mfa-role-option input {
  width: auto;
  margin: 0;
}

/* ---------- FG Stock Position: the board ----------
   The question this screen exists for is "how much of each SKU is in each
   location, right now" -- and it was previously answerable only by reading
   the last row of a day-by-day ledger and hoping the date range reached
   today. The board states it directly: SKUs down, bays across, one live
   figure per cell.

   Three deliberate departures from the ledger it replaces:
   - No date control. A date filter on "what is on the floor at this
     moment" can only produce a wrong answer that looks right.
   - A bay that has never held a SKU is drawn as a dash, not a zero --
     "never been here" and "here, but empty" are different facts.
   - Stock that has come off the line but not been put away is a column of
     its own, outside the bays. It is physically real and no bay can
     account for it, which is exactly the gap loading keeps falling into. */

.stock-board-wrap { overflow-x: auto; }

.stock-board {
  width: 100%;
  border-collapse: separate;
  border-spacing: 0;
  min-width: 640px;
}

.stock-board th,
.stock-board td {
  padding: 0;
  text-align: right;
  vertical-align: bottom;
}

.stock-board thead th {
  font-size: 9.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .09em;
  color: #5f6f88;
  padding: 0 12px 8px;
  white-space: nowrap;
  border-bottom: 1px solid var(--border);
}

.stock-board thead th.sb-sku-head { text-align: left; padding-left: 2px; }

/* The floor column is not a bay, and the total is the answer -- both are
   separated from the bay run by a rule rather than by spacing alone. */
.stock-board .sb-floor { border-left: 1px dashed var(--border); }
.stock-board .sb-total { border-left: 1px solid var(--navy); }

.stock-board tbody tr + tr td { border-top: 1px solid var(--border-light); }

.stock-board td { padding: 14px 12px; }
.stock-board td.sb-sku { text-align: left; padding-left: 2px; }

.sb-sku-name {
  font-size: 13.5px;
  font-weight: 600;
  color: var(--ink);
  line-height: 1.25;
}

.sb-sku-unit {
  font-size: 11px;
  color: var(--muted);
  margin-top: 2px;
}

.sb-qty {
  font-family: var(--font-mono);
  font-variant-numeric: tabular-nums;
  font-size: 15px;
  font-weight: 600;
  color: var(--ink);
  line-height: 1.1;
}

.sb-qty.is-empty { color: #aab2c0; font-weight: 400; }
.sb-qty.is-negative { color: var(--warn); font-weight: 700; }
.sb-qty.is-floor { color: var(--pending); }

/* Share of the SKU's bay stock held in this bay: which bay to send the
   forklift to, without reading four numbers and doing the arithmetic.
   Drawn only where the row genuinely has stock to divide up -- a share
   bar over a negative or empty row would be arithmetic theatre. */
.sb-share {
  height: 3px;
  margin-top: 7px;
  background: var(--border-light);
  border-radius: 2px;
  overflow: hidden;
}

.sb-share-fill { height: 100%; background: var(--navy); border-radius: 2px; }

.stock-board td.sb-negative { background: var(--warn-bg); }

.sb-cell-note {
  font-size: 10.5px;
  color: var(--muted);
  margin-top: 5px;
  white-space: nowrap;
}

.stock-board td.sb-negative .sb-cell-note { color: var(--warn); }

/* The one dark surface on the page, because it carries the one number the
   rest of the board is arithmetic towards. */
.stock-board td.sb-total { background: var(--navy); }

.sb-total-qty {
  font-family: var(--font-display);
  font-size: 24px;
  font-weight: 700;
  letter-spacing: -0.01em;
  font-variant-numeric: tabular-nums;
  color: #fff;
  line-height: 1;
}

.sb-total-qty.is-negative { color: #ff9d94; }

.sb-total-sub {
  font-size: 10.5px;
  color: rgba(255, 255, 255, 0.62);
  margin-top: 4px;
  white-space: nowrap;
}

.stock-board-foot {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 6px 18px;
  padding-top: 12px;
  font-size: 12px;
  color: var(--muted);
}

.stock-board-asof {
  font-family: var(--font-mono);
  font-size: 11.5px;
  color: var(--muted);
  white-space: nowrap;
}

/* Phones: a matrix cannot survive a 375px viewport, so each SKU becomes
   its own card and the bays become rows inside it -- same figures, same
   order, no horizontal scroll. */
@media (max-width: 760px) {
  .stock-board-wrap { overflow-x: visible; }
  .stock-board, .stock-board thead, .stock-board tbody, .stock-board tr, .stock-board th, .stock-board td { display: block; min-width: 0; }
  .stock-board thead { display: none; }

  .stock-board tbody tr {
    background: var(--card);
    border: 1px solid var(--border);
    border-radius: var(--radius);
    margin-bottom: 12px;
    overflow: hidden;
  }

  .stock-board tbody tr + tr td { border-top: 0; }
  .stock-board td { display: flex; justify-content: space-between; align-items: baseline; gap: 12px; padding: 10px 14px; border-top: 1px solid var(--border-light); }
  .stock-board td.sb-sku { display: block; border-top: 0; background: var(--bg); padding: 12px 14px; }
  .stock-board td::before {
    content: attr(data-label);
    font-size: 10px;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: .08em;
    color: #5f6f88;
  }
  .stock-board td.sb-sku::before { content: none; }
  .stock-board td.sb-total::before { color: rgba(255, 255, 255, 0.62); }
  .stock-board .sb-floor, .stock-board .sb-total { border-left: 0; }
  .sb-share { display: none; }
  .sb-cell-note, .sb-total-sub { margin-top: 0; }
}

/* The SKU column sets the board's reading rhythm -- without a floor width
   a two-word product name wraps to three lines and every row grows to
   match it, which is the whole board paying for one column. */
.stock-board th.sb-sku-head,
.stock-board td.sb-sku { min-width: 160px; }
.stock-board tbody td:not(.sb-sku) { min-width: 96px; }

@media (max-width: 760px) {
  .stock-board th.sb-sku-head,
  .stock-board td.sb-sku,
  .stock-board tbody td:not(.sb-sku) { min-width: 0; }
}

/* On a narrow laptop the bay columns scroll -- but the column they are
   arithmetic towards must never be the one that scrolls out of sight, so
   the total is pinned to the right edge and the workings slide under it. */
.stock-board th.sb-total,
.stock-board td.sb-total {
  position: sticky;
  right: 0;
  z-index: 1;
}

.stock-board th.sb-total { background: var(--card); }

@media (max-width: 760px) {
  .stock-board th.sb-total,
  .stock-board td.sb-total { position: static; }
}

/* ---------- Log Trucks: per-truck planned-load states ----------
   A truck row's planned-load section is one of three states (closed /
   locked / open), and only one is ever on screen -- see tlPlannedLoadCell()
   in truck-loading.js for why. The point of all three: a batch of five
   trucks for one customer should read as five short rows, not five copies
   of a full SKU/location/qty picker with an inventory table hanging off
   each one. */

/* closed: a quiet, dashed invitation rather than a button competing with
   Save & Sign for attention -- planning a load here is optional, and an
   solid button reads as "expected," not "available if you want it." */
.tl-plan-toggle {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  margin-top: 10px;
  padding: 6px 0;
  border: none;
  background: none;
  font-family: inherit;
  font-size: 12.5px;
  font-weight: 600;
  color: var(--muted);
  cursor: pointer;
  border-bottom: 1px dashed var(--border);
}
.tl-plan-toggle:hover { color: var(--brand); border-color: var(--brand); }
.tl-plan-toggle:focus-visible { outline: 2px solid var(--brand); outline-offset: 2px; }

/* Collapsed but not empty -- a plan was entered and then collapsed, so
   this reads as a fact on file (solid underline, ink-coloured) rather
   than the dashed, muted invitation an untouched row shows. */
.tl-plan-toggle.has-plan {
  color: var(--ink);
  border-bottom-style: solid;
  border-color: var(--border);
}
.tl-plan-toggle.has-plan:hover { color: var(--brand); border-color: var(--brand); }

/* locked: SKU and quantity are stated as fact (Sales already decided
   them), not offered as a picker -- the one real control here is the
   location select beneath the chip. */
.tl-plan-locked { margin-top: 10px; }

.tl-plan-locked-chip {
  display: flex;
  align-items: baseline;
  gap: 8px;
  flex-wrap: wrap;
  padding: 8px 12px;
  background: var(--neutral-bg);
  border: 1px solid #bfe3d8;
  border-radius: var(--radius);
  margin-bottom: 10px;
}

.tl-plan-locked-label {
  font-size: 9.5px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .07em;
  color: var(--neutral-fg);
}

.tl-plan-locked-sku { font-size: 13px; font-weight: 700; color: var(--ink); }

.tl-plan-locked-loc label { margin-bottom: 4px; }

.tl-loc-avail-note { min-height: 16px; margin-top: 5px; font-size: 12px; }

/* open: the free-entry picker, unchanged in substance from before, just
   now behind a disclosure and with its own quiet way back to closed. */
.tl-plan-open { margin-top: 10px; }

.tl-plan-open-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 8px;
}

.tl-plan-collapse-btn {
  border: none;
  background: none;
  font-family: inherit;
  font-size: 11.5px;
  font-weight: 600;
  color: var(--muted);
  cursor: pointer;
  padding: 0;
  text-decoration: underline;
  text-underline-offset: 2px;
}
.tl-plan-collapse-btn:hover { color: var(--brand); }

/* Which truck this is within the batch being logged -- real structural
   information once a customer brings several trucks at once, not
   decoration: it is the answer to "is this the 2nd of 5, or the 5th of
   5". Distinct in shape from the panel's own numbered step marker so the
   two counting systems (page steps vs. trucks-in-this-batch) don't blur
   into each other. */
.tl-add-truck-card-index {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 20px;
  height: 20px;
  border-radius: 50%;
  background: var(--card);
  border: 1px solid var(--border);
  font-family: var(--font-mono);
  font-size: 11px;
  font-weight: 700;
  color: var(--muted);
  flex-shrink: 0;
}

.tl-add-truck-card-head { align-items: center; }

.tl-trucks-count { margin: 0 0 6px; font-size: 12px; min-height: 15px; }

/* ---------- Finance / Sales: customer orders, payments, receivables ------
   Own namespace (.co-* / .fin-*) rather than extending the .po-* set. The
   order DOCUMENT deliberately reuses .po-doc-* -- a customer order and a
   purchase order are the same kind of sheet pointing opposite ways, and
   two near-identical stylesheets for them would drift. Everything that is
   genuinely new to this module -- a paid/owing reading, an age profile, a
   verification rail, a receipt figure -- lives here. */

/* Right-aligned tabular figures. .po-fig does this already but is scoped
   to #po-doc, so it cannot be borrowed. */
.fin-fig { text-align: right; font-variant-numeric: tabular-nums; }
thead th.fin-fig { text-align: right; }

/* How much has come in, and how much is still owed, as one reading. A bare
   "1,350 / 4,500" makes the reader do the subtraction that actually
   matters, so the outstanding figure is stated outright and the bar just
   carries the proportion at a glance. Not qtyMeter(): that measures
   arrival against an expectation and treats overshoot as the notable case,
   and an overpayment is refused here rather than displayed. */
.co-paid-bar {
  height: 6px;
  border-radius: 3px;
  background: var(--border-light);
  overflow: hidden;
  min-width: 90px;
}

.co-paid-fill {
  display: block;
  height: 100%;
  background: var(--ok);
  border-radius: 3px;
}

.co-paid-fill.overdue { background: var(--warn); }

.co-paid-figures {
  display: flex;
  justify-content: space-between;
  gap: 8px;
  font-size: 11px;
  color: var(--muted);
  margin-top: 3px;
  white-space: nowrap;
}

.co-owing { color: var(--warn); font-weight: 600; }
.co-settled { color: var(--ok); }

/* A cancelled order, a withdrawn document and a reversed payment are all
   "still on the record, no longer in force" -- one treatment for all
   three, so the meaning is learned once. Struck through rather than
   greyed out alone: grey reads as "less important", a strike reads as
   "undone", and undone is the point. */
.co-row-cancelled > td,
.co-row-reversed > td {
  color: var(--muted);
  text-decoration: line-through;
  text-decoration-thickness: 1px;
}

/* The strike must not swallow the sub-line explaining WHY it was undone,
   or the row says "ignore me" with the explanation crossed out too. */
.co-row-cancelled .cell-sub,
.co-row-reversed .cell-sub,
.co-row-cancelled td:last-child,
.co-row-reversed td:last-child {
  text-decoration: none;
}

.co-row-reversal > td { background: var(--warn-bg); }

.co-total-row > td {
  border-top: 2px solid var(--border);
  background: var(--bg);
}

/* Verification: Submitted -> Under Review -> Verified / Rejected, stated
   as the sequence it is rather than a lone status badge. A reader needs to
   know not just where the order stands but what comes next. */
.co-stage-rail {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
  margin-bottom: 10px;
}

.co-stage {
  font-size: 11.5px;
  font-weight: 600;
  padding: 4px 11px;
  border-radius: 999px;
  background: var(--bg);
  color: var(--muted);
  border: 1px solid var(--border-light);
  white-space: nowrap;
}

.co-stage.done { color: var(--ok); border-color: var(--ok-border); background: var(--ok-bg); }
.co-stage.done::before { content: "✓ "; }
/* "current" used to be a 2px ring in the same green as "done" -- against an
   already-green pill that ring reads as almost nothing, which is why a
   fully verified order's rail looked like three identical green pills with
   no visible "you are here". Current now gets a solid fill of its own so
   the eye finds it immediately regardless of which stage it lands on. */
.co-stage.current { background: var(--ok); border-color: var(--ok); color: #fff; box-shadow: 0 0 0 3px var(--ok-bg); }
.co-stage.rejected { color: var(--warn); border-color: var(--warn); background: var(--warn-bg); }
.co-stage.rejected::before { content: "✕ "; }
.co-stage.rejected.current { background: var(--warn); border-color: var(--warn); color: #fff; box-shadow: 0 0 0 3px var(--warn-bg); }
.co-stage-arrow { color: var(--border); font-size: 12px; font-weight: 700; }
/* Green once the stage it follows has actually been reached, so the rail
   reads as one connected path advancing left to right rather than three
   pills that happen to sit in a row. */
.co-stage-arrow.done { color: var(--ok); }

/* "Is there paperwork attached" answered before anything else on the popup,
   not left to be discovered by scrolling to the Sales documents table. */
.co-doc-indicator {
  font-size: 12.5px;
  color: var(--label);
  background: var(--bg);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-sm);
  padding: 7px 12px;
  margin: 10px 0;
}
.co-doc-indicator-warn { color: var(--pending); background: var(--pending-bg); border-color: var(--pending-border); }
.co-doc-indicator a { margin-left: 6px; font-weight: 600; }

.co-review-comment { margin: 8px 0 12px; }

/* ---- One-screen review (migration 084): contract + order | money,
   two checks, one decision ---- */
.co-rv1-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 22px; }
.co-rv1-col h3 { margin: 0 0 8px; font-size: 15px; }
.co-rv1-checks { margin: 18px 0 6px; display: grid; gap: 10px; }
.co-rv1-check {
  display: flex; gap: 10px; align-items: flex-start; font-weight: normal;
  padding: 12px 14px; border: 1px solid var(--border); border-radius: 10px; cursor: pointer;
}
.co-rv1-check input { width: auto; margin: 3px 0 0; }
.co-rv1-check.is-locked { opacity: .65; cursor: default; }
.co-rv1-check .cell-sub { display: block; }
#co-review-foot button:disabled { opacity: .5; cursor: not-allowed; }
@media (max-width: 820px) {
  .co-rv1-grid { grid-template-columns: 1fr; }
}
.co-rv-progress { display: flex; gap: 8px; margin: 4px 0 26px; }
.co-rv-seg {
  flex: 1; height: 6px; padding: 0; border: 0; border-radius: 999px;
  background: var(--border); cursor: pointer; transition: background .2s ease, box-shadow .2s ease;
}
.co-rv-seg:disabled { cursor: default; opacity: .7; }
.co-rv-seg:hover:not(:disabled) { background: #c7cfda; }
.co-rv-seg.done { background: var(--ok); }
.co-rv-seg.flagged { background: var(--warn); }
.co-rv-seg.current { background: var(--ok); box-shadow: 0 0 0 3px var(--ok-bg); }
.co-rv-seg.current.flagged { background: var(--warn); box-shadow: 0 0 0 3px var(--warn-bg); }
.co-rv-seg:focus-visible { outline: 2px solid var(--ink); outline-offset: 3px; }

.co-rv-title {
  font-family: var(--font-display); font-size: 22px; font-weight: 700;
  color: var(--ink); margin: 0 0 6px; letter-spacing: -0.01em; text-wrap: balance;
}
.co-rv-ask { color: var(--label); font-size: 13.5px; line-height: 1.55; margin: 0 0 16px; max-width: 64ch; }
.co-rv-context {
  background: var(--card-subtle); border: 1px solid var(--border-light);
  border-radius: var(--radius); padding: 12px 14px; margin-bottom: 18px;
}
.co-rv-context .co-note-warn { margin: 0; }

.co-rv-tiles { display: grid; grid-template-columns: 1fr 1fr; gap: 14px; }
@media (max-width: 560px) { .co-rv-tiles { grid-template-columns: 1fr; } }
.co-rv-tile {
  display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 6px;
  min-height: 112px; padding: 18px 14px; font: inherit; text-align: center; cursor: pointer;
  background: var(--card); color: var(--label);
  border: 1.5px solid var(--border); border-radius: var(--radius-lg);
  transition: border-color .15s ease, background .15s ease, color .15s ease, transform .15s ease;
}
.co-rv-tile svg { width: 26px; height: 26px; }
.co-rv-tile-label { font-size: 15px; font-weight: 700; color: var(--ink); }
.co-rv-tile-sub { font-size: 11.5px; color: var(--muted); }
.co-rv-tile:hover { background: var(--card-subtle); border-color: #c3cbd6; }
.co-rv-tile:active { transform: scale(.985); }
.co-rv-tile:focus-visible { outline: 2px solid var(--ink); outline-offset: 2px; }
.co-rv-tile.ok.selected { background: var(--ok-bg); border-color: var(--ok); color: var(--ok); }
.co-rv-tile.ok.selected .co-rv-tile-label { color: var(--ok); }
.co-rv-tile.bad.selected { background: var(--warn-bg); border-color: var(--warn); color: var(--warn); }
.co-rv-tile.bad.selected .co-rv-tile-label { color: var(--warn); }

.co-rv-note { margin-top: 16px; }
.co-rv-note textarea, #co-review-reject-reason { width: 100%; resize: vertical; }
.co-rv-hint { font-size: 12px; color: var(--muted); align-self: center; }
.co-rv-tile:disabled { opacity: .38; cursor: not-allowed; pointer-events: none; transform: none; }
.co-rv-doc-gate { font-size: 13px; margin: 0 0 10px; font-style: italic; }

.co-rv-summary { display: flex; flex-direction: column; gap: 8px; margin: 4px 0 18px; }
.co-rv-summary-line {
  display: flex; align-items: center; gap: 12px; width: 100%; padding: 10px 14px;
  font: inherit; text-align: left; cursor: pointer; background: var(--card);
  border: 1px solid var(--border); border-radius: var(--radius);
}
.co-rv-summary-line:hover { background: var(--card-subtle); }
.co-rv-summary-mark {
  flex-shrink: 0; width: 26px; height: 26px; border-radius: 50%;
  display: flex; align-items: center; justify-content: center;
}
.co-rv-summary-mark svg { width: 15px; height: 15px; }
.co-rv-summary-line.ok .co-rv-summary-mark { background: var(--ok-bg); color: var(--ok); }
.co-rv-summary-line.bad .co-rv-summary-mark { background: var(--warn-bg); color: var(--warn); }
.co-rv-summary-text { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 2px; }
.co-rv-summary-text strong { font-size: 13px; color: var(--ink); }
.co-rv-summary-text span { font-size: 12px; color: var(--muted); overflow-wrap: anywhere; }
.co-rv-summary-edit { font-size: 12px; font-weight: 600; color: var(--muted); }
.co-rv-reject-btn { background: var(--warn); border-color: var(--warn); }

@media (prefers-reduced-motion: reduce) {
  .co-rv-seg, .co-rv-tile { transition: none; }
  .co-rv-tile:active { transform: none; }
}

.co-action-row {
  display: flex;
  gap: 10px;
  flex-wrap: wrap;
  margin-top: 12px;
}

/* The three sub-panels below the order document (verification, documents,
   payments). Nested inside an already-padded panel, so they carry a
   lighter frame than a top-level one -- they are sections of one record,
   not three separate screens. */
.co-subpanel {
  margin: 0;
  border: 1px solid var(--border-light);
  box-shadow: none;
}

.co-subhead {
  margin: 18px 0 6px;
  font-size: 13px;
}

.co-upload-row {
  display: flex;
  gap: 12px;
  flex-wrap: wrap;
  align-items: flex-end;
  margin-top: 14px;
  padding-top: 14px;
  border-top: 1px dashed var(--border-light);
}

.co-upload-row > div { flex: 1 1 170px; min-width: 0; }
.co-upload-row > div:last-child { flex: 0 0 auto; }
.co-upload-row label { margin-bottom: 4px; }
.co-upload-row input, .co-upload-row select { margin-bottom: 0; }

/* The create form's paperwork rows: stacked, so only the first is ruled. */
.co-paperwork-row { margin-top: 0; padding-top: 0; border-top: 0; }
.co-paperwork-row + .co-paperwork-row { margin-top: 10px; }
.co-paperwork-row .icon-btn { font-size: 18px; line-height: 1; }

/* Password + the send buttons on one line: signing and sending are one act. */
.co-send-row {
  display: flex; gap: 12px; flex-wrap: wrap; align-items: flex-end;
  justify-content: flex-end; margin-top: 14px;
}
.co-send-sign { flex: 1 1 260px; min-width: 0; max-width: 420px; }
.co-send-sign input { margin-bottom: 0; }
.co-send-actions { display: flex; gap: 10px; flex-wrap: wrap; }

/* Finance's review, drawn inside the order rather than in a second window. */
.co-review-inline { margin-top: 12px; padding-top: 14px; border-top: 1px dashed var(--border-light); }

/* Warnings inside a modal that state what the action will and will not do
   -- specifically that nothing financial is being erased. Worth reading
   before a password is typed, so it is set apart rather than left as
   another line of muted text. */
.co-note-warn {
  background: var(--warn-bg);
  border-left: 3px solid var(--warn);
  border-radius: var(--radius-sm);
  padding: 9px 12px;
  margin: 10px 0 14px;
  font-size: 12px;
  line-height: 1.5;
  color: var(--ink);
}

.co-modal-actions {
  margin-top: 18px;
  display: flex;
  gap: 10px;
  justify-content: flex-end;
}

.co-inline-check {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin: 0;
  font-size: 12px;
  color: var(--label);
  white-space: nowrap;
}

.co-inline-check input { margin: 0; }

/* The amount, on a receipt, is the one thing the person holding it looks
   for. Everything else on that sheet is context for it. */
.co-receipt-amount {
  margin: 18px 0;
  padding: 14px 18px;
  background: var(--bg);
  border-radius: var(--radius);
  border: 1px solid var(--border-light);
}

.co-receipt-figure {
  font-family: var(--font-display);
  font-size: 30px;
  font-weight: 700;
  letter-spacing: -0.01em;
  color: var(--ink);
  font-variant-numeric: tabular-nums;
  line-height: 1.15;
}

/* One customer's outstanding money, split by how old each part of it is.
   Proportional segments rather than four more numeric columns: the
   question this answers is "is this debt fresh or has it been sitting
   there", which is a shape, and the exact figures are one row-click away
   in the breakdown. */
.co-age-bar {
  display: flex;
  height: 8px;
  border-radius: 4px;
  overflow: hidden;
  background: var(--border-light);
  min-width: 90px;
}

.co-age-seg { display: block; height: 100%; }
.co-age-current { background: var(--ok); }
.co-age-30 { background: var(--pending); }
.co-age-60 { background: #e8a33d; }
.co-age-90 { background: #dd7c2a; }
.co-age-over { background: var(--warn); }

@media (max-width: 720px) {
  .co-upload-row > div { flex: 1 1 100%; }
  .co-modal-actions { flex-direction: column-reverse; }
  .co-modal-actions button { width: 100%; }
}

/* ---------- Motion preferences ---------- */
/* Everything above earns its motion by explaining a change of state -- the
   rail travelling, a panel arriving, an indicator appearing. None of it
   carries information that stillness would lose, so honouring the OS
   setting costs nothing and is the difference between a considered
   interface and one that makes somebody ill. Kept near zero rather than at
   zero: a genuine 0s can leave animation-end handlers unfired. */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
}

/* ---------- Notification centre ---------- */
/*
   The plant's departments hand work to each other all day, and until this
   existed the only way to learn that a handover had happened was to open
   the other department's page and look. This is that fact, delivered.
   Scoped to one person: what arrives here is what THIS operator's job
   depends on, resolved from their roles at the moment the event happened
   (includes/notifications.php).
*/

.notif { position: relative; display: inline-flex; }

.notif-bell {
  position: relative;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  /* 40px, not the 32px the topbar's other chrome uses: it is the only
     control in the bar that gets pressed, and it is pressed on a tablet in
     a warehouse. */
  width: 40px;
  height: 40px;
  padding: 0;
  border-radius: var(--radius);
  border: 1px solid transparent;
  background: transparent;
  color: var(--label);
  box-shadow: none;
  transition: background-color var(--dur-fast) var(--ease-out),
              color var(--dur-fast) var(--ease-out),
              border-color var(--dur-fast) var(--ease-out);
}
.notif-bell:hover { background: var(--card-subtle); border-color: var(--border); color: var(--ink); box-shadow: none; }
.notif-bell:active { transform: none; }
.notif-bell[aria-expanded="true"] { background: var(--card-subtle); border-color: var(--border); color: var(--ink); }
.notif-bell:focus-visible { outline: 2px solid var(--accent-blue); outline-offset: 2px; }
.notif-bell svg { width: 19px; height: 19px; display: block; }

/* Positioned outside the icon's own box so a two-digit count grows
   outward instead of squeezing the bell. */
.notif-badge {
  position: absolute;
  top: 4px;
  right: 3px;
  min-width: 17px;
  height: 17px;
  padding: 0 4px;
  border-radius: var(--radius-full);
  background: var(--brand);
  border: 2px solid #ffffff;
  color: #fff;
  font-size: 10px;
  font-weight: 700;
  line-height: 13px;
  text-align: center;
  font-variant-numeric: tabular-nums;
}

/* Anchored to the bell's right edge rather than centred on it, so the
   panel never runs off the viewport on a narrow laptop. */
.notif-panel {
  position: absolute;
  top: calc(100% + 8px);
  right: 0;
  width: min(414px, calc(100vw - 24px));
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-lg);
  z-index: 60;
  overflow: hidden;
  display: flex;
  flex-direction: column;
  text-align: left;
  font-weight: 400;
  color: var(--ink);
  animation: notifPanelIn var(--dur-panel) var(--ease-out);
  transform-origin: top right;
}

/* Grows out of the control that opened it -- the spatial continuity that
   says where the panel came from and where closing it will put it back. */
@keyframes notifPanelIn {
  from { opacity: 0; transform: translateY(-6px) scale(0.985); }
  to   { opacity: 1; transform: none; }
}

.notif-head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 12px;
  padding: 13px 15px;
  border-bottom: 1px solid var(--border-light);
}
.notif-title { font-family: var(--font-display); font-size: 15px; font-weight: 700; color: var(--ink); }
.notif-sub { font-size: 11px; color: var(--muted); margin-top: 1px; }
.notif-head .linklike { font-size: 11.5px; white-space: nowrap; padding: 4px 0; }
.notif-head-actions { display: flex; align-items: center; gap: 10px; }
.notif-sound-btn {
  display: inline-flex; align-items: center; justify-content: center;
  width: 28px; height: 28px; padding: 0;
  border: 1px solid var(--border-light); border-radius: 7px;
  background: transparent; color: var(--muted); box-shadow: none; cursor: pointer;
}
.notif-sound-btn:hover { color: var(--ink); background: var(--bg); }
.notif-sound-btn[aria-pressed="true"] { color: var(--navy-light); }
.notif-sound-btn svg { width: 15px; height: 15px; }

.notif-chips {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  padding: 10px 15px;
  border-bottom: 1px solid var(--border-light);
  background: var(--card-subtle);
}

.notif-chip {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  padding: 4px 9px;
  border-radius: var(--radius-full);
  border: 1px solid var(--border);
  background: #ffffff;
  color: var(--label);
  font-size: 11px;
  font-weight: 600;
  box-shadow: none;
  transition: background-color var(--dur-fast) var(--ease-out),
              border-color var(--dur-fast) var(--ease-out),
              color var(--dur-fast) var(--ease-out);
}
.notif-chip:hover { background: var(--card-subtle); border-color: #cbd5e1; color: var(--ink); box-shadow: none; }
.notif-chip:active { transform: none; }
.notif-chip[aria-pressed="true"] {
  background: var(--ink);
  border-color: var(--ink);
  color: #ffffff;
}
.notif-chip:focus-visible { outline: 2px solid var(--accent-blue); outline-offset: 1px; }

/* The count rides inside the chip, with its own contrast pair per state,
   since the chip inverts when it is the selected one. */
.notif-chip-count {
  min-width: 16px;
  padding: 0 4px;
  border-radius: var(--radius-full);
  background: var(--brand);
  color: #fff;
  font-size: 9.5px;
  line-height: 15px;
  font-variant-numeric: tabular-nums;
}
.notif-chip[aria-pressed="true"] .notif-chip-count { background: #ffffff; color: var(--ink); }

.notif-list {
  /* Capped rather than page-length: a dropdown that can grow past the fold
     hides its own bottom edge and takes the page scroll with it. */
  max-height: min(58vh, 460px);
  overflow-y: auto;
  overscroll-behavior: contain;
}

.notif-item {
  display: flex;
  gap: 11px;
  width: 100%;
  padding: 11px 15px;
  border: none;
  border-bottom: 1px solid var(--border-light);
  border-radius: 0;
  background: #ffffff;
  box-shadow: none;
  text-align: left;
  font-weight: 400;
  font-size: 12.5px;
  color: var(--ink);
  transition: background-color var(--dur-fast) var(--ease-out);
}
.notif-item:last-child { border-bottom: none; }
.notif-item:hover { background: var(--card-subtle); box-shadow: none; }
.notif-item:active { transform: none; }
.notif-item:focus-visible { outline: 2px solid var(--accent-blue); outline-offset: -2px; }

/* Nothing to open. Rendered as a plain row rather than a dead button, so
   it never invites a click that would go nowhere -- some events are
   genuinely just news (a lab report Production can read but not open). */
.notif-item.is-static { cursor: default; }
.notif-item.is-static:hover { background: #ffffff; }

.notif-item.is-unread { background: #fbfdff; }
.notif-item.is-unread:hover { background: #f4f9ff; }

.notif-ico {
  flex-shrink: 0;
  width: 30px;
  height: 30px;
  border-radius: var(--radius);
  display: flex;
  align-items: center;
  justify-content: center;
  background: var(--neutral-bg);
  color: var(--neutral-fg);
}
.notif-ico svg { width: 16px; height: 16px; }

/* One colour per department, so a full inbox is scannable by shape before
   it is read. Colour is never the only carrier -- every row also names its
   department in words on the meta line. */
.notif-ico.cat-sales        { background: #eff6ff; color: #1d4ed8; }
.notif-ico.cat-supply_chain { background: #f0fdfa; color: #0f766e; }
.notif-ico.cat-finance      { background: #f5f3ff; color: #6d28d9; }
.notif-ico.cat-production   { background: #fff7ed; color: #c2410c; }
.notif-ico.cat-quality      { background: #ecfdf5; color: #047857; }
.notif-ico.cat-maintenance  { background: #f8fafc; color: #475569; }
.notif-ico.cat-admin        { background: #fef2f2; color: #b91c1c; }

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

.notif-item-title {
  font-weight: 600;
  color: var(--ink);
  line-height: 1.35;
  /* Text a person typed reaches these lines -- a rejection reason, a
     customer name, a reference number with no spaces in it -- so they have
     to reflow rather than push the panel sideways. */
  overflow-wrap: anywhere;
}
.notif-item-text {
  color: var(--muted);
  font-size: 11.5px;
  line-height: 1.45;
  margin-top: 2px;
  overflow-wrap: anywhere;
  display: -webkit-box;
  -webkit-line-clamp: 3;
  -webkit-box-orient: vertical;
  overflow: hidden;
}

.notif-meta {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 6px;
  margin-top: 5px;
  font-size: 10.5px;
  color: var(--muted);
}
.notif-meta .dot { width: 3px; height: 3px; border-radius: 50%; background: #cbd5e1; flex-shrink: 0; }
.notif-dept { font-weight: 700; letter-spacing: .03em; text-transform: uppercase; font-size: 9.5px; }

/* Severity is stated, not only coloured -- "Urgent" beside a red dot still
   reads as urgent in greyscale, or to an operator who cannot tell the red
   from the amber. */
.notif-sev {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  font-weight: 700;
  font-size: 9.5px;
  text-transform: uppercase;
  letter-spacing: .04em;
}
.notif-sev::before { content: ""; width: 6px; height: 6px; border-radius: 50%; background: currentColor; }
.notif-sev.sev-action   { color: #b45309; }
.notif-sev.sev-warning  { color: #b45309; }
.notif-sev.sev-critical { color: var(--warn); }
.notif-sev.sev-success  { color: var(--ok); }

/* The unread mark: 8px, top-aligned with the title. Deliberately not a
   colour change on the text -- read and unread must differ by something
   present or absent, not by a shade of grey. */
.notif-unread-dot {
  flex-shrink: 0;
  align-self: flex-start;
  margin-top: 5px;
  width: 8px;
  height: 8px;
  border-radius: 50%;
  background: var(--accent-blue);
}

.notif-foot {
  padding: 9px 15px;
  border-top: 1px solid var(--border-light);
  background: var(--card-subtle);
  text-align: center;
}
.notif-foot button { width: 100%; font-size: 11.5px; padding: 7px 12px; }

.notif-empty {
  padding: 34px 22px;
  text-align: center;
  color: var(--muted);
  font-size: 12.5px;
}
.notif-empty svg { width: 30px; height: 30px; color: #cbd5e1; margin-bottom: 8px; }
.notif-empty strong { display: block; color: var(--label); font-size: 13px; margin-bottom: 3px; }

/* Placeholders while the first page loads. A spinner in a 460px panel says
   "something is happening"; these say "roughly this much, roughly here",
   so the arriving content does not shove the reader's eye somewhere new. */
.notif-skeleton { padding: 11px 15px; display: flex; gap: 11px; }
.notif-skeleton .sk {
  background: linear-gradient(90deg, #eef2f7 25%, #f6f9fc 50%, #eef2f7 75%);
  background-size: 200% 100%;
  animation: skShimmer 1.3s infinite linear;
  border-radius: var(--radius-sm);
}
.notif-skeleton .sk-ico { width: 30px; height: 30px; border-radius: var(--radius); flex-shrink: 0; }
.notif-skeleton .sk-lines { flex: 1; }
.notif-skeleton .sk-lines .sk { height: 9px; margin-bottom: 6px; }
.notif-skeleton .sk-lines .sk:nth-child(1) { width: 72%; }
.notif-skeleton .sk-lines .sk:nth-child(2) { width: 94%; }
.notif-skeleton .sk-lines .sk:nth-child(3) { width: 38%; }
@keyframes skShimmer {
  from { background-position: 200% 0; }
  to   { background-position: -200% 0; }
}

/* Full-width sheet on a phone: a 414px popover anchored to the right of a
   375px screen has nowhere to be. */
@media (max-width: 520px) {
  .notif-panel {
    /* Still absolute, so it stays anchored 8px under the bell that opened
       it. position:fixed would have spanned the viewport just as well, but
       with auto offsets it lands at the element's static position -- which
       is the top of the topbar, not below it, so the panel covered the
       control it belongs to. Stretching an absolute box between two
       viewport-relative edges keeps the anchor AND the full width: the
       topbar's 16px gutter minus 8px puts the right edge 8px from the
       screen, and 100vw - 16px carries the left edge to match. */
    right: -8px;
    width: calc(100vw - 16px);
    max-height: 78vh;
  }
  .notif-list { max-height: 54vh; }
}

/* The drawer is operated with fingers, so its rows get the full 44px
   target rather than the 34px that reads well under a cursor. 13px of
   padding around an 18px icon row is what lands exactly on 44. */
@media (max-width: 860px) {
  .side-link, .side-group-toggle { padding: 13px 12px; }
  .side-sublink { padding: 12px 12px 12px 36px; }
}

/* Screen-reader-only, for the live region that announces a changed count
   without putting the number on screen twice. */
.sr-only {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  clip-path: inset(50%);
  white-space: nowrap;
  border: 0;
}

/* The order picker inside Authorize to load: one block per candidate order,
   its money position under the number, and a button per line so a single
   click names both the order and the line the truck is carrying. */
.tl-auth-candidate {
  border: 1px solid var(--border);
  border-radius: var(--radius-md, 8px);
  padding: 10px 12px;
  margin-bottom: 10px;
}
.tl-auth-candidate-head {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-bottom: 4px;
}
.tl-auth-candidate-line { margin-top: 8px; }

/* ==========================================================================
   FINANCE REDESIGN & ENTERPRISE ERP RECEIPT STYLING
   ========================================================================== */

/* --- Finance Hub Unified Sub-navigation --- */
.fin-hub-nav {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 12px;
  background: var(--surface, #ffffff);
  border: 1px solid var(--border, #e2e8f0);
  border-radius: var(--radius-lg, 10px);
  padding: 8px 12px;
  margin-bottom: 20px;
  box-shadow: 0 1px 3px rgba(0, 0, 0, 0.04);
}

.fin-hub-tabs {
  display: flex;
  align-items: center;
  gap: 6px;
  flex-wrap: wrap;
}

.fin-hub-tab {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  padding: 8px 14px;
  border-radius: var(--radius-md, 8px);
  border: 1px solid transparent;
  background: transparent;
  color: var(--label, #475569);
  font-size: 13px;
  font-weight: 600;
  cursor: pointer;
  transition: all 0.15s ease-in-out;
  text-decoration: none;
}

.fin-hub-tab:hover {
  background: #f1f5f9;
  color: var(--ink, #0f172a);
}

.fin-hub-tab.active {
  background: #e6f0fa;
  color: var(--brand, #0066cc);
  border-color: #bee3f8;
}

.fin-hub-tab svg {
  width: 16px;
  height: 16px;
  flex-shrink: 0;
}

.fin-hub-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 18px;
  height: 18px;
  padding: 0 5px;
  border-radius: 999px;
  background: #e53e3e;
  color: #ffffff;
  font-size: 11px;
  font-weight: 700;
  line-height: 1;
}

.fin-hub-actions {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
}

.fin-quick-btn {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 7px 12px;
  border-radius: var(--radius-md, 8px);
  font-size: 12.5px;
  font-weight: 600;
  cursor: pointer;
  border: 1px solid var(--border, #cbd5e1);
  background: #ffffff;
  color: var(--ink, #0f172a);
  transition: all 0.15s ease;
}

.fin-quick-btn:hover {
  background: #f8fafc;
  border-color: #94a3b8;
}

.fin-quick-btn.primary {
  background: var(--brand, #0066cc);
  border-color: var(--brand, #0066cc);
  color: #ffffff;
}

.fin-quick-btn.primary:hover {
  background: #0052a3;
}

.fin-quick-btn svg {
  width: 14px;
  height: 14px;
}

/* --- Segmented Bar & Switchers --- */
.fin-segmented-bar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 12px;
  margin-bottom: 18px;
  border-bottom: 1px solid var(--border, #e2e8f0);
  padding-bottom: 12px;
}

.fin-segmented-switch {
  display: inline-flex;
  background: #f1f5f9;
  border-radius: 8px;
  padding: 3px;
  gap: 4px;
}

.fin-seg-btn {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 6px 14px;
  border-radius: 6px;
  border: none;
  background: transparent;
  color: var(--label, #64748b);
  font-size: 13px;
  font-weight: 600;
  cursor: pointer;
  transition: all 0.15s ease;
}

.fin-seg-btn:hover {
  color: var(--ink, #0f172a);
}

.fin-seg-btn.active {
  background: #ffffff;
  color: var(--ink, #0f172a);
  box-shadow: 0 1px 3px rgba(0, 0, 0, 0.08);
}

.fin-seg-btn svg {
  width: 15px;
  height: 15px;
}

/* --- Liquid Money Account Cards Grid --- */
.fin-account-cards-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: 16px;
  margin-bottom: 24px;
}

.fin-account-card {
  background: #ffffff;
  border: 1px solid var(--border, #e2e8f0);
  border-radius: var(--radius-lg, 10px);
  padding: 16px;
  box-shadow: 0 1px 3px rgba(0, 0, 0, 0.03);
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  transition: transform 0.15s ease, box-shadow 0.15s ease;
}

.fin-account-card:hover {
  transform: translateY(-2px);
  box-shadow: 0 4px 12px rgba(0, 0, 0, 0.06);
  border-color: #cbd5e1;
}

.fin-account-card-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 10px;
}

.fin-account-code {
  font-family: var(--font-mono, monospace);
  font-size: 11px;
  font-weight: 700;
  background: #e2e8f0;
  color: #334155;
  padding: 2px 6px;
  border-radius: 4px;
  margin-right: 6px;
}

.fin-account-type-badge {
  font-size: 11.5px;
  font-weight: 600;
  color: var(--label, #64748b);
}

.fin-account-edit-btn {
  padding: 3px 8px;
  font-size: 11.5px;
}

.fin-account-card-name {
  font-size: 15px;
  font-weight: 700;
  color: var(--ink, #0f172a);
  margin-bottom: 2px;
}

.fin-account-card-institution {
  font-size: 12px;
  color: var(--muted, #64748b);
  margin-bottom: 14px;
}

.fin-account-balance-block {
  background: #f8fafc;
  border: 1px solid #edf2f7;
  border-radius: 8px;
  padding: 10px 12px;
  margin-bottom: 12px;
}

.fin-account-balance-label {
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 0.05em;
  color: var(--muted, #64748b);
  margin-bottom: 2px;
}

.fin-account-balance-val {
  font-family: var(--font-mono, monospace);
  font-size: 18px;
  font-weight: 700;
  color: var(--brand, #0066cc);
}

.fin-account-card-footer {
  display: flex;
  align-items: center;
  justify-content: space-between;
  border-top: 1px solid #f1f5f9;
  padding-top: 8px;
  font-size: 11.5px;
  color: var(--muted, #94a3b8);
}

/* --- Customer Outstanding Debtor Profile & Ledger --- */
.fin-customer-profile-card {
  border: 1px solid #bee3f8;
  background: #ffffff;
  border-radius: var(--radius-lg, 10px);
  padding: 16px 20px;
  margin-top: 20px;
  box-shadow: 0 2px 8px rgba(0, 102, 204, 0.05);
}

.fin-customer-profile-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 12px;
  margin-bottom: 16px;
  padding-bottom: 12px;
  border-bottom: 1px solid #edf2f7;
}

.fin-customer-tabs {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-bottom: 14px;
}

.fin-customer-tab {
  padding: 6px 14px;
  border-radius: 6px;
  border: 1px solid var(--border, #cbd5e1);
  background: #f8fafc;
  color: var(--label, #475569);
  font-size: 12.5px;
  font-weight: 600;
  cursor: pointer;
  transition: all 0.15s ease;
}

.fin-customer-tab:hover {
  background: #edf2f7;
}

.fin-customer-tab.active {
  background: var(--brand, #0066cc);
  border-color: var(--brand, #0066cc);
  color: #ffffff;
}

tr.row-selected td {
  background: #ebf8ff !important;
  font-weight: 600;
}

/* --- Customer Orders Collapsible Builder --- */
.co-builder-panel {
  border: 1px solid var(--border, #e2e8f0);
  border-radius: var(--radius-lg, 10px);
  background: #ffffff;
  margin-bottom: 20px;
  box-shadow: 0 1px 3px rgba(0, 0, 0, 0.03);
}

.co-builder-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 14px 18px;
  border-bottom: 1px solid var(--border, #f1f5f9);
  background: #fafbfc;
  border-top-left-radius: var(--radius-lg, 10px);
  border-top-right-radius: var(--radius-lg, 10px);
}

.co-builder-header h2 {
  margin: 0;
  font-size: 16px;
  font-weight: 700;
  color: var(--ink, #0f172a);
}

.co-builder-body {
  padding: 18px;
}

.co-form-columns {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 20px;
  margin-bottom: 18px;
}

@media (max-width: 768px) {
  .co-form-columns {
    grid-template-columns: 1fr;
    gap: 12px;
  }
}

.co-form-col {
  display: flex;
  flex-direction: column;
  gap: 10px;
}

/* --- Payment Financial Context Card & Shortcuts --- */
.co-pay-context-card {
  background: #f8fafc;
  border: 1px solid #e2e8f0;
  border-radius: var(--radius-md, 8px);
  padding: 14px;
  margin-bottom: 16px;
}

.co-pay-context-card .ctx-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  font-size: 13px;
  margin-bottom: 6px;
}

.co-pay-context-card .ctx-row:last-child {
  margin-bottom: 0;
}

.co-pay-context-card .ctx-k {
  color: var(--muted, #64748b);
  font-weight: 500;
}

.co-pay-context-card .ctx-v {
  font-weight: 600;
  color: var(--ink, #0f172a);
}

.co-pay-context-card .ctx-v.bold-num {
  font-family: var(--font-mono, monospace);
  font-size: 14px;
}

.pay-amount-shortcuts {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  margin-top: 6px;
  margin-bottom: 12px;
}

.pay-shortcut-chip {
  display: inline-flex;
  align-items: center;
  padding: 4px 10px;
  border-radius: 999px;
  border: 1px solid var(--border, #cbd5e1);
  background: #ffffff;
  color: var(--label, #334155);
  font-size: 11.5px;
  font-weight: 600;
  cursor: pointer;
  transition: all 0.12s ease;
}

.pay-shortcut-chip:hover {
  background: #e2e8f0;
  border-color: #94a3b8;
}

.pay-shortcut-chip.primary {
  background: #ebf8ff;
  border-color: #90cdf4;
  color: var(--brand, #0066cc);
}

.pay-shortcut-chip.primary:hover {
  background: #bee3f8;
}

/* ==========================================================================
   OFFICIAL CORPORATE ERP RECEIPT DOCUMENT STYLING (.receipt-doc)
   ========================================================================== */

.receipt-doc {
  background: #ffffff;
  border: 1px solid var(--border, #cbd5e1);
  border-radius: var(--radius-lg, 10px);
  padding: 32px 36px;
  max-width: 820px;
  margin: 0 auto;
  font-family: var(--font-body, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif);
  color: #1e293b;
  box-shadow: 0 4px 20px rgba(0, 0, 0, 0.05);
}

/* Masthead */
.receipt-masthead {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  border-bottom: 2px solid #0f172a;
  padding-bottom: 18px;
  margin-bottom: 22px;
}

.receipt-issuer {
  display: flex;
  align-items: center;
  gap: 14px;
}

.receipt-brand-mark {
  width: 48px;
  height: 48px;
  border-radius: 8px;
  background: #0f172a;
  color: #ffffff;
  display: flex;
  align-items: center;
  justify-content: center;
  font-family: var(--font-display, sans-serif);
  font-weight: 900;
  font-size: 16px;
  letter-spacing: 0.08em;
  flex-shrink: 0;
}

.receipt-issuer-name {
  font-family: var(--font-display, sans-serif);
  font-size: 18px;
  font-weight: 800;
  color: #0f172a;
  letter-spacing: -0.01em;
}

.receipt-issuer-sub {
  font-size: 12.5px;
  font-weight: 600;
  color: #0066cc;
}

.receipt-issuer-tax {
  font-size: 11px;
  color: #64748b;
  margin-top: 1px;
}

.receipt-meta-box {
  text-align: right;
}

.receipt-meta-label {
  font-size: 11px;
  font-weight: 700;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: #64748b;
  margin-bottom: 2px;
}

.receipt-meta-no {
  font-family: var(--font-mono, monospace);
  font-size: 20px;
  font-weight: 800;
  color: #0f172a;
  letter-spacing: -0.01em;
}

.receipt-meta-status {
  margin-top: 4px;
}

/* Hero Payment Amount Banner */
.receipt-hero-banner {
  background: linear-gradient(135deg, #0f172a 0%, #1e293b 100%);
  color: #ffffff;
  border-radius: 8px;
  padding: 20px 24px;
  margin-bottom: 22px;
  position: relative;
  overflow: hidden;
}

.receipt-hero-banner.reversal {
  background: linear-gradient(135deg, #7f1d1d 0%, #991b1b 100%);
}

.receipt-hero-label {
  display: flex;
  align-items: center;
  justify-content: space-between;
  font-size: 12px;
  font-weight: 700;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: #94a3b8;
  margin-bottom: 8px;
}

.receipt-hero-banner.reversal .receipt-hero-label {
  color: #fca5a5;
}

.receipt-hero-method-badge {
  background: rgba(255, 255, 255, 0.15);
  color: #ffffff;
  padding: 3px 10px;
  border-radius: 999px;
  font-size: 11.5px;
  font-weight: 600;
  text-transform: none;
  letter-spacing: normal;
}

.receipt-hero-amount {
  display: flex;
  align-items: baseline;
  gap: 6px;
  margin-bottom: 4px;
}

.receipt-currency-symbol {
  font-size: 20px;
  font-weight: 700;
  color: #cbd5e1;
}

.receipt-amount-val {
  font-family: var(--font-mono, monospace);
  font-size: 34px;
  font-weight: 800;
  letter-spacing: -0.02em;
  color: #ffffff;
}

.receipt-hero-sub {
  font-size: 12px;
  color: #cbd5e1;
  margin-top: 6px;
  border-top: 1px solid rgba(255, 255, 255, 0.12);
  padding-top: 6px;
}

/* Parties & Transaction Info Grid */
.receipt-parties-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 20px;
  margin-bottom: 22px;
}

@media (max-width: 640px) {
  .receipt-parties-grid {
    grid-template-columns: 1fr;
    gap: 12px;
  }
}

.receipt-party-card {
  background: #f8fafc;
  border: 1px solid #e2e8f0;
  border-radius: 8px;
  padding: 14px 16px;
}

.receipt-section-header {
  font-size: 10.5px;
  font-weight: 800;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: #64748b;
  margin-bottom: 10px;
  border-bottom: 1px solid #e2e8f0;
  padding-bottom: 4px;
}

.receipt-party-title {
  font-size: 15px;
  font-weight: 700;
  color: #0f172a;
  margin-bottom: 8px;
}

.receipt-kv-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  font-size: 12.5px;
  margin-bottom: 5px;
}

.receipt-kv-row:last-child {
  margin-bottom: 0;
}

.receipt-k {
  color: #64748b;
}

.receipt-v {
  font-weight: 600;
  color: #1e293b;
}

/* Ledger Allocation Table */
.receipt-ledger-section {
  margin-bottom: 22px;
}

.receipt-ledger-table {
  width: 100%;
  border-collapse: collapse;
  margin-top: 8px;
}

.receipt-ledger-table th {
  background: #f1f5f9;
  font-size: 11px;
  font-weight: 700;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  color: #475569;
  padding: 9px 12px;
  border-top: 1px solid #cbd5e1;
  border-bottom: 1px solid #cbd5e1;
}

.receipt-ledger-table td {
  padding: 12px;
  font-size: 13px;
  border-bottom: 1px solid #e2e8f0;
}

/* Note Box & Reversal Alert */
.receipt-note-box {
  background: #f8fafc;
  border-left: 3px solid #64748b;
  padding: 10px 14px;
  margin-bottom: 22px;
  font-size: 12.5px;
  border-radius: 0 6px 6px 0;
}

.receipt-note-tag {
  font-weight: 700;
  color: #334155;
  margin-right: 6px;
}

.receipt-reversal-alert {
  background: #fef2f2;
  border: 1px solid #fecaca;
  border-left: 4px solid #dc2626;
  color: #991b1b;
  padding: 12px 16px;
  border-radius: 6px;
  font-size: 13px;
  margin-bottom: 22px;
}

.receipt-reversal-reason {
  margin-top: 4px;
  font-size: 12px;
  color: #7f1d1d;
}

/* Official Footer & Signatures */
.receipt-footer-grid {
  display: grid;
  grid-template-columns: 1fr 2fr;
  gap: 24px;
  align-items: center;
  border-top: 1px solid #e2e8f0;
  padding-top: 20px;
  margin-top: 10px;
}

@media (max-width: 640px) {
  .receipt-footer-grid {
    grid-template-columns: 1fr;
    gap: 16px;
  }
}

.receipt-official-seal {
  display: flex;
  align-items: center;
  justify-content: center;
}

.receipt-seal-border {
  border: 2px dashed #0066cc;
  border-radius: 8px;
  padding: 8px 14px;
  text-align: center;
  background: #f0f7ff;
}

.receipt-seal-stamp {
  display: block;
  font-family: var(--font-display, sans-serif);
  font-size: 11px;
  font-weight: 800;
  letter-spacing: 0.12em;
  color: #0066cc;
}

.receipt-seal-sub {
  display: block;
  font-family: var(--font-mono, monospace);
  font-size: 9.5px;
  font-weight: 600;
  color: #64748b;
  margin-top: 2px;
}

.receipt-sign-block {
  display: flex;
  gap: 20px;
}

.receipt-sign-line {
  flex: 1;
  border-top: 1px solid #0f172a;
  padding-top: 6px;
  text-align: center;
}

.receipt-sign-name {
  font-size: 12px;
  font-weight: 700;
  color: #0f172a;
  min-height: 16px;
}

.receipt-sign-title {
  font-size: 10.5px;
  color: #64748b;
  text-transform: uppercase;
  letter-spacing: 0.05em;
}

/* Print Rules for .receipt-doc */
@media print {
  .receipt-doc {
    box-shadow: none !important;
    border: none !important;
    padding: 0 !important;
    max-width: 100% !important;
  }

  .receipt-hero-banner {
    -webkit-print-color-adjust: exact !important;
    print-color-adjust: exact !important;
  }
}


/* ==========================================================================
   Inventory -- Stock Transfers & Stock Adjustments
   Built from the app's existing surfaces (.panel, .card, .badge, chips,
   fin-segmented-switch); only what those documents need that nothing else
   draws lives here: the route (A -> B), the in-transit queue, the document
   timeline, and quantity entry tables.
   ========================================================================== */
.inv-toolbar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
  flex-wrap: wrap;
  margin-bottom: 16px;
}
.inv-lede { margin: 0; color: var(--muted); font-size: 13px; max-width: 62ch; line-height: 1.5; }
.inv-primary-btn { display: inline-flex; align-items: center; gap: 8px; }
.inv-primary-btn svg { width: 16px; height: 16px; }
.inv-danger-btn { background: #ffffff; color: var(--warn); border: 1px solid var(--warn-border); box-shadow: none; }
.inv-danger-btn:hover { background: var(--warn); color: #ffffff; border-color: var(--warn); }
.inv-kpis { margin-bottom: 20px; }

.inv-num-pending { background: var(--pending-bg) !important; color: var(--pending) !important; }
.inv-num-pending svg { width: 15px; height: 15px; }
.inv-num-danger { background: var(--warn-bg) !important; color: var(--warn) !important; }

.inv-filter-bar { display: flex; flex-wrap: wrap; align-items: center; gap: 12px 16px; margin-bottom: 6px; }
.inv-filter-fields { display: flex; flex-wrap: wrap; gap: 10px; align-items: center; }
.inv-inline-label {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin: 0;
  font-size: 11px;
}
.inv-inline-label input,
.inv-inline-label select { margin: 0; width: auto; min-width: 0; padding: 6px 8px; font-size: 13px; }
.inv-range-label { margin: 6px 0 10px; font-size: 12.5px; }

.inv-table td { vertical-align: top; }
.inv-doc-no {
  font-family: var(--font-mono);
  font-size: 12.5px;
  font-weight: 600;
  color: var(--accent-blue-dark);
  padding: 0;
}
.inv-doc-no:hover { text-decoration: underline; }
.inv-row-voided td { color: var(--muted); }
.inv-row-voided .inv-doc-no { color: var(--muted); text-decoration: line-through; }
.inv-unit { color: var(--muted); font-size: 11px; font-weight: 500; }
.inv-muted-num { color: var(--label); font-variant-numeric: tabular-nums; }
.inv-short-tag { margin-top: 4px; color: var(--warn); font-weight: 600; }
.inv-inline-err { margin: 0; font-size: 12px; }
.inv-empty { padding: 18px 4px; color: var(--muted); font-size: 13px; }

.inv-route-cell { white-space: nowrap; }
.inv-route-pill {
  display: inline-block;
  padding: 2px 8px;
  border-radius: var(--radius-sm);
  background: var(--neutral-bg);
  color: var(--neutral-fg);
  font-size: 12px;
  font-weight: 600;
  white-space: nowrap;
}
.inv-route-arrow { width: 14px; height: 14px; vertical-align: middle; color: var(--muted); margin: 0 4px; }

.inv-change { font-weight: 700; font-variant-numeric: tabular-nums; white-space: nowrap; }
.inv-change.is-up { color: var(--ok); }
.inv-change.is-down { color: var(--warn); }
.inv-change .inv-unit { font-weight: 500; }

/* ---- In-transit queue ---- */
.inv-transit-list { display: flex; flex-direction: column; gap: 8px; }
.inv-transit-row {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto auto;
  align-items: center;
  gap: 16px;
  padding: 12px 14px;
  border: 1px solid var(--pending-border);
  border-left: 3px solid var(--pending);
  border-radius: var(--radius);
  background: var(--pending-bg);
}
.inv-transit-row.is-late { border-color: var(--warn-border); border-left-color: var(--warn); background: var(--warn-bg); }
.inv-transit-main { min-width: 0; }
.inv-transit-route { margin: 4px 0; }
.inv-transit-age { text-align: center; line-height: 1.1; }
.inv-transit-age strong { display: block; font-family: var(--font-display); font-size: 20px; color: var(--pending); }
.inv-transit-row.is-late .inv-transit-age strong { color: var(--warn); }
.inv-transit-age span { font-size: 10.5px; color: var(--muted); text-transform: uppercase; letter-spacing: .04em; }
.inv-transit-actions { display: flex; gap: 8px; }
@media (max-width: 640px) {
  .inv-transit-row { grid-template-columns: 1fr auto; }
  .inv-transit-actions { grid-column: 1 / -1; }
  .inv-transit-actions button { flex: 1; }
}

/* ---- Document modals ---- */
.inv-doc-modal { max-height: 90vh; }
.inv-step { padding: 14px 0 6px; border-top: 1px solid var(--border-light); }
.inv-step:first-of-type { border-top: 0; padding-top: 4px; }
.inv-step-head {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 8px 10px;
  margin-bottom: 12px;
  font-size: 13px;
  font-weight: 700;
  color: var(--ink);
}
.inv-step-num {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 22px;
  height: 22px;
  border-radius: 50%;
  background: var(--navy);
  color: #ffffff;
  font-size: 11.5px;
  font-weight: 700;
  flex-shrink: 0;
}
.inv-step-hint { font-weight: 400; color: var(--muted); font-size: 12px; }

.inv-route {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr) 170px;
  align-items: end;
  gap: 10px;
}
.inv-route select, .inv-route input { margin-bottom: 0; }
.inv-swap-btn { margin-bottom: 4px; }
@media (max-width: 640px) {
  .inv-route { grid-template-columns: 1fr; }
  .inv-swap-btn { justify-self: center; transform: rotate(90deg); }
}

.inv-mode { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; margin-top: 14px; }
@media (max-width: 560px) { .inv-mode { grid-template-columns: 1fr; } }
.inv-mode-opt {
  display: flex;
  gap: 10px;
  align-items: flex-start;
  margin: 0;
  padding: 10px 12px;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  cursor: pointer;
  text-transform: none;
  letter-spacing: normal;
  font-weight: 400;
  font-size: 13px;
  color: var(--ink);
}
.inv-mode-opt input { width: auto; margin: 3px 0 0; accent-color: var(--brand); }
.inv-mode-opt strong { display: block; font-size: 13px; }
.inv-mode-opt small { display: block; color: var(--muted); font-size: 12px; line-height: 1.4; margin-top: 2px; }
.inv-mode-opt.is-selected { border-color: var(--brand); background: var(--brand-tint); }

.inv-lines-table { width: 100%; }
.inv-lines-table th.num, .inv-lines-table td.num { text-align: right; }
.inv-lines-table td { vertical-align: middle; }
.inv-lines-table select, .inv-lines-table input { margin-bottom: 0; }
.inv-qty-input { width: 120px; text-align: right; font-variant-numeric: tabular-nums; }
input.is-invalid, select.is-invalid { border-color: var(--warn); box-shadow: 0 0 0 3px rgba(220, 38, 38, 0.12); }
.inv-add-line { margin-top: 10px; }

.inv-summary {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 6px 10px;
  min-height: 20px;
  margin: 12px 0 4px;
  font-size: 13px;
  color: var(--label);
}
.inv-summary:empty { display: none; }
.inv-summary-route { margin-left: auto; color: var(--muted); font-weight: 600; }
.inv-modal-actions {
  display: flex;
  justify-content: flex-end;
  flex-wrap: wrap;
  gap: 10px;
  margin-top: 14px;
}
.inv-modal-actions:empty { display: none; }

.inv-action-form { margin-top: 16px; padding: 14px 16px; border: 1px solid var(--border); border-radius: var(--radius-lg); background: var(--card-subtle); }

/* ---- View: header + timeline ---- */
.inv-view-head { display: flex; align-items: flex-start; justify-content: space-between; gap: 12px; margin-bottom: 8px; }
.inv-view-ref { margin: 0 0 8px; }
.inv-timeline { list-style: none; margin: 12px 0 16px; padding: 0; }
.inv-tl-step { position: relative; display: flex; gap: 12px; padding: 0 0 14px 2px; font-size: 13px; }
.inv-tl-step:not(:last-child)::after {
  content: '';
  position: absolute;
  left: 7px;
  top: 16px;
  bottom: 0;
  width: 2px;
  background: var(--border);
}
.inv-tl-dot { flex-shrink: 0; width: 12px; height: 12px; margin-top: 3px; border-radius: 50%; border: 2px solid var(--border); background: #ffffff; position: relative; z-index: 1; }
.inv-tl-step.is-done .inv-tl-dot { background: var(--ok); border-color: var(--ok); }
.inv-tl-step.is-wait .inv-tl-dot { border-color: var(--pending); background: var(--pending-bg); }
.inv-tl-step.is-void .inv-tl-dot { background: var(--warn); border-color: var(--warn); }
.inv-tl-note { margin-top: 4px; padding: 6px 10px; border-radius: var(--radius-sm); background: var(--bg); color: var(--label); font-size: 12.5px; }

/* ---- Adjustment entry ---- */
.inv-adj-head { display: grid; grid-template-columns: auto minmax(160px, 1fr) 160px minmax(200px, 1fr); gap: 12px; align-items: end; }
.inv-adj-head select, .inv-adj-head input { margin-bottom: 0; }
@media (max-width: 760px) { .inv-adj-head { grid-template-columns: 1fr; } }
.inv-reason-help { margin: 8px 0 0; min-height: 16px; }
.inv-entry-switch { margin-left: auto; }
.inv-adj-tools { display: flex; flex-wrap: wrap; align-items: center; gap: 10px 16px; margin-bottom: 8px; }
.inv-adj-search { flex: 1; min-width: 200px; }
.inv-adj-search input { margin: 0; padding-left: 36px; }
.inv-check {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin: 0;
  font-size: 12.5px;
  font-weight: 500;
  text-transform: none;
  letter-spacing: normal;
  color: var(--label);
}
.inv-check input { width: auto; margin: 0; }
.inv-adj-scroll { max-height: 42vh; overflow-y: auto; border: 1px solid var(--border-light); border-radius: var(--radius); }
.inv-adj-scroll thead th { position: sticky; top: 0; background: var(--card-subtle); z-index: 1; }
.inv-row-entered { background: var(--ok-bg); }
.inv-row-blocked td { color: var(--muted); }
/* ====================================================================
   APPROVALS  (migration_078)
   The CEO's one list. Built entirely from the app's existing surfaces
   (.panel, .badge, .po-total-row, the modal pair) so it reads as part of
   the system rather than as a bolted-on screen -- the only new thing is
   the card, and a card is here because this is the one screen in the app
   where every row is a decision about money leaving the plant rather
   than a record to scan.
   ==================================================================== */

/* Badge tones the rest of the app already ASKS for by name.
   finance-approvals.js and customer-orders.js have been writing
   `badge warn` / `badge bad` / `badge info` since they were written, and
   they have been falling through to the neutral default -- so "Ad-hoc --
   no order", the row a reviewer is most meant to notice, rendered as the
   quietest thing on the screen. Same three colours the existing aliases
   use; no new palette. */
.badge.warn { color: var(--pending); background: var(--pending-bg); }
.badge.bad { color: var(--warn); background: var(--warn-bg); }
.badge.info { color: var(--accent-blue); background: #eff6ff; }

.apr-intro-panel .panel-head-row { align-items: center; }
.apr-count-chip {
  font-size: 12px;
  font-weight: 600;
  padding: 4px 12px;
  border-radius: var(--radius-full);
  color: var(--pending);
  background: var(--pending-bg);
  border: 1px solid var(--pending-border);
  white-space: nowrap;
}

.apr-list { display: grid; gap: 12px; }

.apr-card {
  border: 1px solid var(--border);
  border-left: 3px solid var(--pending);
  border-radius: var(--radius-lg);
  background: var(--card);
  padding: 14px 16px;
  box-shadow: var(--shadow-sm);
}
/* The two questions are told apart by the left edge before a word is
   read: amber for a truck that cannot be filled, red for one that is
   loaded and standing at the barrier. Colour is never the only signal --
   the icon and the type label say the same thing. */
.apr-card-release { border-left-color: var(--warn); }

.apr-card-head { display: flex; align-items: center; gap: 10px; margin-bottom: 12px; }
.apr-card-icon { display: inline-flex; color: var(--muted); }
.apr-card-icon svg { width: 20px; height: 20px; }
.apr-card-title { display: flex; flex-direction: column; line-height: 1.25; min-width: 0; }
.apr-card-title strong { font-size: 15px; }
.apr-card-type { font-size: 12px; color: var(--muted); }
.apr-card-ref { margin-left: auto; font-size: 12px; font-weight: 600; color: var(--muted); white-space: nowrap; }

.apr-card-facts {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
  gap: 10px 18px;
  padding-bottom: 12px;
  border-bottom: 1px solid var(--border-light);
}
.apr-fact { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.apr-fact-k { font-size: 11px; font-weight: 600; text-transform: uppercase; letter-spacing: .04em; color: var(--label); }
.apr-fact-v { font-size: 13.5px; color: var(--ink); overflow-wrap: anywhere; }
/* The amount is what the decision is actually about, so it is the one
   thing on the card allowed to be loud. Tabular figures because these are
   money and they are read down a column. */
.apr-fact-money .apr-fact-v {
  font-size: 18px;
  font-weight: 700;
  color: var(--warn);
  font-variant-numeric: tabular-nums;
}

.apr-moved {
  margin: 10px 0 0;
  padding: 8px 12px;
  border-radius: var(--radius);
  font-size: 12.5px;
  color: var(--accent-blue-dark);
  background: #eff6ff;
  border: 1px solid #bfdbfe;
}

/* THE REASON, as two separate facts (migration 080) rather than one
   clipped sentence. "Why this is held" is the system's own arithmetic --
   quiet, informational. "Why Finance is asking" is a person's judgement
   call, and is the one the reader actually has to weigh, so it gets the
   stronger tone: a left rule and a tint, the same visual language
   .apr-card itself already uses to say "this needs your attention". Old
   rows with neither fact fall back to one plain block, exactly as this
   card has always rendered. */
.apr-reason-block { margin-top: 10px; }
.apr-reason-label {
  display: flex;
  align-items: center;
  gap: 6px;
  font-size: 11px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: .04em;
  color: var(--label);
  margin-bottom: 4px;
}
.apr-reason-label svg { width: 14px; height: 14px; flex: none; }
.apr-reason-block .note { font-size: 13px; color: var(--label); }

.apr-reason-fallback .apr-reason-label { color: var(--muted); }

.apr-reason-system {
  padding: 8px 10px;
  border-radius: var(--radius);
  background: var(--card-subtle);
  border: 1px solid var(--border-light);
}
.apr-reason-system .apr-reason-label { color: var(--muted); }

.apr-reason-ask {
  padding: 10px 12px;
  border-radius: var(--radius);
  border-left: 3px solid var(--brand);
  background: var(--brand-tint);
}
.apr-reason-ask .apr-reason-label { color: var(--brand-dark); }
.apr-reason-ask .note,
.apr-reason-ask .note-body { color: var(--ink); font-weight: 500; }

/* THE CONTRACT, one click away. A quiet row rather than a button among
   buttons: reading whether paperwork exists is a fact to notice before
   deciding, not a decision in itself. */
.apr-docs-row {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-top: 10px;
  padding: 8px 10px;
  border-radius: var(--radius);
  background: var(--card-subtle);
  border: 1px solid var(--border-light);
  font-size: 13px;
  color: var(--label);
}
.apr-docs-icon { width: 16px; height: 16px; flex: none; color: var(--muted); }
.apr-docs-missing { color: var(--warn); font-weight: 600; }
.apr-docs-btn { margin-left: auto; white-space: nowrap; }

.apr-card-actions { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; margin-top: 12px; }

.apr-empty {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 6px;
  padding: 36px 16px;
  text-align: center;
  color: var(--muted);
}
.apr-empty svg { width: 34px; height: 34px; color: var(--ok); margin-bottom: 4px; }
.apr-empty strong { font-size: 14.5px; color: var(--ink); }
.apr-empty span { font-size: 13px; max-width: 46ch; }

.apr-money { margin: 12px 0 4px; }

/* The one honest question, asked once. Two full-width targets rather
   than a dropdown: the choice is consequential, both options have to be
   readable at the same time, and a 44px-tall row is a target somebody can
   hit on a phone in a yard. */
/* Release locked while money is owed (2026-09-24): visibly inactive, not
   merely greyed, so the operator reads it as a state rather than a fault. */
button.tl-btn-locked[disabled] { border-style: dashed; color: var(--warn); opacity: 1; cursor: not-allowed; }
/* What is leaving, on the release form -- shown from the records, never typed. */
.tl-release-summary { border: 1px solid var(--border); border-radius: 8px; padding: 8px 12px; margin-bottom: 12px; background: var(--card-subtle); }

/* No deposit at all, on a card asking the CEO to approve loading: said in red. */
.apr-deposit-none { color: var(--warn); font-weight: 700; }

.apr-scope-options { display: grid; gap: 8px; margin-top: 4px; }
.apr-scope-option {
  display: flex;
  gap: 10px;
  align-items: flex-start;
  padding: 10px 12px;
  margin: 0;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  cursor: pointer;
  text-transform: none;
  letter-spacing: normal;
  font-weight: 400;
  transition: border-color .12s ease, background .12s ease;
}
.apr-scope-option:hover { border-color: var(--navy-light); background: var(--card-subtle); }
.apr-scope-option:has(input:checked) { border-color: var(--brand); background: var(--brand-tint); }
.apr-scope-option:focus-within { outline: 2px solid var(--accent-blue); outline-offset: 2px; }
.apr-scope-option input { width: auto; margin: 3px 0 0; flex: none; }
.apr-scope-body { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.apr-scope-title { font-size: 13.5px; font-weight: 600; color: var(--ink); }
.apr-scope-sub { font-size: 12px; color: var(--muted); }

@media (max-width: 640px) {
  .apr-card-ref { margin-left: 0; width: 100%; }
  .apr-card-head { flex-wrap: wrap; }
  .apr-card-actions button { flex: 1 1 140px; }
}

/* ---------- Signature grace (core.js wireSignatureFields()) ----------
   A signature password field within its session's grace window: the input
   itself is read-only and carries the (invisible) grace token rather than
   a real password, so it must not read as an ordinary editable field. */
.sig-grace-active {
  background: var(--ok-bg);
  border-color: var(--ok);
  cursor: default;
  -webkit-text-security: disc;
}
.sig-grace-note {
  margin-top: 4px;
  font-size: 12px;
  color: var(--ok);
}
.sig-grace-note .btn-link {
  font-size: 12px;
  padding: 0;
  margin-left: 4px;
}

/* ---------- Printed documents (core.js renderPrintDoc()) ----------
   Every Print button in the app produces the same kind of sheet: a
   letterhead, a summary strip, the content, signature lines and a
   footnote. Hidden on screen. On paper the .print-area becomes .pdoc-area,
   panels lose their card chrome, and every table gets one house style. */
.print-only-cell { display: none; }

@media print {
  .print-only-cell { display: table-cell !important; }

  .pdoc-area {
    font-family: "IBM Plex Sans", "Segoe UI", Arial, sans-serif;
    color: #0e1b2e;
    -webkit-print-color-adjust: exact;
    print-color-adjust: exact;
  }

  .pdoc-letterhead {
    display: flex;
    justify-content: space-between;
    align-items: flex-end;
    padding-bottom: 10px;
    border-bottom: 3px solid #0e1b2e;
    position: relative;
  }
  .pdoc-letterhead::after {
    content: "";
    position: absolute;
    left: 0; bottom: -6px;
    width: 90px; height: 3px;
    background: #d92218;
  }
  .pdoc-brand { display: flex; align-items: center; gap: 10px; }
  .pdoc-mark {
    display: inline-flex; align-items: center; justify-content: center;
    width: 38px; height: 38px; border-radius: 8px;
    background: #d92218; color: #fff;
    font-weight: 800; font-size: 16px; letter-spacing: .02em;
  }
  .pdoc-logo { max-height: 40px; max-width: 170px; object-fit: contain; display: block; }
  .pdoc-org { font-size: 15px; font-weight: 800; letter-spacing: .01em; }
  .pdoc-org-sub { font-size: 9.5px; color: #5b6b82; text-transform: uppercase; letter-spacing: .08em; margin-top: 2px; }
  .pdoc-title-block { text-align: right; }
  .pdoc-title { font-size: 22px; font-weight: 800; letter-spacing: -.01em; line-height: 1.1; }
  .pdoc-view { font-size: 10.5px; color: #5b6b82; text-transform: uppercase; letter-spacing: .07em; margin-top: 3px; }

  .pdoc-meta {
    display: grid;
    grid-auto-flow: column;
    grid-auto-columns: 1fr;
    margin-top: 16px;
    border: 1px solid #cfd6e0;
    border-radius: 6px;
    overflow: hidden;
  }
  .pdoc-meta > div { padding: 7px 10px; border-right: 1px solid #cfd6e0; }
  .pdoc-meta > div:last-child { border-right: none; }
  .pdoc-meta span { display: block; font-size: 8.5px; text-transform: uppercase; letter-spacing: .08em; color: #5b6b82; }
  .pdoc-meta strong { display: block; font-size: 12.5px; margin-top: 2px; }

  .pdoc-chips { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 8px; }
  .pdoc-chip {
    display: inline-flex; align-items: baseline; gap: 6px;
    padding: 4px 9px; border-radius: 4px;
    background: #eef1f6; font-size: 10.5px;
  }
  .pdoc-chip strong { font-size: 11px; }
  .pdoc-chip em { font-style: normal; color: #5b6b82; font-size: 9.5px; }

  .pdoc-instruction {
    margin: 10px 0 12px;
    padding: 6px 10px;
    border-left: 3px solid #d92218;
    background: #fdf1f0;
    font-size: 10.5px;
    font-weight: 600;
  }

  /* Report screens print several panels; on paper they are sections of
     one document, not cards floating on a tinted page. */
  .pdoc-area .panel {
    border: none !important;
    box-shadow: none !important;
    background: #fff !important;
    padding: 0 !important;
    margin: 18px 0 0 !important;
    break-inside: avoid-page;
  }
  .pdoc-area .panel h2 {
    font-size: 13px;
    text-transform: uppercase;
    letter-spacing: .06em;
    padding-bottom: 4px;
    border-bottom: 1.5px solid #0e1b2e;
    margin: 0 0 8px;
  }
  .pdoc-area .cards { gap: 8px; margin-top: 14px; }
  .pdoc-area .card { box-shadow: none !important; border: 1px solid #cfd6e0 !important; }
  .pdoc-area .muted { color: #5b6b82; font-size: 9.5px; }

  .pdoc-area colgroup { display: none; }
  .pdoc-area table {
    table-layout: auto;
    width: 100%;
    border-collapse: collapse;
    margin-top: 6px;
    font-size: 10.5px;
  }
  .pdoc-area thead { display: table-header-group; }
  .pdoc-area thead th {
    background: #0e1b2e !important;
    color: #fff !important;
    font-size: 8.5px;
    text-transform: uppercase;
    letter-spacing: .07em;
    padding: 7px 8px;
    border: none;
    text-align: left;
  }
  .pdoc-area tbody td {
    padding: 7px 8px;
    border-bottom: 1px solid #dde3ea;
    vertical-align: middle;
  }
  .pdoc-area tbody tr:nth-child(even) td { background: #f5f7fa; }
  .pdoc-area tbody tr { break-inside: avoid; }
  .pdoc-area tfoot td { font-weight: 800; border-top: 1.5px solid #0e1b2e; padding: 7px 8px; }
  .pdoc-area .badge { border: 1px solid currentColor; background: transparent !important; }

  /* A loading queue: the sequence number is what the dock reads first. */
  .pdoc-area table.pdoc-seq tbody td:first-child {
    font-size: 15px;
    font-weight: 800;
    text-align: center;
    width: 30px;
  }
  #slp-table tbody td:nth-child(3) { font-family: "IBM Plex Mono", Consolas, monospace; font-weight: 700; font-size: 11.5px; }
  #slp-table tbody td:nth-child(5) { font-weight: 700; white-space: nowrap; }

  .pdoc-tick {
    display: inline-block; width: 14px; height: 14px;
    border: 1.5px solid #0e1b2e; border-radius: 2px; vertical-align: middle;
  }
  .pdoc-blank { display: inline-block; width: 52px; border-bottom: 1px solid #0e1b2e; height: 12px; }

  .pdoc-signs {
    display: grid;
    grid-auto-flow: column;
    grid-auto-columns: 1fr;
    gap: 28px;
    margin-top: 42px;
    break-inside: avoid;
  }
  .pdoc-sign-line { border-bottom: 1px solid #0e1b2e; height: 34px; }
  .pdoc-sign-role { font-size: 10px; font-weight: 700; margin-top: 5px; }
  .pdoc-sign-sub { font-size: 8.5px; color: #5b6b82; margin-top: 1px; }
  .pdoc-footnote {
    margin-top: 22px;
    padding-top: 6px;
    border-top: 1px solid #dde3ea;
    font-size: 8px;
    color: #7a879a;
  }
}

/* ---------- Notification popups (notifications.js notifShowPopup()) ----------
   WhatsApp-style cards at the bottom-right: slide in, stay 8s (held while
   hovered), click to open, x to dismiss. Above modals, below nothing. */
.notif-popups {
  position: fixed;
  right: 18px;
  bottom: 18px;
  z-index: 3000;
  display: flex;
  flex-direction: column;
  gap: 10px;
  width: min(360px, calc(100vw - 32px));
  pointer-events: none;
}
.notif-popup {
  pointer-events: auto;
  position: relative;
  display: flex;
  align-items: flex-start;
  gap: 11px;
  width: 100%;
  padding: 12px 34px 12px 12px;
  background: var(--card, #fff);
  color: var(--ink);
  text-align: left;
  border: 1px solid var(--border-light);
  border-left: 4px solid var(--navy-light);
  border-radius: 12px;
  box-shadow: 0 12px 32px rgba(14, 27, 46, .22), 0 2px 6px rgba(14, 27, 46, .12);
  cursor: pointer;
  font: inherit;
  animation: notif-popup-in .28s cubic-bezier(.2, .9, .3, 1.2);
}
.notif-popup:hover { box-shadow: 0 14px 36px rgba(14, 27, 46, .28), 0 2px 6px rgba(14, 27, 46, .14); }
.notif-popup.is-leaving { animation: notif-popup-out .22s ease-in forwards; }
.notif-popup.sev-action { border-left-color: var(--brand); }
.notif-popup.sev-warning { border-left-color: var(--pending); }
.notif-popup.sev-critical { border-left-color: var(--warn); }
.notif-popup.sev-success { border-left-color: var(--ok); }

.notif-popup-icon {
  flex: none;
  display: inline-flex; align-items: center; justify-content: center;
  width: 36px; height: 36px;
  border-radius: 50%;
  background: var(--navy);
  color: #fff;
}
.notif-popup.sev-action .notif-popup-icon { background: var(--brand); }
.notif-popup-icon svg { width: 18px; height: 18px; }
.notif-popup-main { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.notif-popup-top { display: flex; justify-content: space-between; gap: 8px; }
.notif-popup-app { font-size: 10.5px; font-weight: 600; color: var(--muted); text-transform: uppercase; letter-spacing: .04em; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.notif-popup-time { font-size: 10.5px; color: var(--brand); font-weight: 600; flex: none; }
.notif-popup-title { font-size: 13.5px; font-weight: 700; line-height: 1.3; }
.notif-popup-body {
  font-size: 12.5px; color: var(--muted); line-height: 1.4;
  display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden;
}
.notif-popup-close {
  position: absolute; top: 6px; right: 6px;
  width: 24px; height: 24px; padding: 0;
  border: none; border-radius: 6px;
  background: transparent; color: var(--muted); box-shadow: none;
  font-size: 18px; line-height: 1; cursor: pointer;
}
.notif-popup-close:hover { background: var(--bg); color: var(--ink); }
.notif-popup-more {
  justify-content: center;
  padding: 9px 12px;
  font-size: 12.5px; font-weight: 600;
  color: var(--navy-light);
  border-left-width: 1px;
}
.notif-desktop-ask { cursor: default; border-left-color: var(--navy-light); padding-right: 12px; }
.notif-popup-actions { display: flex; gap: 8px; margin-top: 8px; }
.notif-popup-actions button { padding: 6px 12px; font-size: 12px; }

@keyframes notif-popup-in {
  from { opacity: 0; transform: translateX(40px) scale(.96); }
  to { opacity: 1; transform: none; }
}
@keyframes notif-popup-out {
  to { opacity: 0; transform: translateX(40px); }
}
@media (prefers-reduced-motion: reduce) {
  .notif-popup, .notif-popup.is-leaving { animation: none; }
}
@media print { .notif-popups { display: none !important; } }

/* ---------- FG Receipts: shift picker (fg-receipts.js) ----------
   A search box over a clickable table replaced a <select> that had grown
   past 70 flat rows -- every other picker in this app already works this
   way (register + search), this one just hadn't caught up yet. */
.fgr-shift-table-wrap { max-height: 320px; overflow-y: auto; margin-top: 8px; }
.fgr-shift-table { width: 100%; }
.fgr-shift-row { cursor: pointer; }
.fgr-shift-row:hover td { background: var(--card-subtle); }
.fgr-shift-row.is-selected td { background: var(--brand-tint); }
.fgr-shift-more { margin-top: 8px; }
.fgr-shift-chosen {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 12px;
  background: var(--card-subtle);
  border-radius: var(--radius-sm);
}
.fgr-shift-chosen .linklike { margin-left: auto; white-space: nowrap; }

/* ---------- Compact data table (.data-table-compact) ----------
   The professional-ERP-density table: tight rows, fixed column widths from
   a <colgroup> so it never forces a horizontal scrollbar on a normal panel
   width, single bottom-border rows instead of a full grid, and truncated
   (not wrapped) cells so a long batch/reference number can't blow out a
   column. Pilot on FG Receipts' shift picker; the plan is to move other
   registers onto this once it's approved, so change this class rather than
   forking a second one per screen. */
/* Matches the app's existing convention for every other fixed-column table
   (#trips-table, #dips-table, etc. above): below this width the columns
   have no room left to be readable, so .table-responsive scrolls instead
   of squeezing headers down to "D…", "L…", "S…". */
.data-table-compact { table-layout: fixed; min-width: 640px; }
.data-table-compact th, .data-table-compact td {
  border: none;
  border-bottom: 1px solid var(--border);
  padding: 7px 10px;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  font-size: 12.5px;
}
.data-table-compact thead th {
  background: var(--card-subtle);
  border-bottom: 1px solid var(--border);
  position: sticky;
  top: 0;
  z-index: 1;
}
.data-table-compact tbody tr:hover td { background: var(--card-subtle); }
.data-table-compact td.wrap { white-space: normal; }

/* ---------- QC truck inspection queue (receiving-vehicle-qc.js) ---------- */

.qcq-inspect { margin-top: 18px; padding-top: 16px; border-top: 1px solid var(--border); }
.qcq-facts {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(160px, 1fr));
  gap: 10px 18px;
  padding: 12px 14px;
  margin: 8px 0 14px;
  background: var(--bg);
  border-radius: var(--radius);
  font-size: 13px;
}
.qcq-facts .qcq-fact-label { display: block; font-size: 10.5px; font-weight: 700; text-transform: uppercase; letter-spacing: .02em; color: var(--muted); }
.qcq-step { font-size: 14px; margin: 16px 0 6px; }
/* Approving is the go-ahead, so it reads as one -- not the brand red every
   other primary button uses, which would sit beside Reject looking the same. */
button.qcq-approve-btn { background: var(--ok); border-color: var(--ok); }
button.qcq-approve-btn:hover { filter: brightness(0.95); }
button.qcq-approve-btn:disabled { background: #f1f5f9; border-color: var(--border); color: var(--muted); filter: none; }

/* =====================================================================
   Report Center (report-center.html / report-center.js)
   One menu, one viewer for every management report. Built from the
   app's own tokens -- navy for structure, the brand red only for the
   primary action and the current item, colour elsewhere reserved for
   status.
   ===================================================================== */

/* Every control here is a plain control, not the red primary button. */
#tab-reports .rc-cat, #tab-reports .rc-star, #tab-reports .rc-back,
#tab-reports .rc-table th button, #tab-reports .rc-group-toggle {
  background: none; border: 0; box-shadow: none; color: inherit; font: inherit;
  padding: 0; transform: none; border-radius: 0; cursor: pointer;
}

/* ---- Menu ---- */
.rc-home-bar { display: flex; align-items: center; gap: 14px; margin-bottom: 16px; }
.rc-search { position: relative; flex: 1; max-width: 460px; }
.rc-search svg { position: absolute; left: 12px; top: 50%; width: 16px; height: 16px; transform: translateY(-50%); color: var(--muted); pointer-events: none; }
.rc-search input { width: 100%; margin: 0; padding: 10px 12px 10px 36px; border-radius: var(--radius); }
.rc-search-sm { max-width: 260px; }
.rc-search-sm input { padding-top: 7px; padding-bottom: 7px; font-size: 13px; }
.rc-home-count { font-size: 12.5px; color: var(--muted); }

.rc-home-body { display: grid; grid-template-columns: 220px minmax(0, 1fr); gap: 20px; align-items: start; }
.rc-cats {
  position: sticky; top: 76px;
  background: var(--card); border: 1px solid var(--border); border-radius: var(--radius-lg); padding: 8px;
}
.rc-cats-label { padding: 12px 10px 4px; font-size: 10px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: var(--muted); }
#tab-reports .rc-cat {
  display: flex; width: 100%; align-items: center; justify-content: space-between;
  padding: 8px 10px; border-radius: var(--radius); font-size: 13px; font-weight: 500; color: var(--ink); text-align: left;
}
#tab-reports .rc-cat:hover { background: var(--bg); }
#tab-reports .rc-cat.active { background: var(--brand-tint); color: var(--brand-dark); font-weight: 600; box-shadow: inset 3px 0 0 var(--brand); }
.rc-cat-count { font-size: 11px; font-weight: 600; color: var(--muted); background: var(--bg); border-radius: var(--radius-full); padding: 1px 8px; }
.rc-cat.active .rc-cat-count { background: #fff; color: var(--brand-dark); }

.rc-section { background: var(--card); border: 1px solid var(--border); border-radius: var(--radius-lg); margin-bottom: 16px; overflow: hidden; }
.rc-section-head { display: flex; align-items: center; gap: 12px; padding: 14px 18px; border-bottom: 1px solid var(--border-light); background: var(--card-subtle); }
.rc-section-head h3 { margin: 0; font-family: var(--font-display); font-size: 16px; color: var(--ink); }
.rc-section-head p { margin: 2px 0 0; font-size: 12px; color: var(--muted); }
.rc-section-icon { display: grid; place-items: center; width: 34px; height: 34px; border-radius: var(--radius); background: var(--navy); color: #fff; flex-shrink: 0; }
.rc-section-icon svg { width: 18px; height: 18px; }
.rc-cat-sales .rc-section-icon { background: var(--accent-blue); }
.rc-cat-inventory .rc-section-icon { background: var(--navy-light); }
.rc-cat-production .rc-section-icon { background: var(--accent-teal); }
.rc-cat-finance .rc-section-icon { background: #7c3aed; }

.rc-items { display: grid; grid-template-columns: repeat(auto-fill, minmax(320px, 1fr)); }
.rc-item {
  display: flex; align-items: center; gap: 12px; padding: 14px 18px; cursor: pointer;
  border-bottom: 1px solid var(--border-light); border-right: 1px solid var(--border-light);
  transition: background var(--dur-fast) var(--ease-out);
}
.rc-item:hover, .rc-item:focus-visible { background: #f8fafc; outline: none; }
.rc-item:focus-visible { box-shadow: inset 0 0 0 2px var(--brand); }
.rc-item-text { display: flex; flex-direction: column; gap: 3px; min-width: 0; flex: 1; }
.rc-item-title { font-size: 14px; font-weight: 600; color: var(--ink); }
.rc-item:hover .rc-item-title { color: var(--brand-dark); }
.rc-item-desc { font-size: 12.5px; line-height: 1.45; color: var(--muted); }
.rc-item-go { width: 16px; height: 16px; color: var(--border); flex-shrink: 0; }
.rc-item:hover .rc-item-go { color: var(--brand); }
#tab-reports .rc-star { display: grid; place-items: center; width: 26px; height: 26px; border-radius: var(--radius); color: #cbd5e1; flex-shrink: 0; }
#tab-reports .rc-star svg { width: 16px; height: 16px; }
#tab-reports .rc-star:hover { color: #f59e0b; background: var(--pending-bg); }
#tab-reports .rc-star.on { color: #f59e0b; }
#tab-reports .rc-star.on svg { fill: currentColor; }
.rc-empty { padding: 40px 20px; text-align: center; color: var(--muted); background: var(--card); border: 1px dashed var(--border); border-radius: var(--radius-lg); }

/* ---- Viewer header ---- */
.rc-view-head { display: flex; align-items: flex-end; justify-content: space-between; gap: 16px; margin-bottom: 14px; flex-wrap: wrap; }
.rc-view-titles { min-width: 0; }
#tab-reports .rc-back { display: inline-flex; align-items: center; gap: 4px; font-size: 12.5px; font-weight: 600; color: var(--label); margin-bottom: 8px; }
#tab-reports .rc-back:hover { color: var(--brand-dark); }
#tab-reports .rc-back svg { width: 15px; height: 15px; }
.rc-view-crumb { font-size: 10.5px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: var(--brand); }
.rc-view-title { display: flex; align-items: center; gap: 8px; margin: 2px 0 4px; font-family: var(--font-display); font-size: 24px; color: var(--ink); }
.rc-view-desc { margin: 0; font-size: 13px; color: var(--muted); max-width: 760px; }
.rc-view-actions { display: flex; gap: 8px; }
.rc-view-actions button, .rc-view-actions .btn-link { display: inline-flex; align-items: center; gap: 6px; }
.rc-view-actions svg { width: 15px; height: 15px; }
.rc-export { background: var(--navy); color: #fff; border: 1px solid var(--navy); }
.rc-export:hover { background: var(--navy-light); color: #fff; }

/* ---- Filter bar ---- */
.rc-filters {
  display: flex; flex-wrap: wrap; align-items: flex-end; gap: 12px;
  padding: 14px 16px; margin-bottom: 16px;
  background: var(--card); border: 1px solid var(--border); border-radius: var(--radius-lg);
  border-top: 3px solid var(--navy);
}
.rc-field { display: flex; flex-direction: column; min-width: 150px; }
.rc-field label { font-size: 11px; font-weight: 600; letter-spacing: .03em; text-transform: uppercase; color: var(--label); margin-bottom: 4px; }
.rc-field input, .rc-field select { margin: 0; min-width: 150px; }
.rc-field-preset select { min-width: 160px; }
.rc-field-run { margin-left: auto; min-width: 0; }
.rc-field-run button { display: inline-flex; align-items: center; gap: 6px; }
.rc-field-run svg { width: 14px; height: 14px; }
.rc-print-meta { display: none; }

.rc-state { display: flex; align-items: center; gap: 10px; padding: 12px 16px; margin-bottom: 14px; font-size: 13px; color: var(--label); background: var(--card); border: 1px solid var(--border); border-radius: var(--radius); }
.rc-state-error { color: var(--warn); background: var(--warn-bg); border-color: var(--warn-border); }
.rc-spinner { width: 14px; height: 14px; border: 2px solid var(--border); border-top-color: var(--navy); border-radius: 50%; animation: rcSpin .7s linear infinite; }
@keyframes rcSpin { to { transform: rotate(360deg); } }
.rc-dim { opacity: .55; transition: opacity var(--dur-fast); }

/* ---- KPI strip ---- */
.rc-kpis { display: grid; grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); gap: 12px; margin-bottom: 16px; }
.rc-kpi {
  display: flex; flex-direction: column; gap: 4px; padding: 14px 16px;
  background: var(--card); border: 1px solid var(--border); border-radius: var(--radius-lg);
  border-left: 4px solid var(--navy-light);
}
.rc-kpi-label { font-size: 11px; font-weight: 600; letter-spacing: .04em; text-transform: uppercase; color: var(--muted); }
.rc-kpi-value { font-family: var(--font-display); font-size: 24px; font-weight: 700; color: var(--ink); line-height: 1.15; font-variant-numeric: tabular-nums; overflow-wrap: anywhere; }
.rc-kpi-hint { font-size: 12px; color: var(--muted); }
.rc-kpi.tone-ok { border-left-color: var(--ok); }
.rc-kpi.tone-ok .rc-kpi-value { color: var(--ok); }
.rc-kpi.tone-warn { border-left-color: var(--warn); }
.rc-kpi.tone-warn .rc-kpi-value { color: var(--warn); }
.rc-kpi.tone-pending { border-left-color: var(--pending); }
.rc-kpi.tone-pending .rc-kpi-value { color: var(--pending); }

/* ---- Chart ---- */
.rc-chart-panel { padding: 14px 16px 8px; }
.rc-chart-head { display: flex; justify-content: space-between; align-items: center; gap: 12px; margin-bottom: 6px; flex-wrap: wrap; }
.rc-chart-title { font-size: 13px; font-weight: 600; color: var(--ink); }
.rc-chart-legend { display: flex; gap: 14px; font-size: 12px; color: var(--label); }
.rc-legend-item { display: inline-flex; align-items: center; gap: 6px; }
.rc-legend-swatch { display: inline-block; width: 12px; height: 10px; border-radius: 2px; background: var(--accent-blue); }
.rc-legend-swatch.line { height: 3px; background: var(--brand); }
.rc-chart svg { display: block; width: 100%; height: 250px; }
.rc-grid-line { stroke: var(--border-light); stroke-width: 1; }
.rc-axis-line { stroke: var(--border); stroke-width: 1; }
.rc-axis { font-size: 11px; fill: var(--muted); font-family: var(--font-sans); }
.rc-bar.s0 { fill: var(--accent-blue); }
.rc-bar.s1 { fill: var(--accent-teal); }
.rc-bar:hover { fill: var(--navy-light); }
.rc-line { fill: none; stroke: var(--brand); stroke-width: 2; }
.rc-dot { fill: #fff; stroke: var(--brand); stroke-width: 2; }

/* ---- Grid ---- */
.rc-grid-panel { padding: 0; overflow: hidden; }
.rc-grid-bar { display: flex; align-items: center; gap: 12px; padding: 12px 14px; border-bottom: 1px solid var(--border); flex-wrap: wrap; background: var(--card-subtle); }
.rc-inline-label { display: inline-flex; align-items: center; gap: 8px; margin: 0; font-size: 12.5px; font-weight: 600; color: var(--label); white-space: nowrap; }
.rc-inline-label select { margin: 0; padding: 6px 8px; font-size: 13px; min-width: 150px; }
.rc-cols { position: relative; }
.rc-cols > button { display: inline-flex; align-items: center; gap: 6px; padding: 6px 12px; font-size: 13px; }
.rc-cols > button svg { width: 14px; height: 14px; }
.rc-cols-menu {
  position: absolute; top: calc(100% + 6px); left: 0; z-index: 30; width: 250px; max-height: 320px; overflow-y: auto;
  padding: 6px; background: #fff; border: 1px solid var(--border); border-radius: var(--radius); box-shadow: var(--shadow-lg);
}
.rc-col-opt { display: flex; align-items: center; gap: 8px; margin: 0; padding: 6px 8px; font-size: 13px; font-weight: 500; color: var(--ink); border-radius: var(--radius-sm); cursor: pointer; }
.rc-col-opt:hover { background: var(--bg); }
.rc-col-opt input { width: auto; margin: 0; }
.rc-row-count { margin-left: auto; font-size: 12.5px; color: var(--muted); font-variant-numeric: tabular-nums; }

.rc-table-wrap { overflow: auto; max-height: calc(100vh - 220px); }
.rc-table { width: 100%; border-collapse: separate; border-spacing: 0; font-size: 13px; }
.rc-table th, .rc-table td { padding: 8px 12px; border: 0; border-bottom: 1px solid var(--border-light); text-align: left; white-space: nowrap; overflow-wrap: normal; }
.rc-table .num { text-align: right; font-variant-numeric: tabular-nums; }
.rc-table thead th {
  position: sticky; top: 0; z-index: 2;
  background: var(--navy); color: #fff; font-size: 11.5px; font-weight: 600; letter-spacing: .02em;
  border-bottom: 0; padding: 0;
}
#tab-reports .rc-table th button {
  display: flex; align-items: center; gap: 6px; width: 100%; padding: 10px 12px;
  color: #fff; font-weight: 600; text-transform: uppercase; font-size: 11px; letter-spacing: .04em;
}
.rc-table th.num button { justify-content: flex-end; }
#tab-reports .rc-table th button:hover { background: var(--navy-light); }
.rc-sort-ind { font-size: 9px; opacity: .45; }
.rc-table th[aria-sort="ascending"] .rc-sort-ind, .rc-table th[aria-sort="descending"] .rc-sort-ind { opacity: 1; color: #fca5a5; }
.rc-table tbody tr:nth-child(even) td { background: #fbfcfe; }
.rc-table tbody tr:hover td { background: #eef4ff; }
.rc-table td.neg { color: var(--warn); }
.rc-table td.tone-ok.num { color: var(--ok); font-weight: 600; }
.rc-table td.tone-warn.num { color: var(--warn); font-weight: 600; }
.rc-table td.tone-pending.num { color: var(--pending); font-weight: 600; }
.rc-pill { display: inline-block; padding: 2px 8px; border-radius: var(--radius-full); font-size: 11.5px; font-weight: 600; }
.rc-pill.tone-ok { color: var(--ok); background: var(--ok-bg); }
.rc-pill.tone-warn { color: var(--warn); background: var(--warn-bg); }
.rc-pill.tone-pending { color: var(--pending); background: var(--pending-bg); }
.rc-pill.tone-neutral { color: var(--neutral-fg); background: var(--neutral-bg); }
.rc-no-rows { padding: 36px 12px !important; text-align: center !important; color: var(--muted); white-space: normal !important; }

.rc-table tr.rc-group-row td { background: #e8eef6 !important; font-weight: 700; color: var(--ink); border-bottom: 1px solid #d5deea; }
#tab-reports .rc-group-toggle { display: inline-flex; align-items: center; gap: 8px; font-weight: 700; color: var(--ink); }
.rc-caret { display: inline-block; font-size: 11px; color: var(--label); transition: transform var(--dur-fast); }
.rc-group-row.collapsed .rc-caret { transform: rotate(-90deg); }
.rc-group-count { font-size: 11px; font-weight: 600; color: var(--label); background: #fff; border-radius: var(--radius-full); padding: 0 7px; }
.rc-table tr.rc-grouped td:first-child { padding-left: 32px; }

.rc-table tfoot td {
  position: sticky; bottom: 0; z-index: 1;
  background: #eef1f6; font-weight: 700; color: var(--ink);
  border-top: 2px solid var(--navy); border-bottom: 0;
}
.rc-notes { margin: 0; padding: 10px 14px; font-size: 12px; color: var(--muted); border-top: 1px solid var(--border-light); background: var(--card-subtle); }

@media (max-width: 900px) {
  .rc-home-body { grid-template-columns: 1fr; }
  .rc-cats { position: static; display: flex; flex-wrap: wrap; gap: 4px; }
  .rc-cats-label { display: none; }
  #tab-reports .rc-cat { width: auto; gap: 8px; }
  .rc-items { grid-template-columns: 1fr; }
  .rc-field, .rc-field input, .rc-field select { min-width: 0; flex: 1 1 140px; }
  .rc-field-run { margin-left: 0; }
  .rc-table-wrap { max-height: none; }
}

@media print {
  #tab-reports .rc-back, #tab-reports .rc-view-actions, #tab-reports .rc-star,
  #tab-reports .rc-filters, #tab-reports .rc-grid-bar, #tab-reports .rc-state { display: none !important; }
  #tab-reports .rc-print-meta { display: block !important; margin-bottom: 10px; font-size: 11px; color: #334155; }
  #tab-reports .rc-table-wrap { max-height: none; overflow: visible; }
  #tab-reports .rc-table thead th { position: static; background: #0e1b2e !important; -webkit-print-color-adjust: exact; print-color-adjust: exact; }
  #tab-reports .rc-table tfoot td { position: static; }
  #tab-reports .rc-kpi, #tab-reports .panel { break-inside: avoid; }
  #tab-reports .rc-table th, #tab-reports .rc-table td { padding: 5px 8px; font-size: 10.5px; }
}

/* ==========================================================================
   Registers and documents -- ONE design for every list in the app
   ==========================================================================
   A register is a list of documents (renderRegister() in core.js): one row
   per document, drawn exactly like the Report Center's grid -- navy header,
   quiet row rules, right-aligned figures, a hover -- and a click on the row
   opens the document in the shared viewer below. Change a register's look
   here and every register changes with it. */
.reg-table { width: 100%; border-collapse: separate; border-spacing: 0; font-size: 13px; }
.reg-table th, .reg-table td {
  padding: 9px 12px; border: 0; border-bottom: 1px solid var(--border-light);
  text-align: left; vertical-align: middle;
}
.reg-table thead th {
  position: sticky; top: 0; z-index: 2;
  background: var(--navy); color: #fff; font-size: 11px; font-weight: 600;
  letter-spacing: .04em; text-transform: uppercase; white-space: nowrap;
}
.reg-table thead th:first-child { border-top-left-radius: var(--radius-sm); }
.reg-table thead th:last-child { border-top-right-radius: var(--radius-sm); }
.reg-table .num { text-align: right; font-variant-numeric: tabular-nums; white-space: nowrap; }
.reg-table tbody tr:nth-child(even) td { background: #fbfcfe; }
.reg-table tbody tr:hover td { background: #eef4ff; }
.reg-table tr.reg-row { cursor: pointer; }
.reg-table tr.reg-row:focus-visible { outline: 2px solid var(--brand); outline-offset: -2px; }
.reg-table tr.reg-row:hover .reg-no { color: var(--brand-dark); text-decoration: underline; }
.reg-table tfoot td {
  background: #eef1f6; font-weight: 700; color: var(--ink);
  border-top: 2px solid var(--navy); border-bottom: 0;
}
.reg-table .qty-meter { min-width: 150px; }
.reg-no { font-weight: 700; color: var(--ink); font-variant-numeric: tabular-nums; white-space: nowrap; }
.reg-date { font-variant-numeric: tabular-nums; white-space: nowrap; }
.reg-none { color: var(--border); }
.reg-empty { padding: 32px 12px !important; text-align: center !important; color: var(--muted); }
.reg-muted-row td { color: var(--muted); }
.reg-table tr.reg-editing td { background: var(--brand-tint) !important; }
.reg-actions { display: flex; gap: 6px; justify-content: flex-end; flex-wrap: nowrap; }
.reg-actions button { padding: 5px 10px; font-size: 12px; }

.reg-pill {
  display: inline-block; padding: 2px 9px; border-radius: var(--radius-full);
  font-size: 11.5px; font-weight: 600; white-space: nowrap;
}
.reg-pill.tone-ok { color: var(--ok); background: var(--ok-bg); }
.reg-pill.tone-warn { color: var(--warn); background: var(--warn-bg); }
.reg-pill.tone-pending { color: var(--pending); background: var(--pending-bg); }
.reg-pill.tone-neutral { color: var(--neutral-fg); background: var(--neutral-bg); }

/* ---- The document viewer ---- */
.doc-box { max-width: 1120px; padding: 0; }
.doc-bar {
  position: sticky; top: 0; z-index: 5; display: flex; align-items: center; gap: 12px;
  padding: 12px 22px; background: var(--card); border-bottom: 1px solid var(--border-light);
}
.doc-bar-kicker { font-size: 12px; font-weight: 600; color: var(--muted); letter-spacing: .02em; }
.doc-bar-actions { margin-left: auto; display: flex; gap: 8px; align-items: center; flex-wrap: wrap; }
#doc-viewer-actions { display: inline-flex; gap: 8px; }
.doc-bar .btn-link { display: inline-flex; align-items: center; gap: 6px; }
.doc-bar .btn-link svg { width: 15px; height: 15px; }
.doc-sheet { padding: 22px 26px 26px; }

.doc-headline { display: flex; justify-content: space-between; align-items: flex-start; gap: 16px; flex-wrap: wrap; }
.doc-kind { font-size: 10.5px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: var(--brand); }
.doc-number { font-family: var(--font-display); font-size: 26px; font-weight: 700; color: var(--ink); line-height: 1.15; font-variant-numeric: tabular-nums; }
.doc-title { font-size: 15px; color: var(--label); margin-top: 2px; }
.doc-status { display: flex; gap: 6px; flex-wrap: wrap; align-items: center; }
.doc-status .reg-pill { font-size: 12.5px; padding: 4px 12px; }
.doc-stages { margin: 16px 0 4px; }

.doc-facts {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(190px, 1fr));
  gap: 0; margin: 18px 0 6px; border: 1px solid var(--border-light); border-radius: var(--radius);
  background: var(--card-subtle); overflow: hidden;
}
.doc-fact { padding: 10px 14px; border-right: 1px solid var(--border-light); border-bottom: 1px solid var(--border-light); margin: -1px -1px 0 0; }
.doc-fact dt { font-size: 10.5px; font-weight: 700; letter-spacing: .05em; text-transform: uppercase; color: var(--muted); margin-bottom: 3px; }
.doc-fact dd { margin: 0; font-size: 14px; font-weight: 600; color: var(--ink); overflow-wrap: anywhere; }
.doc-fact dd .qty-meter { min-width: 0; }

.doc-section { margin-top: 22px; }
.doc-section h3 { display: flex; align-items: center; gap: 8px; margin: 0 0 10px; font-size: 15px; color: var(--ink); }
.doc-count { font-size: 11px; font-weight: 700; color: var(--label); background: var(--bg); border-radius: var(--radius-full); padding: 1px 8px; }

.doc-note { margin-top: 14px; padding: 10px 14px; border-left: 3px solid var(--border); background: var(--card-subtle); border-radius: 0 var(--radius-sm) var(--radius-sm) 0; font-size: 13px; }
.doc-note-warn { border-left-color: var(--warn); background: var(--warn-bg); }
.doc-note-label { display: block; font-size: 10.5px; font-weight: 700; letter-spacing: .05em; text-transform: uppercase; color: var(--label); margin-bottom: 3px; }

.doc-link-groups { display: grid; grid-template-columns: repeat(auto-fill, minmax(250px, 1fr)); gap: 12px; }
.doc-link-group { display: flex; flex-direction: column; gap: 6px; }
.doc-link-group-label { display: flex; align-items: center; gap: 6px; font-size: 11px; font-weight: 700; letter-spacing: .05em; text-transform: uppercase; color: var(--muted); }
.doc-link {
  display: flex; flex-wrap: wrap; align-items: center; gap: 4px 10px; width: 100%; text-align: left;
  padding: 9px 12px; background: var(--card); color: var(--ink); font-weight: 500;
  border: 1px solid var(--border); border-radius: var(--radius); box-shadow: none;
}
.doc-link:hover { border-color: var(--brand); background: var(--brand-tint); }
.doc-link-no { font-weight: 700; font-variant-numeric: tabular-nums; }
.doc-link-sub { font-size: 12px; color: var(--muted); flex: 1 1 100%; order: 3; }

.doc-meta { font-size: 12.5px; color: var(--muted); margin: 0 0 10px; }
.doc-timeline { list-style: none; margin: 0; padding: 0 0 0 14px; border-left: 2px solid var(--border-light); }
.doc-timeline li { position: relative; padding: 0 0 12px 12px; }
.doc-timeline li::before { content: ""; position: absolute; left: -20px; top: 5px; width: 10px; height: 10px; border-radius: 50%; background: var(--card); border: 2px solid var(--navy-light); }
.doc-tl-head { font-size: 13px; }
.doc-tl-at { color: var(--muted); font-size: 12px; margin-left: 6px; }
.doc-tl-body { font-size: 12.5px; color: var(--label); margin-top: 2px; }
.doc-tl-old { text-decoration: line-through; color: var(--muted); }
.doc-tl-new { font-weight: 600; color: var(--ink); }
.doc-tl-reason { margin-top: 3px; }

@media (max-width: 700px) {
  .doc-bar { padding: 10px 14px; flex-wrap: wrap; }
  .doc-sheet { padding: 16px; }
  .doc-number { font-size: 21px; }
}
@media print {
  .doc-sheet { padding: 0; }
  .reg-table thead th { position: static; -webkit-print-color-adjust: exact; print-color-adjust: exact; }
}

/* The truck plate on a yard row opens the truck's record. A button so it is
   keyboard-reachable; styled to stay the plate it always was. */
.tl-truck-plate.tl-truck-plate-btn { margin: 0; box-shadow: none; color: var(--ink); font: inherit; font-weight: inherit; text-transform: none; letter-spacing: normal; min-height: 0; width: auto; cursor: pointer; }
.tl-truck-plate.tl-truck-plate-btn:hover { background: #ffffff; }
.tl-truck-plate-btn:hover .tl-truck-no { text-decoration: underline; color: var(--brand-dark); }
.tl-truck-plate-btn:focus-visible { outline: 2px solid var(--brand); outline-offset: 2px; border-radius: var(--radius-sm); }
/* A row a tagDocRows() register can open. */
.reg-table tr[data-doc-type] { cursor: pointer; }

/* Report Center drill-down: a row that has records behind it. */
.rc-table tbody tr.rc-drill { cursor: pointer; }
.rc-table tbody tr.rc-drill:hover td { background: #e3edff; }
.rc-table tbody tr.rc-drill:focus-visible { outline: 2px solid var(--brand); outline-offset: -2px; }
.rc-drill-title { font-size: 21px; }
.rc-tone-warn { color: var(--warn); font-weight: 600; }
.rc-tone-pending { color: var(--pending); font-weight: 600; }
.rc-tone-ok { color: var(--ok); font-weight: 600; }
#doc-viewer-actions .btn-link { display: inline-flex; align-items: center; text-decoration: none; }

/* ---- Edit user popup (admin.js openUserEditModal) ----
   Profile and password are separate sections because they are separate
   decisions: a password reset signs the person out everywhere and costs the
   admin their own password, so it is opted into, never a side effect. */
.ue-modal { max-width: 620px; padding: 0; overflow-x: hidden; }
.ue-head {
  display: flex; align-items: center; gap: 14px;
  padding: 18px 20px; border-bottom: 1px solid var(--border-light);
  position: sticky; top: 0; background: var(--card); z-index: 1;
}
.ue-avatar {
  flex: 0 0 44px; height: 44px; border-radius: var(--radius-full);
  background: var(--navy); color: #fff; font-weight: 700; font-size: 15px;
  display: flex; align-items: center; justify-content: center; letter-spacing: .02em;
}
.ue-head-text { flex: 1; min-width: 0; }
.ue-head-text h2 { margin: 0 0 4px; font-size: 18px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.ue-head-meta { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; }
.ue-head-meta .badge { font-size: 10.5px; }
#ue-form { padding: 4px 20px 0; }
.ue-section { padding: 16px 0; border-bottom: 1px solid var(--border-light); }
.ue-section-row { display: flex; align-items: baseline; justify-content: space-between; gap: 10px; }
.ue-section-title {
  margin: 0 0 12px; font-size: 13px; font-weight: 700; color: var(--ink);
  text-transform: none; letter-spacing: 0;
}
.ue-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 12px 14px; }
.ue-grid label { margin: 0; }
.ue-grid input, .ue-grid select, .ue-signature input { margin-top: 6px; width: 100%; }
.ue-span-2 { grid-column: 1 / -1; }
.ue-hint {
  display: block; margin-top: 5px; font-size: 12px; font-weight: 400;
  color: var(--muted); text-transform: none; letter-spacing: normal;
}
.ue-section-row .ue-hint { margin-top: 0; }

.ue-switch {
  display: inline-flex; align-items: center; gap: 10px; cursor: pointer; margin: 0;
  font-size: 13.5px; font-weight: 600; color: var(--ink); text-transform: none; letter-spacing: normal;
}
.ue-switch input { position: absolute; opacity: 0; width: 1px; height: 1px; }
.ue-switch-track {
  position: relative; flex: 0 0 38px; height: 22px; border-radius: var(--radius-full);
  background: #cbd5e1; transition: background .15s ease;
}
.ue-switch-track::after {
  content: ''; position: absolute; top: 3px; left: 3px; width: 16px; height: 16px;
  border-radius: 50%; background: #fff; box-shadow: var(--shadow-sm); transition: transform .15s ease;
}
.ue-switch input:checked + .ue-switch-track { background: var(--brand); }
.ue-switch input:checked + .ue-switch-track::after { transform: translateX(16px); }
.ue-switch input:focus-visible + .ue-switch-track { outline: 2px solid var(--brand); outline-offset: 2px; }

.ue-pw-panel { margin-top: 14px; }
.ue-pw-field { position: relative; display: block; }
.ue-pw-field input { padding-right: 42px; font-family: ui-monospace, SFMono-Regular, Consolas, monospace; letter-spacing: .02em; }
.ue-pw-eye {
  position: absolute; right: 4px; top: calc(50% + 3px); transform: translateY(-50%);
  width: 32px; height: 30px; padding: 5px; display: flex; align-items: center; justify-content: center;
  background: transparent; border: none; box-shadow: none; color: var(--muted);
}
.ue-pw-eye:hover { background: var(--neutral-bg); color: var(--ink); box-shadow: none; }
.ue-pw-eye:active { transform: translateY(-50%); }
.ue-pw-eye svg { width: 18px; height: 18px; }
.ue-pw-tools { display: flex; gap: 8px; flex-wrap: wrap; }
.ue-small-btn { padding: 6px 12px; font-size: 12.5px; }

.ue-meter { height: 6px; border-radius: var(--radius-full); background: var(--neutral-bg); overflow: hidden; }
.ue-meter span { display: block; height: 100%; width: 0; border-radius: inherit; transition: width .2s ease, background .2s ease; }
.ue-meter span.tone-weak { background: var(--warn); }
.ue-meter span.tone-fair { background: var(--pending); }
.ue-meter span.tone-good { background: var(--accent-teal); }
.ue-meter span.tone-strong { background: var(--ok); }
.ue-meter-label { margin-top: 5px; font-size: 12px; color: var(--muted); }

.ue-checklist { list-style: none; margin: 12px 0 0; padding: 0; display: grid; grid-template-columns: 1fr 1fr; gap: 4px 14px; }
.ue-checklist li { display: flex; gap: 7px; font-size: 12.5px; color: var(--muted); }
.ue-checklist li.ok { color: var(--ok); }
.ue-tick { flex: 0 0 12px; font-weight: 700; text-align: center; }

.ue-callout {
  margin-top: 14px; padding: 10px 12px; border-radius: var(--radius);
  background: var(--pending-bg); border: 1px solid var(--pending-border);
  font-size: 12.5px; color: #92400e; line-height: 1.45;
}
.ue-signature { margin: 14px 0 0; }

.ue-error {
  margin: 14px 0 0; padding: 10px 12px; border-radius: var(--radius);
  background: var(--warn-bg); border: 1px solid var(--warn-border); color: var(--warn); font-size: 13px;
}
.ue-foot {
  display: flex; align-items: center; justify-content: space-between; gap: 12px;
  padding: 14px 0 18px; position: sticky; bottom: 0; background: var(--card);
}
.ue-foot .ue-hint { margin: 0; }
.ue-foot-btns { display: flex; gap: 8px; }

@media (max-width: 560px) {
  .ue-grid, .ue-checklist { grid-template-columns: 1fr; }
  .ue-foot { flex-direction: column-reverse; align-items: stretch; }
  .ue-foot-btns button { flex: 1; }
}

/* ---- Dashboard: one period, work queue, money row (2026-09-27) ---- */
.dash-hero-row { display: flex; align-items: flex-end; justify-content: space-between; gap: 12px 20px; flex-wrap: wrap; }
.dash-period { margin: 0; }
.dash-row-title {
  margin: 4px 0 10px; font-size: 12px; font-weight: 700; text-transform: uppercase;
  letter-spacing: .05em; color: var(--label);
}
.dash-row-note { margin-left: 8px; font-weight: 400; text-transform: none; letter-spacing: normal; color: var(--muted); font-size: 12px; }
#dash-money-cards { grid-template-columns: repeat(4, minmax(0, 1fr)); }
@media (max-width: 1100px) { #dash-money-cards { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
@media (max-width: 560px) { #dash-money-cards { grid-template-columns: 1fr; } }
.card .card-body .num { overflow-wrap: anywhere; }

.dash-work { margin-bottom: 20px; }
.dash-work-row {
  display: grid; grid-template-columns: 44px minmax(0, 1fr) auto 16px; align-items: center; gap: 12px;
  width: 100%; padding: 10px 12px; margin: 0; text-align: left;
  background: transparent; color: var(--ink); border: none; border-top: 1px solid var(--border-light);
  border-radius: 0; box-shadow: none; font-weight: 400;
}
.dash-work-row:first-child { border-top: none; }
.dash-work-row:hover, .dash-work-row:focus-visible { background: var(--card-subtle); box-shadow: none; }
.dash-work-row:active { transform: none; }
.dash-work-count {
  min-width: 36px; height: 30px; padding: 0 8px; border-radius: var(--radius);
  display: inline-flex; align-items: center; justify-content: center;
  font-family: var(--font-mono); font-weight: 700; font-size: 15px;
  background: var(--neutral-bg); color: var(--neutral-fg);
}
.dash-work-count.is-stale { background: var(--pending-bg); color: #92400e; }
.dash-work-text { display: flex; flex-direction: column; min-width: 0; }
.dash-work-label { font-weight: 600; font-size: 13.5px; }
.dash-work-action { font-size: 12px; color: var(--muted); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.dash-work-age { font-size: 12px; color: var(--muted); white-space: nowrap; }
.dash-work-age.is-stale { color: var(--pending); font-weight: 600; }
.dash-work-go { color: var(--muted); font-size: 20px; line-height: 1; }
.dash-work-clear { padding: 10px 12px; color: var(--ok); font-weight: 600; font-size: 13px; }
@media (max-width: 640px) {
  .dash-work-row { grid-template-columns: 40px minmax(0, 1fr) 14px; }
  .dash-work-age { grid-column: 2; grid-row: 2; }
  .dash-work-action { white-space: normal; }
}

/* A breakdown bar that opens the records behind it. */
.report-bar-row.dash-bar-open {
  width: 100%; margin: 0; padding: 5px 6px; border: none; border-radius: var(--radius);
  background: transparent; color: inherit; box-shadow: none; font-weight: 400; text-align: left;
}
.report-bar-row.dash-bar-open:hover, .report-bar-row.dash-bar-open:focus-visible { background: var(--card-subtle); box-shadow: none; }
.report-bar-row.dash-bar-open:hover .report-bar-label { color: var(--brand-dark); text-decoration: underline; }
.report-bar-row.dash-bar-open:active { transform: none; }
/* The dashboard's bars carry a second line (each line's own unit count), so
   their value column is wider and that line may wrap -- never push the page
   sideways. */
#chart-dispatch-by-sku .report-bar-label, #chart-production-by-line .report-bar-label { width: 120px; }
#chart-dispatch-by-sku .report-bar-value, #chart-production-by-line .report-bar-value { width: 150px; text-align: right; color: var(--ink); }
#chart-dispatch-by-sku .report-bar-value .cell-sub, #chart-production-by-line .report-bar-value .cell-sub {
  display: block; white-space: normal; font-family: var(--font-sans, inherit); font-weight: 400; font-size: 11.5px; color: var(--muted);
}
.chart-headline .chart-headline-extra { font-size: 12px; color: var(--muted); }
@media (max-width: 640px) {
  #chart-dispatch-by-sku .report-bar-label, #chart-production-by-line .report-bar-label { width: 90px; }
}

/* The brand is a link home (index.html #brand-home). Its text keeps the
   rail's own rule that hides it when the sidebar is icons only. */
a.brand { text-decoration: none; color: inherit; cursor: pointer; transition: background .15s ease; }
a.brand:hover { background: rgba(255, 255, 255, 0.04); }
a.brand:hover .brand-mark { background: var(--brand-dark); }
a.brand:focus-visible { outline: 2px solid #fff; outline-offset: -3px; }

/* ---- View-only pages (core.js applyPageAccessMode, migration 091) ----
   Reached through a view-level grant only: everything that would change
   something is hidden, the reason is stated, and the server refuses any
   change regardless. Filter forms opt back in with data-readonly-ok. */
.tab-panel.is-viewonly form:not([data-readonly-ok]),
.tab-panel.is-viewonly .row-actions,
.tab-panel.is-viewonly [data-write],
.tab-panel.is-viewonly .side-quick { display: none !important; }
.viewonly-banner {
  display: flex; align-items: baseline; gap: 10px; flex-wrap: wrap;
  margin: 0 0 16px; padding: 10px 14px; border-radius: var(--radius);
  background: #eff6ff; border: 1px solid #bfdbfe; color: #1e3a8a; font-size: 13px;
}
.viewonly-banner strong {
  font-size: 11px; text-transform: uppercase; letter-spacing: .06em;
  padding: 2px 8px; border-radius: var(--radius-full); background: #dbeafe;
}

/* ---- Access panel (admin.js, per-user permission levels) ---- */
.ap-modal { max-width: 860px; padding: 0; display: flex; flex-direction: column; max-height: 88vh; overflow: hidden; }
.ap-head { display: flex; align-items: center; gap: 14px; padding: 18px 20px; border-bottom: 1px solid var(--border-light); }
.ap-head-text { flex: 1; min-width: 0; }
.ap-head-text h2 { margin: 0 0 6px; font-size: 18px; }
.ap-roles { display: flex; flex-wrap: wrap; gap: 6px; }
.ap-intro { padding: 12px 20px 0; }
.ap-intro p { margin: 0 0 10px; font-size: 12.5px; color: var(--muted); line-height: 1.5; }
.ap-summary { display: flex; flex-wrap: wrap; gap: 6px; }
.ap-chip { font-size: 11.5px; font-weight: 600; padding: 3px 10px; border-radius: var(--radius-full); border: 1px solid transparent; }
.ap-chip.tone-write { background: var(--ok-bg); color: var(--ok); border-color: var(--ok-border); }
.ap-chip.tone-read { background: #eff6ff; color: #1d4ed8; border-color: #bfdbfe; }
.ap-chip.tone-blocked { background: var(--warn-bg); color: var(--warn); border-color: var(--warn-border); }
.ap-body { flex: 1; min-height: 0; overflow-y: auto; overflow-x: hidden; }
.ap-toolbar {
  display: flex; gap: 8px; flex-wrap: wrap; align-items: center; padding: 12px 20px;
  border-bottom: 1px solid var(--border-light); position: sticky; top: 0; z-index: 1; background: var(--card);
}
.ap-toolbar input[type=search] { flex: 1 1 220px; width: auto; margin: 0; }
.ap-groups { padding: 4px 20px 12px; }
.ap-group { margin-top: 14px; }
.ap-group-title { margin: 0 0 4px; font-size: 11px; font-weight: 700; text-transform: uppercase; letter-spacing: .05em; color: var(--label); }
.ap-row { display: flex; align-items: center; justify-content: space-between; gap: 14px; padding: 8px 10px; border-radius: var(--radius); border-left: 3px solid transparent; }
.ap-row:hover { background: var(--card-subtle); }
.ap-row.is-changed { border-left-color: var(--pending); background: var(--pending-bg); }
.ap-row-text { display: flex; flex-direction: column; flex: 1; min-width: 0; }
.ap-row-label { font-size: 13px; color: var(--ink); }
.ap-row-meta { font-size: 11px; color: var(--muted); }
.ap-seg { display: inline-flex; flex-shrink: 0; border: 1px solid var(--border); border-radius: var(--radius); overflow: hidden; background: #fff; }
.ap-seg-btn {
  padding: 5px 11px; font-size: 12px; font-weight: 600; border: none; border-radius: 0;
  background: #fff; color: var(--muted); box-shadow: none; border-left: 1px solid var(--border);
}
.ap-seg-btn:first-child { border-left: none; }
.ap-seg-btn:hover { background: var(--card-subtle); color: var(--ink); box-shadow: none; }
.ap-seg-btn:active { transform: none; }
.ap-seg-btn.is-on.seg-none { background: var(--neutral-bg); color: var(--neutral-fg); }
.ap-seg-btn.is-on.seg-read { background: #2563eb; color: #fff; }
.ap-seg-btn.is-on.seg-write, .ap-seg-btn.is-on.seg-role { background: var(--ok); color: #fff; }
.ap-seg-btn.is-on.seg-blocked { background: var(--warn); color: #fff; }
.ap-foot { display: flex; align-items: center; justify-content: space-between; gap: 12px; padding: 14px 20px; border-top: 1px solid var(--border-light); background: var(--card); }
@media (max-width: 760px) {
  .ap-row { flex-direction: column; align-items: stretch; }
  .ap-seg { align-self: flex-start; }
  .ap-foot { flex-direction: column-reverse; align-items: stretch; }
}
.ap-row.is-fixed { opacity: .75; }
.ap-fixed { flex-shrink: 0; font-size: 11.5px; font-weight: 600; color: var(--muted); padding: 4px 10px; border: 1px dashed var(--border); border-radius: var(--radius); }
.lu-head-actions { display: flex; align-items: center; gap: 10px; }

/* ---- Master data (master-data.js, migration 092) ----
   The record form, retire dialog and version history reuse the Edit-user
   popup's .ue-* layout, so every admin record form reads the same. */
body.not-admin .admin-only { display: none !important; }
body:not(.not-admin) .non-admin-only { display: none !important; }

.md-add-box { display: flex; justify-content: flex-start; }
.md-new-btn { display: inline-flex; align-items: center; gap: 6px; }
.md-new-btn svg { width: 16px; height: 16px; }
.md-code {
  font-family: ui-monospace, SFMono-Regular, Consolas, monospace; font-size: 12px; font-weight: 600;
  color: var(--navy-light); background: var(--neutral-bg); border-radius: var(--radius-sm);
  padding: 1px 6px; white-space: nowrap;
}
.md-sub { font-size: 12px; color: var(--muted); margin-top: 2px; }
.md-table td { vertical-align: middle; }
.md-actions { white-space: nowrap; text-align: right; }
.md-actions button { padding: 5px 10px; font-size: 12.5px; margin-left: 4px; }
.md-row-inactive td { color: var(--muted); }
.md-row-inactive .md-code { opacity: .7; }
.md-req { color: var(--brand); }

.md-modal { max-width: 720px; max-height: calc(100vh - 48px); overflow-y: auto; }
#md-form, #md-retire-form { padding: 4px 20px 0; }
.md-modal textarea, .md-retire-modal textarea { width: 100%; margin-top: 6px; resize: vertical; }
.md-reason-section { background: var(--pending-bg); margin: 12px -20px 0; padding: 14px 20px; border-top: 1px solid var(--pending-border); border-bottom: 1px solid var(--pending-border); }
.md-reason-section .ue-section-title { margin-bottom: 6px; }
.md-retire-modal { max-width: 520px; }
button.danger { background: var(--warn); border-color: var(--warn); }
button.danger:hover { background: #b91c1c; }

.lu-intro { display: flex; align-items: center; justify-content: space-between; gap: 12px; flex-wrap: wrap; }
.md-feed-btn { white-space: nowrap; }
.md-outside-banner {
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap;
  margin: 0 0 14px; padding: 10px 14px; border-radius: var(--radius);
  background: var(--warn-bg); border: 1px solid var(--warn-border); color: #7f1d1d; font-size: 13.5px;
}
.md-outside-banner.hidden { display: none; }
.md-outside-banner button { margin-left: auto; padding: 5px 12px; font-size: 12.5px; }

.mdh-modal { max-width: 760px; max-height: calc(100vh - 48px); display: flex; flex-direction: column; }
.mdh-toolbar { padding: 10px 20px; border-bottom: 1px solid var(--border-light); }
.mdh-toolbar.hidden { display: none; }
.mdh-body { padding: 8px 20px 20px; overflow-y: auto; }
.mdh-item { display: flex; gap: 12px; padding: 14px 0; border-bottom: 1px solid var(--border-light); }
.mdh-item:last-child { border-bottom: none; }
.mdh-outside { background: linear-gradient(90deg, var(--warn-bg), transparent 60%); margin: 0 -20px; padding-left: 20px; padding-right: 20px; }
.mdh-dot { flex: 0 0 10px; height: 10px; margin-top: 5px; border-radius: 50%; background: var(--accent-blue); }
.mdh-created { background: var(--ok); }
.mdh-deactivated, .mdh-deleted { background: var(--warn); }
.mdh-reactivated { background: var(--accent-teal); }
.mdh-main { flex: 1; min-width: 0; }
.mdh-subject { font-size: 12px; color: var(--muted); margin-bottom: 2px; }
.mdh-line { font-size: 13.5px; color: var(--ink); }
.mdh-line .badge { font-size: 10.5px; }
.mdh-ver { font-family: ui-monospace, SFMono-Regular, Consolas, monospace; font-size: 11.5px; color: var(--muted); }
.mdh-reason { margin-top: 6px; font-size: 13px; color: var(--label); font-style: italic; }
.mdh-diff { width: 100%; margin-top: 8px; border-collapse: collapse; font-size: 12.5px; }
.mdh-diff th { text-align: left; font-weight: 600; color: var(--muted); padding: 4px 8px; border-bottom: 1px solid var(--border); }
.mdh-diff td { padding: 5px 8px; border-bottom: 1px solid var(--border-light); vertical-align: top; overflow-wrap: anywhere; }
.mdh-old { color: var(--warn); text-decoration: line-through; text-decoration-color: rgba(220, 38, 38, .4); }
.mdh-new { color: var(--ok); font-weight: 600; }
.mdh-dl { display: grid; grid-template-columns: minmax(120px, max-content) 1fr; gap: 3px 12px; margin: 8px 0 0; font-size: 12.5px; }
.mdh-dl dt { color: var(--muted); }
.mdh-dl dd { margin: 0; overflow-wrap: anywhere; }

@media (max-width: 640px) {
  .md-modal .ue-grid { grid-template-columns: 1fr; }
  .md-actions { white-space: normal; text-align: left; }
  .md-actions button { margin: 2px 4px 2px 0; }
  .mdh-dl { grid-template-columns: 1fr; }
}

/* ---- Closed periods (finance-accounts.js, migration 093) ---- */
.pl-panel { margin-bottom: 16px; border-left: 4px solid var(--border); }
.pl-panel.pl-is-closed { border-left-color: var(--ok); }
.pl-head { display: flex; align-items: center; justify-content: space-between; gap: 14px; flex-wrap: wrap; }
.pl-state { display: flex; align-items: center; gap: 12px; min-width: 0; }
.pl-lock-icon {
  flex: 0 0 38px; height: 38px; border-radius: var(--radius-full); display: flex; align-items: center; justify-content: center;
  background: var(--neutral-bg); color: var(--muted);
}
.pl-is-closed .pl-lock-icon { background: var(--ok-bg); color: var(--ok); }
.pl-lock-icon svg { width: 18px; height: 18px; }
.pl-label { font-size: 11.5px; font-weight: 700; text-transform: uppercase; letter-spacing: .04em; color: var(--muted); }
.pl-date { font-size: 18px; font-weight: 700; color: var(--ink); }
.pl-actions { display: flex; gap: 8px; flex-wrap: wrap; }
.pl-log { margin-top: 14px; overflow-x: auto; }
.pl-log.hidden { display: none; }
.pl-blockers {
  margin-top: 10px; padding: 10px 12px; border-radius: var(--radius); font-size: 13px;
  background: var(--pending-bg); border: 1px solid var(--pending-border); color: #78350f;
}
.pl-blockers.hidden { display: none; }
.pl-blockers ul { margin: 6px 0 0 18px; padding: 0; }

/* ---- Integrity strip (Admin -> Audit Log, migration 094) ---- */
.integrity-strip { margin: 0 0 14px; padding: 10px 14px; border-radius: var(--radius); font-size: 13.5px; border: 1px solid var(--border); background: var(--neutral-bg); }
.integrity-strip:empty { display: none; }
.integrity-ok { background: var(--ok-bg); border-color: var(--ok-border); color: #065f46; }
.integrity-warn { background: var(--pending-bg); border-color: var(--pending-border); color: #78350f; }
.integrity-bad { background: var(--warn-bg); border-color: var(--warn-border); color: #7f1d1d; }
.integrity-strip ul { margin: 6px 0 0 18px; padding: 0; }

/* Admin -> Security status */
.sec-group { margin-bottom: 14px; }
.sec-group h2 { font-size: 15px; margin: 0 0 8px; }
.sec-list { list-style: none; margin: 0; padding: 0; }
.sec-item { display: flex; gap: 12px; align-items: flex-start; padding: 10px 0; border-top: 1px solid var(--border); }
.sec-item:first-child { border-top: 0; }
.sec-badge { flex: 0 0 26px; height: 26px; border-radius: 50%; display: inline-flex; align-items: center; justify-content: center; font-weight: 700; font-size: 14px; }
.sec-ok .sec-badge { background: var(--ok-bg); color: #065f46; border: 1px solid var(--ok-border); }
.sec-warn .sec-badge { background: var(--pending-bg); color: #78350f; border: 1px solid var(--pending-border); }
.sec-bad .sec-badge { background: var(--warn-bg); color: #7f1d1d; border: 1px solid var(--warn-border); }
.sec-body { min-width: 0; }
.sec-label { font-weight: 600; }
.sec-word { font-weight: 500; font-size: 12px; margin-left: 6px; color: var(--muted, #6b7280); }
.sec-detail { font-size: 13.5px; margin-top: 2px; overflow-wrap: anywhere; }
.sec-prod { font-size: 12.5px; margin-top: 3px; color: var(--muted, #6b7280); }

/* QC lab page: which oil batch each filling line is on (migration 100). */
.ob-current { display: flex; flex-wrap: wrap; gap: 10px; margin: 4px 0 16px; }
.ob-line { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; padding: 10px 14px; border: 1px solid var(--border); border-radius: 10px; min-width: 0; }
.ob-line-name { color: var(--muted); font-size: 12px; font-weight: 600; text-transform: uppercase; letter-spacing: .04em; }

/* Collapsible entry forms (core.js initCollapsibleForms). Collapsed keeps
   only the heading: everything else in the panel -- or, for a form made of
   several panels, everything but the first panel's heading -- is hidden. */
.form-collapse-btn {
  display: inline-flex; align-items: center; gap: 6px;
  margin-left: auto; padding: 5px 12px; font-size: 12px; white-space: nowrap; flex-shrink: 0;
}
.form-collapse-btn svg { width: 14px; height: 14px; transition: transform .2s ease; }
.is-collapsed .form-collapse-btn svg { transform: rotate(180deg); }
[data-collapsible].is-collapsed > :not(.collapse-keep) { display: none !important; }
[data-collapsible].is-collapsed > .collapse-keep:not(.collapse-head) > :not(.collapse-head) { display: none !important; }
[data-collapsible].is-collapsed .panel-section-head.collapse-head { margin-bottom: -20px; border-bottom: 0; }
[data-collapsible].is-collapsed .panel-head-row.collapse-head { margin-bottom: 0; }

/* Filling Line Log, section 3: product & batch / output / losses. */
.prod-sub-title {
  font-size: 11.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase;
  color: var(--muted); margin: 4px 0 10px;
}
.field-hint { font-size: 12px; color: var(--muted); line-height: 1.45; margin-top: -2px; }
.prod-grid-4 { grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); }
.prod-grid-5 { grid-template-columns: repeat(auto-fit, minmax(160px, 1fr)); }
.prod-output {
  margin: 14px 0 20px; padding: 14px 16px 12px;
  border: 1px solid var(--border); border-left: 3px solid var(--brand);
  border-radius: 10px; background: #fafbfc;
}
.prod-output-head { display: flex; align-items: baseline; justify-content: space-between; gap: 12px; flex-wrap: wrap; margin-bottom: 8px; }
.prod-output-head .prod-sub-title { margin: 0; color: #0f172a; }
.prod-output-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 4px 16px; }
.prod-output-grid input[type="number"] { font-size: 18px; font-weight: 700; font-variant-numeric: tabular-nums; }
.prod-output > .field-hint { margin: 2px 0 0; }

/* ===================== Branded documents (doc-templates.js) =====================
   One structure, four looks. --bd-p / --bd-s are the brand colours from
   Admin -> Document templates; --bd-p-ink / --bd-s-ink the readable text
   colour on each. A template only changes how the parts look, never what
   is in them. Sized as an A4 sheet (794px at 96dpi) so the screen, the
   print and the downloaded PDF are the same page. */
.bdoc {
  position: relative; overflow: hidden;
  width: 100%; max-width: 794px; margin: 0 auto;
  background: #fff; color: #1f2937;
  font-size: 12.5px; line-height: 1.45;
  border: 1px solid #e5e7eb; border-radius: 6px;
  -webkit-print-color-adjust: exact; print-color-adjust: exact;
}
.bdoc-head { position: relative; display: flex; justify-content: space-between; align-items: flex-start; gap: 20px; padding: 28px 34px 22px; flex-wrap: wrap; }
.bdoc-brand { display: flex; align-items: center; flex-wrap: wrap; gap: 10px 14px; min-width: 0; position: relative; z-index: 1; }
.bdoc-brand-text { min-width: 0; overflow-wrap: anywhere; }
.bdoc-head > .bdoc-brand { flex: 1 1 0; max-width: 64%; }
.bdoc-head > .bdoc-title-block { flex: 0 0 auto; }
@media (max-width: 640px) { .bdoc-head > .bdoc-brand { max-width: none; } }
.bdoc-logo { max-height: 56px; max-width: min(220px, 100%); object-fit: contain; display: block; }
.bdoc-mark {
  width: 48px; height: 48px; border-radius: 10px; display: inline-flex; align-items: center; justify-content: center;
  background: var(--bd-p); color: var(--bd-p-ink); font-weight: 800; font-size: 17px; letter-spacing: .02em; flex-shrink: 0;
}
.bdoc-co { font-size: 17px; font-weight: 800; color: #111827; letter-spacing: .01em; }
.bdoc-tagline { font-size: 11.5px; color: #6b7280; }
.bdoc-legal { font-size: 11px; color: #6b7280; }
.bdoc-title-block { text-align: right; position: relative; z-index: 1; flex-shrink: 0; }
.bdoc-title { font-size: 24px; font-weight: 800; text-transform: uppercase; letter-spacing: .06em; color: var(--bd-p); line-height: 1.1; }
.bdoc-number { font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace; font-size: 13px; font-weight: 700; margin-top: 4px; color: #111827; }
.bdoc-status { display: inline-block; margin-top: 6px; padding: 2px 9px; border-radius: 999px; font-size: 10.5px; font-weight: 700; text-transform: uppercase; letter-spacing: .05em; background: #f3f4f6; color: #374151; }
.bdoc-status.tone-ok { background: #ecfdf5; color: #047857; }
.bdoc-status.tone-warn { background: #fffbeb; color: #b45309; }
.bdoc-status.tone-blocked { background: #fef2f2; color: #b91c1c; }
.bdoc-body { padding: 4px 34px 22px; position: relative; z-index: 1; }
.bdoc-label, .bdoc-section-title { font-size: 10px; font-weight: 700; text-transform: uppercase; letter-spacing: .08em; color: #6b7280; margin-bottom: 4px; }
.bdoc-section-title { color: var(--bd-s); border-bottom: 1px solid #e5e7eb; padding-bottom: 4px; margin-bottom: 6px; }
.bdoc-meta { display: flex; flex-wrap: wrap; gap: 6px 28px; padding: 10px 0 14px; border-bottom: 1px solid #e5e7eb; margin-bottom: 16px; }
.bdoc-meta .bdoc-kv { display: flex; flex-direction: column; gap: 0; }
.bdoc-meta .bdoc-kv span { font-size: 10px; text-transform: uppercase; letter-spacing: .06em; color: #6b7280; }
.bdoc-kv { display: flex; justify-content: space-between; gap: 12px; padding: 2px 0; }
.bdoc-kv span { color: #6b7280; }
.bdoc-kv strong { color: #111827; font-weight: 600; text-align: right; }
.bdoc-meta .bdoc-kv strong { text-align: left; }
.bdoc-parties { display: grid; grid-template-columns: repeat(auto-fit, minmax(220px, 1fr)); gap: 16px; margin-bottom: 16px; }
.bdoc-party-name { font-size: 15px; font-weight: 700; color: #111827; }
.bdoc-party-line { color: #4b5563; }
/* Tints arrive as plain hex (--bd-p-tint / --bd-p-line, worked out in doc-templates.js):
   the PDF renderer (html2canvas) cannot read color-mix() and refuses the whole page. */
.bdoc-hero { border-radius: 8px; padding: 14px 18px; margin-bottom: 16px; background: var(--bd-p-tint); border: 1px solid var(--bd-p-line); }
.bdoc-hero-top { display: flex; justify-content: space-between; align-items: center; gap: 10px; }
.bdoc-hero-badge { font-size: 10.5px; font-weight: 700; padding: 2px 9px; border-radius: 999px; background: var(--bd-p); color: var(--bd-p-ink); }
.bdoc-hero-amount { font-size: 30px; font-weight: 800; color: #111827; font-variant-numeric: tabular-nums; margin-top: 2px; }
.bdoc-hero-cur { font-size: 15px; font-weight: 700; color: var(--bd-p); }
.bdoc-hero.is-negative .bdoc-hero-amount { color: #b91c1c; }
.bdoc-hero-words { font-style: italic; color: #374151; margin-top: 2px; }
.bdoc-hero-sub { color: #6b7280; font-size: 11.5px; margin-top: 4px; }
.bdoc-table { width: 100%; border-collapse: collapse; margin-bottom: 16px; }
.bdoc-table th { background: var(--bd-s); color: var(--bd-s-ink); font-size: 10.5px; text-transform: uppercase; letter-spacing: .06em; text-align: left; padding: 8px 10px; }
.bdoc-table td { padding: 8px 10px; border-bottom: 1px solid #e5e7eb; vertical-align: top; }
.bdoc-table th, .bdoc-table td { border-left: 0; border-right: 0; }
.bdoc-table .num { text-align: right; font-variant-numeric: tabular-nums; white-space: nowrap; }
.bdoc-table tr { break-inside: avoid; }
.bdoc-sub { font-size: 11px; color: #6b7280; }
.bdoc-bottom { display: grid; grid-template-columns: 1fr minmax(220px, 300px); gap: 24px; align-items: start; margin-bottom: 16px; }
.bdoc-info { display: grid; gap: 12px; }
.bdoc-totals { display: grid; gap: 2px; }
.bdoc-total-row { display: flex; justify-content: space-between; gap: 12px; padding: 5px 0; border-bottom: 1px solid #f3f4f6; font-variant-numeric: tabular-nums; }
.bdoc-total-row span { color: #4b5563; }
.bdoc-total-row strong { white-space: nowrap; }
.bdoc-total-row.is-strong { border-top: 2px solid var(--bd-s); border-bottom: 0; margin-top: 4px; padding-top: 8px; font-size: 15px; }
.bdoc-total-row.is-strong span, .bdoc-total-row.is-strong strong { color: #111827; font-weight: 800; }
.bdoc-note { margin-bottom: 12px; }
.bdoc-note-text { white-space: pre-line; color: #374151; }
.bdoc-alert { border: 1px solid #fecaca; background: #fef2f2; color: #991b1b; border-radius: 6px; padding: 8px 12px; margin-bottom: 14px; font-weight: 600; }
.bdoc-signs { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 28px; margin-top: 30px; align-items: end; }
.bdoc-sign-name { min-height: 18px; font-weight: 600; color: #111827; }
.bdoc-sign-line { border-top: 1px solid #9ca3af; margin-top: 22px; }
.bdoc-stamp { border: 1.5px dashed #9ca3af; border-radius: 50%; width: 110px; height: 110px; justify-self: center; display: flex; align-items: center; justify-content: center; }
.bdoc-stamp span { font-size: 10px; text-transform: uppercase; letter-spacing: .08em; color: #9ca3af; }
.bdoc-table-title { margin-top: 4px; }
.bdoc-table-note { margin: -10px 0 14px; }
.bdoc-party { border-left: 3px solid var(--bd-p); padding-left: 12px; min-width: 0; overflow-wrap: anywhere; }
.bdoc-sign-role { font-size: 10.5px; color: #6b7280; margin-top: 4px; text-transform: uppercase; letter-spacing: .05em; }
.bdoc-foot { padding: 12px 34px 16px; border-top: 1px solid #e5e7eb; text-align: center; font-size: 11px; color: #6b7280; position: relative; z-index: 1; }
.bdoc-foot-text { color: #374151; font-weight: 600; margin-bottom: 3px; }
.bdoc-foot-contact { display: flex; justify-content: center; flex-wrap: wrap; gap: 4px 18px; }
.bdoc-watermark {
  position: absolute; inset: 0; display: flex; align-items: center; justify-content: center; pointer-events: none; z-index: 2;
  font-size: 92px; font-weight: 900; letter-spacing: .08em; color: rgba(185, 28, 28, .12); transform: rotate(-28deg); white-space: nowrap;
}

/* Template: Modern band -- a coloured band across the top, cut on a slant. */
.bdoc-t-band .bdoc-head { padding-bottom: 38px; }
/* Drawn with a hard-stop gradient, not clip-path: the PDF renderer
   (html2canvas) ignores clip-path and would paint the red stripe over the
   whole header. */
.bdoc-t-band .bdoc-head {
  background: linear-gradient(174deg, var(--bd-s) 0%, var(--bd-s) 74%, var(--bd-p) 74%, var(--bd-p) 81%, transparent 81%);
}
.bdoc-t-band .bdoc-co, .bdoc-t-band .bdoc-title, .bdoc-t-band .bdoc-number { color: var(--bd-s-ink); }
.bdoc-t-band .bdoc-tagline, .bdoc-t-band .bdoc-legal { color: var(--bd-s-ink); opacity: .8; }
.bdoc-t-band .bdoc-logo { background: #fff; border-radius: 6px; padding: 4px 6px; }

/* Template: Classic letterhead -- white, a heavy rule under the letterhead. */
.bdoc-t-classic .bdoc-head { border-bottom: 3px solid var(--bd-p); margin: 0 34px; padding-left: 0; padding-right: 0; }
.bdoc-t-classic .bdoc-body { padding-top: 14px; }

/* Template: Corporate -- primary table head, dark contact bar at the foot. */
.bdoc-t-corporate .bdoc-head { border-top: 6px solid var(--bd-p); }
.bdoc-t-corporate .bdoc-table th { background: var(--bd-p); color: var(--bd-p-ink); }
.bdoc-t-corporate .bdoc-foot { background: var(--bd-s); color: var(--bd-s-ink); border-top: 0; }
.bdoc-t-corporate .bdoc-foot-text { color: var(--bd-s-ink); }

/* Template: Minimal -- lines only, no fills. */
.bdoc-t-minimal .bdoc-title { color: #111827; font-weight: 700; }
.bdoc-t-minimal .bdoc-mark { background: transparent; color: var(--bd-p); border: 2px solid var(--bd-p); }
.bdoc-t-minimal .bdoc-table th { background: transparent; color: #111827; border-bottom: 2px solid var(--bd-p); }
.bdoc-t-minimal .bdoc-hero { background: transparent; border: 0; border-left: 3px solid var(--bd-p); border-radius: 0; }

@media (max-width: 640px) {
  .bdoc-head { flex-direction: column; padding: 20px 18px; }
  .bdoc-title-block { text-align: left; }
  .bdoc-body, .bdoc-foot { padding-left: 18px; padding-right: 18px; }
  .bdoc-t-classic .bdoc-head { margin: 0 18px; }
  .bdoc-bottom { grid-template-columns: 1fr; }
  .bdoc-watermark { font-size: 54px; }
}
@media print {
  .bdoc { border: 0; border-radius: 0; max-width: none; }
  .bdoc-table thead { display: table-header-group; }
  .bdoc-signs, .bdoc-bottom { break-inside: avoid; }
}

/* ===================== Admin -> Document templates ===================== */
.tpl-layout { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1.1fr); gap: 18px; align-items: start; }
.tpl-editor .panel { margin-bottom: 14px; }
.tpl-preview-col { position: sticky; top: 12px; }
.tpl-preview { background: #eef0f3; border-radius: 8px; padding: 14px; max-height: 78vh; overflow: auto; }
.tpl-preview.is-full { position: fixed; inset: 0; z-index: 1000; max-height: none; border-radius: 0; padding: 28px; }
.tpl-preview .bdoc { box-shadow: 0 4px 18px rgba(15, 23, 42, .12); }
.tpl-template-cards { display: grid; grid-template-columns: repeat(auto-fit, minmax(130px, 1fr)); gap: 10px; }
.tpl-template-card { position: relative; display: flex; flex-direction: column; gap: 4px; padding: 10px; border: 1.5px solid var(--border); border-radius: 10px; cursor: pointer; text-transform: none; letter-spacing: normal; font-weight: 400; margin: 0; }
.tpl-template-card input { position: absolute; opacity: 0; pointer-events: none; }
.tpl-template-card:has(input:checked) { border-color: var(--brand); box-shadow: 0 0 0 3px var(--brand-tint); }
.tpl-template-card:has(input:focus-visible) { outline: 2px solid var(--brand); outline-offset: 2px; }
.tpl-template-name { font-weight: 700; font-size: 12.5px; color: #0f172a; }
.tpl-template-note { font-size: 11px; color: var(--muted); }
.tpl-template-thumb { position: relative; display: flex; flex-direction: column; gap: 4px; height: 66px; border-radius: 6px; background: #fff; border: 1px solid var(--border); padding: 26px 8px 6px; overflow: hidden; }
.tpl-template-thumb i { position: absolute; left: 0; right: 0; top: 0; height: 18px; }
.tpl-template-thumb b { display: block; height: 5px; border-radius: 2px; background: #e5e7eb; }
.tpl-thumb-band i { background: #1f2937; clip-path: polygon(0 0, 100% 0, 100% 60%, 0 100%); }
.tpl-thumb-classic i { height: 14px; border-bottom: 2px solid var(--brand); background: #fff; }
.tpl-thumb-corporate i { height: 4px; background: var(--brand); }
.tpl-thumb-corporate::after { content: ""; position: absolute; left: 0; right: 0; bottom: 0; height: 10px; background: #1f2937; }
.tpl-thumb-minimal i { height: 14px; border-bottom: 1px solid #9ca3af; background: #fff; }
.tpl-color { display: flex; gap: 8px; align-items: center; }
.tpl-color input[type="color"] { width: 46px; height: 38px; padding: 2px; flex-shrink: 0; margin: 0; }
.tpl-color .tpl-color-hex { font-family: ui-monospace, Menlo, Consolas, monospace; text-transform: uppercase; margin: 0; }
.tpl-warn { color: #b45309; }
.tpl-bank-warn { color: #b45309; margin-bottom: 8px; }
.tpl-logo-row { display: flex; gap: 16px; align-items: flex-start; flex-wrap: wrap; }
.tpl-logo-current { width: 220px; min-height: 76px; border: 1px dashed var(--border); border-radius: 8px; display: flex; align-items: center; justify-content: center; padding: 8px; background: #fafbfc; }
.tpl-logo-current img { max-width: 100%; max-height: 64px; object-fit: contain; }
.tpl-logo-actions { flex: 1; min-width: 220px; display: grid; gap: 8px; }
@media (max-width: 1100px) {
  .tpl-layout { grid-template-columns: 1fr; }
  .tpl-preview-col { position: static; }
}

/* Document viewer records on the branded sheet (core.js documentViewerSheetHtml). */
.bdoc-subtitle { font-size: 12px; margin-top: 3px; opacity: .85; }
.bdoc-t-band .bdoc-subtitle { color: var(--bd-s-ink); }
.bdoc-badges { display: flex; flex-wrap: wrap; gap: 6px; margin: 4px 0 12px; }
.bdoc .doc-stages { margin: 4px 0 14px; }
.bdoc-facts { display: grid; grid-template-columns: repeat(auto-fit, minmax(170px, 1fr)); gap: 0; margin: 4px 0 18px; border: 1px solid #e5e7eb; border-radius: 6px; overflow: hidden; }
.bdoc-fact { padding: 9px 12px; border-right: 1px solid #f1f2f4; border-bottom: 1px solid #f1f2f4; min-width: 0; }
.bdoc-fact dt { font-size: 10px; font-weight: 700; text-transform: uppercase; letter-spacing: .07em; color: #6b7280; margin: 0 0 2px; }
.bdoc-fact dd { margin: 0; font-weight: 600; color: #111827; overflow-wrap: anywhere; }
.bdoc-table tfoot td { font-weight: 800; border-top: 2px solid var(--bd-s); border-bottom: 0; }
.bdoc-note-warn { border-left: 3px solid #d97706; padding-left: 10px; }
/* A note prints whole: the on-screen two-line clamp and its More button are for registers. */
.bdoc .note-body { display: block; -webkit-line-clamp: unset; max-height: none; overflow: visible; white-space: pre-line; }
.bdoc .note-toggle { display: none; }
.bdoc .note { max-width: none; }

/* ---- Searchable dropdowns (combobox.js) ----
   One panel serves every item datalist and every long select. The native
   select stays inside .cbx-select, invisible, so the form still submits and
   validates it; .cbx-trigger is what people see and click. */
.cbx-select { position: relative; display: block; width: 100%; min-width: 0; }
.cbx-select > select.cbx-native {
  position: absolute; inset: 0; width: 100%; height: 100%; margin: 0;
  opacity: 0; pointer-events: none;
}
.cbx-trigger {
  width: 100%; display: flex; align-items: center; gap: 8px;
  padding: 9px 10px 9px 12px; margin: 0;
  background: #ffffff; color: var(--ink);
  border: 1px solid var(--border); border-radius: var(--radius);
  font: inherit; font-size: 13.5px; font-weight: 400; line-height: 1.35; text-align: left;
  box-shadow: none; transition: border-color 0.15s ease, box-shadow 0.15s ease;
}
.cbx-trigger:hover:not(:disabled) { border-color: #cbd5e1; background: #ffffff; }
.cbx-trigger:focus-visible, .cbx-trigger[aria-expanded="true"] {
  outline: none; border-color: var(--brand); box-shadow: 0 0 0 3px rgba(217, 34, 24, 0.12);
}
.cbx-trigger:disabled { background: var(--card-subtle); color: var(--muted); cursor: not-allowed; }
.cbx-trigger.is-empty .cbx-value { color: var(--muted); }
.cbx-value { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cbx-chev { width: 16px; height: 16px; flex-shrink: 0; fill: none; stroke: var(--muted); stroke-width: 1.8; stroke-linecap: round; stroke-linejoin: round; transition: transform var(--dur-fast) var(--ease-out); }
.cbx-trigger[aria-expanded="true"] .cbx-chev { transform: rotate(180deg); stroke: var(--brand); }
.cbx-select:has(select.is-invalid) .cbx-trigger { border-color: var(--warn); box-shadow: 0 0 0 3px rgba(220, 38, 38, 0.12); }

/* Item-name inputs keep typing; the chevron says there's a list. */
input.cbx-input {
  padding-right: 32px;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'%3E%3Cpath d='M6 8l4 4 4-4' fill='none' stroke='%2364748b' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");
  background-repeat: no-repeat; background-position: right 10px center; background-size: 16px;
}
input.cbx-input[aria-expanded="true"] { border-color: var(--brand); box-shadow: 0 0 0 3px rgba(217, 34, 24, 0.12); }
input.cbx-input[readonly] { background-image: none; padding-right: 12px; }

.cbx-panel {
  position: fixed; z-index: 2500;
  display: flex; flex-direction: column;
  background: #ffffff; color: var(--ink);
  border: 1px solid var(--border); border-radius: var(--radius-lg);
  box-shadow: 0 12px 32px -6px rgba(15, 23, 42, 0.18), 0 4px 8px -4px rgba(15, 23, 42, 0.08);
  overflow: hidden; font-size: 13.5px;
  animation: cbx-in var(--dur-fast) var(--ease-out);
}
.cbx-panel[hidden] { display: none; }
@keyframes cbx-in { from { opacity: 0; transform: translateY(-4px); } to { opacity: 1; transform: none; } }
.cbx-panel.is-above { animation-name: cbx-in-up; }
@keyframes cbx-in-up { from { opacity: 0; transform: translateY(4px); } to { opacity: 1; transform: none; } }
@media (prefers-reduced-motion: reduce) { .cbx-panel { animation: none; } .cbx-chev { transition: none; } }

.cbx-search-wrap { position: relative; padding: 8px; border-bottom: 1px solid var(--border-light); flex-shrink: 0; }
.cbx-search-wrap[hidden] { display: none; }
.cbx-search-wrap svg { position: absolute; left: 19px; top: 50%; width: 15px; height: 15px; transform: translateY(-50%); fill: none; stroke: var(--muted); stroke-width: 1.8; stroke-linecap: round; pointer-events: none; }
.cbx-panel input.cbx-search { margin: 0; padding: 7px 10px 7px 32px; font-size: 13.5px; background: var(--card-subtle); border-color: var(--border-light); }
.cbx-panel input.cbx-search:focus { background: #ffffff; }

.cbx-list { overflow-y: auto; overscroll-behavior: contain; padding: 4px; flex: 1 1 auto; min-height: 0; }
.cbx-group {
  padding: 10px 10px 4px; font-size: 10.5px; font-weight: 700; letter-spacing: .06em;
  text-transform: uppercase; color: var(--label);
}
.cbx-group:first-child { padding-top: 6px; }
.cbx-opt {
  display: flex; align-items: center; gap: 10px;
  padding: 8px 10px; border-radius: var(--radius-sm); cursor: pointer;
  line-height: 1.35;
}
.cbx-opt.is-active { background: var(--neutral-bg); }
.cbx-opt.is-selected { color: var(--brand-dark); font-weight: 600; }
.cbx-opt.is-selected.is-active { background: var(--brand-tint); }
.cbx-opt.is-disabled { color: var(--muted); cursor: not-allowed; opacity: .6; }
.cbx-opt.is-placeholder .cbx-label { color: var(--muted); font-style: italic; }
.cbx-label { flex: 1; min-width: 0; overflow-wrap: anywhere; }
.cbx-hint { flex-shrink: 0; max-width: 45%; font-family: var(--font-mono); font-size: 11.5px; font-weight: 400; color: var(--muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.cbx-check { width: 15px; height: 15px; flex-shrink: 0; fill: none; stroke: var(--brand); stroke-width: 2.2; stroke-linecap: round; stroke-linejoin: round; visibility: hidden; }
.cbx-opt.is-selected .cbx-check { visibility: visible; }
.cbx-opt mark { background: var(--pending-bg); color: inherit; border-radius: 2px; padding: 0 1px; box-shadow: inset 0 -1px 0 var(--pending-border); }
.cbx-empty { padding: 16px 12px; color: var(--muted); text-align: center; line-height: 1.5; }
.cbx-empty b { color: var(--ink); font-weight: 600; }
.cbx-foot {
  display: flex; justify-content: space-between; gap: 12px; flex-wrap: wrap;
  padding: 6px 12px; border-top: 1px solid var(--border-light); background: var(--card-subtle);
  font-size: 11px; color: var(--muted); flex-shrink: 0;
}
.cbx-foot:empty { display: none; }
.cbx-foot kbd { font-family: var(--font-mono); font-size: 10px; padding: 0 4px; border: 1px solid var(--border); border-bottom-width: 2px; border-radius: 3px; background: #ffffff; margin: 0 1px; }
@media (max-width: 640px) { .cbx-foot span + span { display: none; } }

/* Compact contexts that size their selects to content. */
.date-picker .cbx-select, .inv-inline-label .cbx-select, .rc-inline-label .cbx-select { display: inline-block; width: auto; }


/* ---- Who's online (presence.js) ----
   The status pill now carries a live count; for admin / the CEO it opens a
   list. It reuses .status-pill's chrome and the bell panel's surface. */
.presence { position: relative; }
button.presence-pill { font: inherit; font-size: 12px; font-weight: 600; color: var(--ink); cursor: default; margin: 0; font-variant-numeric: tabular-nums; }
button.presence-pill.is-clickable { cursor: pointer; }
button.presence-pill.is-clickable:hover, button.presence-pill[aria-expanded="true"] { background: #ffffff; border-color: #cbd5e1; }
button.presence-pill:focus-visible { outline: none; border-color: var(--brand); box-shadow: 0 0 0 3px rgba(217, 34, 24, 0.12); }
button.presence-pill.is-offline { background: var(--warn-bg); border-color: var(--warn-border); color: var(--warn); }
button.presence-pill.is-offline .status-dot { background: var(--warn); box-shadow: 0 0 0 3px rgba(220, 38, 38, 0.18); animation: none; }
@media (max-width: 640px) {
  button.presence-pill { padding: 4px 8px; }
}

.presence-panel {
  position: absolute; top: calc(100% + 8px); right: 0; z-index: 60;
  width: min(360px, calc(100vw - 24px));
  background: var(--card); border: 1px solid var(--border); border-radius: var(--radius-lg);
  box-shadow: var(--shadow-lg); overflow: hidden; text-align: left; color: var(--ink);
  animation: notifPanelIn var(--dur-panel) var(--ease-out); transform-origin: top right;
}
.presence-head { display: flex; align-items: flex-start; justify-content: space-between; gap: 12px; padding: 14px 16px 12px; border-bottom: 1px solid var(--border-light); }
.presence-title { font-family: var(--font-display); font-size: 16px; font-weight: 700; }
.presence-sub { font-size: 12px; color: var(--muted); margin-top: 2px; font-variant-numeric: tabular-nums; }
.presence-list { max-height: min(420px, 60vh); overflow-y: auto; padding: 6px; }
.presence-group { padding: 12px 10px 4px; font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--label); }
.presence-row { display: flex; align-items: center; gap: 10px; padding: 8px 10px; border-radius: var(--radius); }
.presence-row:hover { background: var(--card-subtle); }
.presence-avatar {
  position: relative; flex-shrink: 0; width: 32px; height: 32px; border-radius: 50%;
  display: grid; place-items: center; font-size: 11.5px; font-weight: 700; letter-spacing: .02em;
  background: var(--navy-light); color: #ffffff;
}
.presence-avatar-dot { position: absolute; right: -1px; bottom: -1px; width: 10px; height: 10px; border-radius: 50%; background: var(--ok); border: 2px solid var(--card); }
.presence-row.is-idle .presence-avatar { background: var(--neutral-bg); color: var(--neutral-fg); }
.presence-row.is-idle .presence-avatar-dot { background: var(--pending); }
.presence-who { flex: 1; min-width: 0; display: flex; flex-direction: column; }
.presence-name { font-size: 13.5px; font-weight: 600; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.presence-you { display: inline-block; margin-left: 4px; padding: 1px 6px; border-radius: var(--radius-full); background: var(--neutral-bg); color: var(--neutral-fg); font-size: 10.5px; font-weight: 600; vertical-align: 1px; }
.presence-meta { font-size: 12px; color: var(--muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.presence-where { color: var(--label); }
.presence-ago { flex-shrink: 0; font-size: 11.5px; color: var(--muted); font-variant-numeric: tabular-nums; }
.presence-empty { padding: 22px 12px; text-align: center; color: var(--muted); font-size: 13px; }

/* ---- Line material balance (line-materials.js, blowing-log.js) ----
   What is on each production line: last count + issued since = on the
   line now. Cards for the overview; the same figures as a ledger on the
   Blowing Shift Log. */
.lm-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 520px), 1fr)); gap: 16px; margin-top: 8px; }
.lm-card { border: 1px solid var(--border); border-radius: var(--radius-lg); background: var(--card); overflow: hidden; min-width: 0; }
.lm-card-head { display: flex; justify-content: space-between; align-items: flex-start; gap: 12px; flex-wrap: wrap; padding: 14px 16px; border-bottom: 1px solid var(--border-light); background: var(--card-subtle); }
.lm-card.lm-filling .lm-card-head { box-shadow: inset 3px 0 0 var(--accent-blue); }
.lm-card.lm-blowing .lm-card-head { box-shadow: inset 3px 0 0 var(--accent-teal); }
.lm-card-title { font-family: var(--font-display); font-size: 17px; font-weight: 700; display: flex; align-items: center; gap: 8px; }
.lm-dept { font-family: var(--font-sans); font-size: 10.5px; font-weight: 700; letter-spacing: .05em; text-transform: uppercase; color: var(--label); background: var(--neutral-bg); padding: 2px 8px; border-radius: var(--radius-full); }
.lm-card-sub { font-size: 12.5px; color: var(--muted); margin-top: 3px; }
.lm-card-side { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.lm-log-btn { padding: 6px 12px; font-size: 12.5px; }
.lm-never { color: var(--pending); font-weight: 600; }
.lm-table { width: 100%; margin: 0; }
.lm-table th, .lm-table td { padding: 9px 14px; }
.lm-table td.num, .lm-table th.num, .lm-ledger td.num, .lm-ledger th.num { text-align: right; font-variant-numeric: tabular-nums; }
.lm-name { font-weight: 600; line-height: 1.3; }
.lm-name-sm { color: var(--ink); }
.lm-plus { color: var(--accent-teal-dark); font-weight: 600; font-variant-numeric: tabular-nums; }
.lm-onhand { font-size: 14px; }
.lm-empty { padding: 18px 16px; color: var(--muted); margin: 0; }
.lm-bad { color: var(--warn); }
.lm-context { font-size: 12.5px; color: var(--muted); margin: 0 0 8px; }
.lm-ledger td { vertical-align: top; }
.lm-ledger .lm-count-input { width: 110px; margin: 0; text-align: right; font-variant-numeric: tabular-nums; }
.lm-chips { display: flex; flex-direction: column; align-items: flex-end; gap: 4px; margin-top: 4px; }
.lm-chip {
  font: inherit; font-size: 11.5px; font-weight: 500; padding: 2px 8px; border-radius: var(--radius-full);
  background: var(--card); color: var(--muted); border: 1px dashed var(--border); text-decoration: line-through;
}
.lm-chip.is-on { background: var(--ok-bg); color: var(--ok); border: 1px solid var(--ok-border); text-decoration: none; }
.lm-chip:hover { border-color: var(--accent-teal); background: var(--card); }
.lm-chip.is-on:hover { background: var(--ok-bg); }
.blw-output-grid { grid-template-columns: repeat(auto-fit, minmax(170px, 1fr)); }

/* ---------- Bills of Materials & Costing (bom-setup.js, migrations 104-106) ---------- */
.bs-layout { display: grid; grid-template-columns: 260px minmax(0, 1fr); gap: 16px; align-items: start; }
.bs-products { padding: 14px; position: sticky; top: 12px; }
/* Below a wide desktop the recipe table needs the room: products become a
   row of tiles above it instead of a column beside it. */
@media (max-width: 1280px) {
  .bs-layout { grid-template-columns: minmax(0, 1fr); }
  .bs-products { position: static; }
  .bs-product-list { flex-direction: row; flex-wrap: wrap; }
  .bs-product { width: auto; min-width: 200px; flex: 0 1 260px; }
}
.bs-product-list { display: flex; flex-direction: column; gap: 6px; }
.bs-product { display: flex; flex-direction: column; align-items: flex-start; gap: 2px; text-align: left; width: 100%; padding: 10px 12px; border: 1px solid var(--border); border-radius: var(--radius); background: var(--card); color: var(--ink); cursor: pointer; font: inherit; }
.bs-product:hover { border-color: var(--accent-blue); background: var(--card); }
.bs-product.active { border-color: var(--accent-blue); background: #eff6ff; box-shadow: inset 3px 0 0 var(--accent-blue); }
.bs-product.is-retired { opacity: .6; }
.bs-product-name { font-weight: 700; font-size: 14px; }
.bs-product-state { font-size: 12px; color: var(--ok); }
.bs-product-state.is-missing { color: var(--pending); font-weight: 600; }
.bs-product-draft { font-size: 11px; font-weight: 700; color: var(--pending); text-transform: uppercase; letter-spacing: .04em; }
.bs-main { min-width: 0; }
.bs-bom-head { display: flex; justify-content: space-between; align-items: flex-start; gap: 12px; flex-wrap: wrap; }
.bs-bom-title { font-family: var(--font-display); font-size: 20px; font-weight: 700; display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.bs-bom-sub { font-size: 12.5px; color: var(--muted); margin-top: 3px; }
.bs-bom-actions { display: flex; gap: 8px; flex-wrap: wrap; }
.bs-versions { display: flex; gap: 6px; flex-wrap: wrap; margin-top: 12px; }
.bs-version { display: inline-flex; align-items: center; gap: 6px; padding: 4px 10px 4px 12px; border: 1px solid var(--border); border-radius: var(--radius-full); background: var(--card); font: inherit; font-size: 12.5px; font-weight: 700; color: var(--ink); cursor: pointer; }
.bs-version:hover { background: var(--card); border-color: var(--accent-blue); }
.bs-version.active { border-color: var(--accent-blue); background: #eff6ff; }
.bs-callout { margin-top: 12px; padding: 10px 14px; border: 1px solid var(--pending-border); background: var(--pending-bg); border-radius: var(--radius); font-size: 13px; }
.bs-callout p { margin: 2px 0; }
.bs-lines-table select, .bs-lines-table input { margin: 0; }
.bs-mat-cell { min-width: 240px; }
.bs-num { width: 110px; text-align: right; font-variant-numeric: tabular-nums; }
.bs-num-sm { width: 80px; }
.bs-group { width: 130px; }
.bs-unit, .bs-fixed { font-weight: 600; color: var(--label); }
.bs-warn { font-size: 11.5px; color: var(--warn); margin-top: 3px; }
.bs-remove { color: var(--warn); }
.bs-line-tools { display: flex; gap: 8px; align-items: center; flex-wrap: wrap; margin-top: 10px; }
.bs-help { font-size: 12px; }
.bs-notes-row { margin-top: 12px; max-width: 640px; }
.bs-calc { display: flex; gap: 10px; align-items: center; flex-wrap: wrap; margin-bottom: 8px; }
.bs-calc label { margin: 0; }
.bs-calc input { width: 120px; margin: 0; }
.bs-rate-types { margin: 6px 0 10px; flex-wrap: wrap; }
.bs-bands { display: grid; grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); gap: 8px; margin: 6px 0 14px; }
.bs-band { padding: 10px 12px; border-radius: var(--radius); border: 1px solid; display: flex; flex-direction: column; gap: 2px; font-size: 12.5px; }
.bs-band strong { font-size: 14px; font-variant-numeric: tabular-nums; }
.bs-band-ok { background: var(--ok-bg); border-color: var(--ok-border); color: var(--ok); }
.bs-band-amber { background: var(--pending-bg); border-color: var(--pending-border); color: var(--pending); }
.bs-band-red { background: var(--warn-bg); border-color: var(--warn-border); color: var(--warn); }
.bs-rules-grid { grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); }
.bs-toggle-cell { grid-column: 1 / -1; }
.bs-switch, .bs-inline-check { display: inline-flex; align-items: center; gap: 8px; font-weight: 600; margin: 0; }
.bs-switch input, .bs-inline-check input { width: auto; margin: 0; }
.bs-error { color: var(--warn); font-size: 13px; margin: 8px 0 0; }
.bs-modal-actions { margin-top: 16px; display: flex; gap: 10px; justify-content: flex-end; }
.bs-history { margin-top: 18px; }
.bs-row-actions { display: inline-flex; gap: 10px; align-items: center; white-space: nowrap; }
.bs-row-actions button.secondary { padding: 5px 12px; font-size: 12.5px; }

/* ---------- Material Variance (material-variance.js, migration 106) ---------- */
.mr-order-box { margin-top: 14px; padding: 12px 14px; border: 1px solid var(--border); border-radius: var(--radius); background: var(--card-subtle); }
.mv-filter-panel { display: flex; flex-direction: column; gap: 10px; }
.mv-bands-note { font-size: 12.5px; color: var(--label); margin: -10px 0 16px; display: flex; align-items: center; gap: 6px; flex-wrap: wrap; }
.mv-dot { display: inline-block; width: 10px; height: 10px; border-radius: 50%; }
.mv-dot.ok { background: var(--ok); }
.mv-dot.amber { background: var(--pending); }
.mv-dot.red { background: var(--warn); }
.mv-flag { display: inline-block; font-size: 11.5px; font-weight: 600; padding: 2px 8px; border-radius: var(--radius-full); margin: 1px 2px 1px 0; white-space: nowrap; }
.mv-flag.amber { background: var(--pending-bg); color: var(--pending); }
.mv-flag.red { background: var(--warn-bg); color: var(--warn); }
.mv-flag.ok { background: var(--ok-bg); color: var(--ok); }
.mv-n { display: inline-block; min-width: 20px; padding: 0 6px; border-radius: var(--radius-full); font-weight: 700; text-align: center; }
.mv-n.red { background: var(--warn-bg); color: var(--warn); }
.mv-n.amber { background: var(--pending-bg); color: var(--pending); }
.mv-over { color: var(--warn); font-weight: 600; font-variant-numeric: tabular-nums; }
.mv-under { color: var(--accent-blue); font-variant-numeric: tabular-nums; }
.mv-row-red td:first-child { box-shadow: inset 3px 0 0 var(--warn); }
.mv-problem { white-space: normal; display: inline-block; max-width: 46ch; font-size: 12px; }
.mv-facts { display: flex; flex-wrap: wrap; gap: 10px 26px; align-items: flex-end; padding: 12px 14px; background: var(--card-subtle); border: 1px solid var(--border); border-radius: var(--radius); margin-bottom: 12px; }
.mv-facts div { display: flex; flex-direction: column; gap: 2px; }
.mv-facts span { font-size: 11px; text-transform: uppercase; letter-spacing: .05em; color: var(--muted); font-weight: 700; }
.mv-checks { display: flex; flex-direction: column; gap: 6px; margin-bottom: 12px; }
.mv-check { padding: 9px 12px; border-radius: var(--radius); border: 1px solid var(--ok-border); font-size: 13px; background: var(--ok-bg); }
.mv-check.amber { background: var(--pending-bg); border-color: var(--pending-border); }
.mv-check.red { background: var(--warn-bg); border-color: var(--warn-border); }
.mv-review { font-weight: 600; font-size: 12.5px; }
.mv-review.ok { color: var(--ok); }
.mv-review.stale { color: var(--pending); }
.mv-review.need { color: var(--warn); }
.mv-explain-btn { padding: 4px 10px; font-size: 12px; margin-top: 4px; }
.mv-explain-row td { background: var(--card-subtle); }
.mv-explain-form { display: grid; grid-template-columns: minmax(200px, 1fr) minmax(220px, 2fr) minmax(160px, 1fr) auto; gap: 10px; align-items: end; }
.mv-explain-form label { margin: 0 0 4px; }
.mv-explain-form input, .mv-explain-form select { margin: 0; }
.mv-explain-actions { display: flex; gap: 8px; }
@media (max-width: 760px) { .mv-explain-form { grid-template-columns: minmax(0, 1fr); } }

/* ---------- Production Orders (production-orders.js, migration 107) ---------- */
.prd-stages { display: flex; align-items: center; gap: 6px; flex-wrap: wrap; margin-bottom: 12px; }
.prd-stage { font-size: 12px; font-weight: 700; padding: 4px 12px; border-radius: var(--radius-full); background: var(--neutral-bg); color: var(--muted); }
.prd-stage.done { background: var(--ok-bg); color: var(--ok); }
.prd-stage.now { background: var(--accent-blue); color: #fff; }
.prd-stage.cancelled { background: var(--warn-bg); color: var(--warn); }
.prd-stage-sep { width: 18px; height: 2px; background: var(--border); }
.prd-actions { display: flex; gap: 8px; flex-wrap: wrap; margin-bottom: 12px; }
.prd-notes { font-size: 13px; color: var(--label); margin: -4px 0 8px; }
.prd-notes p { margin: 2px 0; }

.bs-cost-cards { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 8px; margin-bottom: 10px; }
.bs-cost-card { border: 1px solid var(--border); border-radius: var(--radius); padding: 10px 12px; display: flex; flex-direction: column; gap: 2px; background: var(--card); }
.bs-cost-card span { font-size: 11px; font-weight: 700; text-transform: uppercase; letter-spacing: .05em; color: var(--muted); }
.bs-cost-card strong { font-family: var(--font-display); font-size: 20px; font-variant-numeric: tabular-nums; }
.bs-cost-card em { font-style: normal; font-size: 12px; color: var(--label); }
.bs-cost-card.is-total { border-color: var(--accent-blue); background: #eff6ff; }
.bs-cost-card.is-good strong { color: var(--ok); }
.bs-cost-card.is-bad strong { color: var(--warn); }

/* Bills of Materials -> Items: readiness checks, units of measure, rates.
   One compact control size for every field on the page: the app's default
   input (full width, 9px padding, 12px bottom margin) is a form field, and
   inside a table cell it gave every row a different height. Columns are
   fixed by <colgroup> so rows line up down the page. */
#bs-pane-items .reg-table td { vertical-align: middle; }
#bs-pane-items .reg-table input:not([type=checkbox]),
#bs-pane-items .reg-table select,
#bs-pane-items .qs-uom-form input,
#bs-pane-items .qs-uom-form select {
  height: 32px; padding: 5px 9px; margin: 0; font-size: 13px; border-radius: var(--radius-sm);
}
#bs-pane-items .reg-table select, #bs-pane-items .qs-uom-form select { padding-right: 26px; }
#bs-pane-items .reg-table button { padding: 5px 12px; font-size: 12.5px; margin: 0; }
#bs-pane-items .reg-table button.linklike { padding: 0; }
#bs-pane-items .qs-uom-form .bs-num, #iw-uom-panel .bs-num { width: 100%; max-width: 110px; }
#iw-checks-panel .form-help, #iw-uom-panel .form-help, #iw-rates-panel > .form-help { margin: -6px 0 14px; }
#iw-checks-panel .qs-next { margin: 2px 0 0; }

/* Ready to test */
.qs-checks { display: grid; grid-template-columns: repeat(auto-fit, minmax(260px, 1fr)); gap: 8px 16px; }
.qs-check { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; font-size: 13px; padding: 8px 10px; border: 1px solid var(--border-light); border-radius: var(--radius); background: var(--card-subtle); }
.qs-check .reg-pill { min-width: 52px; text-align: center; }
.qs-check-label { font-weight: 600; }
.qs-checks .qs-next { grid-column: 1 / -1; margin: 2px 0 0; }
.qs-inline { display: inline-flex; align-items: center; gap: 6px; white-space: nowrap; font-size: 13px; }

/* 1. Units of measure */
#qs-uom-table { table-layout: fixed; min-width: 860px; }
.qs-u-code { width: 90px; } .qs-u-measure { width: 110px; } .qs-u-size { width: 220px; }
.qs-u-also { width: 120px; } .qs-u-status { width: 100px; } .qs-u-action { width: 84px; }
#qs-uom-table select { width: 100%; }
.qs-active { font-size: 12.5px; text-transform: none; letter-spacing: normal; color: var(--ink); }
.qs-row-action { text-align: right; }
.qs-uom-form { display: flex; align-items: flex-end; gap: 12px; flex-wrap: wrap; margin-top: 14px; padding: 12px 14px; border: 1px dashed var(--border); border-radius: var(--radius); background: var(--card-subtle); }
.qs-add-title { flex-basis: 100%; font-size: 12.5px; font-weight: 700; color: var(--ink); }
.qs-field { display: flex; flex-direction: column; gap: 4px; }
.qs-field label { margin: 0; }
.qs-field input:not(.bs-num), .qs-field select { width: 140px; }
.qs-field-wide input { width: 200px !important; }
.qs-field.hidden { display: none; }
.qs-uom-form button { height: 32px; padding: 5px 16px; font-size: 13px; margin: 0; }

.qs-pack {
  display: grid; grid-template-columns: 100px 96px auto 1fr; align-items: center; gap: 6px;
  margin: 0; font-size: 12.5px; font-weight: 400; color: var(--ink);
  text-transform: none; letter-spacing: normal; white-space: nowrap;
}
.qs-pack-name { text-align: right; font-weight: 600; overflow: hidden; text-overflow: ellipsis; }
.qs-pack-unit { color: var(--label); }
.qs-pack-also { color: var(--muted); overflow: hidden; text-overflow: ellipsis; }
/* Pack-size rows, the base-unit lock and item notes (Items tab) */
.qs-packs { display: flex; flex-direction: column; gap: 6px; }
.qs-unit-fixed { font-weight: 600; font-size: 13px; }
.qs-unit-fixed::before { content: "\1F512\FE0E"; font-size: 10px; margin-right: 5px; opacity: .55; }
.qs-factor { display: flex; align-items: center; gap: 6px; font-size: 12.5px; margin: 6px 0 0; white-space: nowrap; text-transform: none; letter-spacing: normal; }
.qs-notes { display: flex; flex-direction: column; align-items: flex-start; gap: 4px; padding-top: 6px; }
.qs-note-line { font-size: 12px; color: var(--muted); line-height: 1.4; }

@media (max-width: 760px) {
  .qs-field input:not(.bs-num), .qs-field select, .qs-field-wide input { width: 100% !important; }
  .qs-field { flex: 1 1 140px; }
}
/* Bills of Materials -> Items (item-workspace.js): a spreadsheet of every
   item fact. The grid scrolls inside its own frame so the header row and
   the code / name columns stay put while the rest moves under them. */
.iw-count { margin-left: 6px; padding: 1px 8px; border-radius: var(--radius-full); background: var(--neutral-bg); color: var(--neutral-fg); font-size: 11.5px; font-weight: 600; vertical-align: 2px; }
.iw-panel .panel-section-head button { margin: 0; padding: 6px 14px; font-size: 12.5px; }
.iw-toolbar { display: flex; align-items: center; justify-content: space-between; gap: 12px; flex-wrap: wrap; margin-bottom: 12px; }
.iw-views { flex-wrap: wrap; }
.iw-filters { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.iw-filters select, .iw-search input { height: 34px; margin: 0; padding: 6px 10px; font-size: 13px; width: auto; }
.iw-filters select { padding-right: 28px; }
.iw-search { margin: 0; }
.iw-search input { width: 240px; padding-left: 32px; }

.iw-in { height: 30px; margin: 0; padding: 4px 8px; font-size: 13px; border-radius: var(--radius-sm); width: 100%; }
select.iw-in { padding-right: 24px; }
.iw-in.is-edited, .qs-pack.is-edited .iw-in { background: var(--pending-bg); border-color: #f5c451; }
.iw-num { text-align: right; font-variant-numeric: tabular-nums; }
.iw-numwrap { display: flex; align-items: center; gap: 6px; }
.iw-numwrap .iw-in { flex: 1 1 auto; min-width: 0; }
.iw-per { color: var(--muted); font-size: 11.5px; white-space: nowrap; flex-shrink: 0; }

.iw-grid-wrap {
  position: relative; overflow: auto; max-height: calc(100vh - 290px); min-height: 260px;
  border: 1px solid var(--border); border-radius: var(--radius);
}
.iw-grid { width: max-content; min-width: 100%; table-layout: fixed; border-collapse: separate; border-spacing: 0; font-size: 13px; }
.iw-grid th, .iw-grid td { padding: 7px 10px; border-bottom: 1px solid var(--border-light); text-align: left; vertical-align: top; background: var(--card); }
.iw-grid thead th {
  position: sticky; top: 0; z-index: 3; background: var(--navy); color: #fff;
  font-size: 11px; font-weight: 600; letter-spacing: .04em; text-transform: uppercase; white-space: nowrap; padding: 10px;
}
.iw-grid .iw-sticky { position: sticky; z-index: 2; }
.iw-grid thead .iw-sticky { z-index: 4; }
.iw-grid .iw-c-sel { left: 0; text-align: center; }
.iw-grid .iw-c-code { left: 40px; }
.iw-grid .iw-c-name { left: 136px; box-shadow: inset -1px 0 0 var(--border); }
.iw-grid thead .iw-c-name { box-shadow: inset -1px 0 0 rgba(255, 255, 255, .15); }
.iw-grid input[type=checkbox] { width: 15px; height: 15px; margin: 7px 0 0; accent-color: var(--brand); }
.iw-grid thead input[type=checkbox] { margin: 0; }
.iw-grid .md-code, .iw-grid .lm-name, .iw-grid .qs-unit-fixed, .iw-grid .iw-unit, .iw-grid .reg-date { display: inline-block; padding-top: 6px; }
.iw-grid .lm-name { display: block; white-space: normal; overflow-wrap: anywhere; }
.iw-hist { font-size: 11.5px; padding: 0; margin-top: 2px; opacity: 0; }
.iw-grid tr:hover .iw-hist, .iw-hist:focus { opacity: 1; }
.iw-grid tbody tr:hover td { background: #f6f9ff; }
.iw-grid tbody tr.is-selected td { background: var(--brand-tint); }
.iw-grid tbody tr.is-changed td.iw-c-sel { box-shadow: inset 3px 0 0 #f5b301; }
.iw-grid tbody tr.is-missing td.iw-c-code { color: var(--warn); }
.iw-grid .reg-pill { margin-top: 6px; }
.iw-grid .qs-notes .reg-pill, .iw-grid .qs-notes { margin-top: 0; }
.iw-grid .qs-notes { padding-top: 5px; }
.iw-grid .cell-sub { white-space: normal; }
.iw-unit { font-weight: 600; }
.iw-landed { display: inline-block; padding-top: 6px; font-variant-numeric: tabular-nums; }
.iw-packcost { display: grid; gap: 2px; padding-top: 5px; font-size: 12.5px; }
.iw-packcost div { display: flex; justify-content: space-between; gap: 10px; }
.iw-packcost span { color: var(--muted); }
.iw-packcost strong { font-variant-numeric: tabular-nums; font-weight: 600; }
.iw-grid .qs-pack { grid-template-columns: 112px 92px auto 1fr; }
.iw-grid .qs-pack-new select.iw-in { padding-left: 7px; color: var(--label); }
.iw-grid .qs-pack-new:not(.is-edited) .iw-in { border-style: dashed; background-color: transparent; }
.iw-grid .qs-factor .iw-in { width: 90px; }
.iw-help { margin: 10px 0 0 !important; max-width: none; }
kbd { display: inline-block; padding: 0 5px; border: 1px solid var(--border); border-bottom-width: 2px; border-radius: 4px; background: var(--card-subtle); font: 600 11px/1.6 inherit; color: var(--ink); }

/* Selected rows: set one value on all of them */
.iw-bulk {
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap;
  margin-bottom: 10px; padding: 8px 12px; border-radius: var(--radius);
  background: var(--navy); color: #fff;
}
.iw-bulk-count { font-size: 13px; margin-right: 4px; }
.iw-bulk-label { color: #cbd5e1; font-size: 12.5px; }
.iw-bulk .iw-in { width: auto; min-width: 140px; background: #fff; }
.iw-bulk #iw-bulk-field { min-width: 220px; }
.iw-bulk-value { display: inline-flex; align-items: center; gap: 6px; }
.iw-bulk-value .iw-per { color: #cbd5e1; }
.iw-bulk-value .iw-num { width: 130px; min-width: 0; }
.iw-bulk button { margin: 0; padding: 5px 14px; font-size: 12.5px; height: 30px; }
.iw-bulk .linklike { color: #cbd5e1; height: auto; }
.iw-bulk .linklike:hover { color: #fff; }

/* Save bar: stays on screen while the page scrolls */
.iw-savebar {
  position: sticky; bottom: 0; z-index: 5;
  display: flex; align-items: center; justify-content: flex-end; gap: 10px; flex-wrap: wrap;
  margin: 14px -20px -20px; padding: 12px 20px;
  background: var(--card); border-top: 1px solid var(--border);
  border-radius: 0 0 var(--radius-lg) var(--radius-lg);
}
.iw-savebar-text { margin-right: auto; color: var(--muted); font-size: 13px; }
.iw-savebar.is-dirty, #bs-rate-savebar { background: var(--pending-bg); border-top-color: var(--pending-border); }
.iw-savebar.is-dirty .iw-savebar-text, #bs-rate-savebar .iw-savebar-text { color: var(--ink); font-weight: 600; }
.iw-savebar button { margin: 0; }

/* Costs & prices: a new rate typed on every row */
.iw-adjust { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; margin: 0 0 12px; padding: 10px 12px; border: 1px dashed var(--border); border-radius: var(--radius); background: var(--card-subtle); font-size: 13px; }
.iw-adjust-label { font-weight: 600; color: var(--ink); }
.iw-adjust .bs-num { width: 110px; height: 32px; margin: 0; padding: 5px 9px; }
.iw-adjust button { margin: 0; height: 32px; padding: 5px 14px; font-size: 12.5px; }
.iw-adjust .form-help { margin: 0; }
.bs-rates-table input.bs-rate-input { width: 120px; height: 30px; margin: 0 0 0 auto; display: block; padding: 4px 8px; font-size: 13px; }
.bs-rates-table input.bs-rate-input.is-edited { background: var(--pending-bg); border-color: #f5c451; }
.bs-rates-table tr.is-edited td { background: #fffdf3; }
#bs-rate-types .fin-seg-btn[data-count]:not([data-count=""])::after {
  content: attr(data-count); margin-left: 2px; padding: 0 6px; border-radius: var(--radius-full);
  background: #f5b301; color: #fff; font-size: 10.5px; line-height: 16px;
}

/* Review & save dialog */
.bs-save-box { width: min(720px, calc(100vw - 32px)); max-width: none; }
.bs-save-list { max-height: 42vh; overflow: auto; margin: 10px 0 14px; border: 1px solid var(--border-light); border-radius: var(--radius); }
.bs-save-list:empty { display: none; }
.bs-save-table { font-size: 12.5px; }
.bs-save-table th, .bs-save-table td { padding: 7px 10px; }
.bs-save-from { color: var(--muted); text-decoration: line-through; text-decoration-color: rgba(100, 116, 139, .5); }
.bs-save-to { font-weight: 600; color: var(--ink); }
.bs-save-fields { display: grid; grid-template-columns: auto 1fr; gap: 14px; align-items: start; }
.bs-save-date input { width: 170px; margin: 0; }
.bs-save-date.hidden + .bs-save-reason { grid-column: 1 / -1; }
.bs-save-reason textarea { margin: 0; resize: vertical; min-height: 58px; }
.bs-save-reason .form-help { margin: 4px 0 0; }
.qs-check-detail { flex-basis: 100%; font-size: 12px; }

@media (max-width: 760px) {
  .iw-search input { width: 100%; }
  .iw-filters, .iw-search { width: 100%; }
  .iw-grid-wrap { max-height: none; }
  .iw-grid .iw-sticky { position: static; box-shadow: none; }
  .bs-save-fields { grid-template-columns: 1fr; }
}

.prd-close-check { margin: 8px 0 12px; padding: 10px 14px; border: 1px solid var(--pending-border); background: var(--pending-bg); border-radius: var(--radius); font-size: 13px; }
.prd-close-check.is-blocked { border-color: var(--warn); }
.prd-close-check p { margin: 4px 0; }
.prd-close-check ul { margin: 4px 0 6px 18px; padding: 0; }
.card.card-static, .card.card-static:hover { cursor: default; transform: none; box-shadow: none; }
.annunciator-flag.flag-static { cursor: default; }

/* A stock quantity in two units (core.js itemQtyHtml): the reading this
   screen works in, and the other one beneath it, smaller. Hover lists the
   figure in every pack the item has. */
.uq { display: inline-flex; flex-direction: column; line-height: 1.25; vertical-align: top; }
.uq-u { color: var(--muted); font-size: .9em; font-weight: 500; }
.uq-alt { margin-top: 1px; font-size: 11.5px; font-weight: 400; color: var(--muted); white-space: nowrap; }
.uq-alt .uq-u { font-size: 1em; }
.uq-main { white-space: nowrap; }
.uq[title] { cursor: help; }
td.num .uq, th.num .uq, .num .uq, .fin-fig .uq, .rl-stat-value .uq { align-items: flex-end; }
.rl-stat-value .uq { align-items: flex-start; }
.rl-stat-value .uq-alt { font-size: 12px; }
.mv-flag .uq { vertical-align: middle; }

/* BOM page: the edit button beside "What one unit takes" */
.bs-edit-inline { margin-left: auto; }
.bs-edit-inline button { margin: 0; }

/* Oil stores (docs/oil-ledger-plan.md): Ardmore and plant side by side */
.oil-stores { display: grid; grid-template-columns: repeat(auto-fit, minmax(320px, 1fr)); gap: 14px; margin: 10px 0 14px; }
.oil-store { border: 1px solid var(--border, #e3e6ec); border-radius: 10px; padding: 12px 14px; background: var(--surface, #fff); }
.oil-store-head { display: flex; justify-content: space-between; align-items: baseline; gap: 8px; margin-bottom: 8px; }
.oil-store-figs { display: grid; grid-template-columns: repeat(5, minmax(0, 1fr)); gap: 6px; margin-bottom: 8px; }
.oil-store-figs div { display: flex; flex-direction: column; font-size: 12px; }
.oil-store-figs span { color: var(--muted, #6b7280); text-transform: uppercase; letter-spacing: .03em; font-size: 10.5px; }
.oil-store-figs strong { font-size: 14px; }
.oil-store-figs .ok strong { color: var(--ok, #15803d); }
.oil-store-tanks td { padding: 6px 8px; }
@media (max-width: 640px) { .oil-store-figs { grid-template-columns: repeat(2, minmax(0, 1fr)); } }

/* Production order window: which line the hosted Issue to Production form issues to */
.prd-mr-lines { display: flex; gap: 8px; align-items: center; margin: 4px 0 10px; flex-wrap: wrap; }
#prd-mr-host #mr-form .panel { box-shadow: none; }

/* Line Stock: count history (2026-10-21). A toolbar, then one folding row
   per count -- open when it still needs explaining -- with the same light
   lines table as "On the line". Fixed columns so it never runs sideways. */
.lc-toolbar { display: flex; justify-content: space-between; align-items: center; gap: 12px; flex-wrap: wrap; padding-bottom: 12px; border-bottom: 1px solid var(--border-light); }
.lc-toolbar-filters, .lc-toolbar-range { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.lc-toolbar select, .lc-toolbar input, .lc-toolbar button { margin: 0; }
.lc-toolbar select { min-width: 170px; }
.lc-toolbar-range label { margin: 0; font-size: 11px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.lc-toolbar-range input[type="date"] { width: 150px; }
.lc-seg { display: inline-flex; border: 1px solid var(--border); border-radius: var(--radius); overflow: hidden; }
.lc-seg button { margin: 0; border: 0; border-radius: 0; background: #fff; color: var(--muted); font-weight: 600; font-size: 13px; padding: 0 14px; height: 38px; box-shadow: none; }
.lc-seg button + button { border-left: 1px solid var(--border); }
.lc-seg button.is-on { background: var(--navy); color: #fff; }
.lc-rule { display: flex; gap: 8px; align-items: flex-start; margin: 10px 0 14px; font-size: 12.5px; line-height: 1.5; color: var(--muted); }
.lc-rule svg { width: 15px; height: 15px; flex: 0 0 15px; margin-top: 2px; }
#lc-list { display: grid; gap: 8px; }
.lc-empty { padding: 24px; text-align: center; color: var(--muted); border: 1px dashed var(--border); border-radius: var(--radius-lg); margin: 0; }

.lc-item { border: 1px solid var(--border); border-left: 3px solid var(--ok); border-radius: var(--radius-lg); background: #fff; min-width: 0; }
.lc-item.lc-amber { border-left-color: #d97706; }
.lc-item.lc-red { border-left-color: var(--warn); }
.lc-sum { display: grid; grid-template-columns: 16px auto auto minmax(0, 1fr) auto auto; align-items: center; gap: 12px; padding: 11px 14px; cursor: pointer; list-style: none; }
.lc-sum::-webkit-details-marker { display: none; }
.lc-sum::before { content: "\25B8"; color: var(--muted); font-size: 12px; }
.lc-item[open] > .lc-sum::before { content: "\25BE"; }
.lc-item[open] > .lc-sum { border-bottom: 1px solid var(--border-light); }
.lc-sum:hover { background: var(--card-subtle); border-radius: var(--radius-lg); }
.lc-no { font-family: var(--font-display); font-weight: 700; color: var(--ink); font-variant-numeric: tabular-nums; }
.lc-line { justify-self: start; font-size: 12px; font-weight: 700; padding: 2px 9px; border-radius: var(--radius-full); background: #e8eef6; color: var(--navy-light); white-space: nowrap; }
.lc-line-blowing { background: #f1ecfb; color: #5b3fa0; }
.lc-when { color: var(--ink); font-size: 13.5px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.lc-n { color: var(--muted); font-size: 12.5px; white-space: nowrap; }
.lc-status { display: flex; gap: 6px; justify-content: flex-end; flex-wrap: wrap; }

.lc-body { padding: 10px 14px 14px; }
.lc-meta { display: flex; justify-content: space-between; align-items: flex-start; gap: 12px; margin-bottom: 10px; font-size: 12.5px; color: var(--muted); }
.lc-meta button { margin: 0; flex-shrink: 0; }
.lc-note { margin-top: 3px; color: var(--ink); font-size: 13px; }
.lc-table { table-layout: fixed; width: 100%; border-collapse: collapse; font-size: 13px; }
.lc-table col.lc-col-q { width: 130px; }
.lc-table col.lc-col-r { width: 230px; }
.lc-table.erx-lines thead th { position: static; background: var(--card-subtle); color: var(--muted); border-top: 1px solid var(--border-light); border-bottom: 1px solid var(--border); }
.lc-table td { vertical-align: middle; }
.lc-mat { color: var(--ink); overflow-wrap: anywhere; }
.lc-table tr.lc-row-open td { background: #fffaf0; }
.lc-neg { color: var(--warn); }
.lc-pos { color: #b45309; }
.lc-ok { color: var(--ok); font-weight: 600; font-size: 12.5px; }
.lc-result .reg-pill { vertical-align: middle; }
.lc-explain-btn { margin: 0 0 0 6px; height: 28px; padding: 0 10px; font-size: 12px; }
.lc-why { margin-top: 4px; font-size: 12px; color: var(--muted); }

@media (max-width: 900px) {
  .lc-sum { grid-template-columns: 16px auto minmax(0, 1fr); row-gap: 6px; }
  .lc-n { display: none; }
  .lc-when { grid-column: 2 / -1; grid-row: 2; }
  .lc-status { grid-column: 2 / -1; justify-content: flex-start; }
  .lc-table col.lc-col-q { width: 100px; }
  .lc-table col.lc-col-r { width: 170px; }
}
@media (max-width: 640px) {
  .lc-toolbar, .lc-toolbar-range { align-items: stretch; }
  .lc-toolbar-range input[type="date"] { width: 100%; }
  .lc-meta { flex-direction: column; }
  .lc-table { table-layout: auto; min-width: 560px; }
}
.lm-onhand.lm-bad { color: var(--danger, #b42318); }

/* Oil landed cost (BOM page → Items, migration 116) */
.oc-oil { padding: 12px 0; border-top: 1px solid var(--border); }
.oc-oil:first-child { border-top: 0; }
.oc-oil-head { display: flex; align-items: center; gap: 12px; flex-wrap: wrap; margin-bottom: 8px; }
.oc-oil-head button { margin-left: auto; }
.oc-now { font-size: 18px; font-weight: 600; }
.oc-sheet { max-width: 460px; }
.oc-sheet td.num { text-align: right; font-variant-numeric: tabular-nums; }
.oc-sheet-total td { font-weight: 600; border-top: 2px solid var(--border); }
.oc-history { margin-top: 6px; }
.oc-history summary { cursor: pointer; color: var(--muted); font-size: 13px; }
.oc-box { max-width: 720px; width: 100%; }
.oc-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 10px; margin-bottom: 12px; }
.oc-charges input.oc-name { width: 100%; min-width: 140px; }
.oc-charges .oc-per-mt { white-space: nowrap; font-variant-numeric: tabular-nums; }
.oc-total { margin: 12px 0 4px; }

/* ---- Production order: plan form and order window (migration 117) ----
   One visual system for the run: numbered steps on the left of the form,
   what the run needs on the right; in the order window a progress band, a
   KPI strip, then one section per question (materials, blowing, oil, time
   lost, shifts). Actions sit in one bar: changes on the left, the next step
   on the right. */
.pdo-form-box, .pdo-view-box { max-width: 1120px; padding: 0; }
.pdo-modal-head { display: flex; justify-content: space-between; align-items: flex-start; gap: 12px; padding: 18px 22px 14px; border-bottom: 1px solid var(--border); }
.pdo-modal-head h2 { margin: 2px 0 0; font-size: 20px; }
#prd-status-modal .pdo-modal-head { padding: 0 0 12px; margin-bottom: 12px; }
.pdo-eyebrow { font-size: 11px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.pdo-hint { font-size: 12px; color: var(--muted); }
.pdo-req { font-size: 10.5px; font-weight: 700; text-transform: uppercase; letter-spacing: .04em; color: var(--warn); margin-left: 4px; }
.pdo-empty { color: var(--muted); font-size: 13px; padding: 10px 0; }
.pdo-form-grid { display: grid; grid-template-columns: minmax(0, 1.25fr) minmax(0, 1fr); }
.pdo-form-main { padding: 6px 22px 10px; }
.pdo-form-side { padding: 16px 20px; background: var(--card-subtle); border-left: 1px solid var(--border); max-height: 70vh; overflow-y: auto; }
.pdo-step { border: 0; padding: 12px 0 14px; margin: 0; border-bottom: 1px solid var(--border-light); min-width: 0; }
.pdo-step:last-child { border-bottom: 0; }
.pdo-step legend { display: flex; align-items: center; gap: 8px; font-size: 13px; font-weight: 700; color: var(--ink); padding: 0; margin-bottom: 8px; }
.pdo-step-n { width: 22px; height: 22px; border-radius: 50%; background: var(--navy); color: #fff; font-size: 12px; display: inline-flex; align-items: center; justify-content: center; }
.pdo-row-2 { display: grid; grid-template-columns: 1fr 1fr; gap: 0 14px; }
.pdo-seg { display: inline-flex; border: 1px solid var(--border); border-radius: var(--radius); overflow: hidden; margin-bottom: 10px; }
.pdo-seg-btn { margin: 0; border: 0; border-radius: 0; background: var(--card); color: var(--label); font-weight: 600; padding: 7px 14px; box-shadow: none; }
.pdo-seg-btn:hover { background: var(--neutral-bg); color: var(--ink); }
.pdo-seg-btn.active, .pdo-seg-btn.active:hover { background: var(--navy); color: #fff; }
.pdo-target { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1fr); gap: 14px; align-items: end; }
.pdo-input-unit { display: flex; align-items: stretch; }
.pdo-input-unit input { margin: 0; border-top-right-radius: 0; border-bottom-right-radius: 0; font-size: 18px; font-weight: 600; min-width: 0; }
.pdo-input-unit span { display: flex; align-items: center; padding: 0 12px; border: 1px solid var(--border); border-left: 0; border-radius: 0 var(--radius) var(--radius) 0; background: var(--neutral-bg); color: var(--label); font-weight: 600; font-size: 13px; white-space: nowrap; }
.pdo-target-equals { padding: 8px 12px; border-radius: var(--radius); background: var(--card-subtle); border: 1px dashed var(--border); min-height: 44px; font-size: 14px; }
.pdo-target-equals strong { font-size: 18px; }
.pdo-eq-sign { color: var(--muted); font-weight: 700; margin-right: 6px; }
.pdo-rate-grid { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 10px; margin-top: 4px; }
.pdo-rate-grid div, .pdo-kpis div { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.pdo-rate-grid span, .pdo-kpis span { font-size: 10.5px; text-transform: uppercase; letter-spacing: .05em; color: var(--muted); font-weight: 700; }
.pdo-rate-grid strong { font-size: 15px; }
.pdo-rate-grid em, .pdo-kpis em { font-style: normal; font-size: 11.5px; color: var(--muted); }
.pdo-warn { margin: 8px 0 0; padding: 8px 10px; border-left: 3px solid var(--pending); background: var(--pending-bg); font-size: 12.5px; border-radius: 0 var(--radius) var(--radius) 0; }
.pdo-side-head { display: flex; flex-direction: column; gap: 2px; margin-bottom: 10px; }
.pdo-avail-sum { font-size: 13px; font-weight: 700; padding: 8px 10px; border-radius: var(--radius); margin-bottom: 10px; }
.pdo-avail-sum.good { background: var(--ok-bg); color: var(--ok); border: 1px solid var(--ok-border); }
.pdo-avail-sum.bad { background: var(--warn-bg); color: var(--warn); border: 1px solid var(--warn-border); }
.pdo-need-list { list-style: none; margin: 0 0 10px; padding: 0; display: grid; gap: 6px; }
.pdo-need-list li { background: var(--card); border: 1px solid var(--border); border-radius: var(--radius); padding: 8px 10px; }
.pdo-need-list li.is-short { border-color: var(--warn-border); box-shadow: inset 3px 0 0 var(--warn); }
.pdo-need-top { display: flex; justify-content: space-between; gap: 10px; align-items: baseline; }
.pdo-need-name { font-weight: 600; font-size: 13px; min-width: 0; overflow-wrap: anywhere; }
.pdo-need-qty { font-weight: 700; white-space: nowrap; font-variant-numeric: tabular-nums; text-align: right; }
.pdo-need-sub { display: flex; flex-wrap: wrap; gap: 4px 12px; font-size: 11.5px; color: var(--muted); margin-top: 3px; }
.pdo-short { color: var(--warn); font-weight: 700; }
.pdo-okmark { color: var(--ok); font-weight: 700; }
.pdo-modal-foot { display: flex; justify-content: space-between; align-items: center; gap: 12px; padding: 12px 22px; border-top: 1px solid var(--border); background: var(--card-subtle); }
#prd-status-modal .pdo-modal-foot { margin: 14px -20px -20px; }
.pdo-foot-actions { display: flex; gap: 8px; }
.pdo-foot-actions button { margin: 0; }
.pdo-btn-primary { background: var(--navy); }
.pdo-btn-primary:hover { background: var(--navy-light); }
.pdo-btn-danger { background: var(--warn); }
.pdo-btn-danger:hover { background: #b91c1c; }
#prd-form-error { margin: 0 22px 10px; }

/* Order window */
#prd-view-body { padding: 14px 22px 22px; }
.pdo-headline { display: flex; justify-content: space-between; align-items: center; gap: 10px; flex-wrap: wrap; margin-bottom: 10px; }
.pdo-headline .prd-stages { margin: 0; }
.pdo-actionbar { display: flex; justify-content: space-between; gap: 10px; flex-wrap: wrap; padding: 10px 12px; margin-bottom: 14px; background: var(--card-subtle); border: 1px solid var(--border); border-radius: var(--radius-lg); }
.pdo-actionbar > div { display: flex; gap: 8px; flex-wrap: wrap; }
.pdo-act { display: inline-flex; align-items: center; gap: 7px; margin: 0; padding: 8px 14px; font-weight: 600; font-size: 13px; background: var(--card); color: var(--ink); border: 1px solid var(--border); box-shadow: var(--shadow-sm); }
.pdo-act svg { width: 16px; height: 16px; flex: none; }
.pdo-act:hover { background: var(--neutral-bg); color: var(--ink); }
.pdo-act-primary { background: var(--accent-blue); border-color: var(--accent-blue); color: #fff; }
.pdo-act-primary:hover { background: var(--accent-blue-dark); color: #fff; }
.pdo-act-dark { background: var(--navy); border-color: var(--navy); color: #fff; }
.pdo-act-dark:hover { background: var(--navy-light); color: #fff; }
.pdo-act-danger { color: var(--warn); border-color: var(--warn-border); }
.pdo-act-danger:hover { background: var(--warn-bg); color: var(--warn); }
.pdo-alert { margin: 0 0 12px; padding: 10px 14px; border: 1px solid var(--warn-border); background: var(--warn-bg); border-radius: var(--radius); font-size: 13px; color: var(--ink); }
.pdo-progress { padding: 14px 16px; border: 1px solid var(--border); border-radius: var(--radius-lg); background: var(--card); margin-bottom: 10px; }
.pdo-progress-head { display: flex; justify-content: space-between; align-items: baseline; gap: 10px; flex-wrap: wrap; margin-bottom: 8px; }
.pdo-big { font-size: 26px; font-weight: 800; letter-spacing: -.01em; }
.pdo-pct { font-size: 18px; margin-left: 6px; }
.pdo-progress-legend { display: flex; justify-content: space-between; gap: 10px; font-size: 12px; color: var(--muted); margin-top: 6px; flex-wrap: wrap; }
.pdo-bar { position: relative; display: block; height: 10px; border-radius: var(--radius-full); background: var(--neutral-bg); }
.pdo-bar-fill { position: absolute; left: 0; top: 0; bottom: 0; border-radius: var(--radius-full); background: var(--accent-blue); }
.pdo-bar-fill.ok { background: var(--ok); }
.pdo-bar-fill.warn { background: var(--pending); }
.pdo-bar-mark { position: absolute; top: -4px; bottom: -4px; width: 2px; background: var(--ink); border-radius: 1px; }
.pdo-mini .pdo-bar { height: 5px; margin-top: 4px; min-width: 60px; }
.pdo-reg-progress { display: flex; flex-direction: column; gap: 4px; min-width: 140px; font-size: 13px; }
.pdo-kpis { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 10px; padding: 12px 14px; border: 1px solid var(--border); border-radius: var(--radius-lg); background: var(--card-subtle); margin-bottom: 14px; }
.pdo-kpis strong { font-size: 17px; font-variant-numeric: tabular-nums; }
.pdo-kpis strong small { font-size: 12px; font-weight: 500; color: var(--muted); }
.pdo-kpis .pdo-kpi-date { font-size: 15px; }
.pdo-kpis-sm { margin-bottom: 8px; }
.pdo-kpis-sm strong { font-size: 15px; }
.pdo-section { margin-top: 18px; }
.pdo-section-head { display: flex; align-items: baseline; gap: 12px; flex-wrap: wrap; margin-bottom: 8px; padding-bottom: 6px; border-bottom: 2px solid var(--navy); }
.pdo-section-head h3 { margin: 0; font-size: 15px; }
.pdo-mat-table td { vertical-align: top; }
.pdo-ou { font-weight: 700; white-space: nowrap; }
.pdo-ou.over { color: var(--warn); }
.pdo-ou.under { color: var(--pending); }
.pdo-ou.ok { color: var(--label); }
.pdo-blow-bar { display: grid; gap: 6px; margin-bottom: 8px; font-size: 13px; }

/* Close / release / cancel */
.pdo-status-text { font-size: 13.5px; color: var(--label); margin: 0 0 10px; }
.pdo-status-text:empty { display: none; }
.pdo-closebox { display: grid; gap: 10px; margin: 0 0 12px; padding: 12px 14px; border: 1px solid var(--border); border-radius: var(--radius-lg); background: var(--card-subtle); font-size: 13px; }
.pdo-closebox ul { margin: 4px 0 0 18px; padding: 0; }
.pdo-closebox li { margin: 2px 0; }
.pdo-closebox.is-warn { border-color: var(--pending-border); background: var(--pending-bg); }
.pdo-closebox.is-short { border: 2px solid var(--warn); background: var(--warn-bg); }
.pdo-closebox.is-blocked { border-color: var(--warn-border); }
.pdo-closebox-block { color: var(--warn); }
.pdo-short-figs { display: grid; grid-template-columns: repeat(3, 1fr); gap: 10px; }
.pdo-short-figs div { display: flex; flex-direction: column; background: var(--card); border: 1px solid var(--warn-border); border-radius: var(--radius); padding: 8px 10px; }
.pdo-short-figs span { font-size: 10.5px; text-transform: uppercase; letter-spacing: .05em; color: var(--muted); font-weight: 700; }
.pdo-short-figs strong { font-size: 20px; }
.pdo-short-figs .bad strong { color: var(--warn); }
.pdo-short-figs em { font-style: normal; font-size: 11.5px; color: var(--warn); }
.pdo-short-lede { margin: 0; font-weight: 600; color: var(--ink); }
.pdo-ack { display: flex; gap: 8px; align-items: flex-start; margin: 10px 0; padding: 10px 12px; border: 1px solid var(--warn-border); border-radius: var(--radius); background: var(--warn-bg); font-weight: 600; font-size: 13px; cursor: pointer; text-transform: none; letter-spacing: normal; color: var(--ink); }
.pdo-ack input { margin: 2px 0 0; width: auto; }
#prd-status-note { width: 100%; resize: vertical; }

/* Live oil pool on the oil stores panel */
.oil-live { margin-top: 10px; padding-top: 10px; border-top: 1px dashed var(--border); }
.oil-live-head { display: flex; justify-content: space-between; align-items: baseline; gap: 8px; flex-wrap: wrap; margin-bottom: 6px; }
.oil-live .oil-store-figs { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.oil-store-figs .bad strong { color: var(--warn); }

@media (max-width: 860px) {
  .pdo-form-grid { grid-template-columns: 1fr; }
  .pdo-form-side { border-left: 0; border-top: 1px solid var(--border); max-height: none; }
  .pdo-target, .pdo-rate-grid { grid-template-columns: 1fr; }
  .pdo-modal-foot { flex-direction: column; align-items: stretch; }
}
@media (max-width: 520px) {
  .pdo-row-2, .pdo-short-figs { grid-template-columns: 1fr; }
  .pdo-modal-head, .pdo-form-main, #prd-view-body { padding-left: 16px; padding-right: 16px; }
}

/* The production order a shift counts toward, on the shift logs */
.pdo-run-banner { display: grid; grid-template-columns: minmax(180px, auto) minmax(0, 1fr) auto; gap: 8px 18px; align-items: center; margin: 12px 0 4px; padding: 10px 14px; border: 1px solid var(--border); border-left: 4px solid var(--ok); border-radius: var(--radius); background: var(--card-subtle); font-size: 12.5px; }
.pdo-run-banner.is-warn { border-left-color: var(--pending); }
.pdo-run-banner.is-none { display: block; border-left-color: var(--warn); background: var(--warn-bg); }
.pdo-run-banner.hidden { display: none; }
.pdo-run-id { display: flex; flex-direction: column; gap: 1px; }
.pdo-run-id strong { font-size: 14px; }
.pdo-run-id span:last-child { color: var(--muted); }
.pdo-run-bar { display: grid; gap: 4px; min-width: 0; }
.pdo-run-state { display: flex; flex-direction: column; align-items: flex-end; gap: 3px; color: var(--muted); }
@media (max-width: 760px) { .pdo-run-banner { grid-template-columns: 1fr; } .pdo-run-state { align-items: flex-start; } }

/* ---- Oil stock and the daily oil book (Tank Dip Readings, QC tank status) ----
   Same system as the production order: a titled panel, a hero figure per
   store, the stock split by QC status in one bar, the live book as a
   left-to-right sum, then the tanks; the book is one ledger per store. */
.oilx-panel { padding: 0; overflow: hidden; }
.oilx-panel-head { display: flex; justify-content: space-between; align-items: flex-start; gap: 14px; flex-wrap: wrap; padding: 18px 22px 14px; border-bottom: 1px solid var(--border); }
.oilx-title { display: flex; gap: 12px; align-items: flex-start; min-width: 0; flex: 1 1 420px; }
.oilx-title h2 { margin: 0; font-size: 18px; }
.oilx-title p { margin: 3px 0 0; font-size: 12.5px; color: var(--muted); max-width: 720px; }
.oilx-icon { width: 36px; height: 36px; flex: none; border-radius: var(--radius); background: var(--navy); color: #fff; display: inline-flex; align-items: center; justify-content: center; }
.oilx-icon svg { width: 19px; height: 19px; }
.oilx-asof { font-size: 12px; font-weight: 700; color: var(--label); background: var(--neutral-bg); padding: 5px 10px; border-radius: var(--radius-full); white-space: nowrap; }
.oilx-stores { display: grid; grid-template-columns: repeat(auto-fit, minmax(380px, 1fr)); gap: 16px; padding: 18px 22px 22px; align-items: start; }
#ts-stores.oilx-stores, #ts-stores { padding: 0; }
.oilx-store { border: 1px solid var(--border); border-radius: var(--radius-lg); background: var(--card); overflow: hidden; }
.oilx-store-head { display: flex; justify-content: space-between; align-items: flex-start; gap: 10px; padding: 14px 16px 10px; }
.oilx-store-head h3 { margin: 0; font-size: 15px; }
.oilx-store-head span { font-size: 12px; color: var(--muted); }
.oilx-hero { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 10px; padding: 4px 16px 12px; }
.oilx-hero div { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.oilx-hero span, .oilx-step span, .oilx-book-kpis span { font-size: 10.5px; text-transform: uppercase; letter-spacing: .05em; color: var(--muted); font-weight: 700; }
.oilx-hero strong { white-space: nowrap; font-size: clamp(19px, 2.2vw, 26px); font-weight: 800; letter-spacing: -.01em; font-variant-numeric: tabular-nums; }
.oilx-hero strong small { font-size: 13px; font-weight: 600; color: var(--muted); }
.oilx-hero .oilx-mid { font-size: 18px; color: var(--label); }
.oilx-good { color: var(--ok); }
.oilx-bad { color: var(--warn); }
.oilx-stale { color: var(--warn); font-weight: 600; }
.oilx-comp { padding: 0 16px 12px; }
.oilx-compbar { display: flex; height: 10px; border-radius: var(--radius-full); background: var(--neutral-bg); overflow: hidden; }
.oilx-seg { height: 100%; }
.oilx-seg.usable, .oilx-legend i.usable { background: var(--ok); }
.oilx-seg.hold, .oilx-legend i.hold { background: var(--pending); }
.oilx-seg.bad, .oilx-legend i.bad { background: var(--warn); }
.oilx-seg.unconf, .oilx-legend i.unconf { background: #94a3b8; }
.oilx-legend { display: flex; flex-wrap: wrap; gap: 4px 14px; margin-top: 6px; font-size: 11.5px; color: var(--label); }
.oilx-legend span.zero { color: var(--muted); opacity: .7; }
.oilx-legend span.oilx-untested { font-style: italic; color: var(--muted); }
.oilx-legend i { display: inline-block; width: 8px; height: 8px; border-radius: 2px; margin-right: 5px; vertical-align: middle; }
.oilx-live { margin: 0 16px 12px; padding: 12px 14px; border-radius: var(--radius); background: var(--card-subtle); border: 1px solid var(--border); }
.oilx-live-head { display: flex; justify-content: space-between; align-items: baseline; gap: 8px; flex-wrap: wrap; margin-bottom: 8px; font-size: 13px; }
.oilx-live-head span { font-size: 12px; color: var(--muted); }
.oilx-steps { display: grid; grid-template-columns: repeat(auto-fit, minmax(104px, 1fr)); gap: 6px; }
.oilx-steps > i { align-self: center; font-style: normal; font-weight: 800; color: var(--muted); }
.oilx-step { display: flex; flex-direction: column; gap: 1px; padding: 6px 10px; border-radius: var(--radius); background: var(--card); border: 1px solid var(--border-light); min-width: 0; }
.oilx-step strong { font-size: 15px; font-variant-numeric: tabular-nums; }
.oilx-step em { font-style: normal; font-size: 10.5px; color: var(--muted); }
.oilx-step.in strong { color: var(--ok); }
.oilx-step.out strong { color: var(--pending); }
.oilx-step.total { background: var(--navy); border-color: var(--navy); }
.oilx-step.total span, .oilx-step.total strong { color: #fff; }
.oilx-step.total.bad { background: var(--warn); border-color: var(--warn); }
.oilx-live-foot { display: flex; gap: 18px; flex-wrap: wrap; margin-top: 8px; font-size: 12.5px; color: var(--label); }
.oilx-note { margin: 8px 0 0; font-size: 12px; color: var(--label); }
.oilx-note.bad { color: var(--warn); }
.oilx-tanks { border-top: 1px solid var(--border); }
.oilx-tank { display: grid; grid-template-columns: minmax(90px, 1fr) minmax(0, 2fr) minmax(0, 1.4fr); gap: 12px; align-items: center; padding: 9px 16px; border-bottom: 1px solid var(--border-light); font-size: 12.5px; }
.oilx-tank:last-child { border-bottom: 0; }
.oilx-tank-id { display: flex; flex-direction: column; }
.oilx-tank-id strong { font-size: 13.5px; }
.oilx-tank-id span { font-size: 11.5px; color: var(--muted); }
.oilx-tank-fill { display: grid; gap: 4px; }
.oilx-tank-fill em { font-style: normal; color: var(--muted); }
.oilx-gauge { height: 7px; border-radius: var(--radius-full); background: var(--neutral-bg); overflow: hidden; }
.oilx-gauge span { display: block; height: 100%; background: #94a3b8; }
.oilx-gauge span.ok { background: var(--ok); }
.oilx-gauge span.warn, .oilx-gauge span.pending { background: var(--pending); }
.oilx-gauge span.blocked { background: var(--warn); }
.oilx-tank-status { display: flex; flex-direction: column; align-items: flex-start; gap: 2px; }
.oilx-tank-status span:last-child { font-size: 11px; color: var(--muted); }
.oilx-store.is-empty { background: var(--card-subtle); border-style: dashed; }
.oilx-empty { margin: 0; padding: 0 16px 10px; font-size: 13px; color: var(--label); }
.oilx-chips { display: flex; flex-wrap: wrap; gap: 6px; padding: 0 16px 14px; }
.oilx-chips span { font-size: 12px; font-weight: 600; padding: 3px 9px; border-radius: var(--radius-full); background: var(--card); border: 1px solid var(--border); color: var(--label); }

/* Daily oil book */
.oilx-store-switch { margin: 0; align-self: center; }
.oilx-store-switch small { font-weight: 500; opacity: .75; }
.oilx-book-kpis { display: grid; grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); gap: 0; border-bottom: 1px solid var(--border); }
.oilx-book-kpis div { display: flex; flex-direction: column; gap: 2px; padding: 12px 22px; border-right: 1px solid var(--border-light); border-top: 3px solid transparent; }
.oilx-book-kpis div:last-child { border-right: 0; }
.oilx-book-kpis strong { font-size: 19px; font-variant-numeric: tabular-nums; }
.oilx-book-kpis em { font-style: normal; font-size: 11.5px; color: var(--muted); }
.oilx-book-kpis .good { border-top-color: var(--ok); }
.oilx-book-kpis .bad { border-top-color: var(--warn); }
.oilx-book-kpis .bad strong { color: var(--warn); }
.oilx-book-kpis .warn { border-top-color: var(--pending); }
#oil-book-panel .table-responsive { padding: 0 22px; }
.oilx-book td { vertical-align: top; }
.oilx-book tr.oilx-row-bad td:first-child { box-shadow: inset 3px 0 0 var(--warn); }
.oilx-book tr.oilx-row-wait td { color: var(--label); }
.oilx-in { color: var(--ok); }
.oilx-out { color: var(--warn); }
.oilx-carried { color: var(--pending); font-weight: 600; }
.oilx-wait { font-size: 12px; color: var(--muted); }
.oilx-explain-btn { padding: 4px 10px; font-size: 12px; margin-left: 6px; }
.oilx-book-empty { padding: 24px 8px; color: var(--label); text-align: center; }
.oilx-how { margin: 12px 22px 18px; font-size: 12.5px; color: var(--label); }
.oilx-how summary { cursor: pointer; font-weight: 700; color: var(--ink); }
.oilx-how p { margin: 6px 0; max-width: 900px; }
@media (max-width: 640px) {
  .oilx-stores { grid-template-columns: 1fr; padding: 14px 16px; }
  .oilx-hero { grid-template-columns: 1fr 1fr; }
  .oilx-tank { grid-template-columns: 1fr; gap: 6px; }
  .oilx-panel-head, .oilx-book-kpis div { padding-left: 16px; padding-right: 16px; }
  #oil-book-panel .table-responsive { padding: 0 16px; }
}

/* Oil panels: header actions, the day that opens its dips */
.oilx-head-actions { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.oilx-head-actions .pdo-act { text-decoration: none; }
.oilx-day { all: unset; cursor: pointer; display: flex; flex-direction: column; gap: 1px; }
.oilx-day span { font-size: 11.5px; color: var(--accent-blue); white-space: nowrap; }
.oilx-day:hover strong, .oilx-day:focus-visible strong { text-decoration: underline; }
.oilx-day:focus-visible { outline: 2px solid var(--accent-blue); outline-offset: 2px; border-radius: 3px; }

/* Morning dips sheet */
.mdip-box { max-width: 1180px; }
.mdip-head-right { display: flex; align-items: center; gap: 10px; }
.mdip-head-right label { margin: 0; font-size: 11px; text-transform: uppercase; letter-spacing: .05em; color: var(--muted); font-weight: 700; white-space: nowrap; }
.mdip-head-right input[type=date] { margin: 0; width: auto; }
.mdip-body { padding: 12px 22px 6px; max-height: 66vh; overflow-y: auto; }
.mdip-toolbar { display: flex; justify-content: space-between; align-items: center; gap: 12px; flex-wrap: wrap; margin-bottom: 8px; }
.mdip-toolbar p { margin: 0; max-width: 760px; }
.mdip-group { margin-bottom: 16px; }
.mdip-group-head { display: flex; justify-content: space-between; align-items: baseline; gap: 10px; padding-bottom: 6px; margin-bottom: 6px; border-bottom: 2px solid var(--navy); }
.mdip-group-head h3 { margin: 0; font-size: 14.5px; }
.mdip-group-head span { font-size: 12.5px; color: var(--label); }
.mdip-table { table-layout: fixed; min-width: 860px; }
.mdip-table td { vertical-align: middle; }
.mdip-table input { margin: 0; width: 100%; min-width: 0; padding-left: 6px; padding-right: 6px; text-align: right; font-variant-numeric: tabular-nums; }
.mdip-table tr[data-state="new"] td:first-child { box-shadow: inset 3px 0 0 var(--pending); }
.mdip-table tr[data-state="changed"] td:first-child { box-shadow: inset 3px 0 0 var(--warn); }
.mdip-table tr[data-state="recorded"] td:first-child { box-shadow: inset 3px 0 0 var(--ok); }
.mdip-table tr.mdip-sub td { padding-top: 0; font-size: 11px; color: var(--muted); border-top: 0; }
.mdip-mt strong { font-size: 14px; }
.mdip-foot { align-items: flex-end; }
.mdip-foot-left { display: flex; flex-direction: column; gap: 4px; flex: 1; min-width: 0; }
.mdip-foot-left input { margin: 0; max-width: 560px; }
.mdip-foot-left .bs-error { margin: 0; }
@media (max-width: 760px) {
  .mdip-head-right { flex-wrap: wrap; }
  .mdip-body { padding: 10px 14px; max-height: none; }
}

/* ---- Tanker register (migration 118): two legs, one comparison ---- */
#tab-tanker-register .oilx-panel { margin-bottom: 16px; }
.trx-legs { display: grid; grid-template-columns: 1fr 1fr; gap: 16px; margin-bottom: 16px; align-items: start; }
.trx-legs.trx-one { grid-template-columns: minmax(0, 760px); }
.trx-leg { padding: 0; overflow: hidden; margin: 0; border-top: 4px solid var(--navy); }
.trx-leg-plant { border-top-color: var(--accent-teal); }
.trx-leg-head { display: flex; align-items: center; gap: 12px; padding: 16px 20px 12px; border-bottom: 1px solid var(--border); }
.trx-leg-head h2 { margin: 0; font-size: 17px; }
.trx-leg-icon { width: 34px; height: 34px; border-radius: 50%; display: inline-flex; align-items: center; justify-content: center; background: var(--navy); color: #fff; flex: none; }
.trx-leg-plant .trx-leg-icon { background: var(--accent-teal); }
.trx-leg-icon svg { width: 18px; height: 18px; }
.trx-by { margin-left: auto; font-size: 12px; color: var(--label); background: var(--neutral-bg); padding: 4px 10px; border-radius: var(--radius-full); white-space: nowrap; }
.trx-leg form { padding: 14px 20px 16px; }
.trx-grid { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 2px 14px; }
.trx-grid .trx-span2 { grid-column: 1 / -1; }
.trx-grid input, .trx-grid select { width: 100%; }
.trx-leg-foot { display: flex; justify-content: space-between; align-items: center; gap: 12px; flex-wrap: wrap; margin-top: 10px; padding-top: 12px; border-top: 1px solid var(--border-light); }
.trx-leg-foot button { margin: 0; }
.trx-leg-foot .pdo-hint { max-width: 380px; }
.trx-transit { padding: 12px 20px 4px; background: var(--card-subtle); border-bottom: 1px solid var(--border); }
.trx-transit-head { display: flex; justify-content: space-between; align-items: baseline; margin-bottom: 8px; font-size: 13px; }
.trx-transit-list { display: grid; grid-template-columns: repeat(auto-fill, minmax(200px, 1fr)); gap: 8px; padding-bottom: 10px; max-height: 230px; overflow-y: auto; }
.trx-trip { all: unset; box-sizing: border-box; cursor: pointer; display: flex; flex-direction: column; gap: 2px; padding: 9px 11px; border-radius: var(--radius); background: var(--card); border: 1px solid var(--border); font-size: 12px; }
.trx-trip:hover { border-color: var(--accent-teal); }
.trx-trip:focus-visible { outline: 2px solid var(--accent-teal); outline-offset: 1px; }
.trx-trip.active { border-color: var(--accent-teal); box-shadow: inset 3px 0 0 var(--accent-teal); background: #f0fdfa; }
.trx-trip[disabled] { cursor: not-allowed; opacity: .6; }
.trx-trip-main { display: flex; justify-content: space-between; gap: 8px; }
.trx-trip-main strong { font-size: 14px; }
.trx-trip-main span, .trx-trip-sub { color: var(--muted); }
.trx-empty { margin: 0 0 10px; font-size: 12.5px; color: var(--label); }
.trx-picked { display: flex; justify-content: space-between; align-items: center; gap: 10px; margin-bottom: 10px; padding: 8px 12px; border-radius: var(--radius); background: #f0fdfa; border: 1px solid #99f6e4; font-size: 12.5px; }
.trx-picked .linklike { margin: 0; }
.trx-diff { display: flex; align-items: baseline; gap: 8px; flex-wrap: wrap; margin-top: 8px; padding: 8px 12px; border-radius: var(--radius); font-size: 12.5px; border: 1px solid var(--border); }
.trx-diff strong { font-size: 16px; }
.trx-diff.is-ok { background: var(--ok-bg); border-color: var(--ok-border); }
.trx-diff.is-amber { background: var(--pending-bg); border-color: var(--pending-border); }
.trx-diff.is-red { background: var(--warn-bg); border-color: var(--warn-border); color: var(--warn); }
.trx-filters { display: flex; align-items: center; gap: 10px 16px; flex-wrap: wrap; padding: 14px 22px 4px; }
.trx-filters .date-range-presets, .trx-filters .date-picker { margin: 0; }
.trx-search { flex: 1 1 240px; }
.trx-range { padding: 0 22px; margin: 6px 0; }
.trx-table-wrap { padding: 0 22px 18px; }
.trx-table td { vertical-align: top; }
.trx-table thead .trx-group-row th { font-size: 10.5px; letter-spacing: .08em; padding-top: 7px; padding-bottom: 7px; text-align: center; border-bottom: 1px solid rgba(255,255,255,.12); }
.trx-table thead th.trx-g-ardmore { background: #1f385c; }
.trx-table thead th.trx-g-plant { background: #0f5f5a; }
.trx-table tbody td.trx-g-ardmore { background: rgba(31, 56, 92, .035); }
.trx-table tbody td.trx-g-plant { background: rgba(13, 148, 136, .045); }
.trx-diffbar { display: block; height: 4px; margin-top: 4px; border-radius: var(--radius-full); background: var(--neutral-bg); overflow: hidden; min-width: 60px; }
.trx-diffbar span { display: block; height: 100%; background: var(--ok); }
.trx-diffbar span.amber { background: var(--pending); }
.trx-diffbar span.red { background: var(--warn); }
.trx-actions { white-space: nowrap; }
.trx-actions .pdo-act { padding: 4px 10px; font-size: 12px; }
@media (max-width: 980px) { .trx-legs { grid-template-columns: 1fr; } }
@media (max-width: 560px) { .trx-grid { grid-template-columns: 1fr; } .trx-leg form, .trx-leg-head, .trx-transit { padding-left: 16px; padding-right: 16px; } }
.pdo-input-unit input::placeholder { font-weight: 400; color: #94a3b8; }
.pdo-btn-primary { border-color: var(--navy); }

/* Daily oil book: both locations side by side (the tanker register's table) */
.oilx-book-wrap { padding-top: 14px; }
.oilx-book.trx-table { min-width: 1180px; }
.oilx-book.trx-table th small { font-weight: 500; text-transform: none; letter-spacing: 0; opacity: .8; }
.oilx-res { margin-top: 3px; }
.oilx-res .oilx-explain-btn { margin: 4px 0 0; }
.oilx-book .oilx-day span { color: var(--accent-blue); }

/* Customer Order Register: products per order (2026-10-14). Pack size is a
   coloured tag so 3L and 20L cannot be confused at a glance. */
.co-prod { display: flex; flex-direction: column; gap: 8px; min-width: 0; }
.co-prod-line + .co-prod-line { border-top: 1px dashed var(--border); padding-top: 7px; }
.co-prod-head { display: flex; align-items: center; gap: 6px; min-width: 0; }
.co-prod-size { flex: none; font-size: 10.5px; font-weight: 700; letter-spacing: .02em; padding: 1px 6px; border-radius: var(--radius-full); border: 1px solid var(--border); background: var(--neutral-bg); color: var(--neutral-fg); font-variant-numeric: tabular-nums; }
.co-prod-size.co-prod-size-3l { background: #eff6ff; border-color: #bfdbfe; color: var(--accent-blue-dark); }
.co-prod-size.co-prod-size-20l { background: var(--pending-bg); border-color: var(--pending-border); color: #b45309; }
.co-prod-name { flex: 1 1 auto; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; font-weight: 600; color: var(--ink); }
.co-prod-qty { flex: none; font-variant-numeric: tabular-nums; white-space: nowrap; color: var(--ink); }
.co-prod-qty small { color: var(--muted); font-size: 11px; }
.co-prod-ship { margin-top: 3px; font-size: 12px; }
.co-prod-wrong { margin-top: 4px; font-size: 11.5px; font-weight: 600; color: var(--warn); background: var(--warn-bg); border: 1px solid var(--warn-border); border-radius: var(--radius-sm); padding: 2px 6px; }

/* Release form: a truck leaving with less than its permit authorized. */
.tl-short-load { border: 1px solid var(--pending-border); background: var(--pending-bg); border-radius: 8px; padding: 10px 12px; margin-bottom: 12px; }
.tl-short-load-head { margin: 0 0 8px; font-size: 13px; font-weight: 600; color: #92400e; }
.tl-short-load textarea { width: 100%; margin-bottom: 0; }

/* Stock on Hand by Store: a group header reads as a band, and a line is
   clickable because it opens that line's own ledger. */
.reg-table tr.soh-group-row td { background: #e8eef6; font-weight: 700; color: var(--ink); border-bottom: 1px solid #d5deea; }
.reg-table tr.soh-row { cursor: pointer; }
.reg-table tr.soh-row:hover td { background: var(--row-hover, #f3f7fc); }

/* A rail chip that is waiting on somebody (Stock Take: awaiting approval). */
.chip.chip-warn { border-color: var(--warn); color: var(--warn); font-weight: 650; }
.chip.chip-warn.active { background: var(--warn); color: #fff; }
/* ---------- Sign-off check on the shift logs (migration 120, shift-gate.js) ---------- */
.sgt-panel { margin: 10px 0 4px; padding: 12px 14px; border: 1px solid var(--border); border-radius: var(--radius); background: var(--card-subtle); display: grid; gap: 10px; font-size: 13px; min-width: 0; }
.sgt-head { display: flex; flex-wrap: wrap; gap: 8px 12px; align-items: center; }
.sgt-order { display: flex; flex-wrap: wrap; gap: 4px 12px; align-items: baseline; padding: 8px 10px; border-left: 4px solid var(--ok); background: var(--ok-bg); border-radius: var(--radius-sm); }
.sgt-order.is-none { border-left-color: var(--warn); background: var(--warn-bg); }
.sgt-eyebrow { font-size: 11px; text-transform: uppercase; letter-spacing: .06em; color: var(--muted); }
.sgt-table { width: 100%; min-width: 760px; }
.sgt-table td, .sgt-table th { vertical-align: middle; }
.sgt-table .num { text-align: right; font-variant-numeric: tabular-nums; white-space: nowrap; }
.sgt-table input.sgt-extra { width: 96px; text-align: right; }
.sgt-table select.sgt-reason { min-width: 150px; }
.sgt-table input.sgt-note { width: 140px; margin-top: 4px; }
.sgt-row-bad td { background: var(--warn-bg); }
.sgt-neg { color: var(--warn); font-weight: 600; }
.sgt-facts { display: flex; flex-wrap: wrap; gap: 6px 18px; color: var(--muted); }
.sgt-confirm { display: flex; gap: 8px; align-items: flex-start; font-weight: 600; }
.sgt-confirm input { margin-top: 3px; }
.sgt-problems, .sgt-warnings { margin: 0; padding-left: 18px; display: grid; gap: 4px; }
.sgt-problems li { color: var(--warn); }
.sgt-warnings li { color: var(--pending); }
.sgt-ok { margin: 0; color: var(--ok); font-weight: 600; }
.sgt-problem { margin: 0; color: var(--warn); }

/* ---------- Shift plans and what they need (migration 119, shift-plans.js) ---------- */
.shpl-form { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 10px 14px; align-items: end; margin: 6px 0 12px; }
.shpl-label { display: block; font-size: 12px; font-weight: 600; color: var(--label); margin-bottom: 4px; }
.shpl-checks { display: flex; flex-wrap: wrap; gap: 6px 14px; }
.shpl-check { display: inline-flex; gap: 6px; align-items: center; font-weight: 500; }
.shpl-sub { margin: 16px 0 8px; font-size: 14px; }
.shpl-order { border: 1px solid var(--border); border-radius: var(--radius); padding: 12px 14px; margin: 0 0 12px; background: var(--card-subtle); display: grid; gap: 10px; min-width: 0; }
.shpl-order-head { display: flex; flex-wrap: wrap; justify-content: space-between; gap: 8px 18px; }
.shpl-plans { font-size: 12.5px; color: var(--muted); text-align: right; }
.shpl-line { display: grid; gap: 6px; min-width: 0; }
.shpl-line-head { display: flex; flex-wrap: wrap; gap: 6px 12px; align-items: center; }
.shpl-line-head .shpl-issue-btn { margin-left: auto; }
.shpl-table { min-width: 720px; }
.shpl-row-todo td { background: var(--pending-bg); }
.shpl-bad { color: var(--warn); font-weight: 600; }
.shpl-facts { display: flex; flex-wrap: wrap; gap: 6px 18px; font-size: 12.5px; }
.shpl-done { margin: 0; color: var(--ok); font-weight: 600; }
.shpl-oil { display: grid; gap: 4px; padding: 10px 12px; border-left: 4px solid var(--ok); background: var(--ok-bg); border-radius: var(--radius-sm); }
.shpl-oil.is-short { border-left-color: var(--warn); background: var(--warn-bg); }
/* ---------- Dashboard "Today" (shift-plans.js shplLoadToday) ---------- */
.tdy-kpis { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 10px; margin: 4px 0 16px; }
.tdy-kpi { display: grid; gap: 2px; padding: 12px 14px; border: 1px solid var(--border); border-left: 4px solid var(--border); border-radius: var(--radius); background: var(--card); min-width: 0; }
.tdy-kpi.is-ok { border-left-color: var(--ok); }
.tdy-kpi.is-pending { border-left-color: var(--pending); }
.tdy-kpi.is-warn { border-left-color: var(--warn); }
.tdy-kpi-label { font-size: 11.5px; font-weight: 600; letter-spacing: .04em; text-transform: uppercase; color: var(--label); }
.tdy-kpi strong { font-family: var(--font-display); font-size: 24px; line-height: 1.15; color: var(--ink); font-variant-numeric: tabular-nums; }
.tdy-kpi-sub { font-size: 12px; color: var(--muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }

.tdy-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(380px, 1fr)); gap: 14px; margin-bottom: 14px; }
.tdy-card.is-wide { grid-column: 1 / -1; }
.tdy-card.is-wide .tdy-item { max-width: 52ch; }
.tdy-card { display: flex; flex-direction: column; border: 1px solid var(--border); border-radius: var(--radius-lg); background: var(--card); min-width: 0; overflow: hidden; }
.tdy-card > header { display: flex; align-items: center; justify-content: space-between; gap: 10px; padding: 10px 14px; border-bottom: 1px solid var(--border-light); background: var(--card-subtle); }
.tdy-card h3 { margin: 0; font-size: 13.5px; font-weight: 600; color: var(--ink); }
.tdy-card-body { padding: 4px 14px 10px; flex: 1; min-width: 0; }
.tdy-card > footer { padding: 8px 14px; border-top: 1px solid var(--border-light); display: flex; justify-content: flex-end; }
.tdy-action { background: none; border: 0; padding: 0; color: var(--accent-blue); font-weight: 600; font-size: 12.5px; cursor: pointer; }
.tdy-action:hover { color: var(--accent-blue-dark); text-decoration: underline; }

.tdy-table { font-size: 12.5px; }
.tdy-table th { font-size: 11px; }
.tdy-table td { vertical-align: top; }
.tdy-cell-act { text-align: right; white-space: nowrap; width: 1%; }
.tdy-item { display: inline-block; max-width: 30ch; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; vertical-align: bottom; }
.tdy-wrap { white-space: normal; }
.tdy-empty { margin: 12px 0 4px; color: var(--ok); font-weight: 600; font-size: 13px; }
.tdy-foot-note { margin: 8px 0 0; font-size: 12px; color: var(--muted); }
.tdy-sub-head { margin: 12px 0 6px; font-size: 11px; font-weight: 600; letter-spacing: .04em; text-transform: uppercase; color: var(--label); }
.tdy-chips { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: 6px; }
.tdy-chips li { font-size: 12px; padding: 3px 8px; border-radius: var(--radius-full); background: var(--neutral-bg); color: var(--neutral-fg); }
.tdy-shifts { display: flex; flex-wrap: wrap; gap: 4px; }
.tdy-shift { font-size: 11.5px; padding: 2px 7px; border-radius: var(--radius-sm); background: var(--neutral-bg); color: var(--neutral-fg); white-space: nowrap; font-variant-numeric: tabular-nums; }

.tdy-figs { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 10px; padding-top: 10px; }
.tdy-figs > div { display: grid; gap: 2px; padding: 10px 12px; border-radius: var(--radius); background: var(--card-subtle); border: 1px solid var(--border-light); min-width: 0; }
.tdy-figs span { font-size: 11.5px; color: var(--label); font-weight: 600; }
.tdy-figs strong { font-family: var(--font-display); font-size: 19px; font-variant-numeric: tabular-nums; color: var(--ink); }
.tdy-figs em { font-style: normal; font-size: 11.5px; color: var(--muted); }
.tdy-figs .is-good { background: var(--ok-bg); border-color: var(--ok-border); }
.tdy-figs .is-good strong { color: var(--ok); }
.tdy-figs .is-bad { background: var(--warn-bg); border-color: var(--warn-border); }
.tdy-figs .is-bad strong { color: var(--warn); }


@media (max-width: 640px) {
  .tdy-kpis { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .tdy-kpi { padding: 10px 12px; }
  .tdy-kpi strong { font-size: 20px; }
  .tdy-grid { grid-template-columns: minmax(0, 1fr); }
  .tdy-figs { grid-template-columns: minmax(0, 1fr); }
  .tdy-item { max-width: 18ch; }
}

/* ---------- Truck Loading register: truck card (2026-10-14) ----------
   One truck = one card with four readable columns (truck, order, quantity,
   actions) over a footer with the five-step progress line and WHO acts next.
   The left edge carries the state colour so the yard reads it at a glance. */
.tl-band.tlx-band {
  grid-template-columns: minmax(0, 1fr) auto auto;
  padding: 14px 20px;
}
.tlx-band .tl-band-cust { font-size: 16px; }
.tlx-band-meta { font-size: 12px; color: var(--muted); font-variant-numeric: tabular-nums; }

.tl-row.tlx {
  grid-template-columns: minmax(150px, 1fr) minmax(170px, 1.1fr) minmax(230px, 1.5fr) 420px;
  grid-template-areas: "truck order qty actions" "foot foot foot foot" "rem rem rem rem";
  align-items: start;
  gap: 12px 22px;
  padding: 16px 20px 14px 17px;
  border-left: 4px solid var(--border);
}
.tl-row.tlx-hold { border-left-color: var(--warn); }
.tl-row.tlx-wait { border-left-color: var(--pending); }
.tl-row.tlx-go   { border-left-color: var(--ok); }
.tl-row.tlx-idle { border-left-color: #94a3b8; }
.tl-row.tlx-done { border-left-color: var(--border); }
.tl-row.tlx.tl-row-next { border-left-width: 4px; }

.tlx-truck { grid-area: truck; display: flex; flex-direction: column; gap: 6px; min-width: 0; }
.tlx-order { grid-area: order; display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.tlx-qty   { grid-area: qty;   display: flex; flex-direction: column; gap: 3px; min-width: 0; }
.tl-row.tlx .tl-row-actions { grid-area: actions; align-self: center; }
.tlx .tl-truck-plate { font-size: 17px; padding: 5px 12px; border-width: 2px; width: fit-content; }
.tlx-chips { display: flex; flex-wrap: wrap; gap: 6px; }

.tlx-k {
  font-size: 10px; font-weight: 700; letter-spacing: .07em;
  text-transform: uppercase; color: var(--muted);
}
.tlx-k .tlx-dim { text-transform: none; letter-spacing: 0; font-weight: 500; }
.tlx-v { font-size: 15px; font-weight: 700; color: var(--ink); }
.tlx-mono { font-family: var(--font-mono); font-size: 14px; }
.tlx-dim { color: var(--muted); font-weight: 500; }
.tlx-sub { font-size: 12px; color: var(--muted); line-height: 1.35; font-variant-numeric: tabular-nums; }
.tlx-sub b { color: var(--ink); font-weight: 600; }
.tlx-missing {
  color: var(--warn); background: var(--warn-bg); border: 1px solid var(--warn-border);
  padding: 1px 8px; border-radius: 4px; width: fit-content; font-size: 13px;
}

.tlx-big {
  font-family: var(--font-display); font-size: 26px; font-weight: 700; line-height: 1.05;
  color: var(--ink); font-variant-numeric: tabular-nums; letter-spacing: -0.01em;
}
.tlx-of { color: var(--muted); font-weight: 600; }
.tlx-unit { font-size: 13px; font-weight: 600; color: var(--label); letter-spacing: .02em; }
.tlx-bar {
  display: block; height: 8px; border-radius: var(--radius-full);
  background: #e2e8f0; overflow: hidden; margin: 3px 0 1px; max-width: 360px;
}
.tlx-bar > span { display: block; height: 100%; background: var(--accent-blue); border-radius: inherit; }
.tlx-go .tlx-bar > span { background: var(--ok); }

.tlx-foot {
  grid-area: foot; display: flex; align-items: center; gap: 12px 24px; flex-wrap: wrap;
  border-top: 1px dashed var(--border); padding-top: 11px;
}
.tlx-steps { display: flex; list-style: none; margin: 0; padding: 0; gap: 0; flex: 0 0 auto; }
.tlx-steps li {
  position: relative; display: flex; align-items: center; gap: 6px;
  font-size: 12px; font-weight: 600; color: #94a3b8; padding-right: 26px;
}
.tlx-steps li:not(:last-child)::after {
  content: ""; position: absolute; right: 6px; top: 50%; width: 14px; height: 2px;
  background: #e2e8f0;
}
.tlx-dot {
  width: 12px; height: 12px; border-radius: 50%;
  border: 2px solid #cbd5e1; background: #fff; flex: 0 0 auto;
}
.tlx-steps li.is-done { color: var(--ok); }
.tlx-steps li.is-done .tlx-dot { background: var(--ok); border-color: var(--ok); }
.tlx-steps li.is-done:not(:last-child)::after { background: var(--ok-border); }
.tlx-steps li.is-now { color: var(--ink); }
.tlx-hold .tlx-steps li.is-now .tlx-dot { border-color: var(--warn); box-shadow: 0 0 0 3px var(--warn-bg); }
.tlx-wait .tlx-steps li.is-now .tlx-dot { border-color: var(--pending); box-shadow: 0 0 0 3px var(--pending-bg); }
.tlx-go .tlx-steps li.is-now .tlx-dot,
.tlx-idle .tlx-steps li.is-now .tlx-dot { border-color: var(--ok); box-shadow: 0 0 0 3px var(--ok-bg); }
.tlx-steps-void li { color: #cbd5e1; text-decoration: line-through; }

.tlx-next { display: flex; align-items: baseline; gap: 10px; flex: 1 1 320px; min-width: 0; }
.tlx-who {
  flex: 0 0 auto; font-size: 11px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase;
  padding: 3px 9px; border-radius: var(--radius-full);
  background: var(--neutral-bg); color: var(--neutral-fg); border: 1px solid var(--border);
}
.tlx-next-hold .tlx-who { background: var(--warn-bg); color: var(--warn); border-color: var(--warn-border); }
.tlx-next-wait .tlx-who { background: var(--pending-bg); color: var(--pending); border-color: var(--pending-border); }
.tlx-next-go .tlx-who   { background: var(--ok-bg); color: var(--ok); border-color: var(--ok-border); }
.tlx-next-text { font-size: 13px; color: var(--ink); line-height: 1.4; }
.tlx-next-hold .tlx-next-text { color: #7f1d1d; }
.tlx-remarks { grid-area: rem; }

@media (max-width: 1100px) {
  .tl-row.tlx {
    grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
    grid-template-areas: "truck order" "qty qty" "actions actions" "foot foot" "rem rem";
  }
  .tl-row.tlx .tl-row-actions { justify-content: flex-start; grid-column: auto; }
}
@media (max-width: 560px) {
  .tl-row.tlx { grid-template-columns: 1fr; grid-template-areas: "truck" "order" "qty" "actions" "foot" "rem"; }
  .tl-band.tlx-band { grid-template-columns: 1fr; }
  .tlx-steps li { padding-right: 14px; font-size: 11px; }
  .tlx-steps li:not(:last-child)::after { display: none; }
}
/* ---------- ERP document form (2026-10-14) ----------
   One layout for every document form: head (icon, eyebrow, title, state),
   body (main column: party + document fields; side column: delivery and
   terms), lines, then a foot with the note, the action and the totals.
   Purchase order first; customer order, GRN and inventory documents reuse it. */
.erx-card { padding: 0; overflow: hidden; border-top: 4px solid var(--navy); }
.erx-card > form, .erx-card > .erx-banner { padding: 0 22px; }
.erx-head { display: flex; align-items: center; gap: 12px; padding: 16px 22px 12px; margin: 0 0 4px; border-bottom: 1px solid var(--border); }
.erx-head h2 { margin: 0; font-size: 18px; }
.erx-icon { width: 36px; height: 36px; flex: none; border-radius: var(--radius); background: var(--navy); color: #fff; display: inline-flex; align-items: center; justify-content: center; }
.erx-icon svg { width: 19px; height: 19px; }
.erx-title { flex: 1 1 auto; min-width: 0; }
.erx-state { font-size: 12px; font-weight: 600; color: var(--label); background: var(--neutral-bg); border: 1px solid var(--border); padding: 4px 10px; border-radius: var(--radius-full); white-space: nowrap; }
.erx-banner { margin: 12px 22px 0; padding: 12px 14px !important; border-radius: var(--radius); background: var(--pending-bg); border: 1px solid var(--pending-border); }
.erx-banner p { margin: 0 0 6px; font-size: 13px; }
.erx-body { display: grid; grid-template-columns: minmax(0, 2fr) minmax(260px, 1fr); gap: 0 28px; padding-top: 6px; }
.erx-side { border-left: 1px solid var(--border-light); padding-left: 24px; }
.erx-section-title { display: flex; align-items: center; gap: 10px; margin: 14px 0 4px; font-size: 11px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: var(--muted); }
.erx-section-title::after { content: ""; flex: 1; height: 1px; background: var(--border-light); }
.erx-fields { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0 14px; }
.erx-fields-1 { grid-template-columns: 1fr; }
.erx-fields .erx-span2 { grid-column: 1 / -1; }
.erx-fields input, .erx-fields select { width: 100%; }
.erx-party { margin: 4px 0 6px; padding: 12px 14px; border-radius: var(--radius); background: var(--card-subtle); border: 1px solid var(--border); }
.erx-party-main { display: flex; align-items: baseline; gap: 10px; flex-wrap: wrap; margin-bottom: 8px; }
.erx-party-main strong { font-size: 15px; }
.erx-party-main span:last-child:not(.erx-party-code) { font-size: 12px; color: var(--muted); }
.erx-party-code { font-family: var(--font-mono); font-size: 11.5px; font-weight: 600; color: var(--accent-blue); background: #eff6ff; border: 1px solid #bfdbfe; padding: 1px 7px; border-radius: 4px; }
.erx-party-grid { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 6px 14px; font-size: 13px; }
.erx-party-grid span { display: block; font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.erx-lines-title { margin-top: 18px; }
.erx-lines { width: 100%; }
.erx-lines thead th { background: var(--navy); color: #fff; font-size: 11px; letter-spacing: .06em; text-transform: uppercase; padding: 9px 10px; }
.erx-lines thead th.num, .erx-lines td.num { text-align: right; }
.erx-lines td { vertical-align: top; padding: 8px 10px; border-bottom: 1px solid var(--border-light); }
.erx-lines input, .erx-lines select { width: 100%; margin: 0; }
.erx-lines .erx-num { text-align: right; font-variant-numeric: tabular-nums; }
.erx-lines .po-item-line-total { font-weight: 700; font-variant-numeric: tabular-nums; padding-top: 16px; }
.erx-lines .po-line-no { color: var(--muted); font-weight: 600; padding-top: 16px; }
.erx-add { margin: 10px 0 0; }
.erx-foot { display: flex; justify-content: space-between; align-items: flex-end; gap: 18px; flex-wrap: wrap; margin-top: 14px; padding: 14px 0 20px; border-top: 1px solid var(--border-light); }
.erx-foot-note { display: flex; flex-direction: column; gap: 10px; max-width: 520px; }
.erx-foot-actions { display: flex; gap: 10px; flex-wrap: wrap; }
.erx-foot-actions button { margin: 0; }
.erx-totals { min-width: 280px; }
.erx-totals em { font-style: normal; font-weight: 500; color: var(--muted); font-size: 12px; }
.erx-approval { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; margin: 0 0 14px; padding: 10px 14px; border-radius: var(--radius); font-size: 13px; }
.erx-approval.is-draft { background: var(--pending-bg); border: 1px solid var(--pending-border); }
.erx-approval.is-approved { background: var(--ok-bg); border: 1px solid var(--ok-border); }
.erx-approval input { margin: 0; width: 200px; }
.erx-approval button { margin: 0; }
@media (max-width: 980px) {
  .erx-body { grid-template-columns: 1fr; }
  .erx-side { border-left: 0; padding-left: 0; }
  .erx-party-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (max-width: 560px) {
  .erx-fields { grid-template-columns: 1fr; }
  .erx-card > form, .erx-card > .erx-banner { padding: 0 16px; }
  .erx-head { padding-left: 16px; padding-right: 16px; }
}
/* ERP form: variants used by the GRN, Issue to Production and gate forms. */
.erx-card.erx-card { margin-bottom: 16px; }
form.erx-card > .erx-inner { padding: 0 22px; }
.erx-fields-3 { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.erx-fields-4 { grid-template-columns: repeat(4, minmax(0, 1fr)); }
.erx-intro { margin: 10px 22px 0; max-width: 900px; }
.erx-foot-simple { align-items: center; padding-bottom: 18px; }
.erx-table-pad { padding: 0 22px 18px; margin-top: 6px; }
.erx-banner-panel { border-left: 4px solid var(--pending); background: var(--pending-bg); }
.erx-po-banner { margin: 8px 0; padding: 8px 12px; border-radius: var(--radius); background: #eff6ff; border: 1px solid #bfdbfe; }
.erx-po-banner p { margin: 0; }
.erx-lines td input[type="number"] { text-align: right; font-variant-numeric: tabular-nums; }
@media (max-width: 980px) { .erx-fields-3, .erx-fields-4 { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
@media (max-width: 560px) { .erx-fields-3, .erx-fields-4 { grid-template-columns: 1fr; } form.erx-card > .erx-inner, .erx-table-pad { padding-left: 16px; padding-right: 16px; } }

/* Stock transfer / adjustment dialogs in the same look: navy top edge,
   step heads as ERP section titles, navy line-table header. */
.inv-doc-modal { border-top: 4px solid var(--navy); }
.inv-doc-modal .inv-step-head { font-size: 11px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: var(--muted); }
.inv-doc-modal .inv-step-num { background: var(--navy); color: #fff; }
.inv-doc-modal .inv-modal-actions button[type="submit"] { background: var(--navy); border-color: var(--navy); }
.inv-doc-modal .inv-modal-actions button[type="submit"]:hover { background: var(--navy-light); }
/* Customer order builder inside the ERP card: its body carries the padding
   (the form sits one level down), and the old builder chrome steps aside. */
.erx-card > #co-builder-body { padding: 0 22px; }
.erx-card > #co-builder-body > .erx-banner { margin: 12px 0 0; }
.erx-card .co-builder-header.erx-head { background: transparent; padding: 16px 22px 12px; border-radius: 0; }
.erx-card .co-builder-header.erx-head h2 { font-size: 18px; }
.erx-foot .co-send-row { flex-direction: column; align-items: stretch; justify-content: flex-start; margin-top: 0; }
.erx-foot .co-send-sign { flex: 0 0 auto; max-width: 360px; }
.erx-body, .erx-main, .erx-side { min-width: 0; }
/* ---------- Shared register date cell (2026-10-14) ----------
   regDateHtml() in core.js: day in bold, month + year beside, weekday under.
   Used by the dosing registers, the Tanker Register and the daily oil book. */
.reg-date { display: inline-flex; align-items: center; gap: 7px; white-space: nowrap; line-height: 1.1; }
.reg-date-d { font-family: var(--font-display); font-size: 20px; font-weight: 700; color: var(--ink); min-width: 22px; text-align: right; font-variant-numeric: tabular-nums; }
.reg-date-my { display: flex; flex-direction: column; font-size: 12px; font-weight: 600; color: var(--label); }
.reg-date-my em { font-style: normal; font-weight: 500; font-size: 11px; color: var(--muted); }
.oilx-day .reg-date-d { color: var(--ink); }
.oilx-day:hover .reg-date-d, .oilx-day:focus-visible .reg-date-d { text-decoration: underline; }
.oilx-day > span:last-child { margin-top: 3px; }

/* ---------- Vitamin / TBHQ dosing (2026-10-14): Tanker Register look ---------- */
.dsx-leg { margin-bottom: 16px; }
.dsx-grid { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 2px 14px; }
.dsx-grid .dsx-span2 { grid-column: span 2; }
.dsx-grid .dsx-span4 { grid-column: 1 / -1; }
.dsx-grid input, .dsx-grid select { width: 100%; }
.dsx-calc {
  display: flex; align-items: baseline; gap: 10px; flex-wrap: wrap; align-self: end;
  margin: 6px 0 10px; padding: 10px 14px; border-radius: var(--radius);
  background: var(--ok-bg); border: 1px solid var(--ok-border);
}
.dsx-calc-k { font-size: 11px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--ok); }
.dsx-calc strong { font-family: var(--font-display); font-size: 22px; color: var(--ink); font-variant-numeric: tabular-nums; }
.dsx-calc-sub { font-size: 12px; color: var(--muted); }
.dsx-sign { display: flex; gap: 8px; align-items: center; flex-wrap: wrap; }
.dsx-sign input { margin: 0; width: 230px; }
.dsx-table td.num { font-variant-numeric: tabular-nums; white-space: nowrap; }
.dsx-corrected { margin-top: 4px; font-size: 11.5px; color: var(--pending); font-weight: 600; }
.dsx-corrected span { display: block; font-weight: 400; color: var(--label); max-width: 220px; white-space: normal; }
.dsx-modal { max-width: 720px; }
.dsx-modal .dsx-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
@media (max-width: 900px) {
  .dsx-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (max-width: 560px) {
  .dsx-grid, .dsx-modal .dsx-grid { grid-template-columns: 1fr; }
  .dsx-grid .dsx-span2 { grid-column: auto; }
  .dsx-sign input { width: 100%; }
}

/* Line Stock: laid out like the stock transfer form, one line at a time */
.lm-grid { display: block; }
.lm-doc .inv-step:first-of-type { padding-top: 4px; }
.lm-route { display: grid; grid-template-columns: minmax(220px, 1.4fr) minmax(120px, .7fr) minmax(170px, 1fr) auto; align-items: end; gap: 12px; }
.lm-route select { margin-bottom: 0; }
.lm-static { display: flex; align-items: center; min-height: 40px; padding: 0 12px; border: 1px solid var(--border); border-radius: var(--radius); background: var(--card-subtle); font-size: 14px; font-weight: 600; color: var(--ink); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.lm-static.is-stale { color: var(--warn); border-color: var(--warn); background: var(--warn-bg, #fff5f3); }
.lm-route-actions { display: flex; gap: 8px; flex-wrap: wrap; justify-content: flex-end; }
.lm-route-actions button { margin: 0; }
.lm-lines td { vertical-align: middle; }
.lm-lines .lm-name { margin-bottom: 2px; }
.lm-lines .lm-onhand { font-size: 16px; }
.lm-row-bad > td { background: var(--warn-bg, #fff5f3); }
.lm-level-cell { min-width: 150px; white-space: nowrap; }
.lm-level-cell span { display: inline-block; width: 38px; text-align: right; font-size: 12px; color: var(--muted); font-variant-numeric: tabular-nums; vertical-align: middle; }
.lm-level { display: inline-block; vertical-align: middle; width: calc(100% - 44px); height: 8px; border-radius: 4px; background: var(--neutral-bg); overflow: hidden; }
.lm-level i { display: block; height: 100%; border-radius: 4px; background: var(--ok); }
.lm-level.is-low i { background: var(--pending); }
.lm-level.is-bad i { background: var(--warn); }
.lm-track-cell { text-align: right; white-space: nowrap; width: 1%; }
.lm-trail-row > td { background: var(--card-subtle); padding: 8px 14px 14px !important; }
.lm-trail { width: 100%; font-size: 12.5px; border-collapse: collapse; }
.lm-trail th { text-align: left; font-size: 10.5px; letter-spacing: .05em; text-transform: uppercase; color: var(--label); padding: 6px 10px; border-bottom: 1px solid var(--border-light); }
.lm-trail td { padding: 6px 10px; border-bottom: 1px solid var(--border-light); vertical-align: top; }
.lm-trail .num, .lm-trail th.num { text-align: right; font-variant-numeric: tabular-nums; }
.lm-trail-open td { font-weight: 600; }
.lm-history > summary { cursor: pointer; font-family: var(--font-display); font-size: 16px; font-weight: 700; display: flex; align-items: center; gap: 10px; list-style: none; }
.lm-history > summary::-webkit-details-marker { display: none; }
.lm-history > summary::before { content: "\25B8"; color: var(--muted); }
.lm-history[open] > summary::before { content: "\25BE"; }
.lm-history[open] > summary { margin-bottom: 12px; }
#lc-badge:not(:empty) { font-family: var(--font-sans); font-size: 11px; font-weight: 700; color: var(--pending); background: var(--pending-bg, #fff7e6); padding: 2px 9px; border-radius: var(--radius-full); }
@media (max-width: 900px) { .lm-route { grid-template-columns: 1fr 1fr; } .lm-route-actions { grid-column: 1 / -1; justify-content: flex-start; } }
@media (max-width: 560px) { .lm-route { grid-template-columns: 1fr; } }

/* ===================== Shift logs: operator's console (2026-10-21) =====================
   Filling Line Log + Blowing Shift Log. A live board on top (shift-board.js),
   a sticky step rail, and one card per step whose edge says done / up next /
   needs attention. Big targets and big numbers: these are typed on the floor. */
.ops-form-code { font-family: var(--font-mono); font-size: 11px; color: var(--muted); letter-spacing: .02em; margin-top: 2px; }
.ops-log .lu-panel-title h2 { margin: 0; }

.ops-edit-banner {
  margin: 0 0 16px; padding: 12px 16px; border-radius: 10px;
  background: var(--pending-bg); border: 1px solid var(--pending-border); border-left: 4px solid var(--pending);
}
.ops-edit-banner p { margin: 0 0 8px; color: #92400e; font-weight: 600; }
.ops-edit-banner input { margin-bottom: 0; }

/* --- Live board --- */
.ops-board {
  position: relative; overflow: hidden;
  display: grid; grid-template-columns: minmax(200px, 1.3fr) auto repeat(3, minmax(120px, 1fr));
  gap: 18px 22px; align-items: center;
  padding: 20px 22px 16px; margin: 0 0 14px;
  border-radius: 14px; color: #fff;
  background:
    radial-gradient(420px 180px at 100% 0%, rgba(217, 34, 24, .30), transparent 70%),
    radial-gradient(360px 160px at 0% 100%, rgba(13, 148, 136, .22), transparent 70%),
    linear-gradient(135deg, var(--navy) 0%, var(--navy-light) 100%);
  box-shadow: 0 10px 24px -12px rgba(14, 27, 46, .55);
}
.ops-board::after {
  content: ""; position: absolute; inset: 0; pointer-events: none;
  background-image: linear-gradient(rgba(255,255,255,.035) 1px, transparent 1px), linear-gradient(90deg, rgba(255,255,255,.035) 1px, transparent 1px);
  background-size: 22px 22px;
}
.ops-board > * { position: relative; z-index: 1; min-width: 0; }
.ops-board-ident { display: flex; flex-direction: column; gap: 4px; }
.ops-eyebrow { display: inline-flex; align-items: center; gap: 7px; font-size: 10.5px; font-weight: 700; letter-spacing: .14em; text-transform: uppercase; color: #9fb3cf; }
.ops-pulse { width: 8px; height: 8px; border-radius: 50%; background: #34d399; animation: ops-pulse 2s infinite; }
@keyframes ops-pulse { 0% { box-shadow: 0 0 0 0 rgba(52,211,153,.55); } 70% { box-shadow: 0 0 0 9px rgba(52,211,153,0); } 100% { box-shadow: 0 0 0 0 rgba(52,211,153,0); } }
@media (prefers-reduced-motion: reduce) { .ops-pulse { animation: none; } }
.ops-board-title { font-family: var(--font-display); font-size: 21px; line-height: 1.2; font-weight: 700; overflow-wrap: anywhere; }
.ops-board-sub { font-size: 12.5px; color: #b8c6da; overflow-wrap: anywhere; }

.ops-kpi { display: flex; flex-direction: column; gap: 2px; padding-left: 16px; border-left: 1px solid rgba(255,255,255,.12); }
.ops-kpi-label { font-size: 10.5px; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; color: #9fb3cf; }
.ops-kpi-value { font-family: var(--font-display); font-size: 32px; line-height: 1.05; font-weight: 700; font-variant-numeric: tabular-nums; }
.ops-kpi-value.is-bad { color: #fca5a5; }
.ops-kpi-sub { font-size: 11.5px; color: #b8c6da; }

.ops-kpi-ring { position: relative; width: 92px; height: 92px; padding: 0; border: 0; justify-content: center; align-items: center; }
.ops-ring { position: absolute; inset: 0; width: 100%; height: 100%; transform: rotate(-90deg); }
.ops-ring circle { fill: none; stroke-width: 7; }
.ops-ring-track { stroke: rgba(255,255,255,.12); }
.ops-ring-fill { stroke: #94a3b8; stroke-linecap: round; transition: stroke-dashoffset .5s var(--ease-out), stroke .3s; stroke-dasharray: 207.3; stroke-dashoffset: 207.3; }
.ops-kpi-ring.is-met .ops-ring-fill { stroke: #34d399; }
.ops-kpi-ring.is-under .ops-ring-fill { stroke: #fbbf24; }
.ops-kpi-ring.is-stalled .ops-ring-fill { stroke: #f87171; }
.ops-ring-label { display: flex; flex-direction: column; align-items: center; line-height: 1.1; }
.ops-ring-label strong { font-family: var(--font-display); font-size: 20px; font-variant-numeric: tabular-nums; }
.ops-ring-label span { font-size: 8.5px; letter-spacing: .04em; text-transform: uppercase; color: #9fb3cf; margin-top: 2px; }

/* Hour-by-hour bars (filling) */
.ops-strip { grid-column: 1 / -1; display: flex; align-items: flex-end; gap: 5px; height: 70px; padding-top: 10px; border-top: 1px solid rgba(255,255,255,.1); }
.ops-strip-bar { flex: 1 1 0; max-width: 96px; height: 100%; display: flex; flex-direction: column; justify-content: flex-end; align-items: stretch; gap: 3px; cursor: default; }
.ops-strip-bar i { display: block; border-radius: 4px 4px 2px 2px; background: rgba(255,255,255,.18); transition: height .4s var(--ease-out); min-height: 4px; }
.ops-strip-bar b { font-size: 10px; font-weight: 600; color: #9fb3cf; text-align: center; font-family: var(--font-mono); }
.ops-strip-bar.is-met i { background: linear-gradient(180deg, #6ee7b7, #10b981); }
.ops-strip-bar.is-under i { background: linear-gradient(180deg, #fde68a, #f59e0b); }
.ops-strip-bar.is-stalled i { background: linear-gradient(180deg, #fca5a5, #ef4444); }
.ops-strip-bar.is-empty i { background: repeating-linear-gradient(45deg, rgba(255,255,255,.14) 0 3px, transparent 3px 6px); }
.ops-strip-empty { align-self: center; font-size: 12px; color: #9fb3cf; }

/* Good vs rejected (blowing) */
.ops-split { grid-column: 1 / -1; display: flex; height: 10px; border-radius: var(--radius-full); overflow: hidden; background: rgba(255,255,255,.12); }
.ops-split-good { background: linear-gradient(90deg, #10b981, #34d399); transition: flex .4s var(--ease-out); }
.ops-split-bad { background: linear-gradient(90deg, #f87171, #ef4444); transition: flex .4s var(--ease-out); }

/* --- Sticky step rail --- */
.ops-rail {
  position: sticky; top: 8px; z-index: 6;
  display: flex; align-items: center; gap: 6px; flex-wrap: nowrap; overflow-x: auto;
  padding: 7px 8px 9px; margin: 0 0 6px;
  border: 1px solid var(--border); border-radius: 16px; scrollbar-width: none;
  background: rgba(255,255,255,.94); backdrop-filter: blur(8px);
  box-shadow: var(--shadow-md);
}
.ops-rail::before {
  content: ""; position: absolute; left: 16px; bottom: 3px; height: 3px; border-radius: 3px;
  width: calc((100% - 32px) * var(--sb-progress-n, 0));
  background: linear-gradient(90deg, var(--ok), #34d399); transition: width .4s var(--ease-out);
}
.ops-rail::-webkit-scrollbar { display: none; }
button.ops-rail-step {
  display: inline-flex; align-items: center; gap: 8px; flex-shrink: 0;
  padding: 6px 14px 6px 6px; border-radius: var(--radius-full);
  background: transparent; border: 1px solid transparent; box-shadow: none;
  color: var(--label); font-size: 13px; font-weight: 600;
}
button.ops-rail-step:hover { background: var(--neutral-bg); box-shadow: none; }
.ops-rail-dot {
  width: 26px; height: 26px; border-radius: 50%; display: inline-flex; align-items: center; justify-content: center;
  font-size: 12px; font-weight: 700; background: var(--neutral-bg); color: var(--label); border: 1px solid var(--border);
}
button.ops-rail-step.is-current { background: var(--brand-tint); border-color: var(--brand-tint-border); color: var(--brand-dark); }
.ops-rail-step.is-current .ops-rail-dot { background: var(--brand); border-color: var(--brand); color: #fff; box-shadow: 0 0 0 3px rgba(217,34,24,.15); }
button.ops-rail-step.is-done { color: var(--ok); }
.ops-rail-step.is-done .ops-rail-dot { background: var(--ok); border-color: var(--ok); color: #fff; font-size: 0; }
.ops-rail-step.is-done .ops-rail-dot::before { content: "\2713"; font-size: 13px; }
button.ops-rail-step.is-bad { color: var(--warn); }
.ops-rail-step.is-bad .ops-rail-dot { background: var(--warn); border-color: var(--warn); color: #fff; font-size: 0; }
.ops-rail-step.is-bad .ops-rail-dot::before { content: "!"; font-size: 13px; }
.ops-rail-mini { margin-left: auto; padding: 0 10px 0 14px; font-size: 12px; color: var(--muted); white-space: nowrap; font-variant-numeric: tabular-nums; }
.ops-rail-mini strong { color: var(--ink); font-size: 13px; }

/* --- Step cards --- */
.ops-step {
  position: relative; margin-top: 16px; padding: 18px 20px 14px;
  border: 1px solid var(--border); border-radius: 12px; background: var(--card);
  box-shadow: var(--shadow-sm); scroll-margin-top: 72px;
  transition: border-color .2s, box-shadow .2s;
}
.ops-step::before { content: ""; position: absolute; left: -1px; top: 14px; bottom: 14px; width: 4px; border-radius: 0 4px 4px 0; background: var(--border); transition: background .2s; }
.ops-step.is-current { border-color: #f5c2bf; box-shadow: 0 6px 18px -10px rgba(217,34,24,.35); }
.ops-step.is-current::before { background: var(--brand); }
.ops-step.is-done::before { background: var(--ok); }
.ops-step.is-bad::before { background: var(--warn); }
.ops-step-head { display: flex; align-items: center; gap: 14px; margin-bottom: 16px; }
.ops-step-num {
  width: 34px; height: 34px; border-radius: 10px; flex-shrink: 0;
  display: flex; align-items: center; justify-content: center;
  font-family: var(--font-display); font-size: 16px; font-weight: 700;
  background: var(--neutral-bg); color: var(--label); border: 1px solid var(--border);
}
.ops-step.is-current .ops-step-num { background: linear-gradient(135deg, #e5281f, #b3160e); color: #fff; border-color: transparent; box-shadow: 0 2px 6px rgba(217,34,24,.3); }
.ops-step.is-done .ops-step-num { background: var(--ok-bg); color: var(--ok); border-color: var(--ok-border); }
.ops-step.is-bad .ops-step-num { background: var(--warn-bg); color: var(--warn); border-color: var(--warn-border); }
.ops-step-text { flex: 1; min-width: 0; }
.ops-step-title { font-family: var(--font-display); font-size: 17px; font-weight: 700; color: var(--ink); line-height: 1.2; }
.ops-step-sub { font-size: 12.5px; color: var(--muted); margin-top: 2px; }
.ops-step-state:not(:empty) { flex-shrink: 0; font-size: 11px; font-weight: 700; letter-spacing: .04em; text-transform: uppercase; padding: 4px 10px; border-radius: var(--radius-full); background: var(--brand-tint); color: var(--brand-dark); }
.ops-step.is-done .ops-step-state { background: var(--ok-bg); color: var(--ok); }
.ops-step.is-bad .ops-step-state { background: var(--warn-bg); color: var(--warn); }

.ops-grid-3 { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.ops-span-2 { grid-column: span 2; }
.ops-subcard { margin-top: 6px; padding: 12px 14px 2px; border-radius: 10px; background: var(--card-subtle); border: 1px solid var(--border-light); }
.ops-subcard + .ops-subcard { margin-top: 10px; }
.ops-subcard-title { font-size: 11.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--ink); margin-bottom: 10px; }
.ops-subcard-title span { font-weight: 500; letter-spacing: 0; text-transform: none; color: var(--muted); margin-left: 6px; }
.ops-log .pdo-run-banner { margin-top: 14px; }

.ops-tip { margin-top: 12px; font-size: 12.5px; color: var(--label); }
.ops-tip summary { cursor: pointer; display: inline-flex; align-items: center; gap: 6px; font-weight: 600; color: var(--accent-blue); list-style: none; }
.ops-tip summary::-webkit-details-marker { display: none; }
.ops-tip summary::before { content: "i"; width: 16px; height: 16px; border-radius: 50%; display: inline-flex; align-items: center; justify-content: center; font: italic 700 11px/1 Georgia, serif; color: #fff; background: var(--accent-blue); }
.ops-tip p { margin: 8px 0 0; padding: 10px 12px; border-radius: 8px; background: #eff6ff; border: 1px solid #dbeafe; line-height: 1.55; }

/* --- Hourly grid --- */
.ops-legend { display: flex; flex-wrap: wrap; gap: 6px 16px; margin: -6px 0 10px; font-size: 12px; color: var(--muted); }
.ops-legend span { display: inline-flex; align-items: center; gap: 6px; }
.ops-legend i { width: 12px; height: 12px; border-radius: 3px; }
.ops-legend .tone-met { background: var(--ok); }
.ops-legend .tone-under { background: var(--pending); }
.ops-legend .tone-stalled { background: var(--warn); }
.ops-hours-wrap { border: 1px solid var(--border); border-radius: 10px; }
table.ops-hours { counter-reset: ops-hour; border-collapse: separate; border-spacing: 0; min-width: 1120px; }
.ops-hours th, .ops-hours td { border: 0; border-bottom: 1px solid var(--border-light); }
.ops-hours th { background: var(--card-subtle); padding: 10px 8px; white-space: nowrap; }
.ops-hours td { padding: 8px; vertical-align: top; background: var(--card); transition: background .15s; }
.ops-hours tbody tr:last-child td { border-bottom: 0; }
.ops-hours tbody tr:hover td { background: #fbfcfe; }
.ops-hours tbody tr:focus-within td { background: #fffbfa; }
.ops-hours input, .ops-hours select { margin-bottom: 0; padding: 8px 9px; }
.ops-hours input[type="time"] { width: 124px; }
.ops-hours .prod-hour-set-speed { width: 84px; }
.ops-hours .prod-hour-tank { width: 96px; }
.ops-hours .prod-hour-remarks { min-width: 140px; }
.ops-hours th.ops-col-hr, .ops-hours td.ops-col-hr { width: 52px; text-align: center; }
.ops-hours tbody tr { counter-increment: ops-hour; }
.ops-hours td.ops-col-hr { box-shadow: inset 4px 0 0 var(--border); vertical-align: middle; }
.ops-hours td.ops-col-hr::before {
  content: counter(ops-hour); display: inline-flex; align-items: center; justify-content: center;
  width: 30px; height: 30px; border-radius: 8px; font-family: var(--font-display); font-weight: 700; font-size: 14px;
  background: var(--neutral-bg); color: var(--label);
}
.ops-hours tr[data-tone="prod-hour-met"] td.ops-col-hr { box-shadow: inset 4px 0 0 var(--ok); }
.ops-hours tr[data-tone="prod-hour-met"] td.ops-col-hr::before { background: var(--ok-bg); color: var(--ok); }
.ops-hours tr[data-tone="prod-hour-under"] td.ops-col-hr { box-shadow: inset 4px 0 0 var(--pending); }
.ops-hours tr[data-tone="prod-hour-under"] td.ops-col-hr::before { background: var(--pending-bg); color: var(--pending); }
.ops-hours tr[data-tone="prod-hour-stalled"] td.ops-col-hr { box-shadow: inset 4px 0 0 var(--warn); }
.ops-hours tr[data-tone="prod-hour-stalled"] td.ops-col-hr::before { background: var(--warn-bg); color: var(--warn); }
.ops-hours th.ops-col-actual { color: var(--brand-dark); }
.ops-hours .prod-hour-actual-prod {
  width: 100px; font-size: 17px; font-weight: 700; font-variant-numeric: tabular-nums;
  border: 2px solid var(--brand-tint-border); background: var(--brand-tint);
}
.ops-hours .prod-hour-actual-prod:not(:placeholder-shown) { background: #fff; border-color: #cbd5e1; }
.ops-hours .prod-hour-actual-prod:focus { border-color: var(--brand); background: #fff; }
.ops-hours .prod-hour-attain-cell { min-width: 130px; vertical-align: middle; }
.ops-hours .prod-hour-track { height: 10px; }
.ops-hours .prod-hour-value { font-size: 13px; }
.ops-hours .prod-hour-losses-cell { min-width: 290px; }
.ops-loss-entry { display: grid; grid-template-columns: minmax(120px, 1fr) 64px auto auto; gap: 5px; align-items: center; }
button.prod-hour-loss-add-btn { padding: 0 12px; height: 34px; font-size: 12.5px; }
.ops-hours .prod-hour-suggested-loss:not(:empty) { margin-bottom: 5px; color: var(--pending); font-weight: 600; white-space: normal; }
.ops-hours .prod-hour-losses-list { margin-top: 6px; }
.ops-hours .loss-chip { padding: 3px 4px 3px 9px; border-radius: var(--radius-full); font-size: 11.5px; font-weight: 600; border: 1px solid var(--warn-border); }
.ops-hours .loss-chip-remove { width: 18px; height: 18px; border-radius: 50%; display: inline-flex; align-items: center; justify-content: center; box-shadow: none; }
.ops-hours .loss-chip-remove:hover { background: rgba(220,38,38,.12); }
button.prod-hour-remove-btn { width: 34px; height: 34px; padding: 0; color: var(--muted); }
button.prod-hour-remove-btn:hover { color: var(--warn); border-color: var(--warn-border); background: var(--warn-bg); }
.ops-hour-actions { display: flex; gap: 10px; flex-wrap: wrap; margin-top: 10px; }

/* --- Output & losses --- */
.ops-output { border-left-width: 4px; background: linear-gradient(180deg, #fff 0%, #fafbfc 100%); }
.ops-output .prod-output-grid { gap: 10px 12px; }
.ops-tile { padding: 10px 12px 2px; border-radius: 10px; background: #fff; border: 1px solid var(--border-light); }
.ops-tile input { border-color: transparent; background: var(--card-subtle); }
.ops-tile input:focus { border-color: var(--brand); background: #fff; }
.ops-tile-main { border-color: var(--brand-tint-border); background: var(--brand-tint); }
.ops-tile-main input[type="number"] { font-size: 24px; background: #fff; }
.ops-losses { gap: 10px 12px; }
.ops-loss { padding: 10px 12px 2px; border-radius: 10px; background: #fffafa; border: 1px solid #fde4e2; }
.ops-loss label { color: #9f1d17; }
.ops-loss input { font-weight: 600; font-variant-numeric: tabular-nums; }

/* Blowing: the one number that matters, made big */
.ops-made { display: grid; grid-template-columns: minmax(240px, 1fr) minmax(0, 1.6fr); gap: 14px; align-items: stretch; }
.ops-made-hero {
  display: flex; flex-direction: column; justify-content: center;
  padding: 16px 18px 12px; border-radius: 12px;
  background: linear-gradient(160deg, var(--ok-bg) 0%, #fff 100%); border: 1px solid var(--ok-border);
}
.ops-made-hero label { color: #065f46; }
.ops-made-hero input {
  font-family: var(--font-display); font-size: 38px; font-weight: 700; font-variant-numeric: tabular-nums;
  padding: 10px 14px; border: 2px solid var(--ok-border); margin-bottom: 8px;
}
.ops-made-hero input:focus { border-color: var(--ok); box-shadow: 0 0 0 4px rgba(5,150,105,.12); }
.ops-made-rate { margin: 0; font-size: 12.5px; font-weight: 600; color: var(--pending); min-height: 1em; }
.ops-made-side { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 10px 14px; align-content: center; }
.ops-made-side > div:not(.ops-loss) { padding: 10px 12px 2px; border-radius: 10px; background: var(--card-subtle); border: 1px solid var(--border-light); }
.ops-empties-note { align-self: center; margin: 0 0 10px; }

/* --- Sign-off --- */
.ops-step.ops-sign { background: linear-gradient(135deg, var(--navy) 0%, var(--navy-light) 100%); border-color: var(--navy); color: #fff; }
.ops-sign .ops-step-title { color: #fff; }
.ops-sign .ops-step-sub { color: #c3cfe0; font-size: 13px; }
.ops-sign label, .ops-sign label .muted { color: #b8c6da; }
.ops-sign .ops-step-num { background: rgba(255,255,255,.1); color: #fff; border-color: rgba(255,255,255,.2); }
.ops-sign.is-current { box-shadow: 0 12px 28px -14px rgba(14,27,46,.7); }
.ops-sign .ops-step-state:not(:empty) { background: rgba(255,255,255,.12); color: #fff; }
.ops-sign.is-done .ops-step-state { background: rgba(52,211,153,.18); color: #6ee7b7; }
.ops-sign input { background: #fff; }
.ops-sign-row { display: flex; gap: 14px; align-items: flex-end; flex-wrap: wrap; margin-top: 4px; }
.ops-sign-field { flex: 1 1 260px; }
.ops-sign-field input { font-size: 15px; padding: 11px 14px; }
.ops-sign-actions { display: flex; gap: 10px; margin-bottom: 12px; flex-wrap: wrap; }
button.ops-sign-btn { padding: 12px 26px; font-size: 15px; border-radius: 10px; box-shadow: 0 8px 18px -8px rgba(229,40,31,.8); }
button.ops-sign-btn::before { content: "\270E"; margin-right: 8px; }
.ops-sign button.secondary { padding: 12px 18px; border-radius: 10px; }

/* --- Smaller screens --- */
@media (max-width: 1100px) {
  .ops-board { grid-template-columns: auto repeat(3, minmax(0, 1fr)); }
  .ops-board-ident { grid-column: 1 / -1; }
  .ops-rail-mini { display: none; }
}
@media (max-width: 720px) {
  .ops-board { grid-template-columns: repeat(2, minmax(0, 1fr)); padding: 16px; gap: 14px; }
  .ops-kpi-ring { justify-self: start; }
  .ops-kpi-value { font-size: 26px; }
  .ops-strip-bar b { font-size: 9px; }
  .ops-grid-3, .ops-made, .ops-made-side { grid-template-columns: 1fr; }
  .ops-span-2 { grid-column: auto; }
  .ops-step { padding: 14px 14px 10px; }
  .ops-step-state { display: none; }
  .ops-sign-actions, button.ops-sign-btn { width: 100%; }
}

/* ===================== Command centre: the Dashboard (2026-10-21) =====================
   Same idea as the shift-log console: one dark board on top that answers
   "is anything wrong / how is the period going", then what to act on and
   what just happened side by side, then the detail. command-centre.js. */
.cc-hero {
  position: relative; overflow: hidden; color: #fff;
  padding: 22px 24px 20px; margin-bottom: 18px; border-radius: 18px;
  background:
    radial-gradient(520px 220px at 100% 0%, rgba(217, 34, 24, .32), transparent 70%),
    radial-gradient(460px 220px at 0% 100%, rgba(13, 148, 136, .25), transparent 70%),
    linear-gradient(135deg, var(--navy) 0%, var(--navy-light) 100%);
  box-shadow: 0 14px 30px -16px rgba(14, 27, 46, .6);
}
.cc-hero::after {
  content: ""; position: absolute; inset: 0; pointer-events: none;
  background-image: linear-gradient(rgba(255,255,255,.035) 1px, transparent 1px), linear-gradient(90deg, rgba(255,255,255,.035) 1px, transparent 1px);
  background-size: 24px 24px;
}
.cc-hero > * { position: relative; z-index: 1; }
.cc-hero-top { display: flex; justify-content: space-between; align-items: flex-start; gap: 16px 24px; flex-wrap: wrap; margin-bottom: 16px; }
.cc-hello { min-width: 0; flex: 1 1 320px; }
.cc-eyebrow { display: inline-flex; align-items: center; gap: 8px; font-size: 11px; font-weight: 700; letter-spacing: .12em; text-transform: uppercase; color: #9fb3cf; }
.cc-greeting { font-family: var(--font-display); font-size: 28px; line-height: 1.15; margin: 6px 0 4px; color: #fff; }
.cc-asof { margin: 0; font-size: 12.5px; color: #b8c6da; max-width: 70ch; }
.cc-hero-side { display: flex; flex-direction: column; align-items: flex-end; gap: 10px; }
.cc-clock { text-align: right; line-height: 1.15; }
.cc-clock strong { display: block; font-family: var(--font-display); font-size: 30px; font-variant-numeric: tabular-nums; }
.cc-clock span { font-size: 12px; color: #b8c6da; }
.cc-period { background: rgba(255,255,255,.07); border: 1px solid rgba(255,255,255,.12); border-radius: var(--radius-full); padding: 3px; gap: 2px; }
.cc-period .chip { background: transparent; border: 0; color: #c3cfe0; border-radius: var(--radius-full); padding: 6px 14px; box-shadow: none; }
.cc-period .chip:hover { background: rgba(255,255,255,.08); color: #fff; }
.cc-period .chip.active { background: #fff; color: var(--navy); }

/* The annunciator, set into the board */
.cc-hero .annunciator { background: rgba(255,255,255,.06); border: 1px solid rgba(255,255,255,.12); border-left: 4px solid #34d399; border-radius: 14px; margin-bottom: 16px; padding: 14px 16px; backdrop-filter: blur(4px); }
.cc-hero .annunciator.is-watch { border-left-color: #fbbf24; }
.cc-hero .annunciator.is-alert { border-left-color: #f87171; background: rgba(248,113,113,.08); }
.cc-hero .annunciator-lamp { width: 14px; height: 14px; background: #34d399; box-shadow: 0 0 0 4px rgba(52,211,153,.2); }
.cc-hero .annunciator.is-watch .annunciator-lamp { background: #fbbf24; box-shadow: 0 0 0 4px rgba(251,191,36,.2); }
.cc-hero .annunciator.is-alert .annunciator-lamp { background: #f87171; box-shadow: 0 0 0 4px rgba(248,113,113,.25); }
.cc-hero .annunciator-headline { color: #fff; font-family: var(--font-display); font-size: 19px; }
.cc-hero .annunciator-sub { color: #b8c6da; }
.cc-hero .annunciator-flag { background: rgba(255,255,255,.08); border: 1px solid rgba(255,255,255,.16); color: #e2e8f0; border-radius: var(--radius-full); box-shadow: none; }
.cc-hero .annunciator-flag:hover { background: rgba(255,255,255,.16); border-color: rgba(255,255,255,.3); }
.cc-hero .annunciator-flag.flag-alert { background: rgba(248,113,113,.16); border-color: rgba(248,113,113,.45); }
.cc-hero .annunciator-flag.flag-alert .annunciator-flag-count { color: #fecaca; }
.cc-hero .annunciator-flag.flag-watch { background: rgba(251,191,36,.12); border-color: rgba(251,191,36,.4); }
.cc-hero .annunciator-flag.flag-watch .annunciator-flag-count { color: #fde68a; }
.cc-hero .annunciator-flag.flag-static { opacity: .75; }

/* Headline figures */
.cc-kpis { --cc-cols: 4; display: grid; grid-template-columns: repeat(var(--cc-cols), minmax(0, 1fr)); gap: 12px; }
.cc-kpis:empty { display: none; }
button.cc-kpi {
  display: flex; flex-direction: column; align-items: flex-start; gap: 4px; text-align: left; min-width: 0;
  padding: 14px 16px; border-radius: 14px; color: #fff;
  background: rgba(255,255,255,.06); border: 1px solid rgba(255,255,255,.12); box-shadow: none;
  transition: background .15s, transform .15s, border-color .15s;
}
button.cc-kpi:hover { background: rgba(255,255,255,.11); border-color: rgba(255,255,255,.24); transform: translateY(-2px); box-shadow: none; }
button.cc-kpi.is-static { cursor: default; transform: none; }
.cc-kpi-label { font-size: 10.5px; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; color: #9fb3cf; }
.cc-kpi-value { font-family: var(--font-display); font-size: 32px; font-weight: 700; line-height: 1.05; font-variant-numeric: tabular-nums; overflow-wrap: anywhere; }
.cc-kpi-value small { font-size: 13px; font-weight: 600; color: #b8c6da; margin-left: 6px; letter-spacing: .02em; }
.cc-kpi-delta { font-size: 12px; font-weight: 600; }
.cc-kpi-delta.is-up { color: #6ee7b7; }
.cc-kpi-delta.is-down { color: #fca5a5; }
.cc-kpi-sub { font-size: 12px; color: #b8c6da; line-height: 1.35; }
.cc-kpi.is-bad .cc-kpi-sub { color: #fca5a5; font-weight: 600; }
.cc-kpi.is-warn .cc-kpi-sub { color: #fde68a; font-weight: 600; }
.cc-kpi.is-ok .cc-kpi-sub { color: #6ee7b7; }
.cc-kpi-meter { width: 100%; height: 6px; border-radius: 6px; background: rgba(255,255,255,.12); overflow: hidden; margin-top: 2px; }
.cc-kpi-meter i { display: block; height: 100%; border-radius: 6px; background: linear-gradient(90deg, #10b981, #6ee7b7); transition: width .5s var(--ease-out); }

/* Act now + Live activity */
.cc-grid { display: grid; grid-template-columns: minmax(0, 1fr) minmax(300px, 380px); gap: 18px; align-items: start; margin-bottom: 8px; }
.cc-main { min-width: 0; display: grid; gap: 18px; }
.cc-main > .panel { margin-bottom: 0; }
.cc-main:not(:has(> .panel:not(.hidden))) { display: none; }
.cc-panel-title { display: flex; align-items: center; gap: 10px; }
.cc-panel-title h2 { margin: 0; }
.cc-panel-icon { width: 30px; height: 30px; border-radius: 9px; display: inline-flex; align-items: center; justify-content: center; background: var(--neutral-bg); color: var(--navy-light); flex-shrink: 0; }
.cc-panel-icon svg { width: 16px; height: 16px; }
.cc-panel-icon.is-act { background: var(--brand-tint); color: var(--brand); }
.cc-panel-icon.is-live { background: var(--ok-bg); color: var(--ok); }

.cc-act .dash-work-row { border-radius: 12px; border: 1px solid var(--border-light); margin-top: 8px; padding: 12px 14px; }
.cc-act .dash-work-row:first-child { margin-top: 0; border-top: 1px solid var(--border-light); }
.cc-act .dash-work-row:hover { border-color: var(--brand-tint-border); background: #fffafa; transform: translateX(2px); }
.cc-act .dash-work-count { min-width: 40px; height: 40px; border-radius: 12px; font-family: var(--font-display); font-size: 19px; display: inline-flex; align-items: center; justify-content: center; background: var(--brand-tint); color: var(--brand-dark); }
.cc-act .dash-work-count.is-stale { background: var(--warn); color: #fff; box-shadow: 0 4px 10px -4px rgba(220,38,38,.6); }
.cc-act .dash-work-label { font-size: 14px; }
.cc-act .dash-work-go { color: var(--brand); font-size: 22px; }
.cc-act .dash-work-clear { display: flex; align-items: center; gap: 10px; padding: 16px; border-radius: 12px; background: var(--ok-bg); border: 1px solid var(--ok-border); }
.cc-act .dash-work-clear::before { content: "\2713"; width: 28px; height: 28px; border-radius: 50%; display: inline-flex; align-items: center; justify-content: center; background: var(--ok); color: #fff; font-size: 15px; }

.cc-feed { position: sticky; top: 12px; margin-bottom: 0; padding: 18px 18px 8px; }
.cc-feed .panel-head-row { flex-wrap: wrap; gap: 4px 10px; }
.cc-feed-filters { display: flex; flex-wrap: wrap; gap: 6px; margin: -2px 0 10px; }
.cc-feed-filters .chip { padding: 4px 11px; border-radius: var(--radius-full); font-size: 11.5px; }
.cc-feed-list { list-style: none; margin: 0 -6px; padding: 0; max-height: 620px; overflow-y: auto; }
.cc-feed-day { position: sticky; top: 0; z-index: 1; background: var(--card); padding: 10px 6px 6px; font-size: 10.5px; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; color: var(--muted); }
.cc-feed-empty { padding: 18px 6px; color: var(--muted); font-size: 13px; }
.cc-ev { position: relative; }
.cc-ev::before { content: ""; position: absolute; left: 22px; top: 0; bottom: 0; width: 2px; background: var(--border-light); }
.cc-ev-row {
  position: relative; display: grid; grid-template-columns: 34px minmax(0, 1fr) auto; gap: 10px; align-items: start; width: 100%;
  padding: 8px 6px; border-radius: 10px; text-align: left;
  background: transparent; border: 0; box-shadow: none; color: var(--ink); font-weight: 400;
}
button.cc-ev-row:hover { background: var(--card-subtle); box-shadow: none; }
button.cc-ev-row:active { transform: none; }
.cc-ev-icon { width: 32px; height: 32px; border-radius: 10px; display: inline-flex; align-items: center; justify-content: center; background: #eef2f7; color: var(--navy-light); border: 2px solid var(--card); }
.cc-ev-icon svg { width: 15px; height: 15px; }
.cc-ev.is-ok .cc-ev-icon { background: var(--ok-bg); color: var(--ok); }
.cc-ev.is-warn .cc-ev-icon { background: var(--pending-bg); color: var(--pending); }
.cc-ev.is-bad .cc-ev-icon { background: var(--warn-bg); color: var(--warn); }
.cc-ev.is-info .cc-ev-icon { background: #eff6ff; color: var(--accent-blue); }
.cc-ev-text { display: flex; flex-direction: column; gap: 1px; min-width: 0; }
.cc-ev-title { font-size: 13px; font-weight: 600; line-height: 1.3; }
.cc-ev-detail { font-size: 12px; color: var(--muted); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cc-ev-time { font-size: 11px; color: var(--muted); white-space: nowrap; padding-top: 2px; font-variant-numeric: tabular-nums; }
.cc-ev.is-fresh .cc-ev-row { animation: cc-fresh 3s var(--ease-out); }
@keyframes cc-fresh { 0% { background: #fef9c3; } 100% { background: transparent; } }
@media (prefers-reduced-motion: reduce) { .cc-ev.is-fresh .cc-ev-row { animation: none; } }

.dash-row-title .dash-row-note { font-weight: 500; text-transform: none; letter-spacing: 0; color: var(--muted); margin-left: 6px; font-size: 12px; }

@media (max-width: 1180px) {
  .cc-kpis { grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); }
  .cc-grid { grid-template-columns: 1fr; }
  .cc-feed { position: static; }
  .cc-feed-list { max-height: 420px; }
}
@media (max-width: 640px) {
  .cc-hero { padding: 18px 16px; border-radius: 14px; }
  .cc-greeting { font-size: 23px; }
  .cc-hero-side { align-items: flex-start; width: 100%; }
  .cc-clock { text-align: left; }
  .cc-clock strong { font-size: 24px; }
  .cc-period { overflow-x: auto; max-width: 100%; }
  .cc-kpis { grid-template-columns: 1fr 1fr; gap: 8px; }
  .cc-kpi-value { font-size: 24px; }
  button.cc-kpi { padding: 12px; }
}

/* ===================== System-wide refresh (2026-10-21) =====================
   The same look carried to every screen through the shared classes: softer,
   rounder surfaces, display type on headings, cards that lift when they can
   be opened, pill chips. Visual only -- no layout a screen relies on moves. */
.panel { border-radius: 16px; border-color: #e6ebf2; box-shadow: 0 1px 2px rgba(15,23,42,.04), 0 8px 24px -18px rgba(15,23,42,.18); }
.panel h2 { font-family: var(--font-display); font-size: 16.5px; letter-spacing: .005em; }
.panel-head-row h2 { margin-bottom: 0; }
.card { border-radius: 14px; border-color: #e6ebf2; box-shadow: 0 1px 2px rgba(15,23,42,.04); transition: transform .15s var(--ease-out), box-shadow .15s, border-color .15s; }
.card-clickable:hover:not(.card-static) { transform: translateY(-2px); box-shadow: 0 10px 22px -14px rgba(15,23,42,.35); border-color: #cfd8e3; }
.card-icon { border-radius: 10px; }
.card.flag { border-color: #f6c9c5; background: linear-gradient(180deg, #fff 0%, #fffafa 100%); }
.card.attention { border-color: #f4dfae; }
.card.good { border-color: #bde9d4; }
.dash-row-title { font-family: var(--font-display); }
.chip { border-radius: var(--radius-full); transition: background .15s, color .15s, border-color .15s; }
.chip.active { box-shadow: 0 4px 10px -6px rgba(217,34,24,.7); }
.lu-panel-icon { border-radius: 10px; }
.modal-box { border-radius: 16px; }

/* ===================== Dashboard detail rows (2026-10-21, second pass) =====================
   Category bars, empty states, and the Exceptions panel as a ranked list
   rather than a ledger. (The scorecard and flow chart: third pass, below.) */

/* Row titles */
.dash-row-title { display: flex; align-items: center; gap: 10px; }
.dash-row-title::after { content: ""; flex: 1; height: 1px; background: linear-gradient(90deg, var(--border), transparent); }

/* Breakdown panels */
#tab-dashboard .dashboard-chart-grid > .panel { padding-bottom: 14px; }

/* Category bars */
#tab-dashboard .report-bar-row { padding: 7px 8px; border-radius: 10px; }
#tab-dashboard .report-bar-track { height: 12px; border-radius: 12px; background: #eef2f7; overflow: hidden; }
#tab-dashboard .report-bar-fill { border-radius: 12px; background: linear-gradient(90deg, var(--navy-light), var(--accent-blue)); }
#tab-dashboard #chart-production-by-line .report-bar-fill { background: linear-gradient(90deg, var(--accent-teal-dark), #2dd4bf); }
#tab-dashboard button.report-bar-row { width: 100%; background: transparent; border: 0; box-shadow: none; color: inherit; font-weight: 400; }
#tab-dashboard button.report-bar-row:hover { background: var(--card-subtle); }

/* Empty states */
.dash-empty { display: flex; align-items: center; gap: 12px; padding: 14px 16px; border-radius: 12px; background: var(--card-subtle); border: 1px dashed var(--border); color: var(--muted); font-size: 13px; }
.dash-empty-icon { width: 30px; height: 30px; border-radius: 50%; display: inline-flex; align-items: center; justify-content: center; background: #eef2f7; color: #94a3b8; flex-shrink: 0; }
.dash-empty-icon svg { width: 16px; height: 16px; }
.dash-empty.is-ok { background: var(--ok-bg); border: 1px solid var(--ok-border); color: #065f46; font-weight: 600; }
.dash-empty.is-ok .dash-empty-icon { background: var(--ok); color: #fff; }

/* Exceptions panel */
.dash-exc-head { display: flex; align-items: center; justify-content: space-between; gap: 8px 16px; flex-wrap: wrap; margin-bottom: 14px; }
.dash-exc .dash-tabs { padding: 4px; gap: 4px; background: var(--neutral-bg); border-radius: var(--radius-full); display: inline-flex; margin-bottom: 18px; max-width: 100%; overflow-x: auto; }
.dash-exc .dash-tab-btn { border: 0; background: transparent; box-shadow: none; display: inline-flex; align-items: center; gap: 8px; white-space: nowrap; padding: 8px 16px; }
.dash-exc .dash-tab-btn:hover { background: rgba(255,255,255,.7); }
.dash-exc .dash-tab-btn.active { background: #fff; color: var(--ink); box-shadow: 0 1px 3px rgba(15,23,42,.12); }
.dash-tab-count:empty { display: none; }
.dash-tab-count { min-width: 20px; height: 20px; padding: 0 6px; border-radius: var(--radius-full); font-size: 11px; font-weight: 700; display: inline-flex; align-items: center; justify-content: center; }
.dash-tab-count.is-bad { background: var(--warn); color: #fff; }
.dash-tab-count.is-warn { background: var(--pending); color: #fff; }
.dash-exc .dash-tab-panel > .panel-head-row h2 { font-size: 15px; }
.dash-exc .dash-tab-panel > p.muted { margin-top: -4px; }

table.dash-exc-table { border-collapse: separate; border-spacing: 0; }
.reg-table.dash-exc-table thead th { position: static; background: transparent; color: var(--muted); font-size: 10.5px; letter-spacing: .08em; border-bottom: 1px solid var(--border); padding-top: 4px; }
.reg-table.dash-exc-table tbody tr td { padding-top: 12px; padding-bottom: 12px; }
.reg-table.dash-exc-table tbody tr:hover td { background: var(--card-subtle); }
.dash-exc-row td:first-child { box-shadow: inset 4px 0 0 var(--pending); padding-left: 16px; }
.dash-exc-row.is-out_of_stock td:first-child, .dash-exc-row.is-critical td:first-child { box-shadow: inset 4px 0 0 var(--warn); }
.dash-exc-item { font-weight: 600; color: var(--ink); }
.dash-exc-pill { display: inline-flex; align-items: center; gap: 6px; padding: 3px 10px; border-radius: var(--radius-full); font-size: 11px; font-weight: 700; letter-spacing: .03em; text-transform: uppercase; white-space: nowrap; background: var(--pending-bg); color: #92400e; }
.dash-exc-pill::before { content: ""; width: 6px; height: 6px; border-radius: 50%; background: currentColor; }
.dash-exc-pill.is-out_of_stock, .dash-exc-pill.is-critical { background: var(--warn-bg); color: var(--warn); }
.dash-cover { display: flex; align-items: center; gap: 10px; min-width: 150px; }
.dash-cover-track { flex: 1; height: 8px; border-radius: 8px; background: #eef2f7; overflow: hidden; }
.dash-cover-track i { display: block; height: 100%; border-radius: 8px; background: linear-gradient(90deg, #f59e0b, #fbbf24); }
.is-out_of_stock .dash-cover-track i, .is-critical .dash-cover-track i { background: linear-gradient(90deg, #dc2626, #f87171); }
.dash-cover-num { font-family: var(--font-mono); font-size: 12.5px; font-weight: 600; white-space: nowrap; }
.dash-cover-num small { color: var(--muted); font-weight: 400; }
.dash-exc-when { font-weight: 600; color: var(--ink); }
.is-out_of_stock .dash-exc-when, .is-critical .dash-exc-when { color: var(--warn); }
.dash-exc-more:empty { display: none; }
.dash-exc-more { margin: 12px 0 0; font-size: 12.5px; color: var(--muted); }

/* ===================== Dashboard: scorecard, flow chart, grouped exceptions (2026-10-21, third pass) ===================== */

/* Business health: three columns, each a ranked list of figures */
.dash-health { display: grid; grid-template-columns: repeat(auto-fit, minmax(330px, 1fr)); gap: 16px; margin-bottom: 18px; align-items: start; }
.dash-health-col { background: var(--card); border: 1px solid #e6ebf2; border-radius: 16px; padding: 14px 10px 8px; min-width: 0; box-shadow: 0 1px 2px rgba(15,23,42,.04), 0 8px 24px -18px rgba(15,23,42,.18); }
.dash-health-col.hidden { display: none; }
.dash-health-head { display: flex; align-items: center; justify-content: space-between; gap: 10px; padding: 0 8px 10px; border-bottom: 1px solid var(--border-light); margin-bottom: 4px; }
.dash-health-head h3 { margin: 0; font-family: var(--font-display); font-size: 15px; color: var(--ink); }
.dash-health-score { font-size: 11px; font-weight: 700; letter-spacing: .04em; text-transform: uppercase; padding: 3px 10px; border-radius: var(--radius-full); white-space: nowrap; }
.dash-health-score:empty { display: none; }
.dash-health-score.is-flag { background: var(--warn); color: #fff; }
.dash-health-score.is-attention { background: var(--pending-bg); color: #92400e; }
.dash-health-score.is-ok { background: var(--ok-bg); color: var(--ok); }
.dash-health-note { margin: 2px 8px 6px; font-size: 11.5px; color: var(--muted); }
.dash-health-note:empty { display: none; }
.dash-metrics { display: flex; flex-direction: column; }
button.dash-metric {
  display: grid; grid-template-columns: 34px minmax(0, 1fr) auto; align-items: center; gap: 12px;
  width: 100%; padding: 10px 8px; text-align: left; border-radius: 10px;
  background: transparent; border: 0; box-shadow: none; color: var(--ink); font-weight: 400;
  position: relative;
}
button.dash-metric + button.dash-metric::before { content: ""; position: absolute; left: 54px; right: 8px; top: 0; height: 1px; background: var(--border-light); }
button.dash-metric:hover { background: var(--card-subtle); box-shadow: none; }
button.dash-metric:active { transform: none; }
button.dash-metric.card-static { cursor: default; }
.dash-metric-icon { width: 34px; height: 34px; border-radius: 10px; display: inline-flex; align-items: center; justify-content: center; background: var(--neutral-bg); color: var(--neutral-fg); }
.dash-metric-icon svg { width: 17px; height: 17px; }
.dash-metric-text { display: flex; flex-direction: column; min-width: 0; gap: 1px; }
.dash-metric-label { font-size: 13px; font-weight: 600; line-height: 1.3; }
.dash-metric-sub { font-size: 11.5px; color: var(--muted); line-height: 1.35; }
.dash-metric-sub.sub-ok { color: var(--ok); }
.dash-metric-sub.sub-warn { color: var(--warn); }
.dash-metric-num { font-family: var(--font-display); font-size: 22px; font-weight: 700; font-variant-numeric: tabular-nums; white-space: nowrap; text-align: right; }
.dash-metric.is-flag .dash-metric-icon { background: var(--warn-bg); color: var(--warn); }
.dash-metric.is-flag .dash-metric-num { color: var(--warn); }
.dash-metric.is-flag { background: linear-gradient(90deg, rgba(254,242,242,.9), transparent 70%); }
.dash-metric.is-attention .dash-metric-icon { background: var(--pending-bg); color: var(--pending); }
.dash-metric.is-attention .dash-metric-num { color: var(--pending); }
.dash-metric.is-good .dash-metric-icon { background: var(--ok-bg); color: var(--ok); }
.dash-metric.is-calm .dash-metric-icon { background: transparent; color: #a8b4c4; }
.dash-metric.is-calm .dash-metric-label { font-weight: 500; color: var(--muted); }
.dash-metric.is-calm .dash-metric-sub { color: #a8b4c4; }
.dash-metric.is-calm .dash-metric-num { font-size: 16px; color: #a8b4c4; }

/* Production vs dispatch */
.dash-flow { padding-bottom: 12px; }
.dash-flow-stats { display: grid; grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); gap: 10px; margin: 2px 0 14px; }
.dash-flow-stat { display: flex; flex-direction: column; gap: 2px; padding: 10px 14px; border-radius: 12px; background: var(--card-subtle); border: 1px solid var(--border-light); min-width: 0; }
.dash-flow-label { display: inline-flex; align-items: center; gap: 7px; font-size: 11px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--label); }
.dash-flow-label i, .flow-tip i { width: 10px; height: 10px; border-radius: 3px; display: inline-block; }
i.is-prod { background: var(--accent-teal); }
i.is-disp { background: var(--navy-light); }
.dash-flow-stat strong { font-family: var(--font-display); font-size: 26px; line-height: 1.1; font-variant-numeric: tabular-nums; color: var(--ink); }
.dash-flow-stat strong small { font-size: 12px; color: var(--muted); font-weight: 600; margin-left: 2px; }
.dash-flow-note { font-size: 12px; color: var(--muted); }
.dash-flow-note.is-up { color: var(--ok); font-weight: 600; }
.dash-flow-note.is-down { color: var(--warn); font-weight: 600; }
.dash-flow-note.is-idle { color: var(--pending); font-weight: 600; }
.dash-flow-stat.is-net-up { background: var(--ok-bg); border-color: var(--ok-border); }
.dash-flow-stat.is-net-up strong { color: var(--ok); }
.dash-flow-stat.is-net-down { background: var(--pending-bg); border-color: var(--pending-border); }
.dash-flow-stat.is-net-down strong { color: #b45309; }
.dash-flow-chart { position: relative; }
.flow-svg { display: block; width: 100%; height: 250px; overflow: visible; }
.flow-grid { stroke: #edf1f6; stroke-width: 1; vector-effect: non-scaling-stroke; }
.flow-axis { stroke: #cbd5e1; stroke-width: 1; vector-effect: non-scaling-stroke; }
.flow-tick { font-size: 10.5px; fill: var(--muted); font-variant-numeric: tabular-nums; }
.flow-bar.is-prod { fill: var(--accent-teal); }
.flow-bar.is-disp { fill: var(--navy-light); }
.flow-today { fill: rgba(217,34,24,.05); }
.flow-hit { fill: transparent; cursor: crosshair; }
.flow-hit.is-on { fill: rgba(15,23,42,.05); }
.flow-tip { position: absolute; z-index: 5; pointer-events: none; display: flex; flex-direction: column; gap: 3px; min-width: 170px; padding: 9px 12px; border-radius: 10px; background: var(--navy); color: #e2e8f0; font-size: 12px; box-shadow: 0 10px 24px -10px rgba(14,27,46,.6); }
.flow-tip[hidden] { display: none; }
.flow-tip strong { color: #fff; font-size: 12.5px; }
.flow-tip span { display: flex; align-items: center; gap: 7px; }
.flow-tip b { margin-left: auto; color: #fff; font-variant-numeric: tabular-nums; }
.flow-tip em { font-style: normal; color: #9fb3cf; border-top: 1px solid rgba(255,255,255,.12); padding-top: 4px; margin-top: 2px; }

/* Today: exceptions grouped by kind */
.tdy-ex-head { display: flex; align-items: baseline; gap: 12px; margin: 6px 0 10px; }
.tdy-ex-head h3 { margin: 0; font-family: var(--font-display); font-size: 15px; }
.tdy-exg-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(440px, 1fr)); gap: 14px; align-items: start; }
.tdy-exg { border: 1px solid var(--pending-border); border-radius: 14px; background: #fff; overflow: hidden; min-width: 0; }
.tdy-exg.is-warn { border-color: var(--warn-border); }
.tdy-exg > header { display: flex; align-items: center; gap: 12px; padding: 12px 14px; background: linear-gradient(90deg, var(--pending-bg), #fff 80%); }
.tdy-exg.is-warn > header { background: linear-gradient(90deg, var(--warn-bg), #fff 80%); }
.tdy-exg-count { min-width: 34px; height: 34px; border-radius: 10px; display: inline-flex; align-items: center; justify-content: center; font-family: var(--font-display); font-size: 17px; font-weight: 700; color: #fff; background: var(--pending); }
.tdy-exg.is-warn .tdy-exg-count { background: var(--warn); }
.tdy-exg-title { flex: 1; min-width: 0; display: flex; flex-direction: column; }
.tdy-exg-title h4 { margin: 0; font-size: 14px; color: var(--ink); }
.tdy-exg-title span { font-size: 12px; color: var(--muted); font-variant-numeric: tabular-nums; }
.tdy-exg > header .tdy-action { white-space: nowrap; }
.tdy-exg-why { margin: 0; padding: 8px 14px 10px; font-size: 12px; line-height: 1.5; color: var(--label); border-bottom: 1px solid var(--border-light); }
.tdy-exg-rows { list-style: none; margin: 0; padding: 4px 6px 6px; }
.tdy-exg-rows li { display: grid; grid-template-columns: minmax(110px, 150px) minmax(0, 1fr) auto; gap: 4px 14px; align-items: center; padding: 8px; border-radius: 8px; }
.tdy-exg-rows li + li { border-top: 1px solid var(--border-light); }
.tdy-exg-rows li:hover { background: var(--card-subtle); }
.tdy-exg-where { display: flex; flex-direction: column; min-width: 0; }
.tdy-exg-where strong { font-size: 13px; }
.tdy-exg-where span { font-size: 11.5px; color: var(--muted); }
.tdy-exg-detail { font-size: 12px; color: var(--muted); min-width: 0; display: flex; flex-wrap: wrap; gap: 4px; align-items: center; }
.tdy-exg-fig { display: flex; flex-direction: column; align-items: flex-end; text-align: right; }
.tdy-exg-fig strong { font-family: var(--font-mono); font-size: 13.5px; color: var(--ink); white-space: nowrap; }
.tdy-exg-fig span { font-size: 11px; color: var(--muted); white-space: nowrap; max-width: 22ch; overflow: hidden; text-overflow: ellipsis; }
.tdy-exg-rows li.is-warn .tdy-exg-fig strong { color: var(--warn); }
.tdy-exg-flag { color: var(--warn); font-weight: 600; }
.tdy-exg-chip { padding: 2px 8px; border-radius: var(--radius-full); background: var(--warn-bg); color: #991b1b; font-size: 11px; }
@media (max-width: 640px) {
  .tdy-exg-grid { grid-template-columns: 1fr; }
  .tdy-exg-rows li { grid-template-columns: minmax(0, 1fr) auto; }
  .tdy-exg-detail { grid-column: 1 / -1; grid-row: 2; }
  .flow-svg { height: 200px; }
}

/* ===================== Truck Loading: yard flow, plates, tickets (2026-10-21) =====================
   The rail is a dark board like the Dashboard's command centre: four
   stations joined in the order a truck passes them, each lit in its own
   colour once a truck waits there. Every truck number is one plate. A truck
   Sales has planned but nobody has logged is a ticket waiting to be
   punched, not a greyed-out row. */
.tlr {
  display: flex; align-items: stretch; gap: 14px;
  padding: 14px; border-radius: 18px; color: #fff;
  background:
    radial-gradient(480px 160px at 100% 0%, rgba(217, 34, 24, .28), transparent 70%),
    linear-gradient(135deg, var(--navy) 0%, var(--navy-light) 100%);
  box-shadow: 0 14px 30px -18px rgba(14, 27, 46, .6);
}
.tlr-flow { flex: 1 1 auto; display: flex; align-items: stretch; min-width: 0; }
.tl-rail button.tlr-stage {
  flex: 1 1 0; min-width: 0; position: relative;
  display: grid; grid-template-columns: auto minmax(0, 1fr) auto; align-items: center; gap: 12px;
  padding: 12px 14px; border-radius: 14px; text-align: left;
  background: rgba(255,255,255,.04); border: 1px solid rgba(255,255,255,.08); box-shadow: none;
  color: #cbd5e1; font-weight: 400; transition: background .15s, border-color .15s, transform .15s;
}
.tl-rail button.tlr-stage:hover { background: rgba(255,255,255,.09); border-color: rgba(255,255,255,.18); box-shadow: none; transform: translateY(-1px); }
.tlr-node {
  position: relative; width: 42px; height: 42px; border-radius: 12px;
  display: inline-flex; align-items: center; justify-content: center;
  background: rgba(255,255,255,.08); color: #9fb3cf; transition: background .2s, color .2s;
}
.tlr-node svg { width: 19px; height: 19px; }
.tlr-step {
  position: absolute; top: -6px; right: -6px; width: 18px; height: 18px; border-radius: 50%;
  display: inline-flex; align-items: center; justify-content: center;
  font-size: 10px; font-weight: 700; background: #334155; color: #e2e8f0; border: 2px solid var(--navy);
}
.tlr-text { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.tlr-label { font-size: 13px; font-weight: 700; color: #fff; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.tlr-short { font-size: 11.5px; color: #9fb3cf; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.tlr-count { font-family: var(--font-display); font-size: 32px; font-weight: 700; line-height: 1; color: #475569; font-variant-numeric: tabular-nums; }
.tlr-link { flex: 0 0 18px; align-self: center; height: 2px; background: rgba(255,255,255,.14); position: relative; }
.tlr-link::after { content: ""; position: absolute; right: -1px; top: -4px; width: 8px; height: 8px; border-top: 2px solid rgba(255,255,255,.3); border-right: 2px solid rgba(255,255,255,.3); transform: rotate(45deg); }

.tlr-stage.has-trucks .tlr-count { color: #fff; }
.tlr-stage.tone-blue.has-trucks .tlr-node { background: #3b82f6; color: #fff; }
.tlr-stage.tone-red.has-trucks .tlr-node { background: #ef4444; color: #fff; }
.tlr-stage.tone-amber.has-trucks .tlr-node { background: #f59e0b; color: #fff; }
.tlr-stage.tone-green.has-trucks .tlr-node { background: #10b981; color: #fff; }
.tlr-stage.tone-blue.has-trucks { border-color: rgba(59,130,246,.45); }
.tlr-stage.tone-red.has-trucks { border-color: rgba(239,68,68,.55); background: rgba(239,68,68,.10); }
.tlr-stage.tone-amber.has-trucks { border-color: rgba(245,158,11,.45); }
.tlr-stage.tone-green.has-trucks { border-color: rgba(16,185,129,.45); }
@media (prefers-reduced-motion: no-preference) {
  .tlr-stage.is-blocked .tlr-node { animation: tlr-pulse 2s ease-in-out infinite; }
}
@keyframes tlr-pulse { 0%, 100% { box-shadow: 0 0 0 0 rgba(239,68,68,.5); } 50% { box-shadow: 0 0 0 7px rgba(239,68,68,0); } }

.tl-rail button.tlr-stage.is-active { background: #fff; border-color: #fff; color: var(--ink); }
.tlr-stage.is-active .tlr-label { color: var(--ink); }
.tlr-stage.is-active .tlr-short { color: var(--muted); }
.tlr-stage.is-active .tlr-count { color: var(--ink); }
.tlr-stage.is-active .tlr-step { border-color: #fff; }
.tlr-stage.is-active::after { content: "Filter on"; position: absolute; left: 14px; bottom: -9px; font-size: 9.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; padding: 1px 7px; border-radius: var(--radius-full); background: var(--brand); color: #fff; }

.tlr-side { flex: 0 0 auto; display: flex; flex-direction: column; justify-content: center; align-items: stretch; gap: 8px; padding-left: 14px; border-left: 1px solid rgba(255,255,255,.1); }
.tlr-total { font-size: 12px; color: #9fb3cf; text-align: center; white-space: nowrap; }
.tlr-total strong { display: block; font-family: var(--font-display); font-size: 26px; color: #fff; line-height: 1.05; }
.tl-rail button.tlr-history { display: inline-flex; align-items: center; justify-content: center; gap: 6px; padding: 7px 12px; border-radius: 10px; font-size: 12.5px; background: rgba(255,255,255,.08); border: 1px solid rgba(255,255,255,.16); color: #fff; box-shadow: none; }
.tl-rail button.tlr-history:hover { background: rgba(255,255,255,.16); box-shadow: none; }
.tlr-history svg { width: 15px; height: 15px; }

@media (max-width: 1180px) {
  .tlr { flex-direction: column; }
  .tlr-side { flex-direction: row; justify-content: space-between; align-items: center; border-left: 0; border-top: 1px solid rgba(255,255,255,.1); padding: 10px 2px 0; }
  .tlr-total strong { display: inline; font-size: 18px; margin-right: 4px; }
}
@media (max-width: 860px) {
  .tlr-flow { display: grid; grid-template-columns: 1fr 1fr; gap: 8px; }
  .tlr-link { display: none; }
}
@media (max-width: 480px) {
  .tlr-flow { grid-template-columns: 1fr; }
}

/* One number plate everywhere */
.tl-truck-plate.tl-plate {
  display: inline-flex; align-items: stretch; gap: 0; padding: 0 12px 0 0; height: 34px;
  background: #fff; border: 2px solid #0f172a; border-radius: 7px; overflow: hidden;
  box-shadow: inset 0 0 0 2px #fff, 0 2px 6px -2px rgba(15,23,42,.35);
  font-family: var(--font-mono); font-size: 16px; font-weight: 700; letter-spacing: .1em; color: #0f172a;
  width: fit-content;
}
.tl-plate-band { width: 12px; margin-right: 10px; background: linear-gradient(180deg, #2563eb, #1d4ed8); }
.tl-truck-plate.tl-plate .tl-truck-no { align-self: center; }
button.tl-truck-plate.tl-plate:hover { border-color: var(--brand); color: var(--brand-dark); }

/* Planned by Sales: tickets waiting to be punched */
.tl-group.tl-group-plan { border: 1px solid #cfe0f7; border-style: solid; background: #fff; }
.tl-band.tlp-head {
  grid-template-columns: auto minmax(0, 1fr) auto; gap: 14px; padding: 14px 18px;
  background: linear-gradient(90deg, #eff6ff, #fff 75%); border-bottom: 1px solid #dbeafe; border-bottom-style: solid;
}
.tlp-head-icon { width: 38px; height: 38px; border-radius: 11px; display: inline-flex; align-items: center; justify-content: center; background: #2563eb; color: #fff; }
.tlp-head-icon svg { width: 19px; height: 19px; }
.tlp-head-text { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.tlp-head-text strong { font-family: var(--font-display); font-size: 16px; color: var(--ink); }
.tlp-head-text span { font-size: 12.5px; color: var(--muted); }
.tlp-head-count { font-size: 12px; font-weight: 700; padding: 4px 12px; border-radius: var(--radius-full); background: #dbeafe; color: #1d4ed8; white-space: nowrap; }
.tl-row.tl-row-ghost.tlp {
  grid-template-columns: 84px minmax(170px, 1.2fr) minmax(150px, 1fr) auto auto; gap: 18px;
  padding: 14px 18px; opacity: 1; background: #fff; border-bottom: 1px solid var(--border-light); border-bottom-style: solid;
}
.tl-row.tl-row-ghost.tlp:hover { background: #fafcff; }
.tlp-seq {
  display: flex; flex-direction: column; align-items: center; justify-content: center; height: 64px;
  border-radius: 12px; border: 2px dashed #93c5fd; background: #f5f9ff;
}
.tlp-seq span { font-size: 9.5px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: #3b82f6; }
.tlp-seq strong { font-family: var(--font-display); font-size: 26px; line-height: 1.05; color: #1d4ed8; }
.tlp-who { display: flex; flex-direction: column; gap: 6px; min-width: 0; }
.tlp-cust { font-size: 14px; font-weight: 600; color: var(--ink); }
.tlp-load { display: flex; flex-direction: column; gap: 1px; min-width: 0; }
.tlp-qty { font-size: 13px; font-weight: 600; color: var(--label); }
.tlp-qty strong { font-family: var(--font-display); font-size: 22px; color: var(--ink); margin-right: 3px; font-variant-numeric: tabular-nums; }
.tlp-pill { display: inline-flex; align-items: center; gap: 7px; padding: 5px 12px; border-radius: var(--radius-full); font-size: 12px; font-weight: 700; background: #eff6ff; color: #1d4ed8; border: 1px solid #bfdbfe; white-space: nowrap; }
.tlp-pill-dot { width: 7px; height: 7px; border-radius: 50%; background: #3b82f6; }
@media (prefers-reduced-motion: no-preference) { .tlp-pill-dot { animation: ops-pulse 2s infinite; } }
.tl-row.tlp .tl-row-actions button { padding: 9px 16px; border-radius: 10px; }
@media (max-width: 900px) {
  .tl-row.tl-row-ghost.tlp { grid-template-columns: 72px minmax(0, 1fr); }
  .tl-row.tlp .tlp-load, .tl-row.tlp .tlp-state, .tl-row.tlp .tl-row-actions { grid-column: 2; }
  .tl-band.tlp-head { grid-template-columns: auto minmax(0, 1fr); }
  .tlp-head-count { grid-column: 2; justify-self: start; }
}

/* Logged trucks: the card, refined */
.tl-register-groups .tl-group { border-radius: 16px; border-color: #e6ebf2; box-shadow: 0 1px 2px rgba(15,23,42,.04), 0 10px 26px -20px rgba(15,23,42,.3); }
.tl-band.tlx-band { background: linear-gradient(90deg, #f8fafc, #fff 70%); padding: 14px 20px; }
.tlx-band .tl-band-cust { font-family: var(--font-display); font-size: 17px; }
.tl-row.tlx { padding: 18px 20px 14px 18px; }
.tl-row.tlx.tl-row-next { background: linear-gradient(90deg, #f0fdf4, #fff 60%) !important; }
.tlx-qty .tlx-bar { height: 10px; }
.tlx-foot { border-top: 1px solid var(--border-light); padding-top: 12px; gap: 12px 20px; }
.tlx-steps li { font-size: 12px; padding-right: 30px; }
.tlx-steps li:not(:last-child)::after { right: 7px; width: 17px; height: 3px; border-radius: 3px; }
.tlx-dot { width: 18px; height: 18px; border-width: 2px; display: inline-flex; align-items: center; justify-content: center; }
.tlx-steps li.is-done .tlx-dot::before { content: "\2713"; color: #fff; font-size: 11px; font-weight: 700; line-height: 1; }
.tlx-next { padding: 8px 12px; border-radius: 10px; background: var(--card-subtle); border: 1px solid var(--border-light); align-items: center; }
.tlx-next-hold { background: var(--warn-bg); border-color: var(--warn-border); }
.tlx-next-wait { background: var(--pending-bg); border-color: var(--pending-border); }
.tlx-next-go { background: var(--ok-bg); border-color: var(--ok-border); }
.tlx-next-hold .tlx-who { background: var(--warn); color: #fff; border-color: var(--warn); }
.tlx-next-wait .tlx-who { background: var(--pending); color: #fff; border-color: var(--pending); }
.tlx-next-go .tlx-who { background: var(--ok); color: #fff; border-color: var(--ok); }
/* View tabs under the board: one segmented control */
.tl-view-nav { margin-top: 14px; background: var(--neutral-bg); border: 1px solid var(--border-light); border-radius: 14px; box-shadow: none; padding: 5px; }
.tl-view-btn { border-radius: 10px; box-shadow: none; }
.tl-view-btn:hover { background: rgba(255,255,255,.7); }
.tl-view-btn.active { background: #fff; color: var(--ink); border-color: transparent; box-shadow: 0 1px 3px rgba(15,23,42,.12); }
.tl-view-btn.active .tl-tab-badge { background: var(--brand); color: #fff; }
.tl-row.tl-row-ghost.tlp { grid-template-columns: 84px minmax(170px, .9fr) minmax(150px, 1.1fr) auto auto; }

/* ===================== Menu counts (2026-10-21, nav-counts.js) ===================== */
.nav-count {
  margin-left: auto; min-width: 20px; height: 18px; padding: 0 6px; border-radius: var(--radius-full);
  display: inline-flex; align-items: center; justify-content: center; flex-shrink: 0;
  font-size: 10.5px; font-weight: 700; font-variant-numeric: tabular-nums; line-height: 1;
  background: var(--pending); color: #fff;
}
.nav-count.is-stale { background: var(--brand); box-shadow: 0 0 0 3px rgba(217,34,24,.2); }
.side-group-toggle.has-work::after {
  content: ""; position: absolute; top: 7px; right: 14px; width: 9px; height: 9px; border-radius: 50%;
  background: var(--brand); box-shadow: 0 0 0 2px var(--sidebar-bg);
}
.fin-hub-tab .nav-count { margin-left: 2px; }

/* ===================== Finance: tab bar on every Finance page ===================== */
.fin-hub-nav { border-radius: 16px; border-color: #e6ebf2; padding: 6px 8px; box-shadow: 0 1px 2px rgba(15,23,42,.04); }
.fin-hub-tabs { background: var(--neutral-bg); border-radius: 12px; padding: 4px; gap: 2px; }
.fin-hub-tab { border-radius: 9px; padding: 8px 14px; }
.fin-hub-tab:hover { background: rgba(255,255,255,.75); }
.fin-hub-tab.active { background: #fff; color: var(--ink); border-color: transparent; box-shadow: 0 1px 3px rgba(15,23,42,.12); }
.fin-hub-tab.active svg { color: var(--brand); stroke: var(--brand); }
/* Work first, then the books -- the same order as the sidebar. */
.fin-hub-tab[data-fin-hub="finance-dashboard"] { order: 1; }
.fin-hub-tab[data-fin-hub="finance-approvals"] { order: 2; }
.fin-hub-tab[data-fin-hub="finance-payments"] { order: 3; }
.fin-hub-tab[data-fin-hub="customer-outstanding"] { order: 4; }
.fin-hub-tab[data-fin-hub="finance-accounts"] { order: 5; }
.fin-quick-btn { border-radius: 10px; }

/* ===================== Finance dashboard: command centre ===================== */
.fx-hero {
  position: relative; overflow: hidden; color: #fff;
  padding: 22px 24px 18px; margin-bottom: 18px; border-radius: 18px;
  background:
    radial-gradient(520px 220px at 100% 0%, rgba(16, 185, 129, .22), transparent 70%),
    radial-gradient(460px 220px at 0% 100%, rgba(37, 99, 235, .25), transparent 70%),
    linear-gradient(135deg, var(--navy) 0%, var(--navy-light) 100%);
  box-shadow: 0 14px 30px -16px rgba(14, 27, 46, .6);
}
.fx-hero::after {
  content: ""; position: absolute; inset: 0; pointer-events: none;
  background-image: linear-gradient(rgba(255,255,255,.035) 1px, transparent 1px), linear-gradient(90deg, rgba(255,255,255,.035) 1px, transparent 1px);
  background-size: 24px 24px;
}
.fx-hero > * { position: relative; z-index: 1; }
.fx-hero-top { display: flex; justify-content: space-between; align-items: flex-start; gap: 14px 24px; flex-wrap: wrap; margin-bottom: 18px; }
.fx-hello { flex: 1 1 320px; min-width: 0; }
.fx-title { font-family: var(--font-display); font-size: 28px; margin: 6px 0 4px; color: #fff; }
.fx-range { margin: 0; font-size: 12.5px; color: #b8c6da; }
.fx-period { display: flex; flex-direction: column; align-items: flex-end; gap: 8px; }
.fx-custom summary { cursor: pointer; font-size: 12px; font-weight: 600; color: #b8c6da; list-style: none; text-align: right; }
.fx-custom summary::-webkit-details-marker { display: none; }
.fx-custom summary::after { content: " \25BE"; }
.fx-custom[open] summary { color: #fff; }
.fx-custom-body { display: flex; align-items: center; gap: 8px; margin-top: 8px; padding: 8px 10px; border-radius: 12px; background: rgba(255,255,255,.08); border: 1px solid rgba(255,255,255,.14); }
.fx-custom-body label { margin: 0; color: #b8c6da; }
.fx-custom-body input { margin: 0; width: auto; padding: 6px 8px; }
.fx-custom-body button { padding: 7px 14px; }
.fx-kpis { --cc-cols: 5; display: grid; grid-template-columns: repeat(var(--cc-cols), minmax(0, 1fr)); gap: 12px; }
.fx-kpis .cc-kpi-value { font-size: 28px; }
.fx-flowline {
  display: flex; align-items: center; flex-wrap: wrap; gap: 6px 18px; margin-top: 14px; padding: 10px 14px;
  border-radius: 12px; background: rgba(255,255,255,.05); border: 1px solid rgba(255,255,255,.1); font-size: 13px; color: #c3cfe0;
}
.fx-flow-k { font-size: 10.5px; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; color: #9fb3cf; }
.fx-flowline b { color: #fff; font-variant-numeric: tabular-nums; }
.fx-flow-in { color: #6ee7b7; }
.fx-flow-out { color: #fca5a5; }
.fx-flow-net { padding: 2px 10px; border-radius: var(--radius-full); background: rgba(255,255,255,.08); }
.fx-flow-net.is-up b { color: #6ee7b7; }
.fx-flow-net.is-down b { color: #fca5a5; }
.fx-flow-note { margin-left: auto; font-size: 11.5px; color: #8094b0; }

.fx-grid { display: grid; grid-template-columns: minmax(0, 1.5fr) minmax(320px, 1fr); gap: 18px; align-items: start; margin-bottom: 18px; }
.fx-grid > .panel, .fx-grid-2 > .panel { margin-bottom: 0; }
.fx-grid-2 { display: grid; grid-template-columns: repeat(auto-fit, minmax(420px, 1fr)); gap: 18px; align-items: start; margin-bottom: 18px; }

/* Waiting for Finance */
#fx-inbox { display: flex; flex-direction: column; gap: 8px; }
#fx-inbox .dash-empty { margin-bottom: 4px; }
.fx-task {
  display: grid; grid-template-columns: 40px minmax(0, 1fr) auto 52px; align-items: center; gap: 14px;
  width: 100%; padding: 12px 14px; border-radius: 12px; text-align: left;
  background: #fff; border: 1px solid var(--border-light); box-shadow: none; color: var(--ink); font-weight: 400;
}
button.fx-task:hover { border-color: #cbd5e1; background: var(--card-subtle); box-shadow: none; transform: translateX(2px); }
.fx-task-icon { width: 40px; height: 40px; border-radius: 12px; display: inline-flex; align-items: center; justify-content: center; background: var(--neutral-bg); color: var(--neutral-fg); }
.fx-task-icon svg { width: 19px; height: 19px; }
.fx-task-text { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.fx-task-text strong { font-size: 14px; }
.fx-task-text span { font-size: 12px; color: var(--muted); }
.fx-task-age { font-size: 12px; color: var(--muted); white-space: nowrap; }
.fx-task-count { font-family: var(--font-display); font-size: 26px; font-weight: 700; text-align: right; font-variant-numeric: tabular-nums; }
.fx-task.is-open .fx-task-icon { background: var(--pending-bg); color: var(--pending); }
.fx-task.is-open .fx-task-count { color: var(--pending); }
.fx-task.is-hot { border-color: var(--warn-border); background: linear-gradient(90deg, var(--warn-bg), #fff 65%); }
.fx-task.is-hot .fx-task-icon { background: var(--warn); color: #fff; }
.fx-task.is-hot .fx-task-count, .fx-task.is-hot .fx-task-age { color: var(--warn); font-weight: 600; }
.fx-task.is-done { padding: 8px 14px; background: var(--card-subtle); }
.fx-task.is-done .fx-task-icon { width: 30px; height: 30px; background: transparent; color: #a8b4c4; }
.fx-task.is-done .fx-task-text strong { font-weight: 500; color: var(--muted); font-size: 13px; }
.fx-task.is-done .fx-task-text span { color: var(--ok); }
.fx-task.is-done .fx-task-count { font-size: 16px; color: #a8b4c4; }

/* Cash position */
.fx-cash-total { display: flex; flex-direction: column; padding: 14px 16px; border-radius: 12px; background: linear-gradient(135deg, var(--ok-bg), #fff); border: 1px solid var(--ok-border); margin-bottom: 10px; }
.fx-cash-total span { font-size: 11px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: #065f46; }
.fx-cash-total strong { font-family: var(--font-display); font-size: 28px; color: var(--ink); font-variant-numeric: tabular-nums; }
.fx-accounts { list-style: none; margin: 0; padding: 0; }
.fx-accounts li { display: grid; grid-template-columns: 34px minmax(0, 1fr) auto; gap: 12px; align-items: center; padding: 10px 2px; }
.fx-accounts li + li { border-top: 1px solid var(--border-light); }
.fx-acc-icon { width: 34px; height: 34px; border-radius: 10px; display: inline-flex; align-items: center; justify-content: center; background: #eff6ff; color: var(--accent-blue); }
.fx-acc-icon svg { width: 17px; height: 17px; }
.fx-acc-text { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.fx-acc-text strong { font-size: 13.5px; }
.fx-acc-text > span:not(.fx-acc-bar) { font-size: 11.5px; color: var(--muted); }
.fx-acc-bar { display: block; height: 5px; border-radius: 5px; background: #eef2f7; overflow: hidden; margin-top: 4px; }
.fx-acc-bar i { display: block; height: 100%; border-radius: 5px; background: linear-gradient(90deg, #2563eb, #60a5fa); }
.fx-acc-bal { font-family: var(--font-mono); font-size: 14px; font-weight: 600; font-variant-numeric: tabular-nums; }
.fx-accounts li.is-neg .fx-acc-bal { color: var(--warn); }
.fx-link { display: block; margin: 8px 0 2px auto; }

/* Sales vs collections */
.flow-bar.is-sales { fill: var(--navy-light); }
.flow-bar.is-coll { fill: #10b981; }
i.is-sales { background: var(--navy-light); }
i.is-coll { background: #10b981; }

/* Shared list rows */
.fx-age-head { display: flex; align-items: baseline; justify-content: space-between; gap: 10px; flex-wrap: wrap; margin-bottom: 10px; }
.fx-age-head strong { font-family: var(--font-display); font-size: 24px; font-variant-numeric: tabular-nums; }
.fx-age-head span { font-size: 12px; color: var(--muted); }
.fx-age-bar { display: flex; height: 14px; border-radius: 14px; overflow: hidden; gap: 2px; margin-bottom: 10px; background: #eef2f7; }
.fx-age-bar span { display: block; height: 100%; }
.fx-rows, .fx-bars { list-style: none; margin: 0; padding: 0; }
.fx-rows li { display: grid; grid-template-columns: 14px minmax(0, 1fr) 48px 120px; gap: 10px; align-items: center; padding: 8px 2px; }
.fx-rows li + li, .fx-bars li + li { border-top: 1px solid var(--border-light); }
.fx-rows li.is-zero { opacity: .5; }
.fx-rows li.is-bad .fx-row-val { color: var(--warn); }
.fx-dot { width: 12px; height: 12px; border-radius: 4px; display: inline-block; }
.fx-row-label { font-size: 13px; font-weight: 600; display: flex; flex-direction: column; min-width: 0; }
.fx-row-label em, .fx-bar-label em { font-style: normal; font-size: 11.5px; font-weight: 400; color: var(--muted); }
.fx-row-pct { font-size: 12px; color: var(--muted); text-align: right; font-variant-numeric: tabular-nums; }
.fx-row-val { font-family: var(--font-mono); font-size: 13.5px; font-weight: 600; text-align: right; font-variant-numeric: tabular-nums; white-space: nowrap; }
.fx-bars li { display: grid; grid-template-columns: minmax(120px, 1fr) minmax(80px, 1.2fr) 44px 120px; gap: 12px; align-items: center; padding: 9px 2px; }
.fx-bar-label { display: flex; flex-direction: column; min-width: 0; }
.fx-bar-label strong { font-size: 13px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.fx-bar-track { height: 10px; border-radius: 10px; background: #eef2f7; overflow: hidden; }
.fx-bar-track i { display: block; height: 100%; border-radius: 10px; background: linear-gradient(90deg, #10b981, #34d399); }
.fx-bars.is-out .fx-bar-track i { background: linear-gradient(90deg, #f97316, #fb923c); }
.fx-total-line { display: flex; justify-content: space-between; align-items: baseline; padding: 10px 2px 0; margin-top: 4px; border-top: 2px solid var(--border); font-size: 13px; font-weight: 600; }
.fx-total-line strong { font-family: var(--font-mono); font-size: 15px; }

/* Order pipeline */
.fx-sub-head { font-size: 10.5px; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; color: var(--muted); margin: 2px 0 8px; }
.fx-funnel { list-style: none; margin: 0 0 6px; padding: 0; display: grid; grid-template-columns: repeat(3, 1fr); gap: 0; }
.fx-funnel li { position: relative; display: flex; flex-direction: column; align-items: center; padding: 12px 8px; background: var(--neutral-bg); color: var(--muted); clip-path: polygon(0 0, calc(100% - 14px) 0, 100% 50%, calc(100% - 14px) 100%, 0 100%, 14px 50%); }
.fx-funnel li:first-child { clip-path: polygon(0 0, calc(100% - 14px) 0, 100% 50%, calc(100% - 14px) 100%, 0 100%); border-radius: 10px 0 0 10px; }
.fx-funnel li:last-child { clip-path: polygon(0 0, 100% 0, 100% 100%, 0 100%, 14px 50%); border-radius: 0 10px 10px 0; }
.fx-funnel li + li { margin-left: -8px; }
.fx-funnel strong { font-family: var(--font-display); font-size: 24px; line-height: 1.1; color: var(--ink); }
.fx-funnel span { font-size: 11.5px; font-weight: 600; }
.fx-funnel li.has:nth-child(1) { background: #e0e7ff; }
.fx-funnel li.has:nth-child(2) { background: var(--pending-bg); }
.fx-funnel li.has:nth-child(3) { background: var(--ok-bg); }
.fx-funnel li.has:nth-child(3) strong { color: var(--ok); }
.fx-rejected { margin: 0 0 10px; font-size: 12px; font-weight: 600; color: var(--warn); }
.fx-pay-bar { display: flex; height: 14px; border-radius: 14px; overflow: hidden; gap: 2px; margin: 4px 0 10px; }
.fx-pay-bar span { display: block; height: 100%; }
.is-paid { background: #10b981; }
.is-part { background: #f59e0b; }
.is-none { background: #ef4444; }
.is-cancel { background: #cbd5e1; }
.fx-legend { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: 6px 16px; font-size: 12.5px; color: var(--label); }
.fx-legend li { display: inline-flex; align-items: center; gap: 6px; }
.fx-legend i { width: 10px; height: 10px; border-radius: 3px; }
.fx-legend b { color: var(--ink); font-variant-numeric: tabular-nums; }

/* Customers */
.fx-cust { display: flex; align-items: center; gap: 12px; }
.fx-avatar { width: 34px; height: 34px; border-radius: 50%; flex-shrink: 0; display: inline-flex; align-items: center; justify-content: center; font-size: 12px; font-weight: 700; background: linear-gradient(135deg, var(--navy-light), var(--accent-blue)); color: #fff; }
.fx-cust > span:last-child { display: flex; flex-direction: column; min-width: 0; }
.fx-cust em { font-style: normal; font-size: 11.5px; color: var(--muted); }
.fx-paid-track i { background: linear-gradient(90deg, #10b981, #34d399) !important; }

@media (max-width: 1180px) {
  .fx-kpis { grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); }
  .fx-grid { grid-template-columns: 1fr; }
  .fx-flow-note { margin-left: 0; flex-basis: 100%; }
}
@media (max-width: 640px) {
  .fx-hero { padding: 18px 16px; }
  .fx-title { font-size: 23px; }
  .fx-period { align-items: flex-start; width: 100%; }
  .fx-kpis { grid-template-columns: 1fr 1fr; gap: 8px; }
  .fx-grid-2 { grid-template-columns: 1fr; }
  .fx-task { grid-template-columns: 36px minmax(0, 1fr) 40px; }
  .fx-task-age { grid-column: 2; grid-row: 2; }
  .fx-bars li { grid-template-columns: minmax(0, 1fr) 90px; }
  .fx-bars .fx-bar-track { grid-column: 1 / -1; grid-row: 2; }
  .fx-bars .fx-row-pct { display: none; }
  .fx-custom-body { flex-wrap: wrap; }
}
.reg-table.fx-cust-table th.fin-fig, .reg-table.fx-cust-table td.fin-fig { text-align: right; }
.fx-customers .panel-head-row { flex-wrap: wrap; gap: 10px; }
.fx-customers .cc-panel-title > div { min-width: 0; }
.fx-customers #fin-customer-note { white-space: normal; display: block; }
.cc-kpi-value small { white-space: nowrap; }
@media (max-width: 640px) { .fx-kpis .cc-kpi-value { font-size: 21px; } }

/* ===================== Finance pages: one look (2026-10-21) =====================
   Customer Outstanding, Payments & Receipts, Accounts & Expenses and
   Authorize Trucks carry the Overview's dark band with their own figures,
   a light filter toolbar, and the same quiet table style. */
.fxp-hero {
  position: relative; overflow: hidden; color: #fff;
  padding: 20px 22px 18px; margin-bottom: 14px; border-radius: 18px;
  background:
    radial-gradient(520px 220px at 100% 0%, rgba(16, 185, 129, .2), transparent 70%),
    radial-gradient(460px 220px at 0% 100%, rgba(37, 99, 235, .24), transparent 70%),
    linear-gradient(135deg, var(--navy) 0%, var(--navy-light) 100%);
  box-shadow: 0 14px 30px -16px rgba(14, 27, 46, .6);
}
.fxp-hero::after {
  content: ""; position: absolute; inset: 0; pointer-events: none;
  background-image: linear-gradient(rgba(255,255,255,.035) 1px, transparent 1px), linear-gradient(90deg, rgba(255,255,255,.035) 1px, transparent 1px);
  background-size: 24px 24px;
}
.fxp-hero > * { position: relative; z-index: 1; }
.fxp-head { display: flex; justify-content: space-between; align-items: flex-start; gap: 12px 20px; flex-wrap: wrap; margin-bottom: 16px; }
.fxp-head .fx-title { font-size: 25px; }
.fxp-hero .cards.fxp-kpis { grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); gap: 12px; margin: 0; }
.fxp-hero .card { background: rgba(255,255,255,.06); border: 1px solid rgba(255,255,255,.12); box-shadow: none; color: #fff; padding: 14px 16px; }
.fxp-hero .card.card-clickable:hover { background: rgba(255,255,255,.11); border-color: rgba(255,255,255,.24); }
.fxp-hero .card .num { color: #fff; font-size: 24px; }
.fxp-hero .card .label { color: #c3cfe0; }
.fxp-hero .card .cell-sub { color: #9fb3cf; }
.fxp-hero .card .card-icon { background: rgba(255,255,255,.1); color: #c3cfe0; }
.fxp-hero .card.good .card-icon { background: rgba(16,185,129,.25); color: #6ee7b7; }
.fxp-hero .card.attention .card-icon { background: rgba(245,158,11,.25); color: #fde68a; }
.fxp-hero .card.attention .num { color: #fde68a; }
.fxp-hero .card.flag { background: rgba(239,68,68,.12); border-color: rgba(239,68,68,.45); }
.fxp-hero .card.flag .card-icon { background: #ef4444; color: #fff; }
.fxp-hero .card.flag .num { color: #fecaca; }
.fxp-hero .card .cell-sub.sub-ok { color: #6ee7b7; }
.fxp-hero .card .cell-sub.sub-warn { color: #fca5a5; }

.fxp-toolbar {
  display: flex; align-items: center; flex-wrap: wrap; gap: 8px 10px;
  padding: 10px 14px; margin-bottom: 16px; border-radius: 14px;
  background: var(--card); border: 1px solid #e6ebf2; box-shadow: 0 1px 2px rgba(15,23,42,.04);
}
.fxp-toolbar label { margin: 0; font-size: 11px; }
.fxp-toolbar input, .fxp-toolbar select { width: auto; margin: 0; padding: 7px 10px; }
.fxp-toolbar .co-inline-check { text-transform: none; letter-spacing: 0; font-weight: 500; font-size: 12.5px; display: inline-flex; align-items: center; gap: 6px; }
.fxp-toolbar .co-inline-check input { width: auto; }
.fxp-toolbar button { margin-left: auto; }

/* Quiet tables on every Finance page */
#tab-customer-outstanding .reg-table thead th,
#tab-finance-payments .reg-table thead th,
#tab-finance-accounts .reg-table thead th,
#tab-finance-approvals .reg-table thead th {
  position: static; background: transparent; color: var(--muted); font-size: 10.5px; letter-spacing: .08em; border-bottom: 1px solid var(--border);
}
#tab-customer-outstanding .reg-table tbody tr:hover td,
#tab-finance-payments .reg-table tbody tr:hover td,
#tab-finance-accounts .reg-table tbody tr:hover td,
#tab-finance-approvals .reg-table tbody tr:hover td { background: var(--card-subtle); }
#tab-customer-outstanding .reg-table td, #tab-finance-payments .reg-table td,
#tab-finance-accounts .reg-table td, #tab-finance-approvals .reg-table td { padding-top: 11px; padding-bottom: 11px; }
.reg-table th.fin-fig, .reg-table td.fin-fig { text-align: right; }
.fx-row-act { text-align: right; white-space: nowrap; width: 1%; }
button.fx-receive { padding: 5px 12px; font-size: 12px; border-radius: 8px; border-color: var(--ok-border); color: var(--ok); background: var(--ok-bg); }
button.fx-receive:hover { background: var(--ok); color: #fff; border-color: var(--ok); }
.fxp-ledger { border-top: 0; }
.fxp-ledger .fx-avatar { width: 40px; height: 40px; font-size: 14px; }
.fxp-ledger-actions { display: flex; gap: 8px; flex-wrap: wrap; }
.fin-customer-tabs { display: inline-flex; gap: 2px; padding: 4px; border-radius: 12px; background: var(--neutral-bg); }
.fin-customer-tab { border-radius: 9px; }
.fin-customer-tab.active { background: #fff; color: var(--ink); border-color: transparent; box-shadow: 0 1px 3px rgba(15,23,42,.12); }
#tab-finance-accounts .fin-segmented-switch { border-radius: 12px; }
#tab-finance-accounts .pl-panel, #tab-finance-approvals .panel, #tab-finance-accounts .panel { border-radius: 16px; }

/* ===================== Record a payment (finance-pay.js) ===================== */
.modal-box.rp-box { max-width: 880px; width: calc(100% - 32px); padding: 0; overflow: hidden; display: flex; flex-direction: column; max-height: calc(100vh - 48px); }
.rp-head { display: flex; align-items: center; gap: 14px; padding: 18px 22px 14px; background: linear-gradient(135deg, var(--navy), var(--navy-light)); color: #fff; }
.rp-head-icon { width: 42px; height: 42px; border-radius: 12px; display: inline-flex; align-items: center; justify-content: center; background: #10b981; color: #fff; flex-shrink: 0; }
.rp-head-icon svg { width: 21px; height: 21px; }
.rp-head-text { flex: 1; min-width: 0; display: flex; flex-direction: column; }
.rp-head-text h2 { margin: 0; color: #fff; font-family: var(--font-display); font-size: 20px; }
.rp-head-text span { font-size: 12.5px; color: #b8c6da; }
.rp-head .modal-close-btn { color: #fff; background: rgba(255,255,255,.1); border-radius: 10px; }
.rp-steps { list-style: none; margin: 0; padding: 12px 22px; display: flex; gap: 6px; border-bottom: 1px solid var(--border-light); background: var(--card-subtle); }
.rp-steps li { display: inline-flex; align-items: center; gap: 8px; padding: 5px 14px 5px 6px; border-radius: var(--radius-full); font-size: 13px; font-weight: 600; color: var(--muted); }
.rp-steps li span { width: 24px; height: 24px; border-radius: 50%; display: inline-flex; align-items: center; justify-content: center; font-size: 12px; background: #e2e8f0; color: var(--label); }
.rp-steps li.is-now { background: #fff; color: var(--ink); box-shadow: 0 1px 3px rgba(15,23,42,.12); }
.rp-steps li.is-now span { background: var(--brand); color: #fff; }
.rp-steps li.is-done { color: var(--ok); cursor: pointer; }
.rp-steps li.is-done span { background: var(--ok); color: #fff; font-size: 0; }
.rp-steps li.is-done span::before { content: "\2713"; font-size: 12px; }
.rp-pane { padding: 16px 22px; overflow-y: auto; flex: 1 1 auto; min-height: 280px; }
.rp-search { margin-bottom: 12px; }
.rp-list { display: flex; flex-direction: column; gap: 8px; }
.rp-loading { padding: 18px 4px; }
button.rp-item {
  display: grid; grid-template-columns: auto minmax(0, 1fr) auto auto; align-items: center; gap: 14px;
  width: 100%; padding: 12px 14px; border-radius: 12px; text-align: left;
  background: #fff; border: 1px solid var(--border-light); box-shadow: none; color: var(--ink); font-weight: 400;
}
button.rp-item:hover { border-color: var(--ok-border); background: #f6fdf9; box-shadow: none; transform: translateX(2px); }
button.rp-item:disabled { opacity: .55; cursor: not-allowed; transform: none; }
.rp-item-main { display: flex; flex-direction: column; gap: 4px; min-width: 0; }
.rp-item-main strong { font-size: 14px; }
.rp-item-main em, .rp-order-no em, .rp-item-amt em { font-style: normal; font-size: 11.5px; color: var(--muted); }
.rp-item-amt { display: flex; flex-direction: column; align-items: flex-end; }
.rp-item-amt b { font-family: var(--font-mono); font-size: 15px; font-variant-numeric: tabular-nums; }
.rp-order-no { display: flex; flex-direction: column; min-width: 96px; }
.rp-order-no strong { font-family: var(--font-mono); font-size: 13.5px; }
button.rp-order { grid-template-columns: auto minmax(0, 1fr) auto; }
.rp-tags { display: flex; flex-wrap: wrap; gap: 5px; }
.rp-tag { font-size: 11px; font-weight: 600; padding: 2px 8px; border-radius: var(--radius-full); background: var(--neutral-bg); color: var(--neutral-fg); white-space: nowrap; }
.rp-tag.is-bad { background: var(--warn-bg); color: var(--warn); }
.rp-tag.is-warn { background: var(--pending-bg); color: #92400e; }
.rp-tag.is-ok { background: var(--ok-bg); color: var(--ok); }
.rp-customer-card { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; gap: 14px; align-items: center; padding: 14px 16px; border-radius: 14px; background: linear-gradient(135deg, #eff6ff, #fff); border: 1px solid #dbeafe; margin-bottom: 14px; }
.rp-avatar-lg { width: 48px; height: 48px; font-size: 16px; }
.rp-cc-main { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.rp-cc-main strong { font-family: var(--font-display); font-size: 18px; }
.rp-cc-main span { font-size: 12.5px; color: var(--label); }
.rp-cc-terms { color: var(--muted) !important; }
.rp-cc-figs { display: flex; gap: 16px; }
.rp-cc-figs div { display: flex; flex-direction: column; align-items: flex-end; }
.rp-cc-figs span { font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.rp-cc-figs b { font-family: var(--font-mono); font-size: 15px; }
.rp-cc-figs .is-bad b, .rp-cc-figs .is-bad span { color: var(--warn); }
.rp-sub-head { font-size: 10.5px; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; color: var(--muted); margin: 0 0 8px; }
.rp-order-strip { display: grid; grid-template-columns: repeat(5, minmax(0, 1fr)); gap: 1px; border-radius: 12px; overflow: hidden; background: var(--border-light); border: 1px solid var(--border-light); margin-bottom: 16px; }
.rp-order-strip div { display: flex; flex-direction: column; gap: 2px; padding: 10px 12px; background: var(--card-subtle); min-width: 0; }
.rp-order-strip span { font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.rp-order-strip b { font-size: 13.5px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.rp-order-strip .is-due { background: var(--pending-bg); }
.rp-order-strip .is-due b { color: #92400e; font-family: var(--font-mono); }
.rp-amount { padding: 14px 16px; border-radius: 14px; background: linear-gradient(160deg, var(--ok-bg), #fff); border: 1px solid var(--ok-border); margin-bottom: 14px; }
.rp-amount label { color: #065f46; }
.rp-amount-row { display: flex; align-items: center; gap: 10px; }
.rp-cur { font-family: var(--font-display); font-size: 22px; font-weight: 700; color: #065f46; }
.rp-amount-row input { margin: 0; font-family: var(--font-display); font-size: 32px; font-weight: 700; padding: 8px 12px; border: 2px solid var(--ok-border); font-variant-numeric: tabular-nums; }
.rp-amount-row input:focus { border-color: var(--ok); box-shadow: 0 0 0 4px rgba(5,150,105,.12); }
.rp-chips { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 10px; }
button.rp-chip { padding: 5px 12px; border-radius: var(--radius-full); font-size: 12px; font-weight: 600; background: #fff; color: var(--label); border: 1px solid var(--border); box-shadow: none; }
button.rp-chip:hover { border-color: var(--ok); color: var(--ok); background: #fff; box-shadow: none; }
button.rp-chip.is-primary { border-color: var(--ok); color: var(--ok); }
.rp-after { margin: 8px 0 0; font-size: 12.5px; font-weight: 600; color: var(--label); }
.rp-after.is-ok { color: var(--ok); }
.rp-after.is-bad { color: var(--warn); }
.rp-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
.rp-sign { margin-top: 6px; padding: 12px 14px 2px; border-radius: 12px; background: var(--card-subtle); border: 1px solid var(--border-light); }
.rp-foot { display: flex; align-items: center; gap: 12px; padding: 12px 22px; border-top: 1px solid var(--border-light); background: #fff; }
.rp-foot-note { flex: 1; font-size: 12px; color: var(--muted); }
#rp-save-btn { padding: 10px 20px; border-radius: 10px; background: linear-gradient(180deg, #10b981, #059669); border-color: #047857; box-shadow: 0 8px 18px -8px rgba(5,150,105,.8); }
#rp-save-btn:hover { background: linear-gradient(180deg, #059669, #047857); }
@media (max-width: 680px) {
  .rp-order-strip { grid-template-columns: 1fr 1fr; }
  .rp-grid { grid-template-columns: 1fr; }
  .rp-customer-card { grid-template-columns: auto minmax(0, 1fr); }
  .rp-cc-figs { grid-column: 1 / -1; justify-content: flex-start; }
  button.rp-item { grid-template-columns: auto minmax(0, 1fr) auto; }
  .fxp-toolbar button { margin-left: 0; }
}
.rp-search input { padding-left: 36px; margin: 0; }

/* ===================== Oil receipts: vessel discharge into Ardmore (2026-10-21) =====================
   The ops-* console (board, rail, step cards) with the rows this form needs:
   tank lines and landed-charge lines. oil-receipts.js. */
.orc-qty { display: grid; grid-template-columns: minmax(220px, 1fr) minmax(0, 1.8fr); gap: 14px; align-items: stretch; }
.orc-bl .pdo-input-unit input { font-family: var(--font-display); font-size: 30px; font-weight: 700; font-variant-numeric: tabular-nums; padding: 10px 14px; border: 2px solid var(--ok-border); margin-bottom: 8px; }
.orc-tanks-card { margin-top: 0; }
.orc-row { display: grid; gap: 8px; align-items: center; margin-bottom: 8px; }
.orc-row input, .orc-row select { margin-bottom: 0; }
.orc-row .pdo-input-unit { margin: 0; }
.orc-tank-row { grid-template-columns: minmax(120px, 160px) minmax(120px, 180px) 1fr 36px; }
.orc-tank-mt { font-weight: 700; font-variant-numeric: tabular-nums; }
.orc-tank-room { font-size: 12px; }
.orc-tank-room.is-bad { color: var(--warn); font-weight: 600; }
.orc-charge-row { grid-template-columns: minmax(140px, 1.4fr) minmax(100px, 140px) minmax(150px, 1fr) minmax(90px, 120px) 36px; }
.orc-charge-total { font-size: 12.5px; font-weight: 600; color: var(--label); font-variant-numeric: tabular-nums; text-align: right; }
button.orc-row-remove { width: 36px; height: 36px; padding: 0; color: var(--muted); }
button.orc-row-remove:hover { color: var(--warn); border-color: var(--warn-border); background: var(--warn-bg); }
button.orc-add-btn { margin: 2px 0 12px; }
.orc-figure { padding: 10px 12px; border-radius: 8px; background: var(--card-subtle); border: 1px solid var(--border-light); font-weight: 700; font-variant-numeric: tabular-nums; min-height: 40px; }
.orc-check { display: flex; gap: 10px; align-items: flex-start; margin-top: 14px; font-weight: 600; color: var(--ink); cursor: pointer; }
.orc-check input { width: auto; margin: 3px 0 0; }
.orc-check .muted { font-weight: 500; }
.orc-check-msg { margin: 10px 0 0; padding: 10px 12px; border-radius: 8px; background: rgba(248,113,113,.14); border: 1px solid rgba(248,113,113,.4); color: #fecaca; font-weight: 600; }
#orc-table tr.orc-reversed td { color: var(--muted); }
#orc-table tr.orc-reversed td strong { text-decoration: line-through; }
#orc-table tr.orc-reversal td { background: var(--card-subtle); }
#orc-table .orc-short { color: var(--warn); font-size: 12px; font-weight: 600; }
@media (max-width: 720px) {
  .orc-qty { grid-template-columns: 1fr; }
  .orc-tank-row { grid-template-columns: 1fr 1fr 36px; }
  .orc-tank-room { grid-column: 1 / -1; order: 4; }
  .orc-charge-row { grid-template-columns: 1fr 1fr 36px; }
  .orc-charge-basis { grid-column: 1 / 3; }
  .orc-charge-total { text-align: left; }
}

/* ===================== General ledger (2026-10-22, migration 129) =====================
   The Finance pages' look (fxp-hero, fxp-toolbar, quiet tables) plus the
   health panel, the chart's heading rows and the journal editor. general-ledger.js. */
.gl-hero-actions { display: flex; gap: 8px; }
button.gl-new-btn { background: #10b981; border-color: #10b981; color: #fff; border-radius: 10px; padding: 10px 18px; font-weight: 700; }
button.gl-new-btn:hover { background: #059669; border-color: #059669; }
.gl-health { border-radius: 16px; padding: 14px 18px; border-left: 4px solid var(--ok); }
.gl-health.is-bad { border-left-color: var(--warn); background: #fffafa; }
.gl-health-head { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; margin-bottom: 10px; }
.gl-health-head strong { font-family: var(--font-display); font-size: 16px; }
.gl-lamp { width: 12px; height: 12px; border-radius: 50%; background: var(--ok); box-shadow: 0 0 0 4px var(--ok-bg); }
.gl-lamp.is-bad { background: var(--warn); box-shadow: 0 0 0 4px var(--warn-bg); }
.gl-coverage { display: flex; flex-wrap: wrap; gap: 6px 8px; align-items: center; margin: 0 0 12px; padding: 10px 12px; border-radius: 10px; background: #fffbeb; border: 1px solid #fde68a; }
.gl-coverage-title { font-size: 10.5px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: #92400e; margin-right: 4px; }
.gl-cov { font-size: 12px; padding: 3px 9px; border-radius: var(--radius-full); }
.gl-cov.is-in { background: var(--ok-bg); color: var(--ok); }
.gl-cov.is-out { background: #fff; color: #92400e; border: 1px dashed #f59e0b; }
.gl-cov em { font-style: normal; opacity: .75; }
.gl-checks { display: grid; grid-template-columns: repeat(auto-fit, minmax(260px, 1fr)); gap: 8px 16px; }
.gl-check { display: flex; gap: 10px; align-items: flex-start; padding: 8px 10px; border-radius: 10px; background: var(--card-subtle); }
.gl-check-dot { width: 9px; height: 9px; border-radius: 50%; margin-top: 5px; flex-shrink: 0; background: var(--ok); }
.gl-check.is-bad { background: var(--warn-bg); }
.gl-check.is-bad .gl-check-dot { background: var(--warn); }
.gl-check.is-soft .gl-check-dot { background: var(--pending); }
.gl-check-name { font-size: 12.5px; font-weight: 600; color: var(--ink); }
.gl-check-fig { font-size: 12px; font-variant-numeric: tabular-nums; }
.gl-diff { color: var(--warn); }
.gl-seg-actions { display: flex; gap: 12px; align-items: center; flex-wrap: wrap; }
.gl-link { font-size: 13px; font-weight: 600; }
.gl-count { display: inline-flex; min-width: 18px; height: 18px; padding: 0 5px; border-radius: 9px; background: var(--warn); color: #fff; font-size: 11px; align-items: center; justify-content: center; margin-left: 4px; }
/* General ledger: grouped, sticky navigation and the folded health line (2026-11-01). */
.gl-nav { position: sticky; top: 0; z-index: 20; display: flex; align-items: flex-end; justify-content: space-between; gap: 10px 16px; flex-wrap: wrap; margin: 0 0 18px; padding: 12px 16px; background: var(--card); border: 1px solid var(--border); border-radius: 14px; box-shadow: 0 6px 16px -12px rgba(15, 23, 42, .35); }
.gl-nav-groups { display: flex; flex-wrap: wrap; gap: 10px 0; }
.gl-nav-group { display: flex; flex-direction: column; gap: 6px; padding: 0 10px; border-left: 1px solid var(--border-light); }
.gl-nav-group:first-child { padding-left: 0; border-left: 0; }
.gl-nav-label { font-size: 10.5px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: var(--muted); }
.gl-nav-btns { display: flex; flex-wrap: wrap; gap: 4px; }
.gl-nav-btn { display: inline-flex; align-items: center; gap: 4px; padding: 6px 10px; border-radius: 8px; border: 1px solid transparent; background: var(--card-subtle); color: var(--ink); font-size: 12.5px; white-space: nowrap; font-weight: 600; cursor: pointer; transition: background .15s, border-color .15s, color .15s; }
.gl-nav-btn:hover { border-color: var(--border); background: var(--card); }
.gl-nav-btn.active { background: var(--brand-tint); border-color: var(--brand-tint-border); color: var(--brand-dark); }
.gl-nav-btn:focus-visible, .gl-health-toggle:focus-visible { outline: 2px solid var(--brand); outline-offset: 2px; }
.gl-health-pills { display: inline-flex; flex-wrap: wrap; gap: 6px; }
.gl-pill { display: inline-flex; align-items: center; padding: 2px 9px; border-radius: 999px; font-size: 12px; font-weight: 600; background: var(--card-subtle); color: var(--ink); }
.gl-pill.is-ok { background: #ecfdf5; color: #047857; }
.gl-pill.is-bad { background: var(--warn-bg); color: var(--warn); }
.gl-pill.is-soft { background: #fff7ed; color: #c2410c; }
.gl-pill.is-info { background: #fffbeb; color: #92400e; }
.gl-health-when { font-size: 12px; }
.gl-health-toggle { margin-left: auto; padding: 5px 12px; border-radius: 8px; border: 1px solid var(--border); background: var(--card); color: var(--ink); font-size: 12.5px; font-weight: 600; cursor: pointer; }
.gl-health-toggle:hover { background: var(--card-subtle); }
.gl-health .gl-health-head:last-child { margin-bottom: 0; }
@media (max-width: 720px) {
  .gl-nav { position: static; }
  .gl-nav-group { padding: 0; border-left: 0; width: 100%; }
  .gl-health-toggle { margin-left: 0; }
}
#tab-general-ledger .reg-table thead th { position: static; background: transparent; color: var(--muted); font-size: 10.5px; letter-spacing: .08em; border-bottom: 1px solid var(--border); }
#tab-general-ledger .reg-table td { padding-top: 9px; padding-bottom: 9px; }
.gl-head-row td { background: var(--card-subtle); font-size: 12.5px; }
tr.gl-acc-row { cursor: pointer; }
tr.gl-acc-row:hover td, tr.gl-acc-row:focus td { background: #f6f9fd; }
tr.is-retired td { color: var(--muted); }
.gl-code { font-family: var(--font-mono); font-size: 12px; color: var(--label); margin-right: 4px; }
.gl-map-intro { margin: 0 0 10px; }
.gl-empty { padding: 18px; color: var(--muted); border-radius: 14px; }
button.gl-wait-card { display: flex; width: 100%; justify-content: space-between; gap: 16px; text-align: left; padding: 14px 18px; margin-bottom: 10px; border-radius: 14px; border-left: 4px solid var(--pending); background: var(--card); color: var(--ink); font-weight: 400; }
button.gl-wait-card:hover { border-color: var(--pending); box-shadow: var(--shadow-sm); }
.gl-wait-side { text-align: right; flex-shrink: 0; }
.modal-box.gl-wide-box { max-width: 980px; width: calc(100% - 32px); }
.gl-modal-scroll { max-height: 52vh; overflow: auto; }
.gl-journal-facts { display: grid; grid-template-columns: repeat(auto-fit, minmax(190px, 1fr)); gap: 8px 16px; margin: 4px 0 12px; }
.gl-journal-facts div { display: flex; flex-direction: column; gap: 2px; }
.gl-journal-facts span { font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.gl-journal-facts strong { font-weight: 600; font-size: 13px; }
#gl-journal-lines tfoot td { border-top: 2px solid var(--border); }
.gl-decide { margin-top: 12px; padding: 12px 14px; border-radius: 10px; background: var(--card-subtle); border: 1px solid var(--border-light); }
.gl-own-note { margin-right: auto; align-self: center; font-size: 12.5px; }
#gl-journal-actions { display: flex; flex-wrap: wrap; gap: 8px; justify-content: flex-end; }
.modal-box.gl-new-box { padding: 0; overflow: hidden; display: flex; flex-direction: column; max-height: calc(100vh - 48px); }
.gl-new-box .rp-head h2 { margin: 0; color: #fff; font-size: 19px; }
.gl-new-box .rp-head p { margin: 2px 0 0; color: #c3cfe0; font-size: 12.5px; }
.gl-new-box .rp-head .modal-close-btn { margin-left: auto; color: #fff; }
.gl-new-body { padding: 16px 22px; overflow: auto; }
.gl-new-foot { padding: 12px 22px 16px; border-top: 1px solid var(--border); margin: 0; }
.gl-new-hint { font-size: 12.5px; margin: 0 0 10px; }
.gl-lines-edit td { padding: 6px; vertical-align: middle; }
.gl-lines-edit select, .gl-lines-edit input { margin: 0; }
.gl-lines-edit .gl-l-acc { min-width: 260px; }
.gl-lines-edit .gl-l-dr, .gl-lines-edit .gl-l-cr { width: 130px; text-align: right; font-variant-numeric: tabular-nums; font-weight: 600; }
.gl-balance-bar { display: grid; grid-template-columns: 1fr 1fr 2fr; gap: 10px; margin: 12px 0; }
.gl-balance-bar div { padding: 10px 12px; border-radius: 10px; background: var(--card-subtle); border: 1px solid var(--border-light); display: flex; flex-direction: column; gap: 2px; }
.gl-balance-bar span { font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.gl-balance-bar strong { font-variant-numeric: tabular-nums; }
.gl-balance-bar .is-ok { background: var(--ok-bg); border-color: var(--ok-border); color: var(--ok); }
.gl-balance-bar .is-bad { background: var(--pending-bg); border-color: #fde68a; color: #92400e; }
.gl-balance-bar .is-bad strong { font-size: 12.5px; font-weight: 600; }
/* Customer money: trucks against money, order by order (migration 130) */
.gl-pos-totals { display: grid; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); gap: 10px; margin-bottom: 14px; }
.gl-pos-totals div { padding: 12px 14px; border-radius: 12px; background: var(--card); border: 1px solid var(--border); display: flex; flex-direction: column; gap: 2px; }
.gl-pos-totals span { font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.gl-pos-totals strong { font-family: var(--font-display); font-size: 19px; font-variant-numeric: tabular-nums; }
.gl-pos-totals em { font-style: normal; font-size: 12px; color: var(--muted); }
.gl-pos-totals .is-bad { border-color: var(--warn-border); background: var(--warn-bg); }
.gl-pos-totals .is-bad strong { color: var(--warn); }
.gl-pos-totals .is-ok { border-color: var(--ok-border); }
.gl-pos { border-radius: 14px; padding: 14px 18px; margin-bottom: 12px; border-left: 4px solid var(--border); }
.gl-pos.is-flag { border-left-color: var(--warn); }
.gl-pos.is-watch, .gl-pos.is-owing { border-left-color: var(--pending); }
.gl-pos.is-waiting { border-left-color: var(--accent-blue); }
.gl-pos.is-settled { border-left-color: var(--ok); }
.gl-pos-head { display: flex; justify-content: space-between; gap: 12px; flex-wrap: wrap; align-items: flex-start; }
.gl-pos-head .badge { margin-left: 6px; }
.gl-pos-held { text-align: right; display: flex; flex-direction: column; }
.gl-pos-held span { font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); }
.gl-pos-held strong { font-family: var(--font-display); font-size: 20px; font-variant-numeric: tabular-nums; }
.gl-pos.is-flag .gl-pos-held strong { color: var(--warn); }
.gl-pos-figs { display: grid; grid-template-columns: repeat(3, minmax(90px, auto)) 1fr; gap: 6px 18px; margin: 10px 0 6px; align-items: end; }
.gl-pos-figs div { display: flex; flex-direction: column; gap: 1px; font-size: 13px; }
.gl-pos-figs span { font-size: 11px; color: var(--muted); }
.gl-pos-figs b { font-variant-numeric: tabular-nums; }
.gl-pos-bar i { display: block; height: 8px; border-radius: 4px; background: var(--neutral-bg); overflow: hidden; margin-top: 4px; }
.gl-pos-bar em { display: block; height: 100%; background: linear-gradient(90deg, #10b981, #34d399); }
.gl-pos-why { margin: 8px 0 6px; padding: 8px 12px 8px 28px; border-radius: 10px; background: var(--warn-bg); color: #7f1d1d; font-size: 13px; }
.gl-pos-why li + li { margin-top: 4px; }
.gl-pos-next { font-size: 13px; font-weight: 600; margin: 6px 0; }
.gl-pos-next span { font-size: 10.5px; letter-spacing: .06em; text-transform: uppercase; color: var(--muted); margin-right: 6px; }
.gl-pos-trucks { display: flex; flex-wrap: wrap; gap: 6px; margin: 6px 0; }
.gl-truck { font-size: 12px; padding: 3px 9px; border-radius: var(--radius-full); background: var(--card-subtle); border: 1px solid var(--border-light); font-variant-numeric: tabular-nums; }
.gl-truck.is-short { background: var(--warn-bg); border-color: var(--warn-border); color: #7f1d1d; }
.gl-pos-ledger { font-size: 12px; margin-top: 4px; }
/* Exceptions board (phase 7). */
.gl-ex { display: flex; justify-content: space-between; align-items: center; gap: 12px; padding: 12px 16px; margin-bottom: 8px; border-left: 4px solid var(--border-light); }
.gl-ex-high { border-left-color: var(--warn); }
.gl-ex-medium { border-left-color: var(--pending); }
.gl-ex strong { display: block; margin-top: 4px; }
/* Migration 131: refunds, moves, credit notes, write-offs on an order. */
.gl-pos-docs { margin: 6px 0; padding: 8px 12px 8px 28px; border-radius: 10px; background: var(--ok-bg); font-size: 13px; }
.gl-pos-docs li + li { margin-top: 4px; }
.gl-pos-docs .badge { margin: 0 4px; }
.gl-pos-act { margin-top: 8px; }
.gl-set-kinds { display: grid; grid-template-columns: repeat(4, 1fr); gap: 8px; margin: 12px 0 4px; }
button.gl-set-kind { display: flex; flex-direction: column; gap: 3px; text-align: left; padding: 10px 12px; border-radius: 12px; border: 1px solid var(--border-light);
  background: var(--card); color: var(--ink); font-weight: 400; }
button.gl-set-kind strong { font-size: 13.5px; }
button.gl-set-kind span { font-size: 12px; color: var(--muted); }
button.gl-set-kind.active { border-color: var(--accent-blue); box-shadow: 0 0 0 2px color-mix(in srgb, var(--accent-blue) 25%, transparent); }
button.gl-set-kind:disabled { opacity: .55; cursor: not-allowed; }
@media (max-width: 720px) { .gl-set-kinds { grid-template-columns: 1fr 1fr; } }
@media (max-width: 720px) {
  .gl-pos-figs { grid-template-columns: repeat(3, 1fr); }
  .gl-pos-bar { grid-column: 1 / -1; }
  .gl-pos-held { text-align: left; }
}
@media (max-width: 720px) {
  .gl-balance-bar { grid-template-columns: 1fr 1fr; }
  .gl-balance-bar div:last-child { grid-column: 1 / -1; }
  button.gl-wait-card { flex-direction: column; }
  .gl-wait-side { text-align: left; }
}
.gl-cl { display: flex; justify-content: space-between; align-items: center; gap: 12px; padding: 10px 16px; margin-bottom: 6px; border-left: 4px solid var(--border-light); }
.gl-cl-bad { border-left-color: var(--warn); }
.gl-cl-advice { border-left-color: var(--pending); }
.gl-cl strong { margin-left: 4px; }
.gl-cl-act { display: flex; flex-wrap: wrap; align-items: end; gap: 12px; margin: 12px 0 20px; }
.gl-fa-form { display: grid; grid-template-columns: repeat(auto-fit, minmax(190px, 1fr)); gap: 12px; align-items: end; margin: 12px 0; }
/* Opening balances (migration 148). */
.gl-ob-date { display: flex; align-items: center; justify-content: space-between; gap: 12px 20px; flex-wrap: wrap; padding: 14px 18px; margin-bottom: 14px; border-left: 4px solid var(--ok); }
.gl-ob-date.is-bad { border-left-color: var(--warn); background: var(--warn-bg); }
.gl-ob-date > div:first-child { display: flex; flex-direction: column; gap: 2px; }
.gl-ob-date-label { font-size: 10.5px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: var(--muted); }
.gl-ob-date strong { font-family: var(--font-display); font-size: 20px; }
.gl-ob-date-set { display: flex; gap: 8px; align-items: center; }
.gl-ob-total td { border-top: 2px solid var(--border); background: var(--card-subtle); }
.gl-ob-hint { grid-column: 1 / -1; margin: 0; font-size: 12.5px; }
.gl-bd-grid input { width: 5.5em; text-align: right; }

/* Company branding and the demonstration (branding.js, 2026-11-03). */
.login-powered { margin: 14px 0 0; text-align: center; font-size: 12px; color: var(--muted); }
.login-powered:empty { display: none; }
.login-demo-link { display: block; margin-top: 12px; padding: 10px 12px; border-radius: 10px; background: var(--brand-tint); border: 1px solid var(--brand-tint-border); color: var(--brand-dark); font-size: 13px; font-weight: 600; text-align: center; text-decoration: none; }
.login-demo-link:hover { background: var(--card); }
.demo-strip { display: flex; align-items: center; gap: 10px 16px; flex-wrap: wrap; padding: 7px 18px; background: #0f172a; color: #e2e8f0; font-size: 12.5px; }
.demo-strip strong { color: #fff; }
.demo-strip a { color: #fff; font-weight: 600; text-decoration: none; padding: 3px 10px; border-radius: 999px; background: rgba(255, 255, 255, .12); }
.demo-strip a:hover { background: rgba(255, 255, 255, .22); }
.demo-strip-dot { width: 8px; height: 8px; border-radius: 50%; background: #22c55e; box-shadow: 0 0 0 3px rgba(34, 197, 94, .25); }
.demo-strip a:first-of-type { margin-left: auto; }
@media (max-width: 720px) { .demo-strip a:first-of-type { margin-left: 0; } }
.cs-panel { margin-bottom: 18px; }
.cs-intro { margin: 0 0 12px; }
.cs-actions { display: flex; align-items: center; gap: 12px; margin-top: 14px; flex-wrap: wrap; }
