/* styles/tabs/levelling.css */
/* ===========================================================================
   PROJECT LEVELLING CENTER
   A planning-control environment, not a BI dashboard. The design rules that
   produced it:
     · DENSITY IS A FEATURE. A planner compares numbers; whitespace between
       them is friction. Type scale is tight, tables are compact, and the
       screen is allowed to be full.
     · COLOUR MEANS ONE THING. Green = inside capacity / no schedule damage.
       Amber = approaching a limit. Red = over capacity or negative float.
       Slate = the "before" state. Nothing is coloured for decoration.
     · STATE IS ALWAYS VISIBLE. The simulation banner is the loudest element
       on the page, because the one thing a planner must never be unsure of is
       whether they are looking at the master schedule or a proposal.
     · NO ANIMATION that delays a reading. Transitions are on hover states
       only, and every one of them is under 150ms.
   Tokens sit on the same NEXORA palette the SOW Center and the input tab use,
   so the module reads as part of the product rather than a bolt-on.
   ========================================================================= */

#tp-levelling, .lvl-portal {
  --lvl-green:#24B47E; --lvl-green-d:#1B9A6B; --lvl-green-t:#EAF7F1;
  --lvl-ink:#14202A; --lvl-ink-2:#37424D; --lvl-mut:#6B7580; --lvl-mut-2:#8A94A0;
  --lvl-bg:#F5F7F9; --lvl-card:#FFFFFF; --lvl-wash:#FAFBFC;
  --lvl-line:#E6EAEE; --lvl-line-2:#EFF2F5; --lvl-line-3:#D9DFE5;
  --lvl-ok:#2E7D63; --lvl-warn:#C08A3A; --lvl-risk:#C0564A; --lvl-info:#4A77AE; --lvl-neutral:#8A94A0;
  --lvl-ok-t:#E9F7F1; --lvl-warn-t:#FDF4E5; --lvl-risk-t:#FBEEEC; --lvl-info-t:#EDF2F9;
  /* BEFORE AND AFTER ARE A CONTRAST, NOT A VERDICT. "After" was the same
     green the app uses for done, applied, within capacity — so a proposal
     nobody had agreed to yet was already wearing the colour of a settled
     fact. Blue is a state, not an approval. */
  --lvl-before:#8A94A0; --lvl-after:#2563EB;
  /* Categorical slots — the validated 8-hue set. Assigned by ENTITY, never by
     rank, in lvl-charts.js. Passes lightness band, chroma floor, adjacent CVD
     separation and the normal-vision floor on this surface; three of them sit
     under 3:1 contrast in light mode, which is why every chart that uses them
     also ships a legend and a table twin (the relief rule). */
  --lvl-s1:#2a78d6; --lvl-s2:#eb6834; --lvl-s3:#1baf7a; --lvl-s4:#eda100;
  --lvl-s5:#e87ba4; --lvl-s6:#008300; --lvl-s7:#4a3aa7; --lvl-s8:#e34948;
  --lvl-s9:#00a8b3; --lvl-s10:#a96a12; --lvl-s11:#bb3fb0; --lvl-s12:#6d8c14;
  --lvl-other:#8A94A0; --lvl-heat:#F7941D;
  --lvl-r:12px; --lvl-r-s:8px; --lvl-r-xs:5px;
  /* ── ONE TYPE SCALE, NOT SEVENTEEN SIZES ────────────────────────────
     The cockpit was set in 8, 8.5, 9, 9.5, 10, 10.5, 11, 11.5, 12, 12.5,
     13, 15, 16, 17, 19 and 30px. Sixteen sizes is not a hierarchy — two
     values 0.5px apart read as the same size and cost the reader the one
     thing a scale is for, which is knowing what outranks what without
     measuring it. Seven steps, each a clear jump from the last, and 9.5px
     is the FLOOR: the 8px uppercase mono captions were under every
     legibility threshold there is, and they were carrying the labels on
     the six numbers this page exists to report.
     Density is still the rule here — this is a planning console, not a
     landing page — but density is tight SPACING, never unreadable type.

     ── AND THE SCALE BENDS WITH THE SCREEN ────────────────────────────
     The sizes below are the ones this page was designed at, on a 1440x900
     window — that is where each ratio lands. What was wrong was that they
     were the sizes on EVERY window: a 1280x720 laptop got 26px headline
     figures and 16px card headings in boxes two thirds the size, so the
     words were too big for what held them and the chart underneath paid for
     it. Each step is a ratio now, floored where legibility ends and capped
     a little above the design size, and it reads the SMALLER of the two
     viewport dimensions because this page never scrolls — a 1920x900 window
     is as short as a 1280x720 one and has to spend its height the same way.
     The whole cockpit steps down together instead of one row being trimmed
     by a breakpoint while the rest stays large. */
  --lvl-t-1:clamp(9px,min(.7vw,1.11vh),13px);      /* uppercase micro-caption */
  --lvl-t-2:clamp(9.5px,min(.76vw,1.22vh),14px);   /* the note under a figure */
  --lvl-t-3:clamp(10.5px,min(.83vw,1.33vh),16px);  /* a row of a table */
  --lvl-t-4:clamp(11px,min(.9vw,1.44vh),17px);     /* body, tab labels, buttons */
  --lvl-t-5:clamp(13px,min(1.11vw,1.78vh),21px);   /* a card or board heading */
  --lvl-t-6:clamp(18px,min(1.81vw,2.89vh),34px);   /* the page's loudest mark */
  --lvl-t-7:clamp(22px,min(2.22vw,3.56vh),42px);   /* the number a board is about */
  /* the same rhythm, on the same ratio */
  --lvl-sp-1:clamp(3px,min(.28vw,.44vh),5px); --lvl-sp-2:clamp(5px,min(.56vw,.89vh),10px);
  --lvl-sp-3:clamp(7px,min(.83vw,1.33vh),15px); --lvl-sp-4:clamp(9px,min(1.11vw,1.78vh),20px);
  --lvl-sh:0 1px 2px rgba(20,32,42,.04),0 1px 3px rgba(20,32,42,.03);
  --lvl-sh-2:0 4px 16px rgba(20,32,42,.07),0 1px 3px rgba(20,32,42,.04);
  --lvl-font:"Inter","Segoe UI",system-ui,sans-serif;
  --lvl-head:"Plus Jakarta Sans","Inter","Segoe UI",sans-serif;
  --lvl-mono:"JetBrains Mono","SFMono-Regular",Consolas,monospace;
  background:var(--lvl-bg); color:var(--lvl-ink);
}
#tp-levelling *,#tp-levelling *::before,#tp-levelling *::after,
.lvl-portal,.lvl-portal *,.lvl-portal *::before,.lvl-portal *::after{box-sizing:border-box}
#tp-levelling *:focus-visible,.lvl-portal *:focus-visible{outline:2px solid var(--lvl-green);outline-offset:2px;border-radius:var(--lvl-r-xs)}
/* The drawer is moved to <body> at render time: an ancestor of the tab panel
   establishes a containing block for fixed positioning (a transform or a
   filter somewhere in the app shell), which clipped the drawer's own header
   and close button off the top of the screen. Living on <body> it is fixed to
   the viewport, as intended — so it carries its own token block and its own
   font stack rather than inheriting the panel's. */
.lvl-portal{font-family:var(--lvl-font);font-size:12.5px;line-height:1.5;color:var(--lvl-ink);-webkit-font-smoothing:antialiased}
#lvlOut{font-family:var(--lvl-font);font-size:12.5px;line-height:1.5;color:var(--lvl-ink);-webkit-font-smoothing:antialiased;padding:0}
.lvl{display:flex;flex-direction:column;min-height:100%}
.lvl-ic{width:16px;height:16px;flex:0 0 auto}
.lvl-ic-s{width:14px;height:14px}.lvl-ic-xs{width:12px;height:12px}.lvl-ic-l{width:22px;height:22px}.lvl-ic-xl{width:38px;height:38px}

/* ── top bar ─────────────────────────────────────────────────────────── */
.lvl-top{display:flex;align-items:center;justify-content:space-between;gap:18px;flex-wrap:wrap;
  padding:12px 18px;background:var(--lvl-card);border-bottom:1px solid var(--lvl-line);position:sticky;top:0;z-index:30}
.lvl-top-l{display:flex;align-items:center;gap:16px;min-width:0;flex-wrap:wrap}
.lvl-title h1{margin:0;font:800 17px/1.15 var(--lvl-head);letter-spacing:-.01em}
.lvl-title p{margin:2px 0 0;font-size:10.5px;color:var(--lvl-mut);letter-spacing:.04em;text-transform:uppercase;font-weight:600}
.lvl-crumbs{display:flex;align-items:center;gap:5px;font-size:11px;color:var(--lvl-mut);padding-left:16px;border-left:1px solid var(--lvl-line)}
.lvl-crumbs .is-cur{color:var(--lvl-ink);font-weight:600}
.lvl-top-r{display:flex;align-items:center;gap:8px;flex-wrap:wrap}
.lvl-search{display:flex;align-items:center;gap:7px;background:var(--lvl-wash);border:1px solid var(--lvl-line);
  border-radius:var(--lvl-r-s);padding:0 10px;height:32px;color:var(--lvl-mut);min-width:210px}
.lvl-search input{border:0;background:none;outline:0;font:inherit;font-size:12px;color:var(--lvl-ink);width:100%;height:100%}
.lvl-btn{display:inline-flex;align-items:center;gap:6px;height:32px;padding:0 12px;border-radius:var(--lvl-r-s);
  border:1px solid var(--lvl-line-3);background:var(--lvl-card);color:var(--lvl-ink-2);font:600 12px/1 var(--lvl-font);
  cursor:pointer;transition:background .12s,border-color .12s,color .12s;white-space:nowrap}
.lvl-btn:hover{background:var(--lvl-wash);border-color:var(--lvl-mut-2);color:var(--lvl-ink)}
.lvl-btn.is-primary{background:var(--lvl-green);border-color:var(--lvl-green);color:#fff}
.lvl-btn.is-primary:hover{background:var(--lvl-green-d);border-color:var(--lvl-green-d);color:#fff}
.lvl-btn.is-ghost{background:none;border-color:transparent;color:var(--lvl-mut)}
.lvl-btn.is-ghost:hover{background:var(--lvl-wash);color:var(--lvl-ink)}
/* the one destructive variant: it removes work a planner staged, and it
   should not look like the button beside it that keeps it */
.lvl-btn.is-danger{background:var(--lvl-risk);border-color:var(--lvl-risk);color:#fff}
.lvl-btn.is-danger:hover{filter:brightness(.94)}
.lvl-btn.is-sm{height:26px;padding:0 9px;font-size:11px}
.lvl-btn.is-lg{height:38px;padding:0 18px;font-size:13px}
.lvl-btn[disabled]{opacity:.45;cursor:not-allowed}
.lvl-icobtn{display:inline-flex;align-items:center;justify-content:center;width:26px;height:26px;border-radius:var(--lvl-r-xs);
  border:1px solid transparent;background:none;color:var(--lvl-mut);cursor:pointer}
.lvl-icobtn:hover{background:var(--lvl-wash);color:var(--lvl-ink)}
.lvl-link{background:none;border:0;padding:0;font:inherit;color:var(--lvl-green-d);cursor:pointer;text-align:left;
  border-bottom:1px solid transparent}
.lvl-link:hover{border-bottom-color:currentColor}

/* ── rail nav ────────────────────────────────────────────────────────── */
.lvl-rail{display:flex;align-items:center;gap:3px;flex-wrap:wrap;padding:7px 18px;background:var(--lvl-card);
  border-bottom:1px solid var(--lvl-line);position:sticky;top:57px;z-index:29}
.lvl-rail-b{display:inline-flex;align-items:center;gap:6px;height:30px;padding:0 11px;border-radius:var(--lvl-r-s);
  border:1px solid transparent;background:none;color:var(--lvl-ink-2);font:600 12px/1 var(--lvl-font);cursor:pointer;transition:background .12s}
.lvl-rail-b i{font:800 9px/1 var(--lvl-mono);color:var(--lvl-mut-2);font-style:normal}
.lvl-rail-b em{font-style:normal;font:700 10px/1 var(--lvl-mono);background:var(--lvl-line-2);color:var(--lvl-mut);
  padding:2px 5px;border-radius:20px}
.lvl-rail-b:hover{background:var(--lvl-wash)}
.lvl-rail-b.is-on{background:var(--lvl-green-t);border-color:rgba(36,180,126,.28);color:var(--lvl-green-d)}
.lvl-rail-b.is-on i{color:var(--lvl-green-d)}
.lvl-rail-b.is-on em{background:rgba(36,180,126,.18);color:var(--lvl-green-d)}

/* ── simulation state banner — the loudest thing on the page ─────────── */
.lvl-state{display:flex;align-items:center;gap:12px;flex-wrap:wrap;padding:10px 18px;
  border-bottom:1px solid var(--lvl-line);font-size:12px}
.lvl-state.is-live{background:var(--lvl-wash)}
.lvl-state.is-sim{background:linear-gradient(90deg,#FFF8E8,#FFFDF7);border-bottom-color:#EFD9A8}
.lvl-state.is-busy{opacity:.55;pointer-events:none}
.lvl-state-tag{font:800 9px/1 var(--lvl-mono);letter-spacing:.12em;padding:5px 8px;border-radius:var(--lvl-r-xs);
  background:var(--lvl-line-2);color:var(--lvl-mut)}
.lvl-state.is-sim .lvl-state-tag{background:#B9822A;color:#fff}
.lvl-state b{font-weight:700}
.lvl-state em{font-style:normal;color:var(--lvl-mut);font-size:11.5px}
.lvl-state-a{margin-left:auto;display:flex;align-items:center;gap:8px;flex-wrap:wrap}
.lvl-state-warn{font:700 10.5px/1 var(--lvl-font);color:#9A6A1E;text-transform:uppercase;letter-spacing:.05em}

/* ── filters ─────────────────────────────────────────────────────────── */
/* the chrome is one 42px row and one 30px workflow strip now, not four
   bands, so the filter row sticks under 72px rather than 96 */
.lvl-filters{display:flex;align-items:flex-end;gap:10px;flex-wrap:wrap;padding:8px 18px;background:var(--lvl-card);
  border-bottom:1px solid var(--lvl-line);position:sticky;top:72px;z-index:28}
.lvl-fl{display:flex;flex-direction:column;gap:3px;min-width:0}
.lvl-fl.is-wide{flex:1 1 100%}
.lvl-fl>span{font:700 9px/1 var(--lvl-font);letter-spacing:.08em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-fl select,.lvl-fl input,.lvl-sel-s,.lvl-num,.lvl-txt{height:28px;border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-xs);
  background:var(--lvl-card);color:var(--lvl-ink);font:500 12px/1 var(--lvl-font);padding:0 7px;max-width:230px;outline:0}
.lvl-num{width:78px;font-family:var(--lvl-mono);text-align:right}
.lvl-num.is-cap{width:66px}
.lvl-txt{width:100%;max-width:none}
.lvl-fl-r{margin-left:auto;display:flex;align-items:center;gap:8px}
.lvl-seg{display:inline-flex;border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-s);overflow:hidden;background:var(--lvl-card)}
.lvl-seg-b{height:28px;padding:0 11px;border:0;background:none;font:600 11.5px/1 var(--lvl-font);color:var(--lvl-mut);cursor:pointer}
.lvl-seg-b+.lvl-seg-b{border-left:1px solid var(--lvl-line)}
.lvl-seg-b.is-on{background:var(--lvl-green-t);color:var(--lvl-green-d)}
.lvl-chip{height:26px;padding:0 10px;border-radius:20px;border:1px solid var(--lvl-line-3);background:var(--lvl-card);
  font:600 11.5px/1 var(--lvl-font);color:var(--lvl-mut);cursor:pointer}
.lvl-chip.is-on{background:var(--lvl-green-t);border-color:rgba(36,180,126,.3);color:var(--lvl-green-d)}

/* ── layout ──────────────────────────────────────────────────────────── */
.lvl-main{flex:1;padding:14px 18px 24px;display:flex;flex-direction:column;gap:12px}
.lvl-2col{display:grid;grid-template-columns:repeat(auto-fit,minmax(370px,1fr));gap:12px}
.lvl-3col{display:grid;grid-template-columns:repeat(auto-fit,minmax(300px,1fr));gap:12px}
.lvl-card{background:var(--lvl-card);border:1px solid var(--lvl-line);border-radius:var(--lvl-r);box-shadow:var(--lvl-sh);overflow:hidden}
.lvl-card-h{display:flex;align-items:flex-start;justify-content:space-between;gap:12px;padding:11px 14px 9px;border-bottom:1px solid var(--lvl-line-2)}
.lvl-card-h h3{margin:0;font:700 12.5px/1.25 var(--lvl-head);letter-spacing:-.005em}
.lvl-card-h p{margin:3px 0 0;font-size:11px;color:var(--lvl-mut);max-width:96ch;line-height:1.45}
.lvl-card-b{padding:12px 14px 14px}
.lvl-card-b>h4{margin:16px 0 8px;font:700 11px/1 var(--lvl-font);letter-spacing:.06em;text-transform:uppercase;color:var(--lvl-mut)}
.lvl-card-b>h4:first-child{margin-top:0}
.lvl-card-b>h4 small{font-weight:500;text-transform:none;letter-spacing:0;margin-left:8px;color:var(--lvl-mut-2)}
.lvl-card-b h5{margin:0 0 6px;font:700 11px/1 var(--lvl-font);color:var(--lvl-ink-2)}
.lvl-note{margin:10px 0 0;font-size:11px;color:var(--lvl-mut);line-height:1.6}
.lvl-note code{font-family:var(--lvl-mono);font-size:10.5px;background:var(--lvl-line-2);padding:1px 4px;border-radius:3px}
.lvl-more{margin-top:10px;background:none;border:0;color:var(--lvl-green-d);font:600 12px/1 var(--lvl-font);cursor:pointer;padding:0}
.lvl-foot{display:flex;justify-content:space-between;gap:14px;flex-wrap:wrap;padding:10px 18px;border-top:1px solid var(--lvl-line);
  font:500 10.5px/1.5 var(--lvl-mono);color:var(--lvl-mut-2);background:var(--lvl-card)}

/* ── KPIs ────────────────────────────────────────────────────────────── */
/* Cell borders rather than a 1px grid gap over a coloured background: a
   partly-filled final row used to render the empty tail as a slab of grey.
   Top accent per tone makes a critical KPI scannable at a glance. */
.lvl-kpis{display:grid;grid-template-columns:repeat(auto-fit,minmax(146px,1fr));
  background:var(--lvl-card);border:1px solid var(--lvl-line);border-radius:var(--lvl-r);overflow:hidden}
.lvl-kpis.is-sm{grid-template-columns:repeat(auto-fit,minmax(120px,1fr));margin-bottom:14px}
.lvl-kpi{background:var(--lvl-card);padding:10px 12px 9px;display:flex;flex-direction:column;gap:1px;
  border-right:1px solid var(--lvl-line);border-bottom:1px solid var(--lvl-line);
  border-top:2px solid transparent;transition:border-color .12s}
.lvl-kpi:last-child{border-right:0}
.lvl-kpi-l{font:700 8.5px/1.2 var(--lvl-font);letter-spacing:.09em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-kpi-v{font:800 20px/1.1 var(--lvl-mono);letter-spacing:-.02em;margin-top:1px}
.lvl-kpi-s{font-style:normal;font-size:10.5px;color:var(--lvl-mut);margin-top:1px}
.lvl-kpi.is-ok .lvl-kpi-v{color:var(--lvl-ok)}
.lvl-kpi.is-ok{border-top-color:var(--lvl-ok)}
.lvl-kpi.is-warn .lvl-kpi-v{color:var(--lvl-warn)}
.lvl-kpi.is-warn{border-top-color:var(--lvl-warn)}
.lvl-kpi.is-risk .lvl-kpi-v{color:var(--lvl-risk)}
.lvl-kpi.is-risk{border-top-color:var(--lvl-risk)}

/* ── charts ──────────────────────────────────────────────────────────── */
.lvl-chart{width:100%}
.lvl-chart.is-scroll{overflow-x:auto;overflow-y:hidden}
.lvl-svg{display:block;max-width:100%;height:auto;font-family:var(--lvl-font)}
.lvl-chart.is-scroll .lvl-svg{max-width:none;min-width:100%}
/* THE WORKSPACE PANES ARE DRAWN AT THEIR OWN WIDTH, NEVER SQUASHED TO FIT.
   `max-width:100%` on the shared chart class scaled a 3000px timeline down
   into an 830px pane — which is not a fit, it is a 3.6x reduction that made
   every bar four pixels wide and every header label unreadable. These four
   panes size from their width/height attributes and the pane scrolls. */
.lvl-ws svg.lvl-ws-head,.lvl-ws svg.lvl-ws-body,
.lvl-ws svg.lvl-ws-hist,.lvl-ws svg.lvl-ws-hm{max-width:none;height:revert}
.lvl-grid{stroke:var(--lvl-line-2);stroke-width:1}
.lvl-axis{stroke:var(--lvl-line-3);stroke-width:1}
.lvl-ax{font-size:9.5px;fill:var(--lvl-mut-2)}
.lvl-bar{shape-rendering:crispEdges}
.lvl-over{fill:var(--lvl-risk);opacity:.85}
.lvl-cap{stroke:var(--lvl-ink);stroke-width:1.4;stroke-dasharray:5 3}
.lvl-cap-l{font-size:9.5px;font-weight:700;fill:var(--lvl-ink)}
.lvl-totline{fill:none;stroke:var(--lvl-ink);stroke-width:1.3;stroke-dasharray:2 4;opacity:.75}

/* ── WBS TREE TABLE — the Gantt tab's own table, carrying manpower ──── */
.lvl-wbstbl .lvl-wbs-row>th,.lvl-wbstbl .lvl-wbs-row>td{background:var(--wb-bg);color:var(--wb-tx);
  border-bottom:1px solid rgba(255,255,255,.10);border-right:1px solid rgba(255,255,255,.07)}
.lvl-wbstbl .lvl-wbs-row>th{border-left:4px solid var(--wb-ac)}
.lvl-wbstbl .lvl-wbs-row.is-lvl0>th{font:800 12px/1.2 var(--lvl-head);letter-spacing:.02em}
.lvl-wbstbl .lvl-wbs-row.is-lvl1>th{font:700 11.5px/1.2 var(--lvl-font)}
.lvl-wbstbl .lvl-wbs-row.is-lvl2>th,.lvl-wbstbl .lvl-wbs-row.is-lvl3>th{font:600 10.5px/1.2 var(--lvl-font)}
.lvl-wbstbl .lvl-wbs-code{font:800 8.5px/1 var(--lvl-mono);letter-spacing:.06em;
  padding:2px 5px;border-radius:4px;background:rgba(255,255,255,.18);margin-right:6px;display:inline-block}
.lvl-wbstbl .lvl-wbs-chev{display:inline-block;width:0;height:0;border-left:5px solid currentColor;
  border-top:4px solid transparent;border-bottom:4px solid transparent;margin-right:7px;vertical-align:middle;
  transition:transform .12s}
.lvl-wbstbl .lvl-wbs-row.is-open .lvl-wbs-chev{transform:rotate(90deg)}
.lvl-wbstbl .lvl-wbs-row[data-lvl]{cursor:pointer}
.lvl-wbstbl .lvl-wbs-row[data-lvl]:hover>th,.lvl-wbstbl .lvl-wbs-row[data-lvl]:hover>td{filter:brightness(1.12)}
.lvl-wbstbl td.is-zero{opacity:.28}
.lvl-wbstbl-ctrl{display:flex;gap:6px;margin-bottom:8px}
.lvl-wbstbl-ctrl .lvl-btn-sm{font:600 10px/1 var(--lvl-font);padding:4px 10px;border-radius:6px;
  background:var(--lvl-line-2);color:var(--lvl-ink-2);border:none;cursor:pointer;white-space:nowrap}
.lvl-wbstbl-ctrl .lvl-btn-sm:hover{background:var(--lvl-accent);color:#fff}
.lvl-wbs-res>th,.lvl-wbs-res>td{background:var(--lvl-card)!important;color:var(--lvl-ink-2)!important;
  border-bottom:1px solid var(--lvl-line-2)!important;border-right:1px solid var(--lvl-line-2)!important}
.lvl-wbs-res>th{font:600 10.5px/1.3 var(--lvl-font)}
.lvl-wbs-res .lvl-pv-t{font-family:var(--lvl-mono)}
.lvl-wbs-rdot{display:inline-block;width:8px;height:8px;border-radius:50%;margin-right:7px;vertical-align:middle;
  box-shadow:0 0 0 1px rgba(20,32,42,.15)}
.lvl-avg{stroke:var(--lvl-warn);stroke-width:1;stroke-dasharray:2 3}
.lvl-line{fill:none;stroke-width:1.9;stroke-linejoin:round}
.lvl-area{opacity:.10}
.lvl-pt{opacity:.9}
.lvl-legend{display:flex;flex-wrap:wrap;gap:4px 14px;margin-top:10px}
.lvl-lg{display:inline-flex;align-items:center;gap:6px;font-size:11px;color:var(--lvl-mut)}
.lvl-lg i{width:9px;height:9px;border-radius:2px;flex:0 0 auto}
.lvl-lg.is-more{color:var(--lvl-mut-2);font-style:italic}
.lvl-spark polyline{fill:none;stroke:var(--lvl-green);stroke-width:1.4}

/* before / after */
.lvl-ba{display:grid;grid-template-columns:1fr 1fr;gap:14px}
@media (max-width:900px){.lvl-ba{grid-template-columns:1fr}}
.lvl-ba-side{min-width:0;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);padding:10px;background:var(--lvl-wash)}
.lvl-ba-h{display:flex;align-items:center;gap:8px;font:700 11px/1 var(--lvl-font);letter-spacing:.08em;margin-bottom:8px}
.lvl-ba-h em{font-style:normal;font-weight:500;letter-spacing:0;color:var(--lvl-mut);font-size:11px;margin-left:auto}
.lvl-dot{width:9px;height:9px;border-radius:50%;display:inline-block;flex:0 0 auto}
.lvl-dot.is-before{background:var(--lvl-before)}
.lvl-dot.is-after{background:var(--lvl-after)}
.lvl-ba-head{display:grid;grid-template-columns:1fr 1fr;gap:14px;font-size:12px;color:var(--lvl-mut)}
.lvl-ba-head b{color:var(--lvl-ink);margin-right:5px}
@media (max-width:900px){.lvl-ba-head{grid-template-columns:1fr}}

/* heatmap */
.lvl-hm-wrap{overflow:auto;max-height:520px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s)}
.lvl-hm,.lvl-mx{border-collapse:separate;border-spacing:0;width:100%;font-size:10.5px}
.lvl-hm th,.lvl-mx th{position:sticky;top:0;z-index:3;background:var(--lvl-wash);font:700 9.5px/1.2 var(--lvl-font);
  color:var(--lvl-mut);padding:6px 5px;text-align:center;border-bottom:1px solid var(--lvl-line);white-space:nowrap}
.lvl-hm th.lvl-hm-row,.lvl-mx tbody th{position:sticky;left:0;z-index:4;background:var(--lvl-card);text-align:left;min-width:160px;
  border-right:1px solid var(--lvl-line);padding:5px 9px}
.lvl-hm-row span{display:block;font-weight:700;color:var(--lvl-ink);font-size:11px}
.lvl-hm-row em{font-style:normal;color:var(--lvl-mut-2);font-size:9.5px}
.lvl-hm-c{text-align:center;font-family:var(--lvl-mono);font-weight:600;border-bottom:1px solid var(--lvl-line-2);
  padding:4px 3px;color:#fff}
.lvl-hm-c.is-zero{background:var(--lvl-wash)}
.lvl-hm-c.is-low{background:rgba(46,125,99,calc(.20 + var(--i) * .55));color:#0E3A2C}
.lvl-hm-c.is-mid{background:rgba(46,125,99,calc(.45 + var(--i) * .45))}
.lvl-hm-c.is-high{fill:var(--lvl-warn)}
.lvl-hm-c.is-over{fill:var(--lvl-risk)}
.lvl-hm-c.is-ok{fill:var(--lvl-ok)}
.lvl-hm-c.is-none{fill:var(--lvl-wash);fill-opacity:0}
.lvl-mx-c{text-align:right;font-family:var(--lvl-mono);padding:4px 8px;border-bottom:1px solid var(--lvl-line-2);
  background:rgba(46,125,99,calc(var(--i) * .32))}
.lvl-mx-c.is-zero{background:var(--lvl-wash);color:var(--lvl-line-3)}
.lvl-mx-tot{text-align:right;font-family:var(--lvl-mono);font-weight:700;background:var(--lvl-wash)}
.lvl-mx tfoot td,.lvl-mx tfoot th{background:var(--lvl-wash);font-weight:700;font-family:var(--lvl-mono);text-align:right;padding:5px 8px;
  border-top:1px solid var(--lvl-line)}
.lvl-mx tbody th em.lvl-mx-share{display:block;font-style:normal;font-weight:600;font-size:9px;letter-spacing:.02em;
  color:var(--lvl-mut-2);margin-top:2px;white-space:nowrap}
.lvl-mx-c.is-peak{box-shadow:inset 0 0 0 1.5px var(--lvl-green-d);position:relative}
.lvl-mx-c.is-low{background:rgba(46,125,99,calc(.20 + var(--i) * .55));color:#0E3A2C}
.lvl-mx-c.is-mid{background:rgba(46,125,99,calc(.45 + var(--i) * .45));color:#fff}
.lvl-mx-c.is-high{background:rgba(192,138,58,calc(.55 + var(--i) * .40));color:#fff}
.lvl-mx-c.is-over{background:var(--lvl-risk);color:#fff}

/* mobility map */
.lvl-map{max-height:300px}
.lvl-mp-e{stroke-width:2}
.lvl-mp-e.is-high{stroke:var(--lvl-ok)}
.lvl-mp-e.is-medium{stroke:var(--lvl-info);stroke-dasharray:6 3}
.lvl-mp-e.is-limited{stroke:var(--lvl-warn);stroke-dasharray:2 4}
.lvl-mp-el{font-size:8.5px;fill:var(--lvl-mut-2);text-transform:uppercase;letter-spacing:.06em}
.lvl-mp-n circle{fill:var(--lvl-card);stroke:var(--lvl-line-3);stroke-width:1.5}
.lvl-mp-n.is-here circle{fill:var(--lvl-green-t);stroke:var(--lvl-green);stroke-width:2}
.lvl-mp-q{font:700 10px/1 var(--lvl-mono);fill:var(--lvl-ink)}
.lvl-mp-t{font:600 10.5px/1 var(--lvl-font);fill:var(--lvl-ink-2)}

/* movement gantt overlay */
.lvl-mg-l{font-size:10.5px;fill:var(--lvl-ink-2)}
.lvl-mg-ghost{fill:var(--lvl-line-3)}
.lvl-mg-new{fill:var(--lvl-after)}
.lvl-mg-new.is-delay{fill:var(--lvl-warn)}
.lvl-mg-arrow{stroke:var(--lvl-mut-2);stroke-width:1;stroke-dasharray:2 2}
.lvl-mg-d{font:700 8.5px/1 var(--lvl-mono);fill:var(--lvl-mut)}

/* bars */
.lvl-bars{display:flex;flex-direction:column;gap:5px}
.lvl-bars-r{display:grid;grid-template-columns:minmax(90px,1.4fr) 3fr auto;align-items:center;gap:10px;font-size:11.5px}
.lvl-bars-r[role="button"]{cursor:pointer}
.lvl-bars-r[role="button"]:hover .lvl-bars-n{color:var(--lvl-green-d)}
.lvl-bars-n{overflow:hidden;text-overflow:ellipsis;white-space:nowrap;color:var(--lvl-ink-2)}
.lvl-bars-t{display:block;height:9px;background:var(--lvl-line-2);border-radius:5px;overflow:hidden}
.lvl-bars-t i{display:block;height:100%;border-radius:5px}
.lvl-bars-r b{font-family:var(--lvl-mono);font-size:11px;white-space:nowrap}

/* ── tables ──────────────────────────────────────────────────────────── */
.lvl-tbl-wrap{overflow:auto;max-height:560px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s)}
.lvl-tbl{width:100%;border-collapse:separate;border-spacing:0;font-size:11px}
.lvl-tbl thead th{position:sticky;top:0;z-index:3;background:var(--lvl-wash);font:700 9px/1.2 var(--lvl-font);
  letter-spacing:.06em;text-transform:uppercase;color:var(--lvl-mut);padding:7px 8px;text-align:left;
  border-bottom:1px solid var(--lvl-line);white-space:nowrap}
.lvl-tbl thead th.n,.lvl-tbl td.n,.lvl-tbl th.n{text-align:right}
.lvl-tbl tbody th{text-align:left;font-weight:600;padding:5px 8px;border-bottom:1px solid var(--lvl-line-2);vertical-align:top}
.lvl-tbl tbody td{padding:5px 8px;border-bottom:1px solid var(--lvl-line-2);vertical-align:top;color:var(--lvl-ink-2)}
.lvl-tbl tbody td.n{font-family:var(--lvl-mono)}
.lvl-tbl tbody tr:hover td,.lvl-tbl tbody tr:hover th{background:var(--lvl-wash)}
.lvl-tbl tbody th em,.lvl-tbl tbody td em{display:block;font-style:normal;font-size:9.5px;color:var(--lvl-mut-2)}
.lvl-tbl tr.is-over th,.lvl-tbl tr.is-over td{background:var(--lvl-risk-t)}
.lvl-tbl tr.is-moved th,.lvl-tbl tr.is-moved td{background:var(--lvl-green-t)}
.lvl-tbl tr.is-manual th,.lvl-tbl tr.is-manual td{background:var(--lvl-info-t)}
.lvl-ba-tbl td:nth-child(2){color:var(--lvl-mut)}
.lvl-ba-tbl td:nth-child(3){font-weight:700;color:var(--lvl-ink)}
.lvl-cmp th.is-base,.lvl-cmp td.is-base{background:var(--lvl-wash)}
.lvl-cmp thead th em{display:block;font-style:normal;font-weight:500;text-transform:none;letter-spacing:0;color:var(--lvl-mut-2);font-size:10px}
.lvl-cmp td em{display:block;font-style:normal;font-size:10px;margin-top:2px}
.lvl-cmp-a td{background:var(--lvl-wash)}
.lvl-cmp tbody th{position:sticky;left:0;z-index:2;background:var(--lvl-card);font-weight:700}
.lvl-cmp tbody tr:hover th{background:var(--lvl-wash)}
.lvl-cmp thead th:first-child{position:sticky;left:0;z-index:4}
.lvl-cmp-v td{background:var(--lvl-wash);border-top:1px solid var(--lvl-line);font-weight:600}
.lvl-cmp-v td.is-base{color:var(--lvl-mut-2)}
.lvl-zn{max-width:150px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-why{max-width:340px}
.lvl-why b{display:block;font-weight:600;color:var(--lvl-ink)}
.lvl-why p{margin:6px 0 0;font-size:11px;color:var(--lvl-mut);line-height:1.55}
.lvl-fbc{min-width:210px}
.lvl-load{display:inline-block;padding:1px 6px;border-radius:20px;font:700 10.5px/1.5 var(--lvl-mono)}
.lvl-load.is-low{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-load.is-mid{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-load.is-high{background:var(--lvl-warn-t);color:var(--lvl-warn)}
.lvl-load.is-over{background:var(--lvl-risk-t);color:var(--lvl-risk)}

/* tags / deltas */
.lvl-tag{display:inline-block;padding:2px 7px;border-radius:20px;font:700 9.5px/1.5 var(--lvl-font);
  letter-spacing:.04em;text-transform:uppercase;white-space:nowrap}
.lvl-tag.is-ok{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-tag.is-warn{background:var(--lvl-warn-t);color:var(--lvl-warn)}
.lvl-tag.is-risk{background:var(--lvl-risk-t);color:var(--lvl-risk)}
.lvl-tag.is-info{background:var(--lvl-info-t);color:var(--lvl-info)}
.lvl-tag.is-neutral{background:var(--lvl-line-2);color:var(--lvl-mut)}
.lvl-d{font-family:var(--lvl-mono);font-size:10.5px;font-weight:700}
.lvl-d.is-good{color:var(--lvl-ok)}
.lvl-d.is-bad{color:var(--lvl-risk)}
.lvl-d.is-flat{color:var(--lvl-mut-2);font-weight:500}

/* float bar */
.lvl-fb{display:flex;align-items:center;gap:7px;font-size:10px;color:var(--lvl-mut-2)}
.lvl-fb-t{font-family:var(--lvl-mono);white-space:nowrap;font-size:9.5px}
.lvl-fb-track{position:relative;flex:1;min-width:70px;height:8px;border-radius:4px;background:var(--lvl-line-2);overflow:hidden}
.lvl-fb-used{position:absolute;left:0;top:0;height:100%;background:var(--lvl-warn)}
.lvl-fb-free{position:absolute;top:0;height:100%;background:var(--lvl-ok);opacity:.42}
.lvl-fb-dot{position:absolute;top:-2px;width:3px;height:12px;border-radius:2px;background:var(--lvl-ink)}
.lvl-fb-v{font-family:var(--lvl-mono);font-size:10.5px;color:var(--lvl-ink);white-space:nowrap}
.lvl-fb.is-critical .lvl-fb-track{background:var(--lvl-risk-t)}
.lvl-fb.is-critical .lvl-fb-dot{background:var(--lvl-risk)}
.lvl-fb.is-warning .lvl-fb-dot{background:var(--lvl-warn)}

/* ── command panel ───────────────────────────────────────────────────── */
.lvl-cmd-grid{display:grid;grid-template-columns:repeat(auto-fit,minmax(250px,1fr));gap:18px}
.lvl-cmd-col h4{margin:0 0 8px;font:700 10px/1 var(--lvl-font);letter-spacing:.08em;text-transform:uppercase;color:var(--lvl-mut)}
.lvl-cmd-col h4 small{font-weight:500;text-transform:none;letter-spacing:0;color:var(--lvl-mut-2);margin-left:6px}
.lvl-mode{display:flex;flex-direction:column;gap:7px}
.lvl-modec{text-align:left;padding:9px 11px;border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-s);
  background:var(--lvl-card);cursor:pointer;transition:border-color .12s,background .12s}
.lvl-modec:hover{border-color:var(--lvl-mut-2)}
.lvl-modec.is-on{border-color:var(--lvl-green);background:var(--lvl-green-t)}
.lvl-modec b{display:block;font:700 12px/1.3 var(--lvl-font);color:var(--lvl-ink)}
.lvl-modec span{display:block;margin-top:3px;font-size:11px;color:var(--lvl-mut);line-height:1.5}
.lvl-strats{display:flex;flex-direction:column;gap:5px;max-height:250px;overflow:auto}
.lvl-strat{text-align:left;padding:8px 10px;border:1px solid var(--lvl-line-2);border-radius:var(--lvl-r-s);
  background:var(--lvl-card);cursor:pointer}
.lvl-strat:hover{border-color:var(--lvl-mut-2)}
.lvl-strat.is-on{border-color:var(--lvl-green);background:var(--lvl-green-t)}
.lvl-strat b{display:flex;align-items:center;gap:7px;font:700 11.5px/1.3 var(--lvl-font);color:var(--lvl-ink)}
.lvl-strat b em{font-style:normal;font:700 8.5px/1 var(--lvl-font);letter-spacing:.08em;text-transform:uppercase;
  background:var(--lvl-green);color:#fff;padding:2px 6px;border-radius:20px}
.lvl-strat span{display:block;margin-top:3px;font-size:10.5px;color:var(--lvl-mut);line-height:1.5}
.lvl-weights{display:flex;flex-direction:column;gap:7px}
.lvl-w{display:grid;grid-template-columns:1fr 110px 30px;align-items:center;gap:9px;font-size:11.5px;color:var(--lvl-ink-2)}
.lvl-w input[type=range]{width:100%;accent-color:var(--lvl-green)}
.lvl-w b{font-family:var(--lvl-mono);font-size:11px;text-align:right}
.lvl-toggles{display:flex;flex-direction:column;gap:6px;margin-bottom:10px}
.lvl-tg{display:flex;align-items:center;gap:9px;padding:6px 9px;border:1px solid var(--lvl-line-2);border-radius:var(--lvl-r-s);
  background:var(--lvl-card);font:600 11.5px/1.3 var(--lvl-font);color:var(--lvl-ink-2);cursor:pointer;text-align:left}
.lvl-tg i{width:28px;height:16px;border-radius:10px;background:var(--lvl-line-3);position:relative;flex:0 0 auto;transition:background .12s}
.lvl-tg i::after{content:"";position:absolute;left:2px;top:2px;width:12px;height:12px;border-radius:50%;background:#fff;transition:left .12s}
.lvl-tg.is-on{border-color:var(--lvl-green);color:var(--lvl-green-d)}
.lvl-tg.is-on i{background:var(--lvl-green)}
.lvl-tg.is-on i::after{left:14px}
.lvl-cmd-run{grid-column:1/-1;display:flex;align-items:center;gap:10px;flex-wrap:wrap;padding-top:12px;border-top:1px solid var(--lvl-line-2)}
.lvl-cmd-hint{font-size:11px;color:var(--lvl-mut)}

/* impact grid */
.lvl-imp{display:grid;grid-template-columns:repeat(auto-fit,minmax(168px,1fr));gap:var(--lvl-sp-2);
  background:none;border:0;border-radius:0;overflow:visible}
.lvl-imp-c{background:var(--lvl-card);padding:10px 13px 11px;display:flex;flex-direction:column;gap:3px;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r);box-shadow:var(--lvl-sh)}
.lvl-imp-c span{font:700 var(--lvl-t-1)/1.2 var(--lvl-mono,var(--lvl-font));letter-spacing:.1em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-imp-c b{font:800 20px/1.15 var(--lvl-mono);letter-spacing:-.015em;color:var(--lvl-ink);margin-top:1px}
.lvl-imp-c em{font-style:normal;font-size:var(--lvl-t-2);color:var(--lvl-mut)}

/* bottlenecks / opportunities */
.lvl-bn{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:5px}
.lvl-bn-r{display:flex;align-items:flex-start;gap:9px;padding:7px 9px;border:1px solid var(--lvl-line-2);
  border-radius:var(--lvl-r-s);cursor:pointer;background:var(--lvl-card);transition:background .12s,border-color .12s}
.lvl-bn-r:hover{border-color:var(--lvl-mut-2);background:var(--lvl-wash)}
.lvl-bn-n{width:20px;height:20px;border-radius:50%;background:var(--lvl-line-2);color:var(--lvl-mut);
  font:700 10px/20px var(--lvl-mono);text-align:center;flex:0 0 auto}
.lvl-bn-m{flex:1;min-width:0}
.lvl-bn-m b{display:block;font:700 12px/1.3 var(--lvl-font)}
.lvl-bn-m em{display:block;font-style:normal;font-size:10.5px;color:var(--lvl-mut);margin-top:1px}
.lvl-bn-x{color:var(--lvl-mut-2)!important}
.lvl-opp{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:8px}
.lvl-opp-r{padding:8px 10px;border:1px solid var(--lvl-line-2);border-radius:var(--lvl-r-s);background:var(--lvl-wash)}
.lvl-opp-r b{display:block;margin-top:4px;font:700 12px/1.3 var(--lvl-font)}
.lvl-opp-r p{margin:3px 0 0;font-size:11px;color:var(--lvl-mut);line-height:1.5}
.lvl-opp-r em{display:block;margin-top:4px;font-style:normal;font:600 10.5px/1.4 var(--lvl-font);color:var(--lvl-ok)}
.lvl-opp-r .lvl-link{margin-top:5px;font-size:11px}

/* recommendation + quality */
.lvl-rec{display:grid;grid-template-columns:1fr;gap:14px}
.lvl-card-b>.lvl-rec{display:grid;grid-template-columns:1fr 1fr;gap:16px}
@media (max-width:900px){.lvl-card-b>.lvl-rec{grid-template-columns:1fr}}
.lvl-rec-tag{display:inline-block;font:800 9px/1 var(--lvl-font);letter-spacing:.12em;padding:4px 8px;border-radius:20px;
  background:var(--lvl-green);color:#fff}
.lvl-rec-l h4{margin:8px 0 2px;font:800 16px/1.2 var(--lvl-head)}
.lvl-rec-name{margin:0;font-size:11px;color:var(--lvl-mut)}
.lvl-rec-why{list-style:none;margin:10px 0 0;padding:0;display:flex;flex-direction:column;gap:4px}
.lvl-rec-why li{display:flex;align-items:flex-start;gap:6px;font-size:11.5px;color:var(--lvl-ink-2)}
.lvl-rec-why li svg{color:var(--lvl-ok);margin-top:2px}
.lvl-rec-a{display:flex;gap:7px;flex-wrap:wrap;margin-top:12px}
.lvl-q{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);padding:10px 12px;background:var(--lvl-wash)}
.lvl-q-h{display:flex;align-items:baseline;gap:10px;margin-bottom:8px}
.lvl-q-h span{font:700 9.5px/1 var(--lvl-font);letter-spacing:.08em;text-transform:uppercase;color:var(--lvl-mut)}
.lvl-q-h b{font:800 26px/1 var(--lvl-mono);color:var(--lvl-green-d)}
.lvl-q-h b i{font-style:normal;font-size:13px;color:var(--lvl-mut-2)}
.lvl-q-h em{font-style:normal;font:700 10.5px/1 var(--lvl-font);color:var(--lvl-ink-2);margin-left:auto}
.lvl-q-parts{display:flex;flex-direction:column;gap:6px}
.lvl-q-p{display:grid;grid-template-columns:minmax(100px,1.1fr) 2fr auto;grid-template-rows:auto auto;
  column-gap:9px;align-items:center;font-size:11px}
.lvl-q-p>span{color:var(--lvl-ink-2)}
.lvl-q-t{grid-column:2;display:block;height:6px;border-radius:4px;background:var(--lvl-line-2);overflow:hidden}
.lvl-q-t b{display:block;height:100%;background:var(--lvl-green);border-radius:4px}
.lvl-q-p>u{grid-column:3;text-decoration:none;font-family:var(--lvl-mono);font-size:10.5px;white-space:nowrap}
.lvl-q-p>u small{color:var(--lvl-mut-2)}
.lvl-q-p>em{grid-column:1/-1;font-style:normal;font-size:9.5px;color:var(--lvl-mut-2);margin-top:1px}

/* manual levelling */
.lvl-manual{display:grid;grid-template-columns:1.05fr 1fr;gap:18px}
@media (max-width:900px){.lvl-manual{grid-template-columns:1fr}}
.lvl-manual-f{display:grid;grid-template-columns:repeat(auto-fit,minmax(140px,1fr));gap:10px;margin-top:12px}
.lvl-manual-a{display:flex;gap:8px;flex-wrap:wrap;margin-top:14px}
.lvl-live{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);padding:12px;background:var(--lvl-wash)}
.lvl-live.is-bad{border-color:#E5C4BE;background:var(--lvl-risk-t)}
.lvl-live.is-ok{border-color:#BFE3D3;background:var(--lvl-ok-t)}
.lvl-live h4{margin:0 0 10px;font:700 10px/1 var(--lvl-font);letter-spacing:.08em;text-transform:uppercase;color:var(--lvl-mut)}
.lvl-live-g{display:grid;grid-template-columns:repeat(auto-fit,minmax(150px,1fr));gap:9px}
.lvl-live-r{display:flex;flex-direction:column;gap:1px}
.lvl-live-r span{font:700 9px/1.2 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-live-r b{font:700 13px/1.2 var(--lvl-mono)}
.lvl-live-r em{font-style:normal;font-size:10.5px;color:var(--lvl-mut)}
.lvl-viol{list-style:none;margin:12px 0 0;padding:0;display:flex;flex-direction:column;gap:5px}
.lvl-viol li{display:flex;align-items:flex-start;gap:7px;font-size:11.5px;line-height:1.5}
.lvl-viol li.is-error{color:var(--lvl-risk)}
.lvl-viol li.is-warn{color:var(--lvl-warn)}
.lvl-dl{display:grid;grid-template-columns:repeat(auto-fit,minmax(130px,1fr));gap:9px;margin:12px 0 0}
.lvl-dl div{display:flex;flex-direction:column;gap:1px}
.lvl-dl dt{font:700 9px/1.2 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-dl dd{margin:0;font:700 12px/1.3 var(--lvl-mono)}

/* score breakdown / logs */
.lvl-score{display:flex;flex-wrap:wrap;gap:5px;margin-top:8px;align-items:center}
.lvl-score>span{font:700 10px/1 var(--lvl-font);color:var(--lvl-mut);text-transform:uppercase;letter-spacing:.06em}
.lvl-score>span b{font-family:var(--lvl-mono);color:var(--lvl-ink);margin-left:4px}
.lvl-score i{font-style:normal;font:600 10px/1 var(--lvl-mono);padding:2px 6px;border-radius:3px;background:var(--lvl-line-2);color:var(--lvl-mut)}
.lvl-score i.is-pos{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-score i.is-neg{background:var(--lvl-risk-t);color:var(--lvl-risk)}
.lvl-score em{flex:1 1 100%;font-style:normal;font-size:10px;color:var(--lvl-mut-2);margin-top:3px}
.lvl-log{list-style:none;margin:0;padding:0;max-height:280px;overflow:auto;display:flex;flex-direction:column;gap:2px}
.lvl-log li{display:grid;grid-template-columns:34px minmax(120px,1fr) 3fr;gap:9px;align-items:baseline;font-size:11px;
  padding:4px 7px;border-radius:var(--lvl-r-xs)}
.lvl-log li.is-move{background:var(--lvl-ok-t)}
.lvl-log li.is-rejected{background:var(--lvl-wash);color:var(--lvl-mut)}
.lvl-log li span{font-family:var(--lvl-mono);font-size:10px;color:var(--lvl-mut-2)}
.lvl-log li em{font-style:normal;color:var(--lvl-mut)}

/* validation / integrity */
.lvl-val-h{display:flex;align-items:center;gap:8px;flex-wrap:wrap;margin-bottom:10px}
.lvl-val-h em{font-style:normal;font-size:10.5px;color:var(--lvl-mut-2)}
.lvl-val{list-style:none;margin:0;padding:0;max-height:320px;overflow:auto;display:flex;flex-direction:column;gap:3px}
.lvl-val li{display:grid;grid-template-columns:16px minmax(110px,auto) 1fr auto;gap:8px;align-items:baseline;
  font-size:11.5px;padding:5px 8px;border-radius:var(--lvl-r-xs)}
.lvl-val li.is-error{background:var(--lvl-risk-t);color:var(--lvl-risk)}
.lvl-val li.is-warn{background:var(--lvl-warn-t);color:var(--lvl-warn)}
.lvl-val li.is-info{background:var(--lvl-wash);color:var(--lvl-mut)}
.lvl-val li b{font-family:var(--lvl-mono);font-size:10px}
.lvl-val li em{font-style:normal;font-family:var(--lvl-mono);font-size:10px;opacity:.75}
.lvl-integrity{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:6px}
.lvl-integrity li{display:grid;grid-template-columns:16px minmax(140px,auto) 1fr;gap:8px;align-items:baseline;font-size:11px}
.lvl-integrity li.is-ok svg{color:var(--lvl-ok)}
.lvl-integrity li.is-warn svg{color:var(--lvl-warn)}
.lvl-integrity li span{color:var(--lvl-mut);line-height:1.55}
.lvl-integrity code{font-family:var(--lvl-mono);font-size:10.5px;background:var(--lvl-line-2);padding:1px 4px;border-radius:3px}

/* scenarios */
.lvl-sc-a{display:flex;gap:9px;flex-wrap:wrap;margin-bottom:14px}
.lvl-sc-grid{display:grid;grid-template-columns:repeat(auto-fit,minmax(250px,1fr));gap:12px}
.lvl-sc{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);padding:12px;background:var(--lvl-card)}
.lvl-sc.is-on{border-color:var(--lvl-green);box-shadow:0 0 0 2px var(--lvl-green-t)}
.lvl-sc.is-stale{opacity:.72}
.lvl-sc header{display:flex;flex-direction:column;align-items:stretch;gap:6px}
.lvl-sc-t{display:flex;align-items:center;gap:6px;flex-wrap:wrap;min-height:20px}
.lvl-sc header h4{font:700 13px/1.3 var(--lvl-font);margin:0}
.lvl-sc header h4 .lvl-ic{margin-right:5px;vertical-align:-2px}
.lvl-sc-s{margin:0;font-size:10.5px;color:var(--lvl-mut);display:flex;align-items:baseline;gap:8px;flex-wrap:wrap}
.lvl-sc-s b{color:var(--lvl-ink-2);font-weight:600}
.lvl-sc-s em{font-style:normal;color:var(--lvl-mut-2)}
.lvl-sc-v{margin:11px 0 10px;padding:9px 10px;border-radius:6px;background:var(--lvl-wash);border:1px solid var(--lvl-line);
  font-size:11px;line-height:1.5;color:var(--lvl-ink-2)}
.lvl-sc-v b{font-family:var(--lvl-mono);font-weight:700}
.lvl-sc-v .lvl-pos{color:var(--lvl-ok)}
.lvl-sc-v .lvl-neg{color:var(--lvl-risk)}
.lvl-sc-m{display:grid;grid-template-columns:1fr 1fr;gap:8px}
.lvl-sc-m div{display:flex;flex-direction:column;gap:1px}
.lvl-sc-m span{font:700 8.5px/1.2 var(--lvl-font);letter-spacing:.08em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-sc-m b{font:700 13px/1.2 var(--lvl-mono)}
.lvl-sc-m em{font-style:normal;font-size:10px;color:var(--lvl-mut)}
.lvl-sc-x{margin:10px 0 0;font-size:10.5px;color:var(--lvl-mut);display:flex;align-items:center;gap:6px;flex-wrap:wrap}
.lvl-sc-b{display:flex;gap:5px;flex-wrap:wrap;margin-top:10px}

/* audit */
.lvl-audit{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:8px}
.lvl-audit-r{border:1px solid var(--lvl-line);border-left:3px solid var(--lvl-ok);border-radius:var(--lvl-r-s);padding:10px 12px;background:var(--lvl-card)}
.lvl-audit-r.is-reverted{opacity:.65;border-left-color:var(--lvl-warn)}
.lvl-audit-r header{display:flex;align-items:center;gap:8px;flex-wrap:wrap}
.lvl-audit-r header b{font:700 12px/1.3 var(--lvl-font)}
.lvl-audit-r time{margin-left:auto;font-family:var(--lvl-mono);font-size:10px;color:var(--lvl-mut-2)}
.lvl-audit-m{margin:6px 0 0;font-size:11px;color:var(--lvl-ink-2)}
.lvl-audit-x{margin:3px 0 0;font-size:10px;color:var(--lvl-mut);line-height:1.5}
.lvl-audit-b{display:flex;gap:5px;flex-wrap:wrap;margin-top:7px}

/* panel */
.lvl-panel{border:1px solid var(--lvl-green);border-radius:var(--lvl-r);background:var(--lvl-card);box-shadow:var(--lvl-sh-2);overflow:hidden}
.lvl-panel-h{display:flex;align-items:flex-start;justify-content:space-between;gap:12px;padding:12px 15px;
  background:var(--lvl-green-t);border-bottom:1px solid rgba(36,180,126,.25)}
.lvl-panel-h h3{margin:0;font:800 14px/1.2 var(--lvl-head)}
.lvl-panel-h p{margin:3px 0 0;font-size:11px;color:var(--lvl-ink-2)}
.lvl-panel-b{padding:14px 15px}
.lvl-panel-grid{display:grid;grid-template-columns:repeat(auto-fit,minmax(180px,1fr));gap:10px;margin-top:14px}

/* misc */
.lvl-list{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:4px;max-height:260px;overflow:auto}
.lvl-list li{display:flex;align-items:baseline;gap:8px;font-size:11.5px;padding:3px 0;border-bottom:1px solid var(--lvl-line-2)}
.lvl-list li em{font-style:normal;font-size:10px;color:var(--lvl-mut-2);margin-left:auto;font-family:var(--lvl-mono)}
.lvl-ok-s{display:flex;align-items:center;gap:8px;padding:10px 12px;border-radius:var(--lvl-r-s);background:var(--lvl-ok-t);
  color:var(--lvl-ok);font:600 11.5px/1.4 var(--lvl-font)}
.lvl-warn-s{display:flex;align-items:center;gap:7px;margin-top:10px;font-size:11px;color:var(--lvl-warn)}
.lvl-empty-s{padding:22px;text-align:center;color:var(--lvl-mut-2);font-size:11.5px;background:var(--lvl-wash);border-radius:var(--lvl-r-s)}
.lvl-empty{display:flex;flex-direction:column;align-items:center;text-align:center;padding:36px 20px;color:var(--lvl-mut)}
.lvl-empty svg{color:var(--lvl-line-3);margin-bottom:12px}
.lvl-empty h2{margin:0 0 8px;font:800 15px/1.2 var(--lvl-head);color:var(--lvl-ink)}
.lvl-empty p{margin:0;max-width:70ch;font-size:12px;line-height:1.65}
.lvl-err{display:flex;align-items:flex-start;gap:9px;padding:14px;border-radius:var(--lvl-r-s);background:var(--lvl-risk-t);
  color:var(--lvl-risk);font-size:12px}
.lvl-err b{display:block}
.lvl-err span{display:block;font-family:var(--lvl-mono);font-size:11px;margin-top:4px}
.lvl-start{display:flex;justify-content:center;padding:48px 20px}
.lvl-start-card{max-width:720px;background:var(--lvl-card);border:1px solid var(--lvl-line);border-radius:var(--lvl-r);
  padding:30px;box-shadow:var(--lvl-sh);text-align:center}
.lvl-start-card svg{color:var(--lvl-green);opacity:.5}
.lvl-start-card h2{margin:14px 0 10px;font:800 19px/1.2 var(--lvl-head)}
.lvl-start-card p{margin:0;font-size:12.5px;color:var(--lvl-mut);line-height:1.7}
.lvl-start-l{list-style:none;margin:20px 0 0;padding:0;display:grid;grid-template-columns:repeat(auto-fit,minmax(230px,1fr));gap:10px;text-align:left}
.lvl-start-l li{display:flex;align-items:flex-start;gap:8px;font-size:11.5px;color:var(--lvl-mut);
  padding:9px 11px;border:1px solid var(--lvl-line-2);border-radius:var(--lvl-r-s)}
.lvl-start-l li svg{color:var(--lvl-green);margin-top:1px}
.lvl-start-l li b{color:var(--lvl-ink);margin-right:4px}
.lvl-deploy{margin-top:12px}

/* ── dark theme ──────────────────────────────────────────────────────── */
body[data-gantt-theme="dark"] #tp-levelling,body[data-gantt-theme="dark"] .lvl-portal{
  --lvl-ink:#E6EDF3; --lvl-ink-2:#C3CDD6; --lvl-mut:#8B98A5; --lvl-mut-2:#6E7B88;
  --lvl-bg:#0B1220; --lvl-card:#101A2B; --lvl-wash:#0D1626;
  --lvl-line:#1E2B3F; --lvl-line-2:#182437; --lvl-line-3:#27364C;
  --lvl-green-t:#0F2A22; --lvl-ok-t:#0F2A22; --lvl-warn-t:#2A2113; --lvl-risk-t:#2C1614; --lvl-info-t:#131E2E;
  --lvl-ok:#4ADE9B; --lvl-warn:#E3B25C; --lvl-risk:#F08579; --lvl-info:#7FB0E8;
  --lvl-before:#6E7B88; --lvl-after:#60A5FA;
  /* the same eight hues stepped for the dark surface, validated as a set */
  --lvl-s1:#3987e5; --lvl-s2:#d95926; --lvl-s3:#199e70; --lvl-s4:#c98500;
  --lvl-s5:#d55181; --lvl-s6:#008300; --lvl-s7:#9085e9; --lvl-s8:#e66767;
  --lvl-s9:#12a6b0; --lvl-s10:#a5701e; --lvl-s11:#c257b6; --lvl-s12:#77921f;
  --lvl-other:#6E7B88; --lvl-heat:#F0A93E;
}
body[data-gantt-theme="dark"] #tp-levelling .lvl-state.is-sim{background:linear-gradient(90deg,#241C0C,#15100A);border-bottom-color:#4A3A18}
body[data-gantt-theme="dark"] #tp-levelling .lvl-state-warn{color:#E3B25C}
body[data-gantt-theme="dark"] #tp-levelling .lvl-cap{stroke:#E6EDF3}
body[data-gantt-theme="dark"] #tp-levelling .lvl-cap-l{fill:#E6EDF3}
body[data-gantt-theme="dark"] #tp-levelling .lvl-hm-c.is-low{color:#CDEBDF}
body[data-gantt-theme="dark"] #tp-levelling .lvl-tg i::after{background:#0B1220}
body[data-gantt-theme="dark"] #tp-levelling .lvl-verdict.is-sim{background:linear-gradient(90deg,#241C0C,#15100A);border-left-color:#B9822A}
body[data-gantt-theme="dark"] #tp-levelling .lvl-verdict.is-ok{border-left-color:#4ADE9B}
body[data-gantt-theme="dark"] #tp-levelling .lvl-verdict.is-warn{border-left-color:#E3B25C}
body[data-gantt-theme="dark"] #tp-levelling .lvl-verdict.is-risk{border-left-color:#F08579}
body[data-gantt-theme="dark"] #tp-levelling .lvl-kpi.is-ok{border-top-color:#4ADE9B}
body[data-gantt-theme="dark"] #tp-levelling .lvl-kpi.is-warn{border-top-color:#E3B25C}
body[data-gantt-theme="dark"] #tp-levelling .lvl-kpi.is-risk{border-top-color:#F08579}

/* ── print ───────────────────────────────────────────────────────────── */
@media print{
  #tp-levelling .lvl-top,#tp-levelling .lvl-rail,#tp-levelling .lvl-filters,#tp-levelling .lvl-state-a{display:none!important}
  #tp-levelling .lvl-card{break-inside:avoid;box-shadow:none}
  #tp-levelling .lvl-tbl-wrap,#tp-levelling .lvl-hm-wrap{max-height:none;overflow:visible}
}

/* ── narrow screens ──────────────────────────────────────────────────── */
@media (max-width:760px){
  .lvl-top,.lvl-rail,.lvl-filters,.lvl-main{padding-left:12px;padding-right:12px}
  .lvl-rail{top:auto;position:static}
  .lvl-filters{position:static}
  .lvl-top{position:static}
  .lvl-search{min-width:150px}
  .lvl-cmd-grid{grid-template-columns:1fr}
  .lvl-kpis{grid-template-columns:repeat(auto-fit,minmax(120px,1fr))}
}

/* ── "why nothing moved" diagnosis ───────────────────────────────────── */
.lvl-card-blocked{border-color:#EFD9A8;border-left:4px solid var(--lvl-warn)}
.lvl-card-blocked .lvl-card-h{background:var(--lvl-warn-t);border-bottom-color:#EFD9A8}
.lvl-blocked-h{display:grid;grid-template-columns:repeat(auto-fit,minmax(160px,1fr));gap:10px;margin-bottom:12px}
.lvl-blocked-h div{display:flex;flex-direction:column;gap:1px}
.lvl-blocked-h span{font:700 8.5px/1.2 var(--lvl-font);letter-spacing:.09em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-blocked-h b{font:700 13px/1.2 var(--lvl-font)}
.lvl-blocked-h em{font-style:normal;font-size:10.5px;color:var(--lvl-mut)}
.lvl-rej{list-style:none;margin:0 0 14px;padding:0;display:flex;flex-direction:column;gap:5px}
.lvl-rej li{display:grid;grid-template-columns:34px 1fr auto;gap:10px;align-items:baseline;font-size:11.5px;
  padding:6px 9px;border-radius:var(--lvl-r-xs);background:var(--lvl-wash)}
.lvl-rej li b{font-family:var(--lvl-mono);font-weight:700;text-align:right;color:var(--lvl-ink)}
.lvl-rej li span{color:var(--lvl-ink-2)}
.lvl-rej li em{font-style:normal;font-size:10px;color:var(--lvl-mut-2)}
.lvl-suggest{display:flex;align-items:flex-start;gap:10px;padding:12px;border-radius:var(--lvl-r-s);
  background:var(--lvl-green-t);border:1px solid rgba(36,180,126,.25)}
.lvl-suggest>svg{color:var(--lvl-green-d);margin-top:2px}
.lvl-suggest b{display:block;font:700 11px/1 var(--lvl-font);letter-spacing:.06em;text-transform:uppercase;color:var(--lvl-green-d)}
.lvl-suggest p{margin:6px 0 0;font-size:12px;line-height:1.6;color:var(--lvl-ink-2)}
.lvl-suggest-a{display:flex;gap:7px;flex-wrap:wrap;margin-top:11px}
.lvl-audit-r-warn{display:flex;align-items:flex-start;gap:7px;margin:9px 0 0;padding:8px 10px;border-radius:var(--lvl-r-xs);
  background:var(--lvl-warn-t);color:var(--lvl-warn);font-size:11px;line-height:1.55}
.lvl-audit-r-warn svg{margin-top:2px;flex:0 0 auto}

/* ── THE SEMANTIC CHANGE LOG ──────────────────────────────────────────────
   One line per schedule mutation, grouped by what actually changed, with the
   MECHANISM beside it — the field on the schedule that was written. It reads
   as a record rather than a table because that is what it is: an account of
   the operations the plan executed, not a diff of where the bars ended up. */
.lvl-audit-log{margin:10px 0 0;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-xs);
  background:var(--lvl-wash);overflow:hidden}
.lvl-audit-log>summary{cursor:pointer;list-style:none;padding:9px 12px;display:flex;align-items:center;
  gap:8px;flex-wrap:wrap;font:600 11.5px/1.4 var(--lvl-font);color:var(--lvl-ink-2)}
.lvl-audit-log>summary::-webkit-details-marker{display:none}
.lvl-audit-log>summary:hover{background:var(--lvl-card)}
.lvl-audit-log[open]>summary{border-bottom:1px solid var(--lvl-line);background:var(--lvl-card)}
.lvl-audit-log-s{padding:10px 12px}
.lvl-audit-log-s+.lvl-audit-log-s{border-top:1px dashed var(--lvl-line)}
.lvl-audit-log-s h5{margin:0 0 7px;font:700 10px/1 var(--lvl-font);letter-spacing:.08em;
  text-transform:uppercase;color:var(--lvl-mut)}
.lvl-audit-log-s h5 em{font-style:normal;color:var(--lvl-green-d)}
.lvl-audit-log-s ul{margin:0;padding:0;list-style:none;display:grid;gap:6px}
.lvl-audit-log-s li{font-size:11.5px;line-height:1.55;color:var(--lvl-ink);
  padding-left:11px;border-left:2px solid var(--lvl-green-t)}
.lvl-audit-log-s li code{display:inline-block;margin-left:7px;padding:1px 5px;border-radius:3px;
  background:var(--lvl-card);border:1px solid var(--lvl-line);font-size:10px;color:var(--lvl-mut)}
.lvl-audit-log-s li em{display:block;margin-top:2px;font-style:normal;font-size:10.5px;
  line-height:1.5;color:var(--lvl-mut)}

/* ══ VERDICT BANNER ═══════════════════════════════════════════════════════
   The first thing on the page: one sentence of diagnosis and the action that
   follows from it. Everything else on the overview elaborates this. */
/* Left accent stripe: tone is readable at a glance, before any text is read. */
.lvl-verdict{display:grid;grid-template-columns:auto 1fr auto;gap:14px;align-items:start;
  padding:14px 18px;border-radius:var(--lvl-r);border:1px solid var(--lvl-line);background:var(--lvl-card);
  border-left:4px solid var(--lvl-line-3)}
.lvl-verdict-i{width:34px;height:34px;border-radius:9px;display:flex;align-items:center;justify-content:center;flex:0 0 auto}
.lvl-verdict h2{margin:0;font:800 15px/1.3 var(--lvl-head);letter-spacing:-.01em}
.lvl-verdict p{margin:3px 0 0;font-size:12px;line-height:1.5;color:var(--lvl-ink-2);max-width:100ch}
.lvl-verdict-x{color:var(--lvl-mut)!important;font-size:11px!important}
.lvl-verdict-a{display:flex;gap:7px;flex-wrap:wrap;justify-content:flex-end;align-items:center}
.lvl-verdict.is-ok{border-left-color:var(--lvl-ok);background:var(--lvl-ok-t)}
.lvl-verdict.is-ok .lvl-verdict-i{background:var(--lvl-ok);color:#fff}
.lvl-verdict.is-warn{border-left-color:var(--lvl-warn);background:var(--lvl-warn-t)}
.lvl-verdict.is-warn .lvl-verdict-i{background:var(--lvl-warn);color:#fff}
.lvl-verdict.is-risk{border-left-color:var(--lvl-risk);background:var(--lvl-risk-t)}
.lvl-verdict.is-risk .lvl-verdict-i{background:var(--lvl-risk);color:#fff}
.lvl-verdict.is-sim{border-left-color:#B9822A;background:linear-gradient(90deg,#FFF8E8,#FFFDF7)}
.lvl-verdict.is-sim .lvl-verdict-i{background:#B9822A;color:#fff}
@media (max-width:900px){.lvl-verdict{grid-template-columns:auto 1fr}.lvl-verdict-a{grid-column:1/-1;justify-content:flex-start}}
.lvl-kpi-v i{font-style:normal;font-size:13px;color:var(--lvl-mut-2)}
.lvl-neg{color:var(--lvl-risk);font-family:var(--lvl-mono)}

/* ══ SMALL MULTIPLES — the signature overview chart ═══════════════════════ */
.lvl-sm{display:grid;grid-template-columns:repeat(auto-fit,minmax(280px,1fr));gap:8px}
.lvl-sm-c{margin:0;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);padding:7px 9px 3px;background:var(--lvl-card)}
.lvl-sm-c[role="button"]{cursor:pointer;transition:border-color .12s,background .12s}
.lvl-sm-c[role="button"]:hover{border-color:var(--lvl-mut-2);background:var(--lvl-wash)}
.lvl-sm-c.is-over{border-color:#E5C4BE;background:var(--lvl-risk-t)}
.lvl-sm-c figcaption{display:flex;align-items:center;gap:6px;flex-wrap:wrap;margin-bottom:1px;font-size:11px}
.lvl-sm-dot{width:8px;height:8px;border-radius:2px;flex:0 0 auto}
.lvl-sm-c figcaption b{font-weight:700;color:var(--lvl-ink)}
.lvl-sm-n{margin-left:auto;font-family:var(--lvl-mono);font-size:10px;color:var(--lvl-mut)}
.lvl-sm-n b{color:var(--lvl-ink)}
.lvl-sm-c figcaption em{font-style:normal;font:700 8.5px/1 var(--lvl-font);letter-spacing:.05em;text-transform:uppercase;
  padding:2px 5px;border-radius:20px;flex:0 0 auto}
.lvl-sm-bad{background:var(--lvl-risk);color:#fff}
.lvl-sm-ok{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-sm-svg{width:100%;height:auto}
.lvl-sm-band{fill:var(--lvl-ok);opacity:.05}

/* ══ CHART MARKS ══════════════════════════════════════════════════════════ */
.lvl-bar.is-over{fill:var(--lvl-risk)}
.lvl-over{fill:var(--lvl-risk);opacity:.9}
.lvl-hit{fill:transparent;pointer-events:all}
.lvl-endlbl{font:700 10px/1 var(--lvl-mono);fill:var(--lvl-mut)}
.lvl-line{fill:none;stroke-width:2;stroke-linejoin:round;stroke-linecap:round}
.lvl-area{opacity:.09}
.lvl-cap{stroke:var(--lvl-ink);stroke-width:1.5;stroke-dasharray:6 3}
.lvl-cap-l{font:700 10px/1 var(--lvl-font);fill:var(--lvl-ink)}

/* ══ SCALE LEGENDS — a colour scale that means something says so ══════════ */
.lvl-scale{display:flex;align-items:center;gap:6px;flex-wrap:wrap;margin-top:9px;font-size:10.5px;color:var(--lvl-mut)}
.lvl-scale>span{font:700 9px/1 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut-2);margin-right:3px}
.lvl-scale b{font-weight:500;margin-right:9px}
.lvl-scale i{display:inline-block;width:16px;height:11px;border-radius:2px;border:1px solid var(--lvl-line)}
.lvl-ramp{width:90px!important;background:linear-gradient(90deg,rgba(46,125,99,.06),rgba(46,125,99,.55))}
.lvl-lg-e{width:20px!important;height:0!important;border:0!important;border-top:2px solid var(--lvl-ok)!important;border-radius:0!important}
.lvl-lg-e.is-medium{border-top-color:var(--lvl-info)!important;border-top-style:dashed!important}
.lvl-lg-e.is-limited{border-top-color:var(--lvl-warn)!important;border-top-style:dotted!important}
.lvl-lg-n{border-radius:50%!important;width:12px!important;height:12px!important;background:var(--lvl-green-t);border-color:var(--lvl-green)!important}

/* ══ PIVOT TABLE — the numbers half of every deployment view ══════════════ */
.lvl-pv-wrap{overflow:auto;max-height:600px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s)}
.lvl-pv{width:100%;border-collapse:separate;border-spacing:0;font-size:11.5px}
.lvl-pv thead th{position:sticky;top:0;z-index:4;background:var(--lvl-wash);font:700 9.5px/1.2 var(--lvl-font);
  letter-spacing:.05em;text-transform:uppercase;color:var(--lvl-mut);padding:8px 7px;text-align:right;
  border-bottom:1px solid var(--lvl-line);white-space:nowrap}
.lvl-pv thead th.lvl-pv-h{text-align:left;left:0;z-index:6}
.lvl-pv-h{position:sticky;left:0;z-index:3;background:var(--lvl-card);text-align:left;min-width:220px;
  border-right:1px solid var(--lvl-line);padding:6px 9px;font-weight:600}
.lvl-pv-h em{display:inline-block;margin-left:6px;font-style:normal;font:700 9px/1 var(--lvl-mono);
  background:var(--lvl-line-2);color:var(--lvl-mut);padding:2px 5px;border-radius:20px}
.lvl-pv-dot{display:inline-block;width:8px;height:8px;border-radius:2px;margin-right:6px;vertical-align:baseline}
.lvl-pv-c{text-align:right;font-family:var(--lvl-mono);padding:5px 7px;border-bottom:1px solid var(--lvl-line-2);color:var(--lvl-ink-2)}
.lvl-pv-c.is-zero{color:transparent}
.lvl-pv-c.is-mid{background:rgba(46,125,99,.08)}
.lvl-pv-c.is-high{background:var(--lvl-warn-t);color:var(--lvl-warn);font-weight:700}
.lvl-pv-c.is-over{background:var(--lvl-risk);color:#fff;font-weight:800}
.lvl-pv-c.is-peak{font-weight:800;color:var(--lvl-ink);box-shadow:inset 0 0 0 1px var(--lvl-line-3)}
.lvl-pv-t{text-align:right;font-family:var(--lvl-mono);font-weight:700;background:var(--lvl-wash);padding:5px 9px;
  border-bottom:1px solid var(--lvl-line-2);border-left:1px solid var(--lvl-line)}
.lvl-pv-g>th,.lvl-pv-g>td{background:var(--lvl-wash);font-weight:700;border-bottom:1px solid var(--lvl-line)}
.lvl-pv-g[role="button"]{cursor:pointer}
.lvl-pv-g[role="button"]:hover>th,.lvl-pv-g[role="button"]:hover>td{background:var(--lvl-line-2)}
.lvl-pv-r>th{padding-left:26px;font-weight:400;color:var(--lvl-ink-2)}
.lvl-pv-r>th em{display:block;margin:1px 0 0;background:none;padding:0;color:var(--lvl-mut-2);font-size:9.5px}
.lvl-pv-arrow{display:inline-block;width:0;height:0;margin-right:7px;vertical-align:middle;
  border-left:5px solid var(--lvl-mut);border-top:4px solid transparent;border-bottom:4px solid transparent;transition:transform .12s}
.lvl-pv-g.is-open .lvl-pv-arrow{transform:rotate(90deg)}
.lvl-pv-nub{display:inline-block;width:5px;margin-right:7px}
.lvl-pv tfoot td,.lvl-pv tfoot th{position:sticky;bottom:0;background:var(--lvl-card);font-weight:800;font-family:var(--lvl-mono);
  text-align:right;padding:7px;border-top:2px solid var(--lvl-line-3)}
.lvl-pv tfoot th{text-align:left;left:0;z-index:5;font-family:var(--lvl-font)}
.lvl-dep-ctl{display:flex;gap:9px;flex-wrap:wrap;margin:10px 0 12px}

/* ══ SETUP DRAWER ═════════════════════════════════════════════════════════ */
.lvl-drawer-bd{position:fixed;inset:0;background:rgba(20,32,42,.32);z-index:998;animation:lvlFade .12s ease}
.lvl-drawer{position:fixed;top:0;right:0;bottom:0;width:min(560px,94vw);z-index:999;background:var(--lvl-card);
  border-left:1px solid var(--lvl-line);box-shadow:-16px 0 48px rgba(20,32,42,.16);display:flex;flex-direction:column;
  animation:lvlSlide .16s ease}
@keyframes lvlFade{from{opacity:0}to{opacity:1}}
@keyframes lvlSlide{from{transform:translateX(24px);opacity:.4}to{transform:none;opacity:1}}
.lvl-drawer-h{display:flex;align-items:flex-start;justify-content:space-between;gap:12px;padding:16px 18px;border-bottom:1px solid var(--lvl-line)}
.lvl-drawer-h h3{margin:0;font:800 15px/1.2 var(--lvl-head)}
.lvl-drawer-h p{margin:4px 0 0;font-size:11.5px;color:var(--lvl-mut);max-width:52ch}
/* MIN-HEIGHT:0 IS WHAT MAKES THIS SCROLL. In a column flex container a child
   with flex:1 still has min-height:auto, so it refuses to shrink below its
   content: the body grew past the drawer, the drawer's own scrollbar never
   appeared, and the wheel went to the page behind it instead. "The scroll
   moves the page, not the window" is exactly that. overscroll-behavior stops
   the page taking over again when the body reaches its end. */
.lvl-drawer-b{flex:1 1 auto;min-height:0;overflow-y:auto;overscroll-behavior:contain;
  padding:4px 18px 18px}
.lvl-drawer-h,.lvl-drawer-f{flex:0 0 auto}
.lvl-drawer-f{display:flex;gap:8px;justify-content:flex-end;padding:12px 18px;border-top:1px solid var(--lvl-line);background:var(--lvl-wash)}
/* ══ TAKING ONE CHANGE OUT ══════════════════════════════════════════════
   A staged session was all-or-nothing at the point of decision: apply the
   lot or discard the lot. One change can leave it now — and it never leaves
   on a single click, because the thing a planner needs before removing a
   move is what the session looks like WITHOUT it, and that is a question
   only the network can answer.
   ═══════════════════════════════════════════════════════════════════════ */
.lvl-drawer.is-drop{width:min(520px,94vw)}
.lvl-drop-b{flex:1 1 auto;min-height:0;overflow-y:auto;overscroll-behavior:contain;
  padding:var(--lvl-sp-4) var(--lvl-sp-4) var(--lvl-sp-3)}
.lvl-drop-b h4{margin:var(--lvl-sp-4) 0 var(--lvl-sp-2);
  font:700 var(--lvl-t-1)/1.2 var(--lvl-mono,var(--lvl-font));letter-spacing:.11em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
/* the change itself, stated once at the head */
.lvl-drop-w{padding:var(--lvl-sp-3);border-radius:var(--lvl-r-s);
  border:1px solid var(--lvl-line);border-left:3px solid var(--lvl-after);
  background:var(--lvl-wash)}
.lvl-drop-w>b{display:block;font:800 var(--lvl-t-4)/1.3 var(--lvl-head);color:var(--lvl-ink)}
.lvl-drop-w>em{display:block;margin-top:3px;font-style:normal;
  font:500 var(--lvl-t-2)/1.45 var(--lvl-font);color:var(--lvl-mut)}
.lvl-drop-w>s{display:block;margin-top:4px;text-decoration:none;
  font:500 var(--lvl-t-2)/1.4 var(--lvl-font);color:var(--lvl-mut-2)}
/* ── THE VERDICT LEADS ─────────────────────────────────────────────
   A planner is asking one question — can I take this out without breaking
   anything — so that is answered first, in the tone of the answer, before
   any figure. */
.lvl-drop-v{display:grid;grid-template-columns:auto minmax(0,1fr);gap:10px;
  align-items:start;margin-top:var(--lvl-sp-3);padding:var(--lvl-sp-3);
  border-radius:var(--lvl-r-s);border:1px solid var(--lvl-line)}
.lvl-drop-v>svg{margin-top:1px}
.lvl-drop-v b{display:block;font:800 var(--lvl-t-4)/1.3 var(--lvl-head)}
.lvl-drop-v em{display:block;margin-top:3px;font-style:normal;
  font:500 var(--lvl-t-3)/1.5 var(--lvl-font);color:var(--lvl-mut)}
.lvl-drop-v.is-good{border-color:color-mix(in srgb,var(--lvl-ok) 34%,var(--lvl-line));
  background:color-mix(in srgb,var(--lvl-ok) 7%,var(--lvl-card))}
.lvl-drop-v.is-good>svg,.lvl-drop-v.is-good b{color:var(--lvl-ok)}
.lvl-drop-v.is-bad{border-color:color-mix(in srgb,var(--lvl-risk) 34%,var(--lvl-line));
  background:color-mix(in srgb,var(--lvl-risk) 7%,var(--lvl-card))}
.lvl-drop-v.is-bad>svg,.lvl-drop-v.is-bad b{color:var(--lvl-risk)}
.lvl-drop-v.is-flat{background:var(--lvl-wash)}
.lvl-drop-v.is-flat>svg{color:var(--lvl-mut-2)}
.lvl-drop-v.is-flat b{color:var(--lvl-ink)}
/* what it hands back — the one figure a planner gains by removing it */
.lvl-drop-g{display:grid;grid-template-columns:minmax(0,1fr) auto;align-items:center;
  gap:2px 12px;margin-top:var(--lvl-sp-2);padding:var(--lvl-sp-2) var(--lvl-sp-3);
  border-radius:var(--lvl-r-s);border:1px dashed color-mix(in srgb,var(--lvl-ok) 40%,var(--lvl-line));
  background:color-mix(in srgb,var(--lvl-ok) 5%,transparent)}
.lvl-drop-g>span{font:700 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.1em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-drop-g>b{grid-row:1/3;font:800 var(--lvl-t-6)/1 var(--lvl-head);color:var(--lvl-ok)}
.lvl-drop-g>b>i{font-style:normal;font-size:var(--lvl-t-4)}
.lvl-drop-g>em{font-style:normal;font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut)}
/* ── AND EVERY READING THAT MOVES IS A COMPARISON, NOT TWO NUMBERS ─
   Two figures with an arrow between them is arithmetic the reader has to do.
   One track, the session as it stands drawn against the session without this
   change, on a shared scale: the difference is a LENGTH. */
.lvl-drop-m{display:flex;flex-direction:column;gap:var(--lvl-sp-2)}
.lvl-dropm{padding:var(--lvl-sp-2) var(--lvl-sp-3) var(--lvl-sp-3);border-radius:var(--lvl-r-s);
  border:1px solid var(--lvl-line);background:var(--lvl-card)}
.lvl-dropm.is-bad{border-left:3px solid var(--lvl-risk)}
.lvl-dropm.is-good{border-left:3px solid var(--lvl-ok)}
.lvl-dropm-h{display:grid;grid-template-columns:minmax(0,1fr) auto;align-items:baseline;
  gap:2px 8px;margin-bottom:var(--lvl-sp-2)}
/* EVERY CELL IS PLACED. Leaving the delta to auto-placement put it in
   column one — a row that read "+1 ... Peak on site", the number before the
   thing it is a number of. */
.lvl-dropm-h>b{grid-column:1;grid-row:1;min-width:0;
  font:700 var(--lvl-t-3)/1.2 var(--lvl-font);color:var(--lvl-ink)}
.lvl-dropm-h>em{grid-column:1;grid-row:2;font-style:normal;
  font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut-2)}
.lvl-dropm-h>s{grid-column:2;grid-row:1/3;text-decoration:none;align-self:center;
  text-align:right;font:800 var(--lvl-t-5)/1 var(--lvl-head)}
.lvl-dropm.is-bad .lvl-dropm-h>s{color:var(--lvl-risk)}
.lvl-dropm.is-good .lvl-dropm-h>s{color:var(--lvl-ok)}
.lvl-dropm-t{display:grid;grid-template-columns:74px minmax(0,1fr) 52px;align-items:center;
  gap:8px;height:18px}
.lvl-dropm-t+.lvl-dropm-t{margin-top:4px}
.lvl-dropm-t>span{font:500 var(--lvl-t-1)/1 var(--lvl-font);color:var(--lvl-mut-2);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-dropm-t>i{height:10px;border-radius:5px;min-width:2px;
  background:var(--lvl-line-2);box-shadow:inset 0 0 0 1px rgba(20,32,42,.05)}
.lvl-dropm-t>i.is-now{background:var(--lvl-mut-2)}
.lvl-dropm.is-bad .lvl-dropm-t>i.is-out{background:var(--lvl-risk)}
.lvl-dropm.is-good .lvl-dropm-t>i.is-out{background:var(--lvl-ok)}
.lvl-dropm-t>u{text-decoration:none;text-align:right;
  font:700 var(--lvl-t-3)/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ink)}
/* a date has no length, so it keeps the pair — but it keeps it big */
.lvl-dropm-d{display:flex;align-items:baseline;gap:9px}
.lvl-dropm-d>b{font:700 var(--lvl-t-4)/1 var(--lvl-font);color:var(--lvl-mut-2)}
.lvl-dropm-d>i{font-style:normal;color:var(--lvl-mut-2)}
.lvl-dropm-d>u{text-decoration:none;font:800 var(--lvl-t-5)/1 var(--lvl-head);color:var(--lvl-ink)}
/* and "nothing else changed" is worth exactly one line */
.lvl-drop-s{display:flex;align-items:flex-start;gap:6px;margin:var(--lvl-sp-3) 0 0;
  font:500 var(--lvl-t-2)/1.5 var(--lvl-font);color:var(--lvl-mut)}
.lvl-drop-s>svg{flex:none;margin-top:2px;color:var(--lvl-ok)}
.lvl-drop-s b{color:var(--lvl-ink-2)}

/* what else lands somewhere else — the part a list of moves cannot tell you */
.lvl-drop-n{display:flex;flex-direction:column;gap:1px}
.lvl-drop-nr{display:grid;grid-template-columns:minmax(0,1fr) auto 54px;align-items:baseline;
  gap:8px;padding:6px 8px;border-radius:5px}
.lvl-drop-nr:nth-child(odd){background:var(--lvl-wash)}
.lvl-drop-nr>b{min-width:0;font:600 var(--lvl-t-3)/1.2 var(--lvl-font);color:var(--lvl-ink);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-drop-nr>span{font:500 var(--lvl-t-2)/1.2 var(--lvl-mono,var(--lvl-font));color:var(--lvl-mut-2);
  white-space:nowrap}
.lvl-drop-nr>em{font-style:normal;text-align:right;
  font:700 var(--lvl-t-2)/1.2 var(--lvl-mono,var(--lvl-font))}
.lvl-drop-nr>em.is-bad{color:var(--lvl-risk)}
.lvl-drop-nr>em.is-good{color:var(--lvl-ok)}

/* ── THE BAR THAT HOLDS NO DECISION ───────────────────────────────────────
   The window a planner gets when they try to remove a change from a bar that
   has none. It has one job, and the job is a destination: the activity that
   actually moved this one, as the biggest, most obviously pressable thing on
   the panel. Everything else on it is one line.

   The first attempt wrote its own markup — tags the drawer styles do not
   target — and every rule below silently missed. It shares the drawer's
   envelope now, so this file only has to style the one new thing. */
.lvl-carr{display:grid;grid-template-columns:minmax(0,1fr) auto;align-items:center;
  gap:2px 14px;width:100%;text-align:left;cursor:pointer;
  margin-top:var(--lvl-sp-2);padding:14px var(--lvl-sp-3);
  border-radius:var(--lvl-r-s);
  border:1.5px solid color-mix(in srgb,var(--lvl-green) 45%,var(--lvl-line));
  background:linear-gradient(180deg,
    color-mix(in srgb,var(--lvl-green) 9%,var(--lvl-card)),
    color-mix(in srgb,var(--lvl-green) 4%,var(--lvl-card)));
  transition:border-color .12s,box-shadow .12s,transform .08s}
.lvl-carr:hover{border-color:var(--lvl-green);
  box-shadow:0 2px 12px color-mix(in srgb,var(--lvl-green) 22%,transparent)}
.lvl-carr:active{transform:translateY(1px)}
.lvl-carr-k{grid-column:1;font:800 var(--lvl-t-1)/1 var(--lvl-font);letter-spacing:.1em;
  text-transform:uppercase;color:var(--lvl-green-d)}
/* THE NAME IS THE ANSWER, so it is the size of one — and it is not cut
   off. Real activity names run to sixty characters ("Survey and mark
   existing services - General Clearance"), and a one-line ellipsis turns
   the one thing this panel exists to say into "General Cl…". Two lines,
   then clamp. */
.lvl-carr-n{grid-column:1;min-width:0;margin:3px 0 2px;
  font:800 var(--lvl-t-5)/1.25 var(--lvl-head);color:var(--lvl-ink);
  display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;
  overflow:hidden;overflow-wrap:anywhere}
.lvl-carr-h{grid-column:1;font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut)}
.lvl-carr-go{grid-column:2;grid-row:1/4;display:inline-flex;align-items:center;gap:3px;
  white-space:nowrap;padding:7px 10px 7px 13px;border-radius:999px;
  background:var(--lvl-green);color:#fff;
  font:800 var(--lvl-t-2)/1 var(--lvl-font)}
.lvl-carr-go>svg{transform:rotate(-90deg)}

/* the chain it came down — a trail, not a sentence */
.lvl-carr-ch{display:flex;flex-wrap:wrap;align-items:center;gap:4px 0;
  margin-top:var(--lvl-sp-2)}
.lvl-carr-ch>i{font-style:normal;font:600 var(--lvl-t-1)/1 var(--lvl-font);
  padding:5px 9px;border-radius:999px;background:var(--lvl-wash);
  border:1px solid var(--lvl-line);color:var(--lvl-mut);
  max-width:15ch;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-carr-ch>i+i{margin-left:14px;position:relative}
.lvl-carr-ch>i+i::before{content:'';position:absolute;left:-11px;top:50%;
  width:8px;height:1px;background:var(--lvl-line-3)}
.lvl-carr-ch>i.is-this{background:color-mix(in srgb,var(--lvl-warn) 14%,transparent);
  border-color:color-mix(in srgb,var(--lvl-warn) 38%,var(--lvl-line));
  color:var(--lvl-warn);font-weight:800}

/* ── CARRIED, NOT CHOSEN ──────────────────────────────────────────────────
   In the list of what a change is holding, the two kinds are not the same
   fact: a staged decision can be put back on its own, and an activity the
   logic carried only moves because this one does. The row says which. */
.lvl-drop-nr>b>i{display:inline-block;margin-left:7px;padding:0 5px;border-radius:3px;font-style:normal;
  font:600 var(--lvl-t-1)/1.6 var(--lvl-font);letter-spacing:.04em;text-transform:uppercase;
  background:color-mix(in srgb,var(--lvl-warn) 16%,transparent);color:var(--lvl-warn)}
.lvl-drop-nr.is-staged{box-shadow:inset 2px 0 0 var(--lvl-green)}
/* the control that opens it, on every row that lists a change */
.lvl-chg-x{flex:none;width:22px;height:22px;display:flex;align-items:center;justify-content:center;
  border:1px solid transparent;border-radius:6px;background:none;color:var(--lvl-mut-2);
  cursor:pointer;opacity:.55;transition:opacity .12s ease,color .12s ease,background .12s ease}
.lvl-chg-r:hover .lvl-chg-x{opacity:1}
.lvl-chg-x:hover{background:color-mix(in srgb,var(--lvl-risk) 12%,transparent);
  border-color:color-mix(in srgb,var(--lvl-risk) 30%,transparent);color:var(--lvl-risk);opacity:1}

.lvl-set{padding:16px 0;border-bottom:1px solid var(--lvl-line-2)}
.lvl-set:last-child{border-bottom:0}
.lvl-set h4{margin:0 0 4px;font:700 11px/1 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-ink)}
.lvl-set h4 small{font-weight:500;text-transform:none;letter-spacing:0;color:var(--lvl-mut-2);margin-left:7px}
.lvl-set-p{margin:0 0 10px;font-size:11.5px;color:var(--lvl-mut);line-height:1.6}
.lvl-set .lvl-fl{margin-top:10px}
.lvl-set .lvl-strats{max-height:none}

/* ══ MANUAL WORKBENCH ═════════════════════════════════════════════════════ */
.lvl-card-wb .lvl-card-b>h4{display:flex;align-items:baseline;gap:9px;margin:18px 0 8px}
.lvl-card-wb .lvl-card-b>h4 small{font-weight:500;text-transform:none;letter-spacing:0;color:var(--lvl-mut-2);font-size:11px}
.lvl-wb-bar{display:flex;align-items:flex-end;gap:12px;flex-wrap:wrap;padding:11px 12px;margin-bottom:14px;
  background:var(--lvl-wash);border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s)}
.lvl-fl.is-grow{flex:1 1 260px}
.lvl-fl.is-grow select{max-width:none;width:100%}
.lvl-wb-nudge{display:flex;align-items:center;gap:5px;padding-bottom:2px}
.lvl-wb-nudge>span{font:700 9px/1 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut-2);margin-right:2px}
.lvl-wb-shift{min-width:46px;text-align:center;font:800 14px/1 var(--lvl-mono);color:var(--lvl-ink)}
.lvl-wb-jump,.lvl-wb-act{display:flex;gap:6px;flex-wrap:wrap;padding-bottom:2px}
.lvl-wb-act{margin-left:auto}
.lvl-wb-grid{display:grid;grid-template-columns:1.35fr 1fr;gap:16px}
@media (max-width:1100px){.lvl-wb-grid{grid-template-columns:1fr}}
.lvl-wb-grid h4{margin:0 0 8px;font:700 10px/1 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut)}
.lvl-wb-load .lvl-ba{grid-template-columns:1fr 1fr;gap:10px}
.lvl-wb-load .lvl-note{margin-top:8px;display:flex;align-items:center;gap:9px;flex-wrap:wrap}

/* ══ TIMELINE ═════════════════════════════════════════════════════════════ */
.lvl-tl-wrap{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);background:var(--lvl-card)}
.lvl-tl{display:block}
.lvl-tl.is-dragging{cursor:grabbing}
.lvl-tl-zebra{fill:transparent}
.lvl-tl-row:nth-child(even) .lvl-tl-zebra{fill:var(--lvl-wash)}
.lvl-tl-row.is-sel .lvl-tl-zebra{fill:var(--lvl-green-t)}
.lvl-tl-l{font-size:11px;fill:var(--lvl-ink-2);cursor:pointer}
.lvl-tl-row.is-sel .lvl-tl-l{font-weight:700;fill:var(--lvl-ink)}
.lvl-tl-row.is-crit .lvl-tl-l{fill:var(--lvl-risk)}
.lvl-tl-win{fill:var(--lvl-ok);opacity:.16}
.lvl-tl-ghost{fill:var(--lvl-line-3)}
.lvl-tl-bar{fill:var(--lvl-info)}
.lvl-tl-row.is-crit .lvl-tl-bar{fill:var(--lvl-risk)}
.lvl-tl-bar.is-moved{fill:var(--lvl-after)}
.lvl-tl-row.is-sel .lvl-tl-bar{stroke:var(--lvl-ink);stroke-width:1.5}
.lvl-tl-bar[data-lvl-drag]{cursor:grab}
.lvl-tl-bar[data-lvl-drag]:hover{filter:brightness(1.12)}
.lvl-tl-d{font:700 10px/1 var(--lvl-mono);fill:var(--lvl-warn)}
.lvl-tl-now{stroke:var(--lvl-risk);stroke-width:1.5;stroke-dasharray:3 3}

/* ══ DARK ADJUSTMENTS ═════════════════════════════════════════════════════ */
body[data-gantt-theme="dark"] #tp-levelling .lvl-verdict.is-sim{background:linear-gradient(90deg,#241C0C,#15100A);border-left-color:#B9822A}
body[data-gantt-theme="dark"] #tp-levelling .lvl-drawer-bd{background:rgba(0,0,0,.55)}
body[data-gantt-theme="dark"] #tp-levelling .lvl-ramp{background:linear-gradient(90deg,rgba(74,222,155,.08),rgba(74,222,155,.6))}
body[data-gantt-theme="dark"] #tp-levelling .lvl-pv-c.is-mid{background:rgba(74,222,155,.10)}
body[data-gantt-theme="dark"] #tp-levelling .lvl-shape-score{background:var(--lvl-card)}

/* ══ SCENARIO TRADE-OFF ═══════════════════════════════════════════════════ */
.lvl-to{display:flex;flex-direction:column;gap:2px}
.lvl-to-hd,.lvl-to-r{display:grid;grid-template-columns:minmax(180px,1.5fr) repeat(4,minmax(110px,1fr)) auto;gap:12px;align-items:center}
.lvl-to-hd{padding:0 10px 6px;border-bottom:1px solid var(--lvl-line)}
.lvl-to-hd span{font:700 9px/1.2 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-to-r{padding:9px 10px;border-radius:var(--lvl-r-s)}
.lvl-to-r:hover{background:var(--lvl-wash)}
.lvl-to-r.is-flagged{background:var(--lvl-warn-t)}
.lvl-to-r.is-rec{box-shadow:inset 0 0 0 1.5px var(--lvl-ok)}
.lvl-to-n b{display:block;font:700 12.5px/1.3 var(--lvl-font)}
.lvl-to-n em{display:block;font-style:normal;font-size:10.5px;color:var(--lvl-mut);margin-top:1px}
.lvl-to-r>div{display:flex;align-items:center;gap:8px}
.lvl-to-t{flex:1;display:block;height:8px;border-radius:4px;background:var(--lvl-line-2);overflow:hidden;min-width:40px}
.lvl-to-t b{display:block;height:100%;border-radius:4px}
.lvl-to-t b.is-good{background:var(--lvl-ok)}
.lvl-to-t b.is-warn{background:var(--lvl-warn)}
.lvl-to-t b.is-bad{background:var(--lvl-risk)}
.lvl-to-r u{text-decoration:none;font-family:var(--lvl-mono);font-size:11px;min-width:42px;text-align:right;white-space:nowrap}
.lvl-to-a{justify-content:flex-end}
@media (max-width:900px){
  .lvl-to-hd{display:none}
  .lvl-to-r{grid-template-columns:1fr;gap:5px;border:1px solid var(--lvl-line);margin-bottom:8px}
}

/* ══ DEPLOYMENT SHAPE ═════════════════════════════════════════════════════ */
.lvl-shape-gap{fill:var(--lvl-warn);opacity:.10}
.lvl-shape-ideal{fill:none;stroke:var(--lvl-ink);stroke-width:2;stroke-dasharray:7 4;stroke-linejoin:round}
/* the master's own profile, behind the levelled one — an outline, so it says
   "what it was" without competing with the bars for "what it is" */
/* THE GHOST HAD TO BE FOUND BEFORE IT COULD BE READ. At 1.6px in the same
   slate as every other muted mark it was a hairline behind a wall of solid
   bars — the reporter's words were "the before line could be better". It is
   2.4px, darker, and drawn over the bars rather than under them, so the
   outline of what the schedule USED to be reads as one continuous shape. */
.lvl-shape-was{fill:none;stroke:var(--lvl-ink-2);stroke-width:2.4;stroke-linejoin:round;
  stroke-linecap:square;opacity:.75;paint-order:stroke}
.lvl-shape-lbl{font:700 10px/1 var(--lvl-font);fill:var(--lvl-ink)}
/* ── A CHART DRAWN IN THE SHAPE OF ITS BOX SETS ITS TYPE THERE TOO ─────
   The fitted chart's coordinate system is a fraction of the height of the
   unfitted one, so the whole picture is drawn at well over 1x on screen —
   and 9.5 user units of axis type came out at 14px, twice the size of
   anything around it. Its marks are sized in the same units as its frame,
   so they land at the size they were designed at whatever the frame is. */
.lvl-svg.is-wide .lvl-ax{font-size:7px}
.lvl-svg.is-wide .lvl-shape-lbl{font-size:7.4px}
.lvl-svg.is-wide .lvl-grid,.lvl-svg.is-wide .lvl-axis{stroke-width:.7}
.lvl-svg.is-wide .lvl-shape-ideal{stroke-width:1.6}
.lvl-svg.is-wide .lvl-shape-was{stroke-width:1.1}
.lvl-shape-b{fill:var(--lvl-s1,#2a78d6)}
.lvl-shape-b.is-over{fill:var(--lvl-warn)}
.lvl-shape-b.is-under{fill:var(--lvl-line-3)}
.lvl-scurve{stroke:var(--lvl-ok);stroke-width:2.4}
.lvl-lg-b{background:var(--lvl-s1,#2a78d6)}
.lvl-lg-b.is-over{background:var(--lvl-warn)}
.lvl-lg-b.is-under{background:var(--lvl-line-3)}
.lvl-lg-l{width:22px!important;height:0!important;border:0!important;border-top:2px dashed var(--lvl-ink)!important;border-radius:0!important}
.lvl-lg-w{width:22px!important;height:0!important;border:0!important;border-top:2px solid var(--lvl-before)!important;border-radius:0!important}
.lvl-lg-b.is-was{background:var(--lvl-before);opacity:.55}
.lvl-shape-hd{display:grid;grid-template-columns:auto 1fr;gap:14px;align-items:center;padding:11px 14px;margin-bottom:12px;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);background:var(--lvl-wash)}
.lvl-shape-score{display:flex;flex-direction:column;align-items:center;justify-content:center;min-width:86px;
  padding:6px 10px;border-radius:var(--lvl-r-s);background:var(--lvl-card);border:1px solid var(--lvl-line)}
.lvl-shape-score b{font:800 24px/1 var(--lvl-mono)}
.lvl-shape-score i{font-style:normal;font-size:11px;color:var(--lvl-mut-2)}
.lvl-shape-score em{font-style:normal;font:700 8.5px/1.2 var(--lvl-font);letter-spacing:.06em;text-transform:uppercase;margin-top:4px;text-align:center}
.lvl-shape-score.is-good b{color:var(--lvl-ok)}
.lvl-shape-score.is-good{border-color:var(--lvl-ok);background:var(--lvl-ok-t)}
.lvl-shape-score.is-mid b{color:var(--lvl-warn)}
.lvl-shape-score.is-mid{border-color:var(--lvl-warn);background:var(--lvl-warn-t)}
.lvl-shape-score.is-bad b{color:var(--lvl-risk)}
.lvl-shape-score.is-bad{border-color:var(--lvl-risk);background:var(--lvl-risk-t)}
.lvl-shape-note{margin:0;font-size:12px;line-height:1.5;color:var(--lvl-ink-2)}
.lvl-shape-facts{display:flex;gap:14px;flex-wrap:wrap;margin-top:8px}
.lvl-shape-facts div{display:flex;flex-direction:column;gap:1px}
.lvl-shape-facts span{font:700 8.5px/1.2 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-shape-facts b{font:700 13px/1.2 var(--lvl-mono)}

/* ══ CREW LIMIT PANEL ═════════════════════════════════════════════════════ */
.lvl-lim-note{display:flex;align-items:flex-start;gap:9px;padding:10px 12px;margin-bottom:12px;border-radius:var(--lvl-r-s);
  background:var(--lvl-info-t);border:1px solid rgba(74,119,174,.22);font-size:11.5px;line-height:1.6;color:var(--lvl-ink-2)}
.lvl-lim-note svg{color:var(--lvl-info);margin-top:2px;flex:0 0 auto}
.lvl-crew{display:inline-flex;align-items:baseline;gap:4px;font-family:var(--lvl-mono);font-size:11px}
.lvl-crew b{font-weight:700}
.lvl-crew em{font-style:normal;color:var(--lvl-mut-2)}
.lvl-src{display:inline-block;padding:2px 6px;border-radius:20px;font:700 9px/1.5 var(--lvl-font);letter-spacing:.04em;text-transform:uppercase;white-space:nowrap}
.lvl-src.is-crew{background:var(--lvl-info-t);color:var(--lvl-info)}
.lvl-src.is-user{background:var(--lvl-green-t);color:var(--lvl-green-d)}
.lvl-src.is-auto{background:var(--lvl-line-2);color:var(--lvl-mut)}
.lvl-num.is-crew{width:64px}
.lvl-inline-sel{display:inline-flex;align-items:center;gap:6px;margin-top:8px}
.lvl-inline-sel>span{font:700 9px/1 var(--lvl-font);letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-inline-sel select{height:26px;border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-xs);background:var(--lvl-card);
  color:var(--lvl-ink);font:500 11.5px/1 var(--lvl-font);padding:0 7px}
.lvl-wb-sub{margin-bottom:14px}
.lvl-wb-sub h5{display:flex;align-items:baseline;gap:9px;margin:0 0 7px;font:700 11px/1 var(--lvl-font);color:var(--lvl-ink)}
.lvl-wb-sub h5 em{font-style:normal;font-weight:500;font-size:10.5px;color:var(--lvl-mut-2)}
.lvl-wb-sub h5 b{margin-left:auto;font-size:11px}
.lvl-wb-scale{display:flex;justify-content:flex-end}

/* ══ WORKFLOW STEPPER ═════════════════════════════════════════════════════ */
.lvl-steps{display:flex;list-style:none;margin:0;padding:8px 18px;gap:6px;background:var(--lvl-card);
  border-bottom:1px solid var(--lvl-line);overflow-x:auto}
.lvl-step{display:flex;align-items:center;gap:9px;padding:6px 12px 6px 8px;border-radius:var(--lvl-r-s);
  border:1px solid transparent;cursor:pointer;flex:1 1 0;min-width:158px;transition:background .12s,border-color .12s}
.lvl-step:hover{background:var(--lvl-wash)}
.lvl-step-n{display:flex;align-items:center;justify-content:center;width:22px;height:22px;border-radius:50%;flex:0 0 auto;
  background:var(--lvl-line-2);color:var(--lvl-mut);font:800 11px/1 var(--lvl-mono)}
.lvl-step-t{display:flex;flex-direction:column;gap:1px;min-width:0}
.lvl-step-t b{font:700 11.5px/1.2 var(--lvl-font);color:var(--lvl-ink-2)}
.lvl-step-t em{font-style:normal;font-size:10px;line-height:1.35;color:var(--lvl-mut-2)}
.lvl-step.is-done .lvl-step-n{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-step.is-done .lvl-step-t b{color:var(--lvl-ink)}
.lvl-step.is-now{background:var(--lvl-green-t);border-color:rgba(36,180,126,.3)}
.lvl-step.is-now .lvl-step-n{background:var(--lvl-green);color:#fff}
.lvl-step.is-now .lvl-step-t b{color:var(--lvl-green-d)}
@media (max-width:900px){.lvl-step-t em{display:none}.lvl-step{min-width:0;flex:0 0 auto}}

/* ══ LOAD GANTT ═══════════════════════════════════════════════════════════ */
.lvl-lg-gantt .lvl-lg-l{font-size:10.5px;fill:var(--lvl-ink-2);cursor:pointer}
.lvl-lg-row.is-sel .lvl-lg-l{font-weight:700;fill:var(--lvl-ink)}
.lvl-lg-row:nth-child(even) .lvl-tl-zebra{fill:var(--lvl-wash)}
.lvl-lg-row.is-sel .lvl-tl-zebra{fill:var(--lvl-green-t)}
.lvl-lg-win{fill:var(--lvl-mut-2);opacity:.13}
.lvl-lg-bar{fill:var(--lvl-line-3);cursor:grab}
.lvl-lg-bar.is-ok{fill:var(--lvl-ok)}
.lvl-lg-bar.is-high{fill:var(--lvl-warn)}
.lvl-lg-bar.is-over{fill:var(--lvl-risk)}
.lvl-lg-bar.is-none{fill:var(--lvl-line-3)}
.lvl-lg-bar.is-crit{stroke:var(--lvl-ink);stroke-width:1;stroke-opacity:.55}
.lvl-lg-bar.is-moved{stroke:var(--lvl-after);stroke-width:1.4;stroke-opacity:1}
.lvl-lg-bar:hover{filter:brightness(1.12)}
.lvl-lg-hot{fill:var(--lvl-risk);opacity:.07;pointer-events:none}
.lvl-lg-hot.is-shape{fill:var(--lvl-warn);opacity:.07}
.lvl-lg-p{background:var(--lvl-line-3)}
.lvl-lg-p.is-over{background:var(--lvl-risk)}
.lvl-lg-p.is-high{background:var(--lvl-warn)}
.lvl-lg-p.is-ok{background:var(--lvl-ok)}
.lvl-lg-w{background:var(--lvl-mut-2);opacity:.3}

/* ══ CHANGE GANTT ═════════════════════════════════════════════════════════ */
.lvl-cg .lvl-cg-gb{fill:var(--lvl-wash)}
.lvl-cg .lvl-cg-gt{font:800 11px/1 var(--lvl-font);fill:var(--lvl-ink)}
.lvl-cg .lvl-cg-gs{font:600 10px/1 var(--lvl-mono);fill:var(--lvl-mut)}
.lvl-cg .lvl-cg-l{font-size:10.5px;fill:var(--lvl-ink-2);cursor:pointer}
.lvl-cg-row.is-sel .lvl-cg-l{font-weight:700;fill:var(--lvl-ink)}
.lvl-cg-row:hover .lvl-tl-zebra{fill:var(--lvl-wash)}
.lvl-cg-row.is-sel .lvl-tl-zebra{fill:var(--lvl-green-t)}
.lvl-cg-was{fill:none;stroke:var(--lvl-before);stroke-width:1;stroke-dasharray:3 2}
.lvl-cg-now{fill:var(--lvl-neutral);cursor:pointer}
.lvl-cg-row.is-later .lvl-cg-now{fill:var(--lvl-warn)}
.lvl-cg-row.is-earlier .lvl-cg-now{fill:var(--lvl-ok)}
.lvl-cg-row.is-logic .lvl-cg-now{fill:var(--lvl-info)}
.lvl-cg-now:hover{filter:brightness(1.12)}
.lvl-cg-arw{stroke:var(--lvl-mut-2);stroke-width:1;stroke-dasharray:2 2}
.lvl-cg-arh{fill:var(--lvl-mut-2)}
.lvl-cg-row.is-later .lvl-cg-arw,.lvl-cg-row.is-later .lvl-cg-arh{stroke:var(--lvl-warn);fill:var(--lvl-warn)}
.lvl-cg-row.is-earlier .lvl-cg-arw,.lvl-cg-row.is-earlier .lvl-cg-arh{stroke:var(--lvl-ok);fill:var(--lvl-ok)}
.lvl-cg-d{font:700 10px/1 var(--lvl-mono);fill:var(--lvl-mut)}
.lvl-cg-row.is-later .lvl-cg-d{fill:var(--lvl-warn)}
.lvl-cg-row.is-earlier .lvl-cg-d{fill:var(--lvl-ok)}
.lvl-cg-row.is-logic .lvl-cg-d{fill:var(--lvl-info)}
.lvl-grid.is-year{stroke:var(--lvl-line);stroke-width:1.2;opacity:.9}
.lvl-cg-mk{stroke:var(--lvl-before);stroke-width:1.4;stroke-dasharray:4 3}
.lvl-cg-mk.is-after{stroke:var(--lvl-after)}
.lvl-cg-mkt{font:800 9px/1 var(--lvl-mono);fill:var(--lvl-before)}
.lvl-cg-mkt.is-after{fill:var(--lvl-after)}
.lvl-cg-lg{width:14px;height:9px;border-radius:2px;background:var(--lvl-neutral)}
.lvl-cg-lg.is-was{background:transparent;border:1px dashed var(--lvl-before)}
.lvl-cg-lg.is-later{background:var(--lvl-warn)}
.lvl-cg-lg.is-earlier{background:var(--lvl-ok)}
.lvl-cg-lg.is-logic{background:var(--lvl-info)}
.lvl-cg-lg.is-mk{background:transparent;border-left:2px dashed var(--lvl-after);width:4px}

/* ══ SCENARIO LEDGER ══════════════════════════════════════════════════════ */
.lvl-lg-head{display:flex;flex-wrap:wrap;align-items:center;gap:8px;margin-bottom:12px}
.lvl-lg-head>span{margin-left:auto;font-size:11px;color:var(--lvl-mut)}
.lvl-led{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);overflow:hidden}
.lvl-led-g+.lvl-led-g{border-top:1px solid var(--lvl-line)}
.lvl-led-h{display:flex;align-items:center;gap:10px;padding:9px 12px;background:var(--lvl-wash);cursor:pointer;width:100%;
  border:0;text-align:left;font:inherit;color:inherit}
.lvl-led-h:hover{background:var(--lvl-line-2)}
.lvl-led-h i{width:4px;height:16px;border-radius:2px;flex:0 0 auto}
.lvl-led-h b{font:700 12px/1.3 var(--lvl-font)}
.lvl-led-h em{font-style:normal;font-size:11px;color:var(--lvl-mut)}
.lvl-led-h u{margin-left:auto;text-decoration:none;font:700 10px/1 var(--lvl-mono);color:var(--lvl-mut)}
.lvl-led-b{padding:0}
.lvl-led-b table{width:100%;border-collapse:collapse}
.lvl-led-r>td{padding:7px 12px;border-top:1px solid var(--lvl-line-2);font-size:11.5px;vertical-align:top}
.lvl-led-n b{display:block;font:600 12px/1.3 var(--lvl-font)}
.lvl-led-n em{display:block;font-style:normal;font-size:10.5px;color:var(--lvl-mut);margin-top:2px}
.lvl-led-dt{font-family:var(--lvl-mono);font-size:10.5px;white-space:nowrap}
.lvl-led-dt s{color:var(--lvl-mut-2);text-decoration:line-through}
.lvl-led-dt b{color:var(--lvl-ink)}
.lvl-led-sh{font:800 11px/1 var(--lvl-mono);white-space:nowrap}
.lvl-led-sh.is-later{color:var(--lvl-warn)}
.lvl-led-sh.is-earlier{color:var(--lvl-ok)}
.lvl-led-sh.is-logic{color:var(--lvl-info)}
.lvl-led-w{color:var(--lvl-mut);font-size:11px;line-height:1.5}
.lvl-led-f{font-family:var(--lvl-mono);font-size:10.5px;white-space:nowrap;text-align:right}
.lvl-led-f.is-tight{color:var(--lvl-risk)}

/* ══ RESOURCE CHANGE (scenario) ═══════════════════════════════════════════ */
.lvl-rc{display:grid;gap:14px}
.lvl-rc-r{border:1px solid var(--lvl-line);border-left-width:3px;border-radius:var(--lvl-r-s);padding:12px 14px;background:var(--lvl-card)}
.lvl-rc-r.is-good{border-left-color:var(--lvl-ok)}
.lvl-rc-r.is-bad{border-left-color:var(--lvl-risk)}
.lvl-rc-r.is-neutral{border-left-color:var(--lvl-line-3)}
.lvl-rc-r>header{display:flex;align-items:center;gap:9px;flex-wrap:wrap;margin-bottom:10px}
.lvl-rc-r>header i{width:10px;height:10px;border-radius:3px;flex:0 0 auto}
.lvl-rc-r>header b{font:700 13px/1.3 var(--lvl-font)}
.lvl-rc-r>header em{font-style:normal;font-size:11px;color:var(--lvl-mut)}
.lvl-rc-r>header .lvl-tag{margin-left:auto}
.lvl-rc-m{display:grid;grid-template-columns:repeat(auto-fit,minmax(140px,1fr));gap:10px;margin-bottom:12px}
.lvl-rc-m>div{border:1px solid var(--lvl-line-2);border-radius:var(--lvl-r-xs);padding:7px 9px}
.lvl-rc-m span{display:block;font:700 9px/1 var(--lvl-mono);letter-spacing:.1em;color:var(--lvl-mut-2);text-transform:uppercase}
.lvl-rc-m b{display:block;font:800 15px/1.2 var(--lvl-mono);margin-top:4px}
.lvl-rc-m em{display:block;font-style:normal;font-size:10.5px;color:var(--lvl-mut);margin-top:2px}

/* ══ SHARED SMALL BITS ════════════════════════════════════════════════════ */
.lvl-warn-l{display:flex;align-items:center;gap:8px;margin:12px 0 0;padding:9px 12px;border-radius:var(--lvl-r-xs);
  background:var(--lvl-warn-t);border:1px solid var(--lvl-warn);color:var(--lvl-ink-2);font-size:12px}
.lvl-sub{display:block;font-style:normal;font:500 10px/1.3 var(--lvl-mono);color:var(--lvl-mut-2);margin-top:2px}
.lvl-num-c{font-family:var(--lvl-mono);font-size:11px;text-align:center;white-space:nowrap}
.lvl-num-c s{color:var(--lvl-mut-2)}

/* ══════════════════════════════════════════════════════════════════════════
   THE WORKSPACE — one screen, four panes

   The page does not scroll. The programme scrolls down, time scrolls
   sideways, and the toolbar, the column headers and the inspector never
   move. Everything is sized from the viewport so a planner can work without
   losing the thing they were looking at.
   ══════════════════════════════════════════════════════════════════════════ */
/* the panel becomes a viewport-height column when the workspace is open, and
   `--lvl-vh` is measured after paint — the chrome above it is not a constant
   anyone can hard-code, and guessing it is what left the page scrolling */
.lvl.is-ws{display:block}
/* `.lvl-main` is a COLUMN flex container in the base stylesheet. Giving its
   children `flex:1` there made the workspace a flex ITEM whose MAIN size is
   its height — and flex-grow beats the height property, so the panel ignored
   even an `!important` height and grew to its content. It is a plain block
   here, and the workspace sizes itself. */
.lvl.is-ws .lvl-main{display:block;padding-bottom:0;min-height:0}
.lvl.is-ws .lvl-steps{display:none}
/* the workspace toolbar carries the view controls, so the page-level filter
   bar is duplication until it is asked for */
/* ON EVERY VIEW, NOT JUST THE WORKSPACE. Six selects a planner sets once a
   session sat permanently above the content on six of the eight views. */
.lvl .lvl-filters{display:none}
.lvl.is-wsf .lvl-filters{display:flex}
.lvl.is-ws .lvl-foot{display:none}
.lvl-tb-btn.is-on{background:var(--lvl-green-t);border-color:rgba(36,180,126,.3);color:var(--lvl-green-d)}
.lvl.is-ws .lvl-foot{padding-top:6px;padding-bottom:6px}
.lvl-ws{--ws-cols:clamp(198px,22vw,330px);--ws-insp:clamp(272px,24vw,340px);--ws-row:22px;
  display:flex;flex-direction:column;height:var(--lvl-vh,calc(100vh - var(--app-content-top) - 186px));min-height:360px;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r);background:var(--lvl-card);overflow:hidden}
.lvl-ws-grid{flex:1;display:grid;grid-template-columns:minmax(0,1fr) var(--ws-insp);min-height:0}
/* the inspector shut to a rail — 30px instead of 326, and the timeline takes
   every pixel it gives back */
.lvl-ws-grid:has(.lvl-ws-insp.is-rail){grid-template-columns:minmax(0,1fr) 30px}
.lvl-ws-insp.is-rail{padding:0;overflow:hidden;background:var(--lvl-wash);border-left:1px solid var(--lvl-line)}
.lvl-ws-insp-o{display:flex;flex-direction:column;align-items:center;gap:8px;width:100%;height:100%;padding:10px 0;
  border:0;background:none;cursor:pointer;color:var(--lvl-mut);font:600 10px/1 var(--lvl-font)}
.lvl-ws-insp-o:hover{background:var(--lvl-line-2);color:var(--lvl-ink)}
.lvl-ws-insp-o svg{transform:rotate(180deg);flex:0 0 auto}
.lvl-ws-insp-o span{writing-mode:vertical-rl;letter-spacing:.08em;text-transform:uppercase;font-size:9px}
.lvl-ws-insp-o em{font-style:normal;padding:1px 5px;border-radius:99px;background:var(--lvl-green);color:#fff;font:700 9px/1.5 var(--lvl-mono)}
.lvl-ws-insp{position:relative}
.lvl-ws-insp-x{position:absolute;top:6px;right:8px;z-index:4;width:20px;height:20px;border:0;border-radius:5px;
  background:none;cursor:pointer;color:var(--lvl-mut-2);display:flex;align-items:center;justify-content:center}
.lvl-ws-insp-x:hover{background:var(--lvl-line-2);color:var(--lvl-ink)}


/* EVERY PANE HAS A FIXED PLACE ON THE PAGE. The rows are declared here, once,
   so opening the crew heat or the week drill-in can never resize the Gantt
   under the planner's hands — a pane that moves its neighbours is a pane you
   cannot learn. Each pane scrolls INSIDE its own row instead. */
/* THE PROGRAMME GETS THE ROOM. The rows used to be `minmax(120px,1fr) 104px
   168px` — 272 fixed pixels for the two subordinate panes, which on a 1280x720
   laptop left the Gantt 125px and six rows of seventy-one. The subordinate
   panes are now SHARES with floors, so the split holds at every screen size,
   and each one can be shut when it is not being read. */
.lvl-ws-chart{position:relative;display:grid;
  grid-template-rows:minmax(112px,2.05fr) minmax(104px,1.5fr) minmax(78px,1.05fr);
  min-width:0;min-height:0;border-right:1px solid var(--lvl-line);overflow:hidden}
/* a shut pane is its own header strip and nothing more */
.lvl-ws-chart.hm-shut{grid-template-rows:minmax(112px,2.4fr) 24px minmax(78px,1fr)}
.lvl-ws-chart.hg-shut{grid-template-rows:minmax(112px,2.05fr) minmax(104px,1.5fr) 24px}
.lvl-ws-chart.hm-shut.hg-shut{grid-template-rows:minmax(112px,1fr) 24px 24px}
/* on a short screen the programme takes an even bigger share — 720px of
   laptop cannot carry all three panes at a comfortable height */
@media (max-height:820px){
  .lvl-ws-chart{grid-template-rows:minmax(96px,1.7fr) minmax(88px,1.35fr) minmax(80px,1.05fr)}
  .lvl-ws-chart.hm-shut{grid-template-rows:minmax(104px,2.3fr) 24px minmax(88px,1.15fr)}
}
.lvl-ws-blank{display:flex;flex-direction:column;align-items:center;justify-content:center;gap:6px;
  height:100%;color:var(--lvl-mut);text-align:center;padding:40px}
.lvl-ws-blank b{font:700 14px/1.4 var(--lvl-font);color:var(--lvl-ink)}
.lvl-ws-blank p{font-size:12px;max-width:340px;margin:0}

/* ── toolbar ─────────────────────────────────────────────────────────── */
/* ONE ROW, ALWAYS. Wrapping put 61px of controls above the programme the
   moment the pane was narrow — and a control that moves to a second line when
   you resize the window is a control you have to hunt for. It scrolls
   sideways instead, with the two chips a planner checks first pinned to the
   end so they cannot scroll away. */
/* ── IT WRAPS, IT DOES NOT HIDE ───────────────────────────────────────
   The row was nowrap + overflow-x:auto with the scrollbar suppressed, so a
   toolbar 2229px wide in a 1402px bar simply ENDED — 692px of controls off
   the right edge at 1440, 852px at 1280, with nothing on screen to suggest
   they existed. Regrouped it now fits one row on a laptop; where it does not
   it takes a second row, which is a toolbar you can see rather than one you
   have to know how to drag. Overflow is visible so the Layers menu can hang
   below the bar. */
.lvl-ws-tb{display:flex;align-items:center;gap:9px;flex-wrap:wrap;
  padding:5px 12px;border-bottom:1px solid var(--lvl-line);background:var(--lvl-card);
  position:relative;z-index:12}
.lvl-ws-tb>*{flex:0 0 auto}
.lvl-tbg{display:flex;align-items:center;gap:7px}
.lvl-tbg.is-tog{gap:4px}
.lvl-tbg.is-end{margin-left:auto;gap:8px}
.lvl-tbg>label{font:600 10.5px/1 var(--lvl-font);color:var(--lvl-mut)}
.lvl-tb-btn{display:inline-flex;align-items:center;gap:6px;height:30px;padding:0 11px;border-radius:var(--lvl-r-s);
  border:1px solid var(--lvl-line-3);background:var(--lvl-card);color:var(--lvl-ink-2);
  font:600 12px/1 var(--lvl-font);cursor:pointer}
.lvl-tb-btn:hover{background:var(--lvl-wash)}
.lvl-tb-btn em{font-style:normal;font:800 9px/1 var(--lvl-mono);background:var(--lvl-green-t);color:var(--lvl-green-d);
  padding:2px 5px;border-radius:9px}
.lvl-ws-tb .lvl-sel-s{height:28px;min-width:104px;max-width:180px}
.lvl-ws-tb .lvl-tb-btn{height:28px;padding:0 10px}
.lvl-ws-tb .lvl-seg-b{height:28px;padding:0 10px}
/* ── TWO MENUS, ONE MECHANISM ─────────────────────────────────────────
   View holds how the programme is being looked at — which trade, how wide a
   column, the date it is measured against. Show holds what is drawn on top of
   the bars. Both are decisions a planner makes a few times a session; on the
   bar the four Show switches alone cost 450px of a 1402px row to say so. */
.lvl-tbg.is-menu{position:relative}
.lvl-tb-btn.is-menu.is-open{background:var(--lvl-wash);border-color:var(--lvl-line-3)}
.lvl-tb-car{width:0;height:0;border:3.5px solid transparent;border-top-color:var(--lvl-mut-2);
  margin-left:1px;transform:translateY(2px)}
.lvl-tb-btn.is-menu.is-open .lvl-tb-car{transform:translateY(-1px) rotate(180deg)}
.lvl-tb-pop{position:absolute;top:calc(100% + 6px);left:0;z-index:40;min-width:232px;
  padding:5px;border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-s);background:var(--lvl-card);
  box-shadow:0 12px 30px -12px rgba(15,30,45,.34);display:flex;flex-direction:column;gap:1px}
.lvl-tb-opt{display:flex;align-items:flex-start;gap:9px;padding:7px 9px;border:0;border-radius:var(--lvl-r-xs);
  background:none;cursor:pointer;text-align:left;color:var(--lvl-ink-2);font:600 11.5px/1.3 var(--lvl-font)}
.lvl-tb-opt:hover{background:var(--lvl-wash)}
.lvl-tb-opt>i{flex:0 0 auto;width:22px;height:13px;border-radius:8px;background:var(--lvl-line-3);
  position:relative;margin-top:1px;transition:background .14s}
.lvl-tb-opt>i::after{content:"";position:absolute;top:1.5px;left:1.5px;width:10px;height:10px;border-radius:50%;
  background:#FFF;box-shadow:0 1px 2px rgba(15,30,45,.3);transition:transform .14s}
.lvl-tb-opt.is-on{color:var(--lvl-ink)}
.lvl-tb-opt.is-on>i{background:var(--lvl-green)}
.lvl-tb-opt.is-on>i::after{transform:translateX(9px)}
.lvl-tb-opt em{display:block;font-style:normal;font:400 10px/1.35 var(--lvl-font);color:var(--lvl-mut);margin-top:2px}
/* the View menu holds controls rather than switches, so each one gets its
   name and the one line saying what it changes */
.lvl-tb-pop.is-wide{min-width:288px;padding:9px;gap:0}
.lvl-tb-fld{display:block;padding:7px 3px}
.lvl-tb-fld+.lvl-tb-fld{border-top:1px solid var(--lvl-line-2)}
.lvl-tb-fld>label{display:block;font:700 11px/1.3 var(--lvl-font);color:var(--lvl-ink)}
.lvl-tb-fld>em{display:block;font-style:normal;font:400 10px/1.4 var(--lvl-font);color:var(--lvl-mut);margin:2px 0 6px}
.lvl-tb-fld .lvl-sel-s{width:100%;max-width:none}
.lvl-tb-fldr{display:flex;align-items:center;gap:4px}
.lvl-tb-fldr .lvl-sel-s{flex:1}
.lvl-tb-more{display:block;width:100%;margin-top:7px;padding:8px 9px;border:0;border-top:1px solid var(--lvl-line-2);
  border-radius:0 0 var(--lvl-r-xs) var(--lvl-r-xs);background:none;cursor:pointer;text-align:left;
  font:700 11px/1.3 var(--lvl-font);color:var(--lvl-green-d)}
.lvl-tb-more:hover{background:var(--lvl-green-t)}
.lvl-tb-more span{display:block;font-weight:400;font-size:10px;line-height:1.4;color:var(--lvl-mut);margin-top:2px}
/* a filter narrows the programme silently, so the bar says which trade */
.lvl-tb-stat.is-note{background:var(--lvl-info-t);color:var(--lvl-info);font-weight:700}
/* ── THREE LEVERS, ALL OF THEM ON SCREEN ──────────────────────────────
   The guide costs move, spread and shorten on every bar and reported only
   the winner, so "spread it" — which is the answer on a peak, and the one
   lever that spends no float — lost by a point and vanished. */
.lvl-lv{display:flex;flex-direction:column;gap:4px}
.lvl-lv-b{display:flex;align-items:center;gap:9px;width:100%;padding:8px 10px;cursor:pointer;text-align:left;
  border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-s);background:var(--lvl-card);color:inherit;font:inherit}
.lvl-lv-b:hover{border-color:var(--lvl-green);background:var(--lvl-green-t)}
.lvl-lv-b.is-best{border-color:rgba(36,180,126,.42);box-shadow:inset 2.5px 0 0 var(--lvl-green)}
.lvl-lv-k{flex:0 0 16px;font-style:normal;font:800 13px/1 var(--lvl-mono);text-align:center;color:var(--lvl-info)}
.lvl-lv-b.is-best .lvl-lv-k{color:var(--lvl-green-d)}
.lvl-lv-t{flex:1;min-width:0}
.lvl-lv-t b{display:block;font:700 11.5px/1.3 var(--lvl-font)}
.lvl-lv-t b em{font-style:normal;font:800 8px/1 var(--lvl-mono);letter-spacing:.08em;text-transform:uppercase;
  color:var(--lvl-green-d);background:var(--lvl-green-t);padding:2px 4px;border-radius:3px;margin-left:6px;vertical-align:1px}
.lvl-lv-t>em{display:block;font-style:normal;font:400 10px/1.4 var(--lvl-mono);color:var(--lvl-mut);margin-top:2px}
.lvl-lv-g{flex:0 0 auto;text-decoration:none;font:800 11px/1 var(--lvl-mono);color:var(--lvl-ok)}
.lvl-lv-c{flex:0 0 auto;font:700 8.5px/1 var(--lvl-mono);letter-spacing:.05em;text-transform:uppercase;
  color:var(--lvl-warn);background:var(--lvl-warn-t);padding:3px 5px;border-radius:3px}
.lvl-zoom{width:104px;accent-color:var(--lvl-green)}
.lvl-tog{display:inline-flex;align-items:center;gap:6px;height:26px;padding:0 9px 0 4px;border-radius:14px;
  border:1px solid var(--lvl-line-3);background:var(--lvl-card);color:var(--lvl-mut);
  font:600 11px/1 var(--lvl-font);cursor:pointer}
.lvl-tog i{width:22px;height:13px;border-radius:8px;background:var(--lvl-line-3);position:relative;transition:background .14s}
.lvl-tog i::after{content:"";position:absolute;top:1.5px;left:1.5px;width:10px;height:10px;border-radius:50%;
  background:#fff;transition:transform .14s}
.lvl-tog.is-on{color:var(--lvl-ink);border-color:rgba(36,180,126,.32)}
.lvl-tog.is-on i{background:var(--lvl-green)}
.lvl-tog.is-on i::after{transform:translateX(9px)}
.lvl-tb-stat{font:600 11px/1 var(--lvl-font);color:var(--lvl-mut);padding:5px 9px;border-radius:14px;background:var(--lvl-line-2)}
.lvl-tb-stat b{font-family:var(--lvl-mono);font-weight:800}
.lvl-tb-stat.is-bad{background:var(--lvl-risk-t);color:var(--lvl-risk)}
.lvl-tb-stat.is-good{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-tb-stat.is-ok{background:var(--lvl-ok-t);color:var(--lvl-ok)}

/* ── gantt: fixed columns + scrolling timeline ───────────────────────── */
.lvl-gt{display:grid;grid-template-columns:var(--ws-cols) minmax(0,1fr);min-height:0;overflow:hidden;border-bottom:1px solid var(--lvl-line)}
.lvl-gt-cols{display:flex;flex-direction:column;min-height:0;border-right:1px solid var(--lvl-line);background:var(--lvl-card)}
.lvl-gt-colh{display:grid;grid-template-columns:minmax(0,1fr) 32px 46px;align-items:center;gap:4px;
  height:54px;padding:0 8px;border-bottom:1px solid var(--lvl-line);background:var(--lvl-wash);
  font:700 9px/1 var(--lvl-mono);letter-spacing:.09em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-gt-colh .c-num,.lvl-gt-colh .c-float{text-align:right}
.lvl-gt-colb{flex:1;overflow:hidden auto;scrollbar-width:none}
.lvl-gt-colb::-webkit-scrollbar{display:none}
.lvl-gtr{display:grid;grid-template-columns:minmax(0,1fr) 32px 46px;align-items:center;gap:4px;
  height:var(--ws-row);padding:0 8px;font-size:10.5px;color:var(--lvl-ink-2);cursor:pointer;
  border-bottom:1px solid transparent}
.lvl-gtr:hover{background:var(--lvl-wash)}
.lvl-gtr .c-name{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-gtr .c-num{text-align:right;font:600 9.5px/1 var(--lvl-mono);color:var(--lvl-mut)}
.lvl-gtr .c-num.is-over{color:var(--lvl-risk);font-weight:800}
.lvl-gtr .c-float{display:flex;align-items:center;justify-content:flex-end;gap:4px;
  font:600 9.5px/1 var(--lvl-mono);color:var(--lvl-mut)}
.lvl-gtr .c-float.is-tight{color:var(--lvl-warn)}
.lvl-gtr .c-float.is-none{color:var(--lvl-risk);font-weight:800}
.lvl-gtr .c-float svg{width:10px;height:10px;opacity:.6}
.lvl-gtr.is-wbs{font:700 10.5px/1 var(--lvl-font)}
.lvl-gtr.is-wbs .c-float{color:var(--lvl-mut-2);font-weight:600}
.lvl-gtr.is-wbs:hover{filter:brightness(1.15)}
.lvl-gt-tw{font-style:normal;font-size:8px;color:var(--lvl-mut-2);width:11px;flex:0 0 11px}
.lvl-gt-dot{display:inline-block;width:5px;height:5px;border-radius:50%;margin-right:5px;vertical-align:1px}
.lvl-gt-dot.is-over{background:var(--lvl-risk)}
.lvl-gtr.is-wbs .c-name b{font-family:var(--lvl-mono);font-size:9.5px;opacity:.8;margin-right:5px;font-weight:700}
.lvl-gtr.is-wbs.is-l0 .c-name{font-size:11px}
.lvl-gtr.is-wbs .c-name{display:flex;align-items:center;gap:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-gtr.is-sel{background:var(--lvl-green-t);font-weight:700;color:var(--lvl-ink)}
.lvl-gtr.is-rel{background:var(--lvl-wash)}
.lvl-gtr.is-lit{background:var(--lvl-green-t)}
.lvl-gtr.is-dim{opacity:.35}
/* ── THE SIGNED GAP RIBBON ────────────────────────────────────────────
   Sits under the time header, on the Gantt's own axis, so the column above a
   bar is that bar's week. Warm and up = above the ideal (move work out);
   cool and down = below it (room to fill). */
.lvl-gt-gaph{display:flex;align-items:center;gap:10px;height:34px;padding:0 8px;
  border-bottom:1px solid var(--lvl-line);background:var(--lvl-wash);
  font:600 8.5px/1 var(--lvl-mono);letter-spacing:.05em;text-transform:uppercase;color:var(--lvl-mut-2);
  overflow:hidden;white-space:nowrap}
.lvl-gt-gaph b{font-weight:800;color:var(--lvl-mut)}
.lvl-gt-gaph span{display:flex;align-items:center;gap:3px;text-transform:none;letter-spacing:0;font-size:8.5px}
.lvl-gt-gaph i{width:7px;height:7px;border-radius:1.5px;flex:0 0 7px}
.lvl-gt-gaph i.is-over{background:var(--lvl-risk)}
.lvl-gt-gaph i.is-under{background:var(--lvl-info)}
.lvl-ws-gap{border-bottom:1px solid var(--lvl-line);background:var(--lvl-wash)}
.lvl-gap-mid{stroke:var(--lvl-line);stroke-width:1}
.lvl-gap-c{cursor:pointer}
.lvl-gap-c.is-over{fill:var(--lvl-risk);fill-opacity:.72}
.lvl-gap-c.is-under{fill:var(--lvl-info);fill-opacity:.62}
.lvl-gap-c.is-flat{fill:var(--lvl-mut-2);fill-opacity:.5}
.lvl-gap-c:hover{fill-opacity:1}
.lvl-gap-none{fill:var(--lvl-mut);font:600 10px/1 var(--lvl-font)}

/* ── WHAT THIS BAR SHOULD DO ──────────────────────────────────────────
   A hollow target where the curve wants the activity, an arrow from here to
   there, and the score it buys. The dash MARCHES toward the target: on a
   programme of several hundred rows a static hairline is not findable, and
   the one thing this mark has to be is findable. Motion is the only channel
   left — colour is carrying pressure and fill is carrying trade. */
/* THE TARGET FINISH. Everything to the right of it is time the programme does
   not have — a different statement from "later than planned", so the zone is
   shaded rather than the edge merely drawn. A hairline at week 84 is not
   something anybody notices while dragging a bar at week 40. */
.lvl-ws-limit{stroke:var(--lvl-risk);stroke-width:1.6;stroke-dasharray:5 3;opacity:.9}
.lvl-ws-past{fill:var(--lvl-risk);fill-opacity:.055;pointer-events:none}
.lvl-ws-limb{fill:var(--lvl-risk)}
.lvl-ws-limt{fill:#fff;font:800 8.5px/1 var(--lvl-mono);letter-spacing:.06em}
.lvl-tb-date{font:600 10.5px/1 var(--lvl-mono);padding:4px 6px}
.lvl-tb-x{border:0;background:none;cursor:pointer;color:var(--lvl-mut);font-size:11px;padding:2px 4px;border-radius:4px}
.lvl-tb-x:hover{background:var(--lvl-line-2);color:var(--lvl-risk)}

.lvl-ws-guide{cursor:pointer}
/* ── A SUGGESTION SHOULD READ AS ONE OBJECT ──────────────────────────
   The lane, the arrow and the label were three marks of three weights that
   happened to be near each other. Now the connector is a quiet hairline that
   only carries DISTANCE, and the weight is all in the target — the thing the
   planner is actually being asked to look at. The march is slower and
   shallower too: at 1.1s it read as an alarm on a screen with forty of them. */
.lvl-ws-gline{stroke:var(--lvl-info);stroke-width:1;stroke-dasharray:3 3;opacity:.55;
  animation:lvlGuideMarch 2.2s linear infinite}
@keyframes lvlGuideMarch{from{stroke-dashoffset:6}to{stroke-dashoffset:0}}
.lvl-ws-ghead{fill:var(--lvl-info);opacity:.75}
/* the target is the statement: a solid, rounded, slightly inset bar with a
   little lift under it, so on a dense programme the eye finds the SET of
   suggestions before it reads any one of them */
.lvl-ws-gtarget{fill:var(--lvl-info);fill-opacity:1;stroke:none;
  filter:drop-shadow(0 1px 0 rgba(11,18,32,.18))}
.lvl-ws-gt{fill:var(--lvl-info);font:800 8.5px/1 var(--lvl-mono);opacity:.9}
.lvl-ws-ggain{fill:var(--lvl-ok);font-weight:800}
.lvl-ws-guide:hover .lvl-ws-gt{opacity:1}
.lvl-ws-guide:hover .lvl-ws-gline{opacity:.9}
.lvl-ws-guide:hover .lvl-ws-gtarget{fill-opacity:1}
.lvl-ws-guide:hover .lvl-ws-gtarget{filter:drop-shadow(0 1px 3px rgba(74,119,174,.5))}
/* spending float, and spending the finish date, are different asks */
.lvl-ws-guide.is-float .lvl-ws-gline,.lvl-ws-guide.is-float .lvl-ws-gtarget{stroke:var(--lvl-warn)}
.lvl-ws-guide.is-float .lvl-ws-ghead{fill:var(--lvl-warn)}
.lvl-ws-guide.is-float .lvl-ws-gt{fill:var(--lvl-warn)}
.lvl-ws-guide.is-float .lvl-ws-gtarget{fill:var(--lvl-warn)}
.lvl-ws-guide.is-costly .lvl-ws-gline,.lvl-ws-guide.is-costly .lvl-ws-gtarget{stroke:var(--lvl-risk)}
.lvl-ws-guide.is-costly .lvl-ws-ghead{fill:var(--lvl-risk)}
.lvl-ws-guide.is-costly .lvl-ws-gt{fill:var(--lvl-risk)}
.lvl-ws-guide.is-costly .lvl-ws-gtarget{fill:var(--lvl-risk)}
/* BLOCKED is not an instruction, it is an explanation: above the curve with
   no float, so no drag fixes it and only the logic can. It does not march —
   there is nothing to march towards. */
/* RE-CREWING IS NOT RESCHEDULING. A duration suggestion holds the start and
   moves the finish, so its target is drawn as a bracket round the new span in
   a colour of its own — telling a planner to move work when you meant "put
   fewer people on it for longer" is the wrong instruction entirely. */
.lvl-ws-guide.is-dur .lvl-ws-gline,.lvl-ws-guide.is-dur .lvl-ws-gtarget{stroke:var(--lvl-s1,#6E8BC0)}
.lvl-ws-guide.is-dur .lvl-ws-ghead{fill:var(--lvl-s1,#6E8BC0)}
.lvl-ws-guide.is-dur .lvl-ws-gt{fill:var(--lvl-s1,#6E8BC0)}
.lvl-ws-guide.is-dur .lvl-ws-gtarget{fill:var(--lvl-s1,#6E8BC0);fill-opacity:.95}
.lvl-ws-gblock{fill:none;stroke:var(--lvl-risk);stroke-width:1.4;stroke-dasharray:2 2;opacity:.75}
@media (prefers-reduced-motion:reduce){
  .lvl-ws-gline{animation:none;stroke-dasharray:none}
}

/* ── THE CURVE READOUT ───────────────────────────────────────────────
   The score every mark in curve mode serves, on the same screen as the marks.
   It used to live on another tab, which meant moving a bar and then going to
   look for whether it had helped. */
.lvl-ws-key.is-curve{gap:14px}
.lvl-cv-score{display:flex;align-items:baseline;gap:3px}
.lvl-cv-score b{font:800 15px/1 var(--lvl-mono)}
.lvl-cv-score i{font-style:normal;font-size:9px;color:var(--lvl-mut-2)}
.lvl-cv-score em{font-style:normal;font-weight:700;font-size:9.5px;margin-left:4px;color:var(--lvl-mut)}
.lvl-cv-score.is-good b{color:var(--lvl-ok)}
.lvl-cv-score.is-mid b{color:var(--lvl-warn)}
.lvl-cv-score.is-bad b{color:var(--lvl-risk)}
.lvl-cv-f{color:var(--lvl-mut);white-space:nowrap}
.lvl-cv-f u{text-decoration:none;font:800 10.5px/1 var(--lvl-mono);color:var(--lvl-ink-2);margin-right:3px}
.lvl-cv-i{font-style:normal;font-size:8.5px;color:var(--lvl-mut-2);margin-left:4px}
.lvl-cv-next{color:var(--lvl-ink-2);white-space:nowrap}
.lvl-cv-next b{color:var(--lvl-info);font-weight:800}
.lvl-cv-blk{color:var(--lvl-risk);white-space:nowrap}
.lvl-cv-blk b{font-weight:800}
.lvl-ws-key i.k-guide{width:14px;height:0;border-top:1.6px dashed var(--lvl-info);border-radius:0;background:none}

/* ── THE FIT REVIEW LIST ──────────────────────────────────────────────── */
/* the before curve sits behind the after one, quieter and dashed */
.lvl-scurve.is-before{stroke:var(--lvl-before);stroke-width:1.8;stroke-dasharray:5 4;opacity:.85}
.lvl-fit-tabs{display:flex;align-items:center;gap:6px;padding:8px 12px 0}
.lvl-fit-tab{border:1px solid var(--lvl-line);background:var(--lvl-card);border-radius:6px;cursor:pointer;
  padding:4px 10px;font:700 10px/1 var(--lvl-font);color:var(--lvl-mut)}
.lvl-fit-tab.is-on{background:var(--lvl-green-t);border-color:var(--lvl-green);color:var(--lvl-ink)}
.lvl-fit-legend{margin-left:auto;display:flex;align-items:center;gap:4px;font-size:9.5px;color:var(--lvl-mut)}
.lvl-fit-legend i{width:12px;height:0;border-top:2px solid var(--lvl-after);margin-left:6px}
.lvl-fit-legend i.k-before{border-top:2px dashed var(--lvl-before)}
.lvl-fit-legend i.k-ideal{border-top:2px dashed var(--lvl-mut-2)}
/* THE BEFORE AND AFTER IS THE DECISION, so it gets the room. At 18px rows in
   a third of a panel it was a thumbnail of a chart rather than a chart. */
.lvl-rp-g.is-gantt{min-height:170px;overflow:auto;flex:1 1 auto}
/* the before/after uses the workspace Gantt itself: activity names pinned on
   the left, the same bars and shadows on the right */
.lvl-fit-ba{display:grid;grid-template-columns:140px max-content;background:var(--lvl-card)}
.lvl-fit-ba-l{border-right:1px solid var(--lvl-line)}
.lvl-fit-ba-r{height:22px;display:flex;align-items:center;padding:0 8px;font-size:10px;
  color:var(--lvl-ink-2);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-fit-ba-t{min-width:0}
/* IT IS DRAWN AT ITS OWN SIZE AND THE COLUMN SCROLLS. Scaling the SVG to
   its column lined the labels up at exactly one width: the HTML label
   gutter beside it does not scale, so a chart stretched 1.8x drew a 38px
   header 68px tall against a gutter still padded 38. Same factor or no
   factor — this is no factor. */
.lvl-fit-ba{overflow-x:auto}
.lvl-fit-ba-t svg{display:block}
.lvl-fit-ba-more{margin:6px 12px 8px;font-size:10px;color:var(--lvl-mut)}
.lvl-fit-bahead{display:flex;align-items:center;gap:8px;padding:9px 12px 5px;
  font:700 11px/1 var(--lvl-font);color:var(--lvl-ink)}
.lvl-fit-balg{margin-left:auto;display:flex;align-items:center;gap:5px;font:600 9.5px/1 var(--lvl-font);color:var(--lvl-mut)}
.lvl-fit-balg i{width:14px;height:7px;border-radius:2px;margin-left:7px}
.lvl-fit-balg i.k-was{background:var(--lvl-before);opacity:.5}
.lvl-fit-balg i.k-now{background:var(--lvl-after)}
/* the list is secondary to the picture now */
/* the list of dates is secondary to the picture above it */
.lvl-fit-l{flex:0 1 auto;min-height:0;max-height:20%;overflow:auto;border-bottom:1px solid var(--lvl-line)}
.lvl-fit-r{display:flex;align-items:center;gap:9px;padding:7px 14px;cursor:pointer;
  border-bottom:1px solid var(--lvl-line-2)}
.lvl-fit-r:hover{background:var(--lvl-wash)}
.lvl-fit-r.is-off{opacity:.42}

/* a re-phase reads as one decision, with its bars underneath it ---------- */
.lvl-fit-r.is-cohort{background:var(--lvl-wash);border-bottom:0;
  box-shadow:inset 3px 0 0 var(--lvl-info)}
.lvl-fit-r.is-cohort .lvl-fit-n>b{font-weight:700}
.lvl-fit-more{display:block;width:100%;text-align:left;padding:4px 14px 6px 46px;
  border:0;border-bottom:1px solid var(--lvl-line-2);background:var(--lvl-wash);
  font:600 9.5px/1.3 var(--lvl-font);color:var(--lvl-mut);cursor:pointer}
.lvl-fit-more:hover{color:var(--lvl-ink)}
.lvl-fit-sub{border-bottom:1px solid var(--lvl-line-2);background:var(--lvl-card);
  max-height:190px;overflow-y:auto;overscroll-behavior:contain}
.lvl-fit-subr{flex:0 0 auto;display:grid;
  grid-template-columns:minmax(0,1fr) minmax(0,auto) 48px;gap:8px;align-items:center;
  padding:4px 14px 4px 46px}
.lvl-fit-subr>b{font:500 10px/1.3 var(--lvl-font);color:var(--lvl-ink);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-fit-subr>em{font:500 9.5px/1.3 var(--lvl-font);color:var(--lvl-mut-2);font-style:normal;
  white-space:nowrap}
.lvl-fit-subr>u{font:700 10px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-mut);
  text-align:right;text-decoration:none}
.lvl-fit-x{font-style:normal;font-size:13px;color:var(--lvl-green);flex:0 0 auto}
.lvl-fit-k{font-style:normal;font:800 12px/1 var(--lvl-mono);flex:0 0 14px;text-align:center;color:var(--lvl-info)}
.lvl-fit-r.is-stretch .lvl-fit-k,.lvl-fit-r.is-compress .lvl-fit-k{color:var(--lvl-s1,#6E8BC0)}
/* THE RESULT, BEFORE THE WORKING. The panel opens with the curve the plan
   produces against the one it was aiming at, because a list of twenty date
   changes is not an answer to "make the deployment look like the curve". */
/* ── THE PANEL'S BUDGET ───────────────────────────────────────────────
   Four things compete for one fixed-height panel: the curve it produces, the
   numbers, the before/after, and the list of dates. The before/after is the
   DECISION, so it gets the flexible space and the other three are capped —
   it was being pushed below the fold by a chart and a table nobody has to
   read to answer "do I accept this". */
.lvl-rp-g.is-curve{max-height:none;flex:0 0 auto;padding:4px 8px 0}
.lvl-rp-g.is-curve .lvl-chart{border:0;overflow:hidden}
/* ── ONE SCROLLING COLUMN, NOT SIX FIGHTING OVER 516 PIXELS ───────────
   Measured, in a 1440x900 viewport: header, tabs, the S-curve, four stat
   tiles, the before/after Gantt, forty-two change lines, the "what is still
   off" notes and the buttons were all flex children of ONE fixed-height
   panel. The before/after collapsed to its 170px min-height while the chart
   inside it was 434px tall — a Gantt seen through a letterbox — the S-curve
   was squeezed from 150px to 83, and .lvl-fit-l, the whole list of changes,
   computed to LITERALLY ZERO HEIGHT. That is the "before and after is the
   same / I cannot see anything" report, and no amount of tuning the chart
   fixes it: the layout itself was the bug.

   The header and the buttons pin. Everything between them is one column that
   scrolls, and each section draws at its natural height. */
.lvl-rp.is-fit>.lvl-rp-b{flex:1 1 auto;min-height:0;overflow:auto;display:block}
.lvl-rp.is-fit .lvl-rp-g.is-gantt,
.lvl-rp.is-fit .lvl-rp-g.is-curve,
.lvl-rp.is-fit .lvl-fit-l,
.lvl-rp.is-fit .lvl-fit-rest{flex:none;max-height:none;min-height:0;overflow:visible}
.lvl-rp.is-fit .lvl-rp-g.is-curve .lvl-chart{overflow:visible}
/* ── COLLAPSED, AND THE PROPOSAL IS STILL LIVE ────────────────────────
   The panel is anchored over the right-hand half of the timeline, which on a
   front-loaded programme is exactly where the changes are. Collapsed it is a
   strip along the bottom and the whole Gantt is the before/after. */
.lvl-rp.is-fit.is-min{top:auto;bottom:0;width:min(520px,46%);height:auto;
  border-top:2px solid var(--lvl-green);border-radius:var(--lvl-r-s) 0 0 0;
  box-shadow:-10px -6px 26px -16px rgba(15,30,45,.34)}
.lvl-fit-min{display:flex;align-items:center;gap:8px;padding:9px 12px}
.lvl-fit-min-t{flex:1;min-width:0}
.lvl-fit-min-t b{display:block;font:700 11.5px/1.3 var(--lvl-font)}
.lvl-fit-min-t em{display:block;font-style:normal;font-size:10px;line-height:1.45;color:var(--lvl-mut);margin-top:1px}
.lvl-fit-rest .lvl-note.is-bad{color:var(--lvl-risk)}
.lvl-fit-r.is-off .lvl-fit-x{color:var(--lvl-mut-2)}
.lvl-fit-n{flex:1;min-width:0}
.lvl-fit-n b{display:block;font:700 11.5px/1.3 var(--lvl-font);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-fit-n em{display:block;font-style:normal;font-size:10px;color:var(--lvl-mut);margin-top:1px}
.lvl-fit-s{font:800 11px/1 var(--lvl-mono);color:var(--lvl-ink-2);flex:0 0 auto}
.lvl-fit-g{font:800 11px/1 var(--lvl-mono);color:var(--lvl-ok);flex:0 0 auto;min-width:32px;text-align:right}
.lvl-fit-rest{flex:0 0 auto;padding:4px 14px 10px;border-bottom:1px solid var(--lvl-line);
  max-height:20%;overflow:auto}
.lvl-fit-rest .lvl-note{margin:6px 0 0}
.lvl-fit-rej{margin-top:8px;font-size:10.5px}
.lvl-fit-rej summary{cursor:pointer;color:var(--lvl-mut);font-weight:700}
.lvl-fit-rej ul{margin:6px 0 0;padding-left:16px;color:var(--lvl-mut)}
.lvl-fit-rej li{margin:3px 0}

.lvl-gt-time{overflow:auto;min-height:0;position:relative}
.lvl-gt-headw{position:sticky;top:0;z-index:3;background:var(--lvl-card);
  box-shadow:0 1px 0 var(--lvl-line)}
.lvl-gt-bodyw{position:relative}
.lvl-gt-time svg{display:block}

/* header bands */
.lvl-hb{fill:var(--lvl-card);stroke:var(--lvl-line-2);stroke-width:1}
.lvl-hb.is-year{fill:var(--lvl-wash)}
.lvl-hb.is-month{fill:var(--lvl-wash)}
.lvl-ht{font:600 9px/1 var(--lvl-mono);fill:var(--lvl-ink)}
.lvl-ht.is-year{font-weight:800;font-size:10px;fill:var(--lvl-ink)}
.lvl-ht.is-week{fill:var(--lvl-mut-2);font-size:8.5px}
.lvl-ht.is-month{fill:var(--lvl-ink);font-weight:700}
.lvl-ws-nowl{stroke:var(--lvl-ink);stroke-width:1;stroke-dasharray:3 2}
.lvl-ws-nowb{fill:var(--lvl-ink)}
.lvl-ws-nowt{font:700 8px/1 var(--lvl-mono);fill:#fff}

/* body */
.lvl-ws-grid2{}
.lvl-ws-z{fill:transparent}
.lvl-ws-r:nth-child(even) .lvl-ws-z{fill:rgba(20,32,42,.014)}
.lvl-ws-r.is-sel .lvl-ws-z{fill:var(--lvl-green-t)}
.lvl-ws-r.is-lit .lvl-ws-z{fill:var(--lvl-green-t)}
.lvl-ws-r.is-dim{opacity:.3}
.lvl-ws-grid{stroke:var(--lvl-line-2);stroke-width:1}
.lvl-ws-grid.is-group{stroke:var(--lvl-line-3)}
.lvl-ws-hgrid{stroke:var(--lvl-line-2);stroke-width:1}
/* the WBS roll-up reads as a BRACKET over what it contains, not as another
   task bar — tapered ends are the convention every scheduler already knows */
.lvl-ws-sum{fill:var(--lvl-ink-2);opacity:.62}
.lvl-ws-r.is-wbs:hover .lvl-ws-sum{opacity:.85}
/* BAR COLOUR IS PRESSURE — whether this activity's own crews are over their
   limit while it runs. That is the diagnosis the chart exists to carry, and it
   owns the fill. The proposed position is a hollow outline in the proposed
   hue, so identity and magnitude never compete for the same pixels. */
/* A BAR IS AN OBJECT, NOT A BLOCK OF COLOUR. A flat fill with no boundary
   dissolves into the heat wash behind it and into its neighbours above and
   below; the eye needs an edge to find the shape. A 1px edge in the fill's own
   hue, darkened, gives it one without introducing a second colour. */
.lvl-ws-bar{cursor:grab;stroke:rgba(11,18,32,.34);stroke-width:1;paint-order:fill stroke}
.lvl-ws-bar.is-actual{fill:var(--lvl-ok)}
.lvl-ws-bar.is-actual.is-high{fill:var(--lvl-warn)}
.lvl-ws-bar.is-actual.is-over{fill:var(--lvl-risk)}
.lvl-ws-bar.is-actual.is-none{fill:var(--lvl-mut-2);fill-opacity:.55}
/* COOL BARS ON A WARM FIELD. With the heat map on, the field carries crew
   pressure per period — so the bar carrying it too in the same warm hues gave
   the two marks no edge between them and they read as one shape. Slate
   separates from every step of the warm ramp, and the critical outline and
   the milestone diamond still read on top of it. */
.lvl-ws-bar.is-actual.is-cool{fill:#55637E;fill-opacity:1}
.lvl-ws-bar.is-actual.is-cool.is-over{fill:#3E4A63}
.lvl-ws-bar.is-actual.is-cool.is-none{fill:#8A93A6;fill-opacity:.8}
/* trade fills come from `style`, so no class may override them */
.lvl-ws-bar.is-trade{fill:inherit}
.lvl-ws-seg{cursor:grab}
.lvl-ws-seg.is-crit .lvl-ws-bar{stroke:var(--lvl-ink);stroke-width:1;stroke-opacity:.55}
.lvl-ws-seg:hover .lvl-ws-bar{filter:brightness(1.1)}
.lvl-ws-brk{fill:var(--lvl-risk)}
.lvl-ws-grip{fill:transparent;cursor:ew-resize}
.lvl-ws-grip:hover{fill:var(--lvl-ink);fill-opacity:.28}
/* MOVED: the bar keeps whatever fill it earned — crew colours, the density
   ramp, its pressure band — and says "moved" with an outline instead. Painting
   it one flat green was the same mark meaning two things, and it cost the
   planner the crew and period reading on the one bar they had just edited. */
.lvl-ws-bar.is-moved{stroke:var(--lvl-after);stroke-width:1.7;stroke-opacity:1;cursor:grab}
.lvl-ws-seg.is-moved .lvl-ws-bar{stroke:var(--lvl-after);stroke-width:1.7;stroke-opacity:1}
.lvl-ws-seg.is-moved.is-crit .lvl-ws-bar,.lvl-ws-bar.is-moved.is-crit{stroke:var(--lvl-after)}
/* legacy single-fill proposed bar — kept for the older timeline charts */
.lvl-ws-bar.is-proposed{fill:var(--lvl-ok);fill-opacity:.9;stroke:var(--lvl-ok);stroke-width:1.6;cursor:grab}
.lvl-ws-bar.is-proposed.is-p-over{stroke:var(--lvl-risk);fill:var(--lvl-risk)}
.lvl-ws-bar.is-proposed.is-p-high{stroke:var(--lvl-warn);fill:var(--lvl-warn)}
.lvl-ws-bar.is-proposed.is-p-ok{stroke:var(--lvl-ok);fill:var(--lvl-ok)}
/* ghost: faded dotted gray baseline at old position */
/* A SHADOW, NOT AN OUTLINE. Dashed strokes were the problem: the baseline
   shadow and the suggestion target were both dashed low-opacity rectangles,
   and two of those at the same height are one shape to the eye. The shadow is
   now a soft solid block with no stroke at all — it recedes, which is what a
   shadow is for — and the suggestion lives on its own lane below the bar. */
.lvl-ws-ghost{fill:var(--lvl-mut-2);fill-opacity:.26;stroke:none;pointer-events:none}
/* cascade ghost: amber for indirectly-affected activities (not the dragged one) */
.lvl-ws-cascade{fill:rgba(247,148,29,.20);stroke:none}
.lvl-ws-ghostbar{opacity:.12;pointer-events:none}
.lvl-ws-bar.is-actual.is-ghost{opacity:0;pointer-events:none}
.lvl-ws-bar.is-crit{stroke:var(--lvl-ink);stroke-width:1.2;stroke-opacity:.6}
.lvl-ws-bar:hover{filter:brightness(1.1)}
/* BESIDE the bar, in ink. White-on-fill made the label a hostage to whatever
   the fill was doing and stole the bar's own length; the thin halo is the
   surface colour, so it survives a heat cell behind it without becoming an
   outline. */
.lvl-ws-q{font:600 10px/1 var(--lvl-font);font-variant-numeric:tabular-nums;fill:var(--lvl-ink);
  pointer-events:none;letter-spacing:.005em;
  paint-order:stroke;stroke:var(--lvl-card);stroke-width:2.6px;stroke-linejoin:round}
.lvl-ws-q.is-quiet{fill:var(--lvl-mut)}
.lvl-ws-over{fill:var(--lvl-risk)}
.lvl-ws-shift{stroke:var(--lvl-s1);stroke-width:1;stroke-dasharray:2 2}
.lvl-ws-shift.is-stretch{stroke-dasharray:1 2;stroke-width:1.6}
.lvl-ws-shiftt{font:700 8.5px/1 var(--lvl-mono);fill:var(--lvl-s1)}
.lvl-ws-float{fill:var(--lvl-mut-2);opacity:.4}
.lvl-ws-ms{fill:var(--lvl-ink);cursor:pointer}
.lvl-ws-link{fill:none;stroke:var(--lvl-mut-2);stroke-width:1.1;opacity:.75;stroke-linejoin:round;stroke-linecap:round}
.lvl-ws-link.is-driving{stroke:var(--lvl-risk);stroke-width:1.6;opacity:1}
.lvl-ws-link.is-changed{stroke:var(--lvl-info);stroke-width:1.6;opacity:1;stroke-dasharray:4 2.5}
.lvl-ws-linka{fill:var(--lvl-mut-2);opacity:.75}
.lvl-ws-linka.is-driving{fill:var(--lvl-risk);opacity:1}
.lvl-ws-linka.is-changed{fill:var(--lvl-info);opacity:1}
.lvl-ws-linkt{font:700 7.5px/1 var(--lvl-mono);fill:var(--lvl-mut-2);letter-spacing:.03em;dominant-baseline:middle;
  paint-order:stroke;stroke:var(--lvl-card);stroke-width:2.6px;stroke-linejoin:round}
.lvl-ws-linkt.is-changed{fill:var(--lvl-info)}
/* the old dot the arrowhead replaced — kept so nothing that still emits it breaks */
.lvl-ws-linkd{fill:var(--lvl-mut-2)}
.lvl-ws-linkd.is-driving{fill:var(--lvl-risk)}
.lvl-ws-lit{fill:var(--lvl-green);opacity:.1;pointer-events:none}

/* ── the heat wash: ONE hue, stepped by opacity ──────────────────────── */
/* TWO WASHES THAT MULTIPLY. The vertical carries the period's pressure, the
   horizontal carries the activity's own; `multiply` makes the crossing darker
   than either band alone, so the place to work emerges from the chart instead
   of having to be computed and announced. Neither band alone is loud — it is
   the product that has to be unmissable. */
/* ── THE HEAT MAP ──────────────────────────────────────────────────────
   THE CELLS ARE SOLID. Three rounds of this were translucent washes that
   multiplied into the surface, and the pixel measurement is why that ends
   here: a 0.24-alpha red over white lands at rgb(240,215,212) — ten to forty
   units from the surface it sits on — and the orange never reached the screen
   at all. A heat map you have to be told is there is not a heat map.

   The ramp is warm sequential: pale yellow through orange to deep red, with
   relative lightness falling at EVERY step (0.887 → 0.086), so it is a real
   sequential scheme rather than a rainbow. The cell's step is half the weight
   of each axis, so a mildly loaded activity in a quiet period is pale yellow
   and a heavy one inside an over-limit period is deep red — orange running
   into red as the two pressures compound, carried in the fill itself rather
   than in a blend mode, which is what makes it survive onto the screen. */
.lvl-cell{pointer-events:none}
/* the crossing — both pressures over at once — is the only thing on the chart
   that reaches the deep reds, so it needs no second marker */
.lvl-cell.is-x{}
/* a surface halo round every bar, so a cell behind it reads as a cell the bar
   sits in rather than as a coloured border on the bar */
.lvl-ws-halo{fill:var(--lvl-card);pointer-events:none}
/* a group row is structure, not a measurement */

/* TWO RAMPS, BECAUSE ONE CANNOT ANSWER TWO QUESTIONS. With a single ramp a
   dark cell and a dark column are the same colour, and the eye cannot tell
   "this period is loaded" from "this activity is loaded" — which is the only
   thing the chart is for.

   The COLUMN is red and stays in the pale half: pink context.
   The CELL is the warm yellow-to-red ramp and reaches the deep end.
   A pink field with orange cells on it separates cleanly, and the cells that
   go deep red are where both pressures are at the limit. */
.lvl-cell.is-f1{fill:#FFF1D0}
.lvl-cell.is-f2{fill:#FEE0A3}
.lvl-cell.is-f3{fill:#FDC873}
.lvl-cell.is-f4{fill:#FBA94A}
.lvl-cell.is-f5{fill:#F4862E}
.lvl-cell.is-f6{fill:#E3611D}
.lvl-cell.is-f7{fill:#C63E16}
.lvl-cell.is-f8{fill:#9E2411}
.lvl-cell.is-v.is-f1{fill:#FDEFEC}
.lvl-cell.is-v.is-f2{fill:#FADFD9}
.lvl-cell.is-v.is-f3{fill:#F6CAC1}
.lvl-cell.is-v.is-f4{fill:#F0AFA2}
.lvl-cell.is-v.is-f5{fill:#E88E7E}
.lvl-cell.is-v.is-f6{fill:#DC6D5C}
.lvl-cell.is-v.is-f7{fill:#CB5243}
.lvl-cell.is-v.is-f8{fill:#B03B2E}

/* THE COLUMN IS SOLID TOO, stepped at 0.6 of its own value so it lands in the
   pale half of the ramp: it fills the plot the way a heat map's background is
   supposed to, and leaves the deep end for the cells that carry the crossing.
   As a wash it measured ten units from the surface and the cells had nothing
   to stand out from. */
/* the old translucent wash class, kept only so nothing that still emits it
   paints something unexpected */
.lvl-heat{pointer-events:none;fill:var(--lvl-risk);opacity:.18}

/* the whole layer goes with the Heatmap toggle — switched off in the markup
   rather than hidden in CSS, so it costs nothing when it is off */

/* ── the crew heat matrix ────────────────────────────────────────────── */
/* ── CREW HEAT: A MATRIX, AND A STRIP WHEN IT IS SHUT ────────────────── */
.lvl-hm.is-shut{display:block;overflow:hidden}
.lvl-hm-h{display:flex;align-items:center;gap:8px;width:100%;padding:4px 10px;border:0;background:none;
  cursor:pointer;text-align:left;color:var(--lvl-ink-2);min-height:24px}
.lvl-hm-h:hover{background:var(--lvl-line-2)}
.lvl-hm-h b{font:700 10.5px/1 var(--lvl-font);color:var(--lvl-ink);flex:0 0 auto}
.lvl-hm-h em{font-style:normal;font:500 10px/1 var(--lvl-font);color:var(--lvl-mut);flex:0 0 auto}
.lvl-hm-tw{font-style:normal;font-size:9px;color:var(--lvl-mut-2);flex:0 0 auto}
.lvl-hm-peek{display:flex;align-items:center;gap:10px;margin-left:auto;overflow:hidden;flex:1 1 auto;justify-content:flex-end}
.lvl-hm-peek u{display:inline-flex;align-items:center;gap:4px;text-decoration:none;font:600 10px/1 var(--lvl-font);color:var(--lvl-mut);white-space:nowrap}
.lvl-hm-peek i{width:7px;height:7px;border-radius:2px;flex:0 0 auto}
.lvl-hm-peek b{font:700 10px/1 var(--lvl-mono);color:var(--lvl-risk)}
/* the matrix's own period band, so it reads without borrowing the Gantt's */
.lvl-hm-ax{font:600 8px/1 var(--lvl-mono);fill:var(--lvl-mut-2);letter-spacing:.02em}
.lvl-hm-ax-r{stroke:var(--lvl-line-2);stroke-width:1;opacity:.55}
.lvl-hm-v{font:700 9.5px/1 var(--lvl-mono);fill:var(--lvl-ink);pointer-events:none;opacity:.72}
.lvl-hm-v.is-deep{fill:#fff;opacity:.96}
.lvl-hm{display:grid;grid-template-columns:var(--ws-cols) minmax(0,1fr);border-bottom:1px solid var(--lvl-line);
  background:var(--lvl-wash);min-height:0;overflow:hidden}
.lvl-hm-side{border-right:1px solid var(--lvl-line);padding:4px 8px 6px;min-width:0;overflow:hidden auto;scrollbar-width:none}
.lvl-hm-side::-webkit-scrollbar{display:none}
.lvl-hm-t{display:flex;align-items:center;gap:6px;padding:3px 0 5px;
  font:700 9.5px/1 var(--lvl-font);color:var(--lvl-ink-2)}
.lvl-hm-t i{font-style:normal;font-size:8px;color:var(--lvl-mut-2)}
.lvl-hm-t em{font-style:normal;margin-left:auto;font:500 9px/1 var(--lvl-mono);color:var(--lvl-mut-2)}
.lvl-hm-names{display:grid;gap:0}
.lvl-hm-n{display:flex;align-items:center;gap:5px;height:14px;font-size:9.5px;color:var(--lvl-ink-2);cursor:pointer;min-width:0}
.lvl-hm-n i{width:6px;height:6px;border-radius:2px;flex:0 0 auto}
.lvl-hm-n b{font-weight:500;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-hm-n u{margin-left:auto;text-decoration:none;font:600 9px/1 var(--lvl-mono);color:var(--lvl-mut-2)}
.lvl-hm-n u.is-over{color:var(--lvl-risk);font-weight:800}
.lvl-hm-n:hover{color:var(--lvl-ink)}
.lvl-hm-n.is-on{font-weight:700;color:var(--lvl-green-d)}
.lvl-hm-side .lvl-link{font-size:9.5px;margin-top:3px}
.lvl-hm-time{overflow:hidden auto;scrollbar-width:none}
.lvl-hm-time::-webkit-scrollbar{display:none}
.lvl-hm-time svg{display:block}
/* sequential: ONE hue, stepped. The cells are marks, not a wash, so they get
   the full range the background wash deliberately gives up. */
/* SEQUENTIAL TO THE LIMIT, STATUS BEYOND IT. One hue light-to-dark carries
   "how hard is this crew being worked"; the reserved red carries "this is
   over the limit". Changing hue at the boundary is legitimate because that is
   where the meaning changes — below it the answer is a quantity, at it the
   answer is a breach. */
.lvl-hm-c{fill:var(--lvl-heat,#3f6ea8);cursor:pointer}
.lvl-hm-c.is-h0{fill:var(--lvl-line-2);opacity:.5}
.lvl-hm-c.is-h1{opacity:.26}
.lvl-hm-c.is-h2{opacity:.46}
.lvl-hm-c.is-h3{opacity:.66}
.lvl-hm-c.is-h4{opacity:.88}
.lvl-hm-c.is-h5{fill:var(--lvl-risk);opacity:.88}
.lvl-hm-c.is-h6{fill:var(--lvl-risk);opacity:1}
.lvl-hm-c.is-lit{stroke:var(--lvl-ink);stroke-width:1.4}
.lvl-hm-c:hover{stroke:var(--lvl-ink);stroke-width:1.2}

/* ── histogram pane ──────────────────────────────────────────────────── */
.lvl-hg{display:grid;grid-template-columns:var(--ws-cols) minmax(0,1fr);border-bottom:1px solid var(--lvl-line);
  background:var(--lvl-card);min-height:0;overflow:hidden}
.lvl-hg-legend{padding:8px 10px;border-right:1px solid var(--lvl-line);min-width:0}
.lvl-hg-legend>b{display:block;font:700 11px/1.3 var(--lvl-font);color:var(--lvl-ink)}
.lvl-hg-sub{display:block;font-size:9.5px;line-height:1.45;color:var(--lvl-mut);margin-top:2px}
.lvl-hg-mode{margin-top:6px}
.lvl-hg-mode .lvl-seg{height:22px}
.lvl-hg-mode .lvl-seg-b{height:20px;padding:0 8px;font-size:10px}
.lvl-hg-keys{display:grid;grid-template-columns:1fr 1fr;gap:2px;margin-top:6px}
.lvl-hgk{display:inline-flex;align-items:center;gap:5px;padding:2px 0;border:0;background:none;cursor:pointer;
  font:500 10px/1 var(--lvl-font);color:var(--lvl-mut);text-align:left}
.lvl-hgk i{width:9px;height:9px;border-radius:2px;background:var(--lvl-line-3);flex:0 0 auto}
.lvl-hgk.is-on{color:var(--lvl-ink-2)}
.lvl-hgk.is-actual.is-on i{background:var(--lvl-s3)}
.lvl-hgk.is-proposed.is-on i{background:var(--lvl-s1)}
.lvl-hgk.is-cap.is-on i{background:none;height:0;border-top:2px dashed var(--lvl-ink-2)}
.lvl-hgk.is-ideal.is-on i{background:none;height:0;border-top:2px dashed var(--lvl-s7)}
.lvl-hgk.is-off{opacity:.35;cursor:default}
.lvl-hg-peak{margin-top:7px;font:600 10px/1 var(--lvl-mono);color:var(--lvl-mut)}
.lvl-hg-peak b{color:var(--lvl-risk);font-weight:800}
.lvl-hg-time{overflow:hidden auto;scrollbar-width:none}
.lvl-hg-time::-webkit-scrollbar{display:none}
.lvl-hg-time svg{display:block}
.lvl-ws-hb.is-actual{fill:var(--lvl-s3)}
.lvl-ws-hb.is-proposed{fill:var(--lvl-s1)}
.lvl-ws-hb.is-over{fill:var(--lvl-risk)}
.lvl-ws-hb.is-series{stroke:var(--lvl-card);stroke-width:.5}
.lvl-ws-hotband{fill:var(--lvl-risk);opacity:.06}
.lvl-ws-cap{stroke:var(--lvl-ink-2);stroke-width:1.4;stroke-dasharray:5 3}
.lvl-ws-ideal{fill:none;stroke:var(--lvl-s7);stroke-width:1.6;stroke-dasharray:5 3;opacity:.75}
.lvl-ws-peak line{stroke:var(--lvl-risk);stroke-width:1.2}
.lvl-ws-peak rect{fill:var(--lvl-risk)}
.lvl-ws-peak text{font:800 9px/1 var(--lvl-mono);fill:#fff}
.lvl-ws-hhit{cursor:pointer;fill:transparent}
.lvl-ws-hhit.is-lit{fill:var(--lvl-green);opacity:.12}

/* ── foot: minimap + legend ──────────────────────────────────────────── */
.lvl-ws-foot{display:flex;align-items:center;gap:14px;padding:4px 10px;background:var(--lvl-wash);
  border-top:1px solid var(--lvl-line);flex:0 0 auto}
.lvl-ws-mini-w{flex:0 0 180px;height:26px;border-radius:3px}
.lvl-ws-mini-w.is-nav{cursor:ew-resize;box-shadow:inset 0 0 0 1px var(--lvl-line-2)}
.lvl-ws-mini-w.is-nav svg{touch-action:none}
.lvl-ws-mini{width:100%;height:26px}
.lvl-ws-mb{fill:var(--lvl-mut-2);opacity:.55}
.lvl-ws-mb.is-over{fill:var(--lvl-risk);opacity:.85}
.lvl-ws-mview{fill:color-mix(in srgb,var(--lvl-green) 13%,transparent);stroke:var(--lvl-green);stroke-width:1.2;pointer-events:none;
  transition:x .08s linear,width .08s linear}
@media (prefers-reduced-motion:reduce){.lvl-ws-mview{transition:none}}
.lvl-ws-key{display:flex;align-items:center;gap:6px;flex-wrap:wrap;font-size:9.5px;color:var(--lvl-mut)}
.lvl-ws-key i{width:11px;height:8px;border-radius:2px;margin-left:8px;flex:0 0 auto}
.lvl-ws-key i:first-child{margin-left:0}
.lvl-ws-key b{font-weight:700;color:var(--lvl-ink-2);margin-right:2px}
.lvl-ws-key .k-over{background:var(--lvl-risk)}
.lvl-ws-key .k-high{background:var(--lvl-warn)}
.lvl-ws-key .k-ok{background:var(--lvl-ok)}
.lvl-ws-key .k-none{background:var(--lvl-mut-2);opacity:.55}
.lvl-ws-key .k-actual{background:var(--lvl-ok)}
.lvl-ws-key .k-proposed{background:rgba(42,120,214,.14);border:1.4px solid var(--lvl-s1)}
.lvl-ws-key .k-crit{background:none;border:1.2px solid var(--lvl-ink)}
.lvl-ws-key .k-float{background:var(--lvl-mut-2);opacity:.4;height:3px}
/* the swatch has to be the ramp the matrix actually draws: sequential to
   the limit, then the reserved red */
.lvl-ws-key .k-heat{width:42px;background:linear-gradient(90deg,
  color-mix(in srgb,var(--lvl-heat) 26%,transparent) 0%,
  color-mix(in srgb,var(--lvl-heat) 88%,transparent) 58%,
  var(--lvl-risk) 62%,var(--lvl-risk) 100%)}

.lvl-ws-key .k-brk{background:var(--lvl-risk);height:3px}
.lvl-ws-key .k-other{background:var(--lvl-other,#8A94A0)}
.lvl-ws-key-n{color:var(--lvl-mut-2);margin-left:6px}
.lvl-ws-key .k-ms{background:var(--lvl-ink);transform:rotate(45deg);width:7px;height:7px;border-radius:1px}

/* ── drag a trade across the calendar ────────────────────────────────── */
.lvl-hm-c[data-lvl-resdrag]{cursor:grab}
.lvl-ws-hm.is-resdrag,.lvl-ws-hist.is-resdrag{cursor:grabbing}
.lvl-ws-hm.is-resdrag .lvl-hm-c,.lvl-ws-hist.is-resdrag .lvl-ws-hb{pointer-events:none}
.lvl-ws-hb[data-lvl-resdrag]{cursor:grab}
.lvl-hm-ghost{fill:var(--lvl-ink);opacity:.35;pointer-events:none}
.lvl-hm-ghostt{font:800 8.5px/1 var(--lvl-mono);fill:var(--lvl-ink);pointer-events:none}

/* ── a trade-move proposal, over the chart column ────────────────────── */
/* THE PROPOSAL SITS BESIDE THE PROGRAMME, NOT OVER IT. It used to cover the
   whole workspace, which hid the very Gantt the change is drawn on — and the
   Gantt now shows the proposal live, so covering it threw away the answer.
   It takes the right-hand column and leaves the timeline readable. */
.lvl-rp{position:absolute;right:0;top:0;bottom:0;width:min(600px,48%);z-index:8;display:flex;flex-direction:column;
  border-left:2px solid var(--lvl-green);border-radius:var(--lvl-r-s) 0 0 var(--lvl-r-s);background:var(--lvl-card);
  box-shadow:-14px 0 34px -18px rgba(15,30,45,.34);animation:lvlRpIn .16s ease-out}
.lvl-rp.is-narrow{width:min(400px,34%);bottom:auto;max-height:100%}
@keyframes lvlRpIn{from{opacity:0;transform:translateX(14px)}to{opacity:1;transform:none}}
@media (prefers-reduced-motion:reduce){.lvl-rp{animation:none}}
.lvl-rp-h{position:relative;padding:11px 40px 11px 14px;border-bottom:1px solid var(--lvl-line);background:var(--lvl-green-t)}
.lvl-rp-h b{display:block;font:700 13px/1.35 var(--lvl-font)}
.lvl-rp-h em{display:block;font-style:normal;font-size:11px;color:var(--lvl-mut);margin-top:2px}
.lvl-rp-x{position:absolute;top:9px;right:10px;width:24px;height:24px;border:0;border-radius:6px;background:none;
  cursor:pointer;color:var(--lvl-mut);font-size:13px}
.lvl-rp-x:hover{background:var(--lvl-line-2);color:var(--lvl-ink)}
.lvl-rp-sum{display:grid;grid-template-columns:repeat(auto-fit,minmax(126px,1fr));gap:1px;background:var(--lvl-line);
  border-bottom:1px solid var(--lvl-line)}
.lvl-rp-s{background:var(--lvl-card);padding:8px 12px}
.lvl-rp-s span{display:block;font:700 8.5px/1 var(--lvl-mono);letter-spacing:.09em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-rp-s b{display:block;font:800 13px/1.2 var(--lvl-mono);margin-top:4px}
.lvl-rp-s em{display:block;font-style:normal;font-size:10px;color:var(--lvl-mut);margin-top:2px}
.lvl-rp-s.is-good b{color:var(--lvl-ok)}
.lvl-rp-s.is-bad b{color:var(--lvl-risk)}
/* ── DRAGGED INTO THE LOGIC ───────────────────────────────────────────
   One row per relationship that is holding the bar, and on each row the
   relationships it could become. The planner picks per row, because a
   programme rarely has one answer for two different predecessors. */
.lvl-rlx{flex:0 0 auto;max-height:34%;overflow:auto;border-bottom:1px solid var(--lvl-line);background:var(--lvl-card)}
.lvl-rlx-r{display:flex;align-items:center;gap:10px;padding:9px 14px;border-bottom:1px solid var(--lvl-line-2)}
.lvl-rlx-r:last-child{border-bottom:0}
.lvl-rlx-n{flex:1;min-width:0}
.lvl-rlx-n b{display:block;font:700 12px/1.3 var(--lvl-font);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-rlx-n em{display:block;font-style:normal;font-size:10px;color:var(--lvl-mut);margin-top:2px}
.lvl-rlx-o{display:flex;gap:5px;flex-shrink:0}
.lvl-rlx-b{position:relative;border:1px solid var(--lvl-line);border-radius:6px;background:var(--lvl-card);cursor:pointer;
  padding:5px 9px;font:800 11px/1 var(--lvl-mono);color:var(--lvl-ink-2)}
.lvl-rlx-b:hover{border-color:var(--lvl-green);color:var(--lvl-ink)}
.lvl-rlx-b.is-on{background:var(--lvl-green-t);border-color:var(--lvl-green);color:var(--lvl-ink)}
.lvl-rlx-b.is-warn{border-style:dashed;color:var(--lvl-warn)}
.lvl-rlx-b i{display:block;font:700 7.5px/1 var(--lvl-mono);letter-spacing:.08em;text-transform:uppercase;
  color:var(--lvl-ok);font-style:normal;margin-top:3px}
.lvl-rlx-warn{display:flex;align-items:flex-start;gap:6px;margin:0;padding:9px 14px;
  background:var(--lvl-amber-t,rgba(247,148,29,.08));border-bottom:1px solid var(--lvl-line)}
.lvl-rp-g{flex:0 0 auto;max-height:40%;overflow:auto;border-bottom:1px solid var(--lvl-line);background:var(--lvl-card)}
.lvl-rp-g .lvl-chart{border:0}
.lvl-rp .lvl-tbl-wrap{flex:1;min-height:0;overflow:auto;border:0;border-radius:0}
.lvl-rp-t tbody tr{cursor:pointer}
.lvl-rp-t tbody tr.is-off{opacity:.42}
.lvl-rp-t tbody tr.is-blocked{opacity:.55;cursor:default}
.lvl-rp-t tbody tr:hover{background:var(--lvl-wash)}
.lvl-rp-c{width:26px}
.lvl-rp-c i{display:inline-flex;align-items:center;justify-content:center;width:14px;height:14px;border-radius:3px;
  border:1px solid var(--lvl-line-3);font-style:normal;font-size:9px;color:#fff}
.lvl-rp-c i.is-on{background:var(--lvl-green);border-color:var(--lvl-green)}
.lvl-rp-why{color:var(--lvl-mut);font-size:11px}
.lvl-rp-a{display:flex;gap:8px;justify-content:flex-end;padding:10px 14px;border-top:1px solid var(--lvl-line);
  background:var(--lvl-wash)}

/* ── stretch panel + relationship editor ─────────────────────────────── */
.lvl-rp.is-narrow{left:auto;right:0;width:min(400px,34%);top:0;bottom:auto;max-height:100%}
.lvl-rp-crew{padding:10px 14px;border-bottom:1px solid var(--lvl-line)}
.lvl-rp-crew h6{display:flex;align-items:baseline;justify-content:space-between;gap:10px;margin:0 0 7px;
  font:700 8.5px/1.4 var(--lvl-mono);letter-spacing:.09em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-rp-crew h6>span{flex:0 0 auto}
.lvl-rp-crew h6 small{flex:1 1 auto;font:600 9px/1.4 var(--lvl-mono);letter-spacing:.02em;text-transform:none;color:var(--lvl-mut);text-align:right}
.lvl-rp-cr{display:flex;align-items:center;gap:7px;font-size:11.5px;padding:3px 0}
.lvl-rp-cr i{width:8px;height:8px;border-radius:2px;flex:0 0 auto}
.lvl-rp-cr b{margin-left:auto;font-family:var(--lvl-mono);font-weight:700}
.lvl-rp-cr em{font-style:normal;font:700 10px/1 var(--lvl-mono);color:var(--lvl-mut);min-width:38px;text-align:right}
.lvl-rp-cr em.is-good{color:var(--lvl-ok)}
.lvl-rp-nudge{display:flex;align-items:center;gap:5px;padding:9px 14px;border-bottom:1px solid var(--lvl-line)}
.lvl-rp-nudge span{font:700 8.5px/1 var(--lvl-mono);letter-spacing:.09em;text-transform:uppercase;color:var(--lvl-mut-2);margin-right:3px}
.lvl-rp-none{padding:14px}
/* the honest answer when the float cannot pay for the gesture: what is in the
   way, and the two ways out, on the screen instead of in a toast */
.lvl-rp-none-b{display:grid;grid-template-columns:22px 1fr;gap:6px 11px;align-items:start;
  margin:12px 14px 0;padding:12px 14px;border-radius:var(--lvl-r-xs);
  background:color-mix(in srgb,var(--lvl-warn) 8%,transparent);
  border:1px solid color-mix(in srgb,var(--lvl-warn) 26%,transparent)}
.lvl-rp-none-b svg{grid-row:1/3;color:var(--lvl-warn)}
.lvl-rp-none-b b{font:700 12px/1.35 var(--lvl-sans);color:var(--lvl-ink)}
.lvl-rp-none-b p{grid-column:2;margin:0;font:400 11px/1.55 var(--lvl-sans);color:var(--lvl-mut)}
.lvl-rp-none-b .lvl-btn{grid-column:2;justify-self:start;margin-top:4px}
.lvl-rp-forced{display:inline-block;margin-left:7px;padding:1px 6px;border-radius:99px;font:700 8.5px/1.6 var(--lvl-mono);
  letter-spacing:.08em;text-transform:uppercase;font-style:normal;
  background:color-mix(in srgb,var(--lvl-warn) 20%,transparent);color:var(--lvl-warn)}
.lvl-ws-body.is-stretching{cursor:ew-resize}

.lvl-rel{display:grid;gap:4px}
.lvl-rel-r{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-xs);overflow:hidden;background:var(--lvl-card)}
.lvl-rel-r.is-staged{border-color:var(--lvl-info)}
.lvl-rel-h{display:flex;align-items:center;gap:7px;width:100%;padding:6px 9px;border:0;background:none;cursor:pointer;
  font:inherit;color:inherit;text-align:left}
.lvl-rel-h:hover{background:var(--lvl-wash)}
.lvl-rel-r.is-open .lvl-rel-h{background:var(--lvl-green-t)}
.lvl-rel-d{font-style:normal;font-size:11px;color:var(--lvl-mut-2);flex:0 0 auto}
.lvl-rel-h b{font:600 11px/1.3 var(--lvl-font);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-rel-h u{margin-left:auto;text-decoration:none;font:700 9.5px/1 var(--lvl-mono);color:var(--lvl-ink-2);
  background:var(--lvl-line-2);padding:3px 6px;border-radius:3px;flex:0 0 auto}
.lvl-rel-s{font-style:normal;font:700 8px/1 var(--lvl-mono);letter-spacing:.06em;text-transform:uppercase;
  color:var(--lvl-info);background:var(--lvl-info-t);padding:3px 5px;border-radius:3px;flex:0 0 auto}
.lvl-rel-b{padding:8px 9px;border-top:1px solid var(--lvl-line-2)}
.lvl-rel-opts{display:flex;gap:4px}
.lvl-rel-t{flex:1;height:26px;border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-xs);background:var(--lvl-card);
  cursor:pointer;font:700 10.5px/1 var(--lvl-mono);color:var(--lvl-ink-2)}
.lvl-rel-t:hover{border-color:var(--lvl-green)}
.lvl-rel-t.is-on{background:var(--lvl-green);border-color:var(--lvl-green);color:#fff}
.lvl-rel-lag{display:flex;align-items:center;gap:4px;margin-top:6px}
.lvl-rel-lag span{font:700 8.5px/1 var(--lvl-mono);letter-spacing:.09em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-rel-l{flex:1;height:24px;border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-xs);background:var(--lvl-card);
  cursor:pointer;font:600 10px/1 var(--lvl-mono);color:var(--lvl-mut)}
.lvl-rel-l:hover{border-color:var(--lvl-green);color:var(--lvl-ink)}
.lvl-in-s h5 small{font-weight:600;font-size:9.5px;color:var(--lvl-mut-2);margin-left:auto}

/* ── inspector ───────────────────────────────────────────────────────── */
.lvl-ws-insp{display:flex;flex-direction:column;min-height:0;background:var(--lvl-card)}
.lvl-in-tabs{display:flex;border-bottom:1px solid var(--lvl-line);background:var(--lvl-wash)}
.lvl-in-tab{flex:1;display:inline-flex;align-items:center;justify-content:center;gap:5px;height:36px;border:0;
  background:none;cursor:pointer;font:600 11px/1 var(--lvl-font);color:var(--lvl-mut);
  border-bottom:2px solid transparent}
.lvl-in-tab:hover{color:var(--lvl-ink-2)}
.lvl-in-tab.is-on{color:var(--lvl-ink);border-bottom-color:var(--lvl-green);background:var(--lvl-card)}
.lvl-in-tab em{font-style:normal;font:800 8.5px/1 var(--lvl-mono);background:var(--lvl-green-t);color:var(--lvl-green-d);
  padding:2px 5px;border-radius:8px}
.lvl-in-body{flex:1;overflow-y:auto;min-height:0}
.lvl-in-blank{padding:34px 20px;text-align:center;color:var(--lvl-mut)}
.lvl-in-blank b{display:block;font:700 13px/1.4 var(--lvl-font);color:var(--lvl-ink);margin:10px 0 6px}
.lvl-in-blank p{font-size:11.5px;line-height:1.55;margin:0 0 8px}
.lvl-in-lede{padding:12px 14px 0;margin:0;font-size:11px;line-height:1.55;color:var(--lvl-mut)}
.lvl-in-h{padding:12px 14px;border-bottom:1px solid var(--lvl-line)}
.lvl-in-h>b{display:block;font:700 13px/1.35 var(--lvl-font)}
.lvl-in-h>em{display:block;font-style:normal;font:500 10px/1.3 var(--lvl-mono);color:var(--lvl-mut-2);margin-top:2px}
.lvl-in-tags{display:flex;gap:5px;margin-top:8px}
.lvl-in-cols{display:grid;grid-template-columns:1fr 1fr;border-bottom:1px solid var(--lvl-line)}
.lvl-in-col{padding:11px 14px}
.lvl-in-col+.lvl-in-col{border-left:1px solid var(--lvl-line)}
.lvl-in-col.is-prop{background:var(--lvl-green-t)}
.lvl-in-col.is-idle{opacity:.55}
.lvl-in-col h6{margin:0 0 8px;font:700 9px/1 var(--lvl-mono);letter-spacing:.08em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-in-col dl{margin:0;display:grid;gap:5px}
.lvl-in-col dl>div{display:flex;justify-content:space-between;gap:8px;font-size:11px}
.lvl-in-col dt{color:var(--lvl-mut)}
.lvl-in-col dd{margin:0;font-family:var(--lvl-mono);font-weight:600;color:var(--lvl-ink)}
.lvl-in-s{padding:12px 14px;border-bottom:1px solid var(--lvl-line)}
.lvl-in-s h5{display:flex;align-items:baseline;gap:6px;margin:0 0 9px;font:700 11px/1.3 var(--lvl-font)}
.lvl-in-s h5 u{margin-left:auto;text-decoration:none;font:800 9px/1 var(--lvl-mono);color:var(--lvl-ok);
  background:var(--lvl-ok-t);padding:3px 6px;border-radius:3px}
.lvl-in-s h5 u.is-hold{color:var(--lvl-mut);background:var(--lvl-line-2)}
.lvl-in-s .lvl-note{margin:8px 0 0;font-size:10.5px;line-height:1.5}
.lvl-in-fl{display:flex;justify-content:space-between;font:600 10.5px/1 var(--lvl-mono);color:var(--lvl-ink-2)}
.lvl-in-fl.is-scale{color:var(--lvl-mut-2);font-weight:500;margin-top:4px}
.lvl-in-flt{height:6px;border-radius:3px;background:var(--lvl-line-2);margin-top:6px;overflow:hidden}
.lvl-in-flt i{display:block;height:100%;background:var(--lvl-green);border-radius:3px}
.lvl-in-im{margin:0;display:grid;gap:6px}
.lvl-in-im>div{display:flex;justify-content:space-between;gap:8px;font-size:11px}
.lvl-in-im dt{color:var(--lvl-mut)}
.lvl-in-im dd{margin:0;font-family:var(--lvl-mono);font-weight:600;display:flex;gap:6px;align-items:baseline}
.lvl-in-im dd em{font-style:normal;font-size:10px}
.lvl-in-im dd em.is-good{color:var(--lvl-ok)}
.lvl-in-im dd em.is-bad{color:var(--lvl-risk)}
.lvl-pos{color:var(--lvl-ok)}
.lvl-in-foot{display:flex;gap:8px;padding:12px 14px;border-top:1px solid var(--lvl-line);background:var(--lvl-wash);
  position:sticky;bottom:0}
.lvl-in-foot .lvl-btn{flex:1;justify-content:center}
.lvl-qz{padding:10px 12px;display:grid;gap:7px}
.lvl-qz-r{display:flex;gap:9px;align-items:flex-start;padding:8px 10px;border:1px solid var(--lvl-line);
  border-radius:var(--lvl-r-xs);background:var(--lvl-card)}
.lvl-qz-n{flex:0 0 20px;height:20px;border-radius:50%;background:var(--lvl-green-t);color:var(--lvl-green-d);
  display:inline-flex;align-items:center;justify-content:center;font:800 10px/1 var(--lvl-mono)}
.lvl-qz-r.is-logic .lvl-qz-n{background:var(--lvl-info-t);color:var(--lvl-info)}
.lvl-qz-m{min-width:0}
.lvl-qz-m b{display:block;font:600 11.5px/1.35 var(--lvl-font)}
.lvl-qz-m em{display:block;font-style:normal;font:500 10px/1.4 var(--lvl-mono);color:var(--lvl-mut);margin-top:2px}
.lvl-qz-r{position:relative}
.lvl-qz-undo{position:absolute;top:8px;right:8px;width:22px;height:22px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-xs);
  background:var(--lvl-card);color:var(--lvl-mut);cursor:pointer;font:12px/1 var(--lvl-mono);
  display:flex;align-items:center;justify-content:center;opacity:0;transition:opacity .15s}
.lvl-qz-r:hover .lvl-qz-undo{opacity:1}
.lvl-qz-undo:hover{background:var(--lvl-risk-t);color:var(--lvl-risk);border-color:var(--lvl-risk)}
.lvl-qz-metrics{display:flex;flex-wrap:wrap;gap:8px;padding:10px 12px;border-bottom:1px solid var(--lvl-line);
  background:var(--lvl-wash)}
.lvl-qz-metric{font:500 10.5px/1.3 var(--lvl-font);color:var(--lvl-ink);padding:2px 8px;
  border-radius:var(--lvl-r-xs);background:var(--lvl-card);border:1px solid var(--lvl-line)}
.lvl-qz-metric b{font-weight:700}
.lvl-qz-metric.is-good{border-color:var(--lvl-green);color:var(--lvl-green-d);background:var(--lvl-green-t)}
.lvl-qz-metric.is-bad{border-color:var(--lvl-risk);color:var(--lvl-risk);background:var(--lvl-risk-t)}
/* ── impact strip ───────────────────────────────────────────────────── */
.lvl-is{display:flex;align-items:center;gap:8px;padding:6px 14px;border-bottom:1px solid var(--lvl-line);
  font:500 11px/1.4 var(--lvl-font);color:var(--lvl-ink);background:var(--lvl-wash);flex-wrap:wrap}
.lvl-is.is-ok{border-left:3px solid var(--lvl-green)}
.lvl-is.is-warn{border-left:3px solid #F7941D}
.lvl-is.is-err{border-left:3px solid var(--lvl-risk);background:var(--lvl-risk-t)}
.lvl-is-icon{font-size:14px;flex:0 0 18px;text-align:center}
.lvl-is.is-ok .lvl-is-icon{color:var(--lvl-green)}
.lvl-is.is-warn .lvl-is-icon{color:#F7941D}
.lvl-is.is-err .lvl-is-icon{color:var(--lvl-risk)}
.lvl-is-parts{display:flex;flex-wrap:wrap;gap:4px;align-items:center}
.lvl-is-seg{white-space:nowrap}
.lvl-is-seg b{font-weight:700}
.lvl-is-dot{color:var(--lvl-line);margin:0 2px}
.lvl-is-note{font:400 10px/1.3 var(--lvl-font);color:var(--lvl-risk);margin-left:8px;flex-basis:100%}
.lvl-is-good{color:var(--lvl-green-d);font-weight:600}
.lvl-is-bad{color:var(--lvl-risk);font-weight:600}
.lvl-is-warn{color:#F7941D;font-weight:600}
/* ── floating apply bar ────────────────────────────────────────────── */
.lvl-fab{display:flex;align-items:center;justify-content:space-between;gap:12px;
  padding:8px 14px;border-top:2px solid var(--lvl-green);background:var(--lvl-card);
  box-shadow:0 -2px 8px rgba(0,0,0,.06);position:relative;z-index:10;flex-wrap:wrap}
.lvl-fab-info{display:flex;align-items:center;gap:6px;flex-wrap:wrap;
  font:500 11px/1.4 var(--lvl-font);color:var(--lvl-ink)}
.lvl-fab-count b{font-weight:700}
.lvl-fab-sep{color:var(--lvl-line)}
.lvl-fab-stat{white-space:nowrap}
.lvl-fab-actions{display:flex;gap:6px;align-items:center;flex-wrap:wrap}
.lvl-btn.is-xs{font:500 10px/1 var(--lvl-font);padding:4px 8px;border-radius:var(--lvl-r-xs)}
.lvl-btn.is-sm{font:600 11px/1 var(--lvl-font);padding:6px 14px}
.lvl-in-body .lvl-ov-list{padding:0 12px 12px}
.lvl-in-body .lvl-ov{font-size:11px}

@media (max-width:1180px){
  .lvl-ws{height:auto;min-height:0}
  .lvl-ws-grid{grid-template-columns:1fr}
  .lvl-ws-chart{border-right:0;border-bottom:1px solid var(--lvl-line)}
  .lvl-gt{height:460px}
}

/* ══ WORK GANTT (WBS) ═════════════════════════════════════════════════════
   Density is the point. A planning Gantt is read by scanning, and a scan needs
   rows close enough that the eye does not travel — so the type is small, the
   weight carries the hierarchy, and no row is given a coloured slab when a
   2px accent and a dot will do.                                             */
.lvl-wg-wrap{border:1px solid var(--lvl-line);border-top:0;border-radius:0 0 var(--lvl-r-s) var(--lvl-r-s);background:var(--lvl-card)}
.lvl-lp-wrap{border:1px solid var(--lvl-line);border-bottom:0;border-radius:var(--lvl-r-s) var(--lvl-r-s) 0 0;background:var(--lvl-card)}
.lvl-wg .lvl-wg-wbsb{fill:var(--lvl-wash)}
.lvl-wg-wbs{cursor:pointer}
.lvl-wg-wbs:hover .lvl-wg-wbsb{fill:var(--lvl-line-2)}
.lvl-wg-acc{opacity:.75}
.lvl-wg-tw{font-size:8px;fill:var(--lvl-mut-2)}
.lvl-wg-wl{font:700 10px/1 var(--lvl-font);fill:var(--lvl-ink);letter-spacing:-.005em}
.lvl-wg-wn{font:600 9px/1 var(--lvl-mono);fill:var(--lvl-mut-2)}
.lvl-wg-wnp{fill:var(--lvl-mut-2);opacity:.7}
.lvl-wg-dot{fill:var(--lvl-risk)}
.lvl-wg-sum{fill:var(--lvl-mut-2);opacity:.3}
.lvl-wg-cap{fill:var(--lvl-mut-2);opacity:.5}
.lvl-wg-hd{stroke:var(--lvl-line);stroke-width:1}
.lvl-wg-ind{stroke:var(--lvl-line-2);stroke-width:1}
.lvl-wg .lvl-lg-l{font-size:10px;fill:var(--lvl-ink-2);cursor:pointer}
.lvl-wg-ax{font-size:9px;fill:var(--lvl-mut-2)}
.lvl-wg-ax.is-q{fill:var(--lvl-mut);font-weight:700}
.lvl-grid.is-q{stroke:var(--lvl-line-3)}
.lvl-wg-q{font:600 9px/1 var(--lvl-mono);fill:var(--lvl-mut)}
.lvl-wg-q.is-over{fill:var(--lvl-risk);font-weight:800}
.lvl-wg-tf{font:600 9px/1 var(--lvl-mono);fill:var(--lvl-mut-2)}
.lvl-wg-tf.is-tight{fill:var(--lvl-warn)}
.lvl-wg-tf.is-none{fill:var(--lvl-risk);font-weight:800}
.lvl-tl-d{font:700 9px/1 var(--lvl-mono);fill:var(--lvl-after)}
.lvl-lg-wend{stroke:var(--lvl-mut-2);stroke-width:1;opacity:.4}
.lvl-wg-lit,.lvl-lp-lit{fill:var(--lvl-green);opacity:.09;pointer-events:none}
.lvl-wg-row.is-lit .lvl-tl-zebra{fill:var(--lvl-green-t)}
.lvl-wg-row.is-lit .lvl-lg-l{fill:var(--lvl-ink);font-weight:700}
.lvl-wg-row.is-dim{opacity:.28}
.lvl-wg-row.is-sel .lvl-tl-zebra{fill:var(--lvl-green-t)}
.lvl-wg-row.is-sel .lvl-lg-l{font-weight:800;fill:var(--lvl-ink)}
.lvl-wg-h{display:flex;align-items:baseline;gap:12px;margin:14px 0 7px}
.lvl-wg-h h4{margin:0}
.lvl-wg-live{margin-left:auto;font-size:11px;color:var(--lvl-mut);min-height:15px;text-align:right;flex:1 1 40%}
.lvl-wg-live b{color:var(--lvl-ink)}
.lvl-wg-scale{margin-top:7px}
.lvl-scale-x{color:var(--lvl-mut-2);font-size:10px}

/* ══ LOAD PROFILE (drawn in the gantt's geometry) ═════════════════════════ */
.lvl-lp-b{fill:var(--lvl-neutral)}
.lvl-lp-b.is-series{fill:none}
.lvl-lp-b.is-over{fill:var(--lvl-risk)}
.lvl-lp-over{fill:var(--lvl-risk);opacity:.85}
.lvl-lp-flag{fill:var(--lvl-risk)}
.lvl-lp-ideal{fill:none;stroke:var(--lvl-ink-2);stroke-width:1.5;stroke-dasharray:5 3;opacity:.5}
.lvl-lp-ghost{fill:none;stroke:var(--lvl-before);stroke-width:1.4;opacity:.75}
.lvl-lp-t{font:700 11px/1 var(--lvl-font);fill:var(--lvl-ink)}
.lvl-lp-s{font:500 9.5px/1 var(--lvl-font);fill:var(--lvl-mut)}
.lvl-lp-lgt{font:500 9px/1 var(--lvl-font);fill:var(--lvl-mut)}
.lvl-lp-hit{cursor:pointer}
.lvl-lp-hit.is-lit{fill:var(--lvl-green);opacity:.12}
.lvl-hg-lit{fill:var(--lvl-green);opacity:.10;pointer-events:none}

.lvl-wg-link{fill:none;stroke:var(--lvl-mut-2);stroke-width:1;opacity:.75}
.lvl-wg-link.is-driving{stroke:var(--lvl-risk);stroke-width:1.5;opacity:1}
.lvl-wg-linkd{fill:var(--lvl-mut-2)}
.lvl-wg-linkd.is-driving{fill:var(--lvl-risk)}
.lvl-lg-k{width:12px;height:0;border-top:1px solid var(--lvl-mut-2)}
.lvl-lg-k.is-driving{border-top:1.5px solid var(--lvl-risk)}
.lvl-wg-row.is-rel .lvl-lg-l{fill:var(--lvl-ink);font-weight:600}
.lvl-wg-row.is-rel .lvl-tl-zebra{fill:var(--lvl-wash)}

/* ══ THE SPLIT: gantt beside the decision rail ════════════════════════════ */
.lvl-split{display:grid;grid-template-columns:minmax(0,1fr) 322px;gap:14px;align-items:start}
.lvl-split-main{min-width:0}
.lvl-side{position:sticky;top:8px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);
  background:var(--lvl-card);max-height:calc(100vh - 40px);overflow-y:auto}
@media (max-width:1240px){.lvl-split{grid-template-columns:1fr}.lvl-side{position:static;max-height:none}}
.lvl-side-empty{padding:26px 18px;text-align:center;color:var(--lvl-mut)}
.lvl-side-empty b{display:block;font:700 13px/1.4 var(--lvl-font);color:var(--lvl-ink);margin:8px 0 6px}
.lvl-side-empty p{font-size:11.5px;line-height:1.55;margin:0 0 8px}
.lvl-rl-h{padding:12px 14px;border-bottom:1px solid var(--lvl-line);background:var(--lvl-wash)}
.lvl-rl-h>b{display:block;font:700 13px/1.35 var(--lvl-font)}
.lvl-rl-h>em{display:block;font-style:normal;font:500 10px/1.3 var(--lvl-mono);color:var(--lvl-mut-2);margin-top:2px}
.lvl-rl-d{display:grid;gap:5px;margin-top:9px}
.lvl-rl-d span{display:flex;gap:8px;font-size:11px;color:var(--lvl-ink-2)}
.lvl-rl-d i{flex:0 0 66px;font-style:normal;font:700 8.5px/1.5 var(--lvl-mono);letter-spacing:.08em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-rl-nudge{display:flex;align-items:center;gap:4px;margin-top:11px;flex-wrap:wrap}
.lvl-rl-nudge .lvl-btn{min-width:30px;padding:0 6px}
.lvl-rl-date{flex:1 1 100%;margin-top:5px}
.lvl-wb-shift{min-width:44px;text-align:center;font:800 12px/1 var(--lvl-mono);color:var(--lvl-green-d)}
.lvl-rl-s{padding:12px 14px;border-bottom:1px solid var(--lvl-line)}
.lvl-rl-s:last-child{border-bottom:0}
.lvl-rl-s.is-live{background:var(--lvl-green-t)}
.lvl-rl-s h5{display:flex;align-items:baseline;gap:6px;margin:0 0 9px;font:700 11px/1.3 var(--lvl-font)}
.lvl-rl-s h5 small{font-weight:500;font-size:10px;color:var(--lvl-mut-2)}
.lvl-rl-s h5 u{margin-left:auto;text-decoration:none;font:800 9.5px/1 var(--lvl-mono);color:var(--lvl-ok);
  background:var(--lvl-ok-t);padding:3px 6px;border-radius:3px}
.lvl-rl-s h5 u.is-hold{color:var(--lvl-mut);background:var(--lvl-line-2)}
.lvl-rl-s .lvl-note{margin:8px 0 0;font-size:10.5px;line-height:1.5}
.lvl-rl-cur{margin:7px 0 0;font:600 11px/1.4 var(--lvl-mono);color:var(--lvl-ink-2)}
.lvl-rl-g{display:grid;gap:6px}
.lvl-rl-a{display:flex;gap:7px;margin-top:10px}
.lvl-rl-a .lvl-btn{flex:1}

/* ══ SHIFT EXPLORER ═══════════════════════════════════════════════════════ */
.lvl-sx-wrap{margin:0 -2px}
.lvl-sx-fill{fill:var(--lvl-green);opacity:.13}
.lvl-sx-line{fill:none;stroke:var(--lvl-green-d);stroke-width:1.8;stroke-linejoin:round}
.lvl-sx-nowline{stroke:var(--lvl-mut-2);stroke-width:1;stroke-dasharray:3 3;opacity:.7}
.lvl-sx-zone{fill:var(--lvl-risk);opacity:.05}
.lvl-sx-zero{stroke:var(--lvl-ink);stroke-width:1.2}
.lvl-sx-rule{stroke:var(--lvl-mut-2);stroke-width:1;stroke-dasharray:2 3}
.lvl-sx-rule.is-tf{stroke:var(--lvl-risk)}
.lvl-sx-rt{font:800 8px/1 var(--lvl-mono);fill:var(--lvl-mut-2)}
.lvl-sx-rt.is-tf{fill:var(--lvl-risk)}
.lvl-sx-p{fill:var(--lvl-mut-2);stroke:var(--lvl-card);stroke-width:1}
.lvl-sx-p.is-good{fill:var(--lvl-ok)}
.lvl-sx-p.is-bad{fill:var(--lvl-risk)}
.lvl-sx-p.is-now{fill:var(--lvl-ink);stroke-width:1.5}
.lvl-sx-p.is-best{fill:var(--lvl-ok);stroke:var(--lvl-ok);stroke-width:2.5;fill-opacity:1}
.lvl-sx-p.is-blocked{fill:var(--lvl-line-3);stroke-dasharray:1 1}
.lvl-sx-hit{fill:transparent;cursor:pointer}
.lvl-sx-hit:hover{fill:var(--lvl-green);fill-opacity:.08}
.lvl-sx-bl{font:800 9px/1 var(--lvl-mono);fill:var(--lvl-ok)}
.lvl-sx-empty{padding:16px 12px;font-size:11px;line-height:1.5;color:var(--lvl-mut);
  border:1px dashed var(--lvl-line-3);border-radius:var(--lvl-r-xs);text-align:center}

/* ══ CREW METERS ══════════════════════════════════════════════════════════ */
.lvl-mtr{display:grid;gap:7px}
.lvl-mtr-r{display:grid;grid-template-columns:1fr 74px 42px 60px;align-items:center;gap:7px}
.lvl-mtr-n{display:flex;align-items:center;gap:5px;font-size:10.5px;color:var(--lvl-ink-2);min-width:0}
.lvl-mtr-n i{width:7px;height:7px;border-radius:2px;flex:0 0 auto}
.lvl-mtr-n{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-mtr-t{position:relative;height:7px;border-radius:4px;background:var(--lvl-line-2);overflow:visible}
.lvl-mtr-t u{position:absolute;left:0;top:0;height:100%;border-radius:4px;background:var(--lvl-ok);display:block}
.lvl-mtr-t s{position:absolute;top:0;height:100%;background:var(--lvl-risk);border-radius:0 4px 4px 0;display:block}
.lvl-mtr-t b{position:absolute;top:-2px;width:2px;height:11px;background:var(--lvl-before);border-radius:1px}
.lvl-mtr-r.is-high .lvl-mtr-t u{background:var(--lvl-warn)}
.lvl-mtr-r.is-over .lvl-mtr-t u{background:var(--lvl-risk)}
.lvl-mtr-r.is-none .lvl-mtr-t{background:repeating-linear-gradient(90deg,var(--lvl-line-2) 0 3px,transparent 3px 6px)}
.lvl-mtr-v{font:700 10.5px/1 var(--lvl-mono);text-align:right}
.lvl-mtr-v i{font-style:normal;font-size:8.5px;color:var(--lvl-mut-2)}
.lvl-mtr-c{font:600 9.5px/1 var(--lvl-mono);color:var(--lvl-mut);text-align:right}
.lvl-mtr-c em{font-style:normal;display:block;margin-top:2px;color:var(--lvl-ok)}
.lvl-mtr-r.is-over .lvl-mtr-c{color:var(--lvl-risk)}

/* ══ ONE PERIOD, OPENED ═══════════════════════════════════════════════════ */
.lvl-pp{position:absolute;left:12px;right:12px;bottom:12px;z-index:6;max-height:52%;overflow:auto;
  border:1px solid var(--lvl-green);border-radius:var(--lvl-r-s);background:var(--lvl-card);
  box-shadow:var(--lvl-sh-2)}
.lvl-pp-h{display:flex;align-items:center;gap:10px;flex-wrap:wrap;padding:9px 12px;background:var(--lvl-green-t)}
.lvl-pp-h b{font:700 12.5px/1.3 var(--lvl-font)}
.lvl-pp-h em{font-style:normal;font-size:11px;color:var(--lvl-mut)}
.lvl-pp-h .lvl-btn{margin-left:auto}
.lvl-pp .lvl-tbl-wrap{border:0;border-radius:0}

/* ══ QUICK ACTIONS (in the rail) ══════════════════════════════════════════ */
.lvl-qa.is-empty{display:flex;align-items:flex-start;gap:8px;font-size:11px;line-height:1.5;color:var(--lvl-mut)}
.lvl-qa-g{display:grid;gap:7px}
.lvl-qa-c{display:block;width:100%;text-align:left;border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-xs);
  background:var(--lvl-card);padding:8px 10px;cursor:pointer;font:inherit;color:inherit;
  transition:border-color .12s,background .12s}
.lvl-qa-c:hover{border-color:var(--lvl-green);background:var(--lvl-green-t)}
.lvl-qa-c.is-on{border-color:var(--lvl-green);background:var(--lvl-green-t);box-shadow:inset 2px 0 0 var(--lvl-green)}
.lvl-qa-c.is-best{border-left:2.5px solid var(--lvl-ok)}
.lvl-qa-c.is-warn{border-left:2.5px solid var(--lvl-warn)}
.lvl-qa-c.is-best.is-warn{border-left-color:var(--lvl-ok)}
.lvl-qa-t{display:block;font:600 11px/1.35 var(--lvl-font)}
.lvl-qa-t i{font-style:normal;font-size:8px;font-weight:800;letter-spacing:.08em;text-transform:uppercase;
  color:var(--lvl-ok);background:var(--lvl-ok-t);padding:2px 4px;border-radius:3px;margin-left:5px;vertical-align:1px}
.lvl-qa-r{display:grid;grid-template-columns:repeat(4,1fr);gap:4px;margin-top:6px}
.lvl-qa-r u{display:block;text-decoration:none;font:800 10.5px/1 var(--lvl-mono)}
.lvl-qa-r i{display:block;font-style:normal;font-size:8px;color:var(--lvl-mut-2);margin-top:2px}
.lvl-qa-w{display:inline-block;margin-top:6px;font:700 8.5px/1 var(--lvl-mono);color:var(--lvl-warn);
  background:var(--lvl-warn-t);padding:3px 5px;border-radius:3px}
.lvl-qa-w.is-bad{color:var(--lvl-risk);background:var(--lvl-risk-t)}

/* ══ WORKBENCH (whole-programme) ══════════════════════════════════════════ */
.lvl-wb-top{margin-bottom:16px}
.lvl-wb-top-h{display:flex;align-items:baseline;gap:12px;margin-bottom:8px}
.lvl-wb-top-h h4{margin:0}
.lvl-wb-top-h>span{margin-left:auto}
.lvl-wb-sel{margin-top:16px;border:1px solid var(--lvl-green);border-radius:var(--lvl-r-s);overflow:hidden}
.lvl-wb-sel .lvl-wb-bar{margin:0;border:0;border-bottom:1px solid var(--lvl-line);border-radius:0;background:var(--lvl-green-t)}
.lvl-wb-sel .lvl-live{border:0;border-radius:0}
.lvl-wb-who{flex:1 1 260px;min-width:0}
.lvl-wb-who b{display:block;font:700 13px/1.3 var(--lvl-font)}
.lvl-wb-who em{display:block;font-style:normal;font-size:11px;color:var(--lvl-mut);margin-top:2px}
.lvl-arrow{font-style:normal;color:var(--lvl-mut-2);margin:0 4px}
.lvl-mono{font-family:var(--lvl-mono);font-size:11px}

/* ── THE CHROME GETS OUT OF THE WAY ON A SHORT SCREEN ──────────────────
   On a 1280x720 laptop the page header, the section rail and the master bar
   were 190px — a quarter of the screen spent before any data. Gated on a
   media query rather than on the measured height, because the measurement
   reads this chrome and a rule that changed it would chase its own tail. */
@media (max-height:860px){
  .lvl-ws-tb{gap:8px;padding:4px 10px}
  .lvl-tb-btn,.lvl-ws-tb .lvl-sel-s,.lvl-ws-tb .lvl-seg-b{height:26px}
  .lvl-tog{height:26px}
  .lvl-ws-foot{padding:2px 10px;gap:10px}
  .lvl-ws-mini-w,.lvl-ws-mini{height:20px}
  .lvl.is-ws .lvl-top{padding:8px 18px}
  .lvl.is-ws .lvl-title p,.lvl.is-ws .lvl-crumbs{display:none}
  .lvl.is-ws .lvl-title h1{font-size:15px}
  .lvl.is-ws .lvl-rail{padding:4px 18px}
  .lvl.is-ws .lvl-rail-b{padding:5px 9px}
  .lvl.is-ws .lvl-state{padding:7px 18px}
  .lvl.is-ws .lvl-state em{display:none}
}
@media (max-height:760px){
  .lvl.is-ws .lvl-rail-b span{display:none}
  .lvl.is-ws .lvl-rail-b{padding:5px 8px;gap:5px}
}

/* ── A LABEL COLUMN THAT CAN BE READ ──────────────────────────────────
   "WBS-100-A General Clearance" in 120px is "WBS-100-A Genera". The code is
   worth its width on a wide screen and not on a narrow one — the indent
   already carries the level, and the full string stays in the row's title. */
@media (max-width:1560px){
  .lvl-gtr.is-wbs .c-name b{display:none}
}
@media (max-width:1300px){
  .lvl-gt-colh,.lvl-gtr{grid-template-columns:minmax(0,1fr) 28px 40px}
  .lvl-gt-colh{font-size:8.5px}
}

/* the histogram's caption is worth 55px of a 900px screen and not of a 720px
   one — the chart is the point, the sentence is the footnote */
@media (max-height:820px){
  .lvl-hg-sub{display:none}
  .lvl-ws-key{font-size:9.5px;gap:7px}
}

/* ══ THE WORKSPACE'S ONE HEADER ROW ═══════════════════════════════════════
   Three stacked bars — title, 01→08 rail, master/simulation state — were
   176px of furniture before the programme started, on the one view where
   every pixel is the programme. One 42px row carries all three jobs. */
.lvl-hdr1{display:flex;align-items:center;gap:12px;padding:5px 14px;min-height:42px;flex-wrap:nowrap;
  background:var(--lvl-card);border-bottom:1px solid var(--lvl-line);position:sticky;top:0;z-index:30}
/* the actions never shrink — Apply and Generate are the point of the row —
   so the state chip is the one that gives ground, and the nav drops its
   labels before either of them is squeezed */
.lvl-hdr1-a{flex:0 0 auto}
.lvl-hdr1-nav{flex:0 0 auto;min-width:0}
.lvl-hdr1-st{flex:1 1 0;min-width:0}
.lvl-hdr1-nav{display:flex;align-items:center;gap:2px;flex:0 0 auto}
.lvl-hdr1-b{display:inline-flex;align-items:center;gap:5px;height:28px;padding:0 8px;border:1px solid transparent;
  border-radius:var(--lvl-r-xs);background:none;cursor:pointer;color:var(--lvl-mut);
  font:600 11.5px/1 var(--lvl-font);white-space:nowrap}
.lvl-hdr1-b:hover{background:var(--lvl-wash);color:var(--lvl-ink)}
.lvl-hdr1-b.is-on{background:var(--lvl-green-t);border-color:rgba(36,180,126,.32);color:var(--lvl-green-d)}
.lvl-hdr1-b em{font-style:normal;font:800 9px/1 var(--lvl-mono);padding:2px 4px;border-radius:8px;
  background:var(--lvl-line-2);color:var(--lvl-mut)}
.lvl-hdr1-b.is-on em{background:var(--lvl-green);color:#fff}
.lvl-hdr1-st{display:flex;align-items:center;gap:8px;min-width:0;flex:1 1 auto;
  font:500 11px/1 var(--lvl-font);color:var(--lvl-mut);overflow:hidden;white-space:nowrap;text-overflow:ellipsis}
.lvl-hdr1-st b{flex:0 0 auto;padding:3px 7px;border-radius:99px;font:800 8.5px/1 var(--lvl-mono);letter-spacing:.09em}
.lvl-hdr1-st.is-live b{background:var(--lvl-line-2);color:var(--lvl-mut)}
.lvl-hdr1-st.is-sim b{background:var(--lvl-warn);color:#fff}
.lvl-hdr1-st.is-sim{color:var(--lvl-ink);font-weight:700}
.lvl-hdr1-st u{text-decoration:none;font:600 10px/1 var(--lvl-mono);color:var(--lvl-mut-2);flex:0 1 auto;overflow:hidden;text-overflow:ellipsis}
.lvl-hdr1-a{display:flex;align-items:center;gap:6px;margin-left:auto;flex:0 0 auto}
.lvl-hdr1-a .lvl-tb-btn{height:28px;padding:0 8px}
.lvl-btn.is-sm{height:28px;padding:0 11px;font-size:11.5px}
/* the workspace is the whole panel now — no page chrome above it to allow for */
.lvl.is-ws .lvl-foot{display:none}
/* Keyed at 1720px, not 1400: the constraint is the PANEL, and the app shell
   takes ~300px of the viewport before the panel starts. At 1600 the labelled
   nav plus the state chip plus the actions overflowed and Generate was clipped
   off the right edge. */
@media (max-width:1720px){
  .lvl-hdr1-b span{display:none}
  .lvl-hdr1-b{padding:0 7px}
}

/* the two heat axes and their crossing, in the legend — an encoding nobody
   can name is decoration */
.lvl-ws-key .k-hv{width:44px;background:linear-gradient(90deg,#FDEFEC,#F6CAC1,#F0AFA2,#E88E7E)}
.lvl-ws-key .k-ha{width:44px;background:linear-gradient(90deg,#FFF1D0,#FDC873,#F4862E,#C63E16)}
.lvl-ws-key .k-hx{background:#9E2411}
.lvl-ws-key b{font:700 10px/1 var(--lvl-font);color:var(--lvl-ink)}

/* the right-hand end of the toolbar carries the two things a planner checks
   first — how many periods are over, and whether a filter is on. When the row
   scrolls they must not scroll away with it. */
.lvl-tbg.is-end{padding-left:10px}
/* MULTIPLY DARKENS, WHICH IS THE POINT ON A LIGHT SURFACE AND WRONG ON A DARK
   ONE — two washes multiplied over #101A2B go to black and the crossing
   disappears into the background. Screen is the dual: it lightens, so the
   crossing is still the brightest thing where the two axes meet. */
/* ON A DARK SURFACE the same ramp reads as a light block. Stepped for #101A2B
   instead: it climbs INTO the warm hues from the surface rather than down from
   white, and lightness still moves monotonically across the ramp. */
/* ON A DARK SURFACE the same ramps read as a light block, so both are stepped
   again for #101A2B: they climb INTO the warm hues from the surface rather
   than down from white, and lightness still moves monotonically.

   KEYED ON THE APP'S OWN THEME ATTRIBUTE, never on `prefers-color-scheme`.
   This app does not follow the OS: it switches on `body[data-gantt-theme]`.
   A bare media query meant that on a machine whose OS was dark but whose app
   was light, THIS BLOCK ALONE flipped — dark-mode fills painted across a
   white page, and the whole plot came out brown. Nothing in this stylesheet
   may key on the OS preference while the rest of it keys on the attribute. */
  body[data-gantt-theme="dark"] .lvl-cell.is-f1{fill:#3A2E1C}
  body[data-gantt-theme="dark"] .lvl-cell.is-f2{fill:#4E3A1E}
  body[data-gantt-theme="dark"] .lvl-cell.is-f3{fill:#654721}
  body[data-gantt-theme="dark"] .lvl-cell.is-f4{fill:#7E5423}
  body[data-gantt-theme="dark"] .lvl-cell.is-f5{fill:#985E22}
  body[data-gantt-theme="dark"] .lvl-cell.is-f6{fill:#B3641F}
  body[data-gantt-theme="dark"] .lvl-cell.is-f7{fill:#CE651B}
  body[data-gantt-theme="dark"] .lvl-cell.is-f8{fill:#E86416}
  body[data-gantt-theme="dark"] .lvl-cell.is-v.is-f1{fill:#2A1D1C}
  body[data-gantt-theme="dark"] .lvl-cell.is-v.is-f2{fill:#37231F}
  body[data-gantt-theme="dark"] .lvl-cell.is-v.is-f3{fill:#472922}
  body[data-gantt-theme="dark"] .lvl-cell.is-v.is-f4{fill:#582F26}
  body[data-gantt-theme="dark"] .lvl-cell.is-v.is-f5{fill:#6B3529}
  body[data-gantt-theme="dark"] .lvl-cell.is-v.is-f6{fill:#7F3B2C}
  body[data-gantt-theme="dark"] .lvl-cell.is-v.is-f7{fill:#93412F}
  body[data-gantt-theme="dark"] .lvl-cell.is-v.is-f8{fill:#A84732}


/* ── THE WORKFLOW, AS A STRIP ─────────────────────────────────────────
   Six steps, left to right, the one you are on lit. It replaces a 70px band
   of five cards with a sentence each that said the same thing on every view
   forever; the sentences are titles now and each step is still the button
   that takes you there. */
.lvl-flow{display:flex;align-items:center;gap:2px;margin:0;padding:0 14px;list-style:none;
  height:30px;background:var(--lvl-card);border-bottom:1px solid var(--lvl-line);
  position:sticky;top:42px;z-index:29;overflow-x:auto;scrollbar-width:none}
.lvl-flow::-webkit-scrollbar{display:none}
.lvl-flow-s{display:inline-flex;align-items:center;gap:6px;flex:0 0 auto;height:22px;padding:0 9px 0 6px;
  border-radius:99px;cursor:pointer;font:600 10.5px/1 var(--lvl-font);color:var(--lvl-mut-2);white-space:nowrap}
.lvl-flow-s:hover{background:var(--lvl-wash);color:var(--lvl-ink-2)}
.lvl-flow-s i{display:inline-flex;align-items:center;justify-content:center;width:15px;height:15px;border-radius:50%;
  font-style:normal;font:800 8.5px/1 var(--lvl-mono);background:var(--lvl-line-2);color:var(--lvl-mut-2)}
.lvl-flow-s.is-done{color:var(--lvl-mut)}
.lvl-flow-s.is-done i{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-flow-s.is-now{background:var(--lvl-green-t);color:var(--lvl-green-d);font-weight:700}
.lvl-flow-s.is-now i{background:var(--lvl-green);color:#fff}
.lvl-flow-s+.lvl-flow-s::before{content:"";width:10px;height:1px;background:var(--lvl-line-3);margin-right:4px}
/* search, on the one header row that survived */
.lvl-hdr1-q{display:flex;align-items:center;gap:5px;height:28px;padding:0 9px;border-radius:99px;
  border:1px solid var(--lvl-line-3);background:var(--lvl-card);color:var(--lvl-mut-2);max-width:210px}
.lvl-hdr1-q input{border:0;background:none;outline:0;min-width:0;width:100%;
  font:500 11.5px/1 var(--lvl-font);color:var(--lvl-ink)}
.lvl-hdr1-q:focus-within{border-color:var(--lvl-green)}
@media (max-width:1180px){.lvl-hdr1-q{display:none}}

/* ── A PAGE OF SECTIONS, NOT A STACK OF CARDS ─────────────────────────
   The Control Centre was 3014px of ten cards with identical weight, so a
   planner scrolling it had no way to tell the diagnosis from a detail. A
   section head is the one thing that was missing: it groups the cards under
   it, numbers the reading order, and gives the page a rhythm the cards
   themselves cannot. */
.lvl-sec{display:flex;flex-direction:column;gap:10px}
.lvl-sec+.lvl-sec{margin-top:8px}
.lvl-sec-h{display:flex;align-items:baseline;gap:10px;padding:2px 2px 0}
.lvl-sec-h h2{margin:0;font:800 13px/1.2 var(--lvl-head);letter-spacing:-.01em;color:var(--lvl-ink)}
.lvl-sec-h i{font-style:normal;font:800 9px/1 var(--lvl-mono);letter-spacing:.1em;color:var(--lvl-mut-2);
  background:var(--lvl-line-2);padding:4px 6px;border-radius:4px}
.lvl-sec-h p{margin:0;flex:1;font-size:11px;line-height:1.45;color:var(--lvl-mut)}
.lvl-sec-h .lvl-btn{flex:0 0 auto;align-self:center}

/* ── THE KPI STRIP GETS A PRIORITY ────────────────────────────────────
   Eight equal tiles gave "143 overload days" and "levelling state: none" the
   same weight. The lead tiles are the diagnosis and read at a glance; the
   rest are context and sit at two-thirds the size. */
.lvl-kpis.is-lead{grid-template-columns:repeat(auto-fit,minmax(190px,1fr))}
.lvl-kpis.is-lead .lvl-kpi{padding:13px 15px 12px}
.lvl-kpis.is-lead .lvl-kpi-v{font-size:26px}
.lvl-kpis.is-lead .lvl-kpi-l{font-size:9px}
.lvl-kpis.is-rest{grid-template-columns:repeat(auto-fit,minmax(132px,1fr));margin-top:-2px}
.lvl-kpis.is-rest .lvl-kpi{padding:8px 11px 7px}
.lvl-kpis.is-rest .lvl-kpi-v{font-size:15px}
.lvl-kpis.is-rest .lvl-kpi-s{font-size:9.5px}

/* ── THE RULES OF THE RUN ─────────────────────────────────────────────
   Mode, strategy, the finish, the target date, milestones, crew limits and
   existing pins — every one of them was already stored and every one was
   invisible until the setup drawer was opened, so the Control Centre showed
   a result and never the rules that produced it. */
/* the dividers ride the tiles, not the grid gaps — a gap-coloured grid shows
   a grey slab wherever the last row is short of a full set */
/* ══ THE BRIEF IS NINE FACTS YOU SCAN ═══════════════════════════════════
   Nine rules stacked full-width, each with a value and a sentence, was 900px
   of prose down half a board whose whole job is to let a planner check in ONE
   LOOK what the run is being asked to do. A card each, in a grid, sized so a
   column of them is read the way a dashboard is read rather than the way a
   contract is. The sentence is kept for the ones whose answer needs it and
   goes to the title on the rest.
   ═══════════════════════════════════════════════════════════════════════ */
.lvl-rules{display:grid;grid-template-columns:repeat(auto-fit,minmax(158px,1fr));gap:var(--lvl-sp-2);
  background:none;border:0;border-radius:0;overflow:visible}
.lvl-rule{position:relative;display:flex;flex-direction:column;gap:3px;width:100%;
  text-align:left;font:inherit;cursor:pointer;
  background:var(--lvl-card);border:1px solid var(--lvl-line);border-radius:var(--lvl-r);
  border-top:3px solid var(--lvl-line-3);box-shadow:var(--lvl-sh);
  padding:10px 12px 11px;transition:border-color .12s ease,box-shadow .12s ease}
.lvl-rule:hover{border-color:var(--lvl-mut-2);box-shadow:var(--lvl-sh-2)}
.lvl-rule-g{position:absolute;right:8px;top:10px;display:flex;color:var(--lvl-mut-2);
  opacity:0;transition:opacity .12s}
.lvl-rule:hover .lvl-rule-g{opacity:1}
.lvl-rule-l{display:block;font:700 var(--lvl-t-1)/1.2 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.1em;text-transform:uppercase;color:var(--lvl-mut-2);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis;padding-right:12px}
.lvl-rule-v{display:block;font:800 var(--lvl-t-5)/1.2 var(--lvl-head);color:var(--lvl-ink)}
/* two lines, reserved — so a grid of them lines up instead of stepping */
.lvl-rule-n{display:-webkit-box;-webkit-box-orient:vertical;-webkit-line-clamp:2;line-clamp:2;
  overflow:hidden;font-style:normal;font:500 var(--lvl-t-2)/1.35 var(--lvl-font);
  color:var(--lvl-mut);min-height:calc(var(--lvl-t-2) * 1.35 * 2)}
.lvl-rule.is-ok{border-top-color:var(--lvl-ok)}
.lvl-rule.is-idle{border-top-color:var(--lvl-line-2)}
.lvl-rule.is-ok .lvl-rule-v{color:var(--lvl-ok)}
.lvl-rule.is-warn{border-top-color:var(--lvl-warn)}
.lvl-rule.is-warn .lvl-rule-v{color:var(--lvl-warn)}
.lvl-rule.is-risk{border-top-color:var(--lvl-risk)}
.lvl-rule.is-risk .lvl-rule-v{color:var(--lvl-risk)}
.lvl-rule.is-idle .lvl-rule-v{color:var(--lvl-mut-2);font-weight:700}

/* ── BEFORE → AFTER, AS CARDS ─────────────────────────────────────────
   Six questions with six answers: how long, when it ends, how many bars
   moved, how many people at the peak, how many days break a limit, and
   whether the critical path changed. The ten-row table is still underneath
   for everything else — it is just no longer the first thing on the page. */
/* the six numbers that decide a run, on the same cards as everything else
   the page states a number on — a bordered cell in a grid read as a table,
   which is not what six competing answers are */
.lvl-ba-cards{display:grid;grid-template-columns:repeat(auto-fit,minmax(212px,1fr));gap:var(--lvl-sp-2)}
.lvl-ba-c{border:1px solid var(--lvl-line);border-top:3px solid var(--lvl-line-3);
  border-radius:var(--lvl-r);padding:11px 13px 12px;background:var(--lvl-card);
  box-shadow:var(--lvl-sh)}
.lvl-ba-l{display:block;font:700 var(--lvl-t-1)/1.2 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.1em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-ba-p{display:flex;align-items:baseline;gap:7px;margin-top:6px;flex-wrap:wrap}
.lvl-ba-p b{font:700 var(--lvl-t-5)/1.15 var(--lvl-mono);color:var(--lvl-mut-2)}
.lvl-ba-p i{font-style:normal;font-size:var(--lvl-t-3);color:var(--lvl-mut-2)}
.lvl-ba-p u{text-decoration:none;font:800 24px/1.1 var(--lvl-mono);letter-spacing:-.02em;color:var(--lvl-ink)}
.lvl-ba-c>em{display:block;font-style:normal;font-size:10.5px;line-height:1.4;color:var(--lvl-mut);margin-top:4px}
.lvl-ba-c.is-good{border-left-color:var(--lvl-ok)}
.lvl-ba-c.is-good .lvl-ba-p u,.lvl-ba-c.is-good>em{color:var(--lvl-ok)}
.lvl-ba-c.is-bad{border-left-color:var(--lvl-risk)}
.lvl-ba-c.is-bad .lvl-ba-p u,.lvl-ba-c.is-bad>em{color:var(--lvl-risk)}
.lvl-ba-c.is-info{border-left-color:var(--lvl-info)}
.lvl-ba-c.is-info .lvl-ba-p u{color:var(--lvl-info)}
.lvl-ba-c.is-flat{border-left-color:var(--lvl-line-3)}
/* the full table, kept but folded away */
.lvl-more-d>summary{cursor:pointer;padding:9px 12px;border:1px dashed var(--lvl-line-3);border-radius:var(--lvl-r-s);
  font:600 11px/1 var(--lvl-font);color:var(--lvl-mut);background:var(--lvl-card);list-style:none}
.lvl-more-d>summary::-webkit-details-marker{display:none}
.lvl-more-d>summary::before{content:"\25B8  ";color:var(--lvl-mut-2)}
.lvl-more-d[open]>summary::before{content:"\25BE  "}
.lvl-more-d>summary:hover{border-color:var(--lvl-green);color:var(--lvl-ink)}
.lvl-more-d[open]>summary{margin-bottom:9px}

/* ══ THE LEVELLING BRIEF ═══════════════════════════════════════════════
   Measured, then rebuilt: the first version was 2,057 characters of prose
   for 15 controls, zero charts in a panel whose subject is a shape, and
   1,431px of content in an 836px window. Two questions now, both of them
   pictures, and the prose lives in title attributes. */
.lvl-drawer.is-brief{width:min(560px,96vw)}
.lvl-drawer.is-brief .lvl-drawer-b{padding:14px 16px 16px;display:flex;flex-direction:column;gap:0}
/* a question label — the whole structure of the panel, in 20px */
.lvl-q{display:flex;align-items:baseline;gap:9px;margin:16px 0 7px;flex:0 0 auto}
.lvl-drawer.is-brief .lvl-brief-say{margin-top:auto}
.lvl-q:first-child{margin-top:0}
.lvl-q>span{font:800 9.5px/1 var(--lvl-font);letter-spacing:.1em;text-transform:uppercase;color:var(--lvl-ink-2)}
.lvl-q>em{font-style:normal;font-size:10px;color:var(--lvl-mut-2);flex:1;min-width:0}
/* ── the two paths, each drawing its own question ── */
.lvl-paths{display:grid;grid-template-columns:1fr 1fr;gap:9px}
.lvl-path{display:block;width:100%;text-align:left;padding:10px 11px 11px;cursor:pointer;font:inherit;color:inherit;
  border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-s);background:var(--lvl-card);
  transition:border-color .12s,background .12s,box-shadow .12s}
.lvl-path:hover{border-color:var(--lvl-mut-2);background:var(--lvl-wash)}
.lvl-path.is-on{border-color:var(--lvl-green);background:var(--lvl-green-t);
  box-shadow:inset 0 0 0 1px rgba(36,180,126,.35)}
.lvl-path b{display:block;font:700 12px/1.25 var(--lvl-font);color:var(--lvl-ink);margin-top:8px}
.lvl-path em{display:block;font-style:normal;font:500 10.5px/1.35 var(--lvl-font);color:var(--lvl-mut);margin-top:3px}
.lvl-path em b{display:inline;font:800 12px/1 var(--lvl-mono)}
.lvl-path em.is-bad{color:var(--lvl-risk)}
.lvl-path em.is-bad b{color:var(--lvl-risk)}
.lvl-path em.is-ok{color:var(--lvl-ok)}
.lvl-path em.is-ok b{color:var(--lvl-ok)}
.lvl-path-art{display:block;width:100%;height:46px}
.lvl-path-art .a-now{fill:none;stroke:var(--lvl-green);stroke-width:2;stroke-linejoin:round}
.lvl-path-art .a-ideal{fill:none;stroke:var(--lvl-mut-2);stroke-width:1.4;stroke-dasharray:3 3}
.lvl-path-art .a-bar{fill:var(--lvl-line-3)}
.lvl-path-art .a-bar.is-over{fill:var(--lvl-risk)}
.lvl-path-art .a-cap{stroke:var(--lvl-mut-2);stroke-width:1.2;stroke-dasharray:3 2}
.lvl-path.is-on .lvl-path-art .a-bar{fill:var(--lvl-mut-2)}
.lvl-path.is-on .lvl-path-art .a-bar.is-over{fill:var(--lvl-risk)}
/* ── everything else is a chip on a row ── */
.lvl-row{display:flex;align-items:center;gap:7px;flex-wrap:wrap}
.lvl-push{display:flex;align-items:center;gap:7px;flex-wrap:wrap}
.lvl-push-n{display:flex;align-items:center;gap:6px;margin-left:2px}
.lvl-push-n .lvl-num{width:58px}
.lvl-push-n span{font:600 10.5px/1 var(--lvl-font);color:var(--lvl-mut)}
.lvl-push-n.is-off{opacity:.4}
.lvl-inline{display:inline-flex;align-items:center;gap:5px}
.lvl-inline .lvl-num.is-tiny{width:46px}
.lvl-inline span{font:600 10.5px/1 var(--lvl-font);color:var(--lvl-mut)}
.lvl-hint{font-style:normal;font-size:10.5px;color:var(--lvl-mut-2);margin-left:auto}
.lvl-hint.is-ok{color:var(--lvl-ok)}
.lvl-hint.is-bad{color:var(--lvl-risk);font-weight:600}
.lvl-drawer.is-brief .lvl-chip{display:inline-flex;align-items:center;gap:5px;height:30px;padding:0 11px}
.lvl-drawer.is-brief .lvl-chip u{text-decoration:none;font:800 9px/1 var(--lvl-mono);
  background:var(--lvl-green);color:#fff;padding:2px 4px;border-radius:8px}
.lvl-chip.is-res{height:26px;padding:0 9px;font-size:11px}
.lvl-chip.is-res i{width:8px;height:8px;border-radius:2px;display:inline-block}
.lvl-ceilpick{display:flex;flex-wrap:wrap;gap:5px;margin-top:8px;padding:9px;border-radius:var(--lvl-r-s);
  background:var(--lvl-wash);border:1px solid var(--lvl-line-2)}
.lvl-brief-say{margin:18px 0 0;align-self:stretch;padding:11px 13px;border-radius:var(--lvl-r-s);background:var(--lvl-green-t);
  border:1px solid rgba(36,180,126,.3);font-size:11.5px;line-height:1.65;color:var(--lvl-ink-2)}
.lvl-brief-say b{color:var(--lvl-ink)}
.lvl-brief-say i{font-style:italic;color:var(--lvl-mut)}

/* the two overall goals — a rectangle beside a trapezoid says the difference
   faster than a sentence can */
.lvl-goals{display:grid;grid-template-columns:1fr 1fr;gap:8px}
.lvl-goal{display:block;width:100%;text-align:left;padding:9px 10px 10px;cursor:pointer;font:inherit;color:inherit;
  border:1px solid var(--lvl-line-3);border-radius:var(--lvl-r-s);background:var(--lvl-card)}
.lvl-goal:hover{border-color:var(--lvl-mut-2);background:var(--lvl-wash)}
.lvl-goal.is-on{border-color:var(--lvl-green);background:var(--lvl-green-t);
  box-shadow:inset 0 0 0 1px rgba(36,180,126,.35)}
.lvl-goal b{display:block;font:700 11.5px/1.2 var(--lvl-font);color:var(--lvl-ink);margin-top:6px}
.lvl-goal em{display:block;font-style:normal;font:500 10px/1.4 var(--lvl-font);color:var(--lvl-mut);margin-top:3px}
.lvl-goal-art{display:block;width:100%;height:30px}
.lvl-goal-art polyline{fill:none;stroke:var(--lvl-mut-2);stroke-width:1.8;stroke-linejoin:round}
.lvl-goal.is-on .lvl-goal-art polyline{stroke:var(--lvl-green)}
.lvl-ramps{margin-top:8px}
.lvl-ramps .lvl-inline span{min-width:0}
.lvl-ramps .lvl-inline>b{font:700 10.5px/1 var(--lvl-mono);color:var(--lvl-mut-2)}

/* ── WHICH TRADES ARE OVER, AND BY HOW MUCH ───────────────────────────
   "5 of 22 over their ceiling" is a count, and a count is not something a
   planner can act on. The next question is always WHICH. */
.lvl-ceils{margin-top:8px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);
  background:var(--lvl-card);overflow:hidden}
.lvl-ceils-h{display:flex;align-items:center;gap:7px;padding:7px 10px;background:var(--lvl-risk-t);
  font:700 9.5px/1 var(--lvl-font);letter-spacing:.06em;text-transform:uppercase;color:var(--lvl-risk)}
.lvl-ceils-h.is-ok{background:var(--lvl-ok-t);color:var(--lvl-ok);text-transform:none;letter-spacing:0;font-size:11px}
.lvl-ceils-h .lvl-link{margin-left:auto;font:700 10px/1 var(--lvl-font);text-transform:none;letter-spacing:0}
.lvl-ceil{display:flex;align-items:center;gap:8px;width:100%;padding:6px 10px;border:0;
  border-top:1px solid var(--lvl-line-2);background:var(--lvl-card);font:inherit;color:inherit;text-align:left;cursor:pointer}
.lvl-ceil[disabled]{cursor:default}
.lvl-ceil:not([disabled]):hover{background:var(--lvl-wash)}
.lvl-ceil-x{font-style:normal;font-size:12px;color:var(--lvl-mut-2);flex:0 0 auto}
.lvl-ceil.is-on .lvl-ceil-x{color:var(--lvl-green)}
.lvl-ceil-d{width:8px;height:8px;border-radius:2px;flex:0 0 auto}
.lvl-ceil-n{flex:0 0 96px;font:600 11px/1.2 var(--lvl-font);color:var(--lvl-ink-2);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-ceil-b{position:relative;flex:1;min-width:40px;height:7px;border-radius:4px;background:var(--lvl-line-2);overflow:hidden}
.lvl-ceil-b>i{position:absolute;left:0;top:0;bottom:0;background:var(--lvl-ok);border-radius:4px}
.lvl-ceil-b>u{position:absolute;top:-3px;bottom:-3px;width:2px;background:var(--lvl-ink);opacity:.85;border-radius:1px}
.lvl-ceil.is-over .lvl-ceil-b>i{background:var(--lvl-risk)}
.lvl-ceil-v{flex:0 0 auto;font:800 11px/1 var(--lvl-mono);color:var(--lvl-ink)}
.lvl-ceil-v em{font-style:normal;font-weight:600;color:var(--lvl-mut-2)}
.lvl-ceil-p{flex:0 0 42px;text-align:right;text-decoration:none;font:700 10px/1 var(--lvl-mono);color:var(--lvl-mut)}
.lvl-ceil.is-over .lvl-ceil-p{color:var(--lvl-risk)}
.lvl-ceil:not(.is-on):not([disabled]){opacity:.5}
.lvl-ceils-more{display:block;width:100%;padding:7px 10px;border:0;border-top:1px solid var(--lvl-line-2);
  background:var(--lvl-wash);cursor:pointer;font:600 10.5px/1 var(--lvl-font);color:var(--lvl-mut)}
.lvl-ceils-more:hover{color:var(--lvl-ink);background:var(--lvl-line-2)}

/* ══ THE LEVELLING RESULT, TRADE BY TRADE ═══════════════════════════════
   Same panel chrome as the curve match — one visual language, two objectives.
   Each block is a trade a planner can sign off on its own, so the block is
   the card and the approval sits inside it, not in a footer that applies to
   everything at once. */
/* ── THE PANEL IS FIXED TO THE VIEWPORT, NOT TO THE DOCUMENT ──────────
   .lvl-rp is position:absolute, which was right while it lived inside the
   workspace pane. This one is chrome — it is rendered beside the drawer so a
   run started from the Control Centre has somewhere to appear — and against
   an unpositioned ancestor "top:0;bottom:0" resolved to the whole DOCUMENT.
   On a long page that is a panel several thousand pixels tall with its header
   scrolled off the top, its footer somewhere below the fold, and no scrollbar
   of its own. Fixed to the viewport it is a panel again: header, a body that
   scrolls, actions on the bottom edge, all of it always in view. */
.lvl-rp.is-trades{position:fixed;top:0;right:0;bottom:0;left:auto;
  width:min(560px,44vw);height:auto;max-height:100vh;z-index:997;
  border-radius:0;box-shadow:-16px 0 48px rgba(20,32,42,.18)}
.lvl-rp.is-trades>.lvl-rp-h,
.lvl-rp.is-trades>.lvl-rp-a{flex:0 0 auto}
.lvl-rp.is-trades>.lvl-rp-b{flex:1 1 auto;min-height:0;overflow-y:auto;
  overscroll-behavior:contain;display:block;padding:10px}
.lvl-rp.is-trades>.lvl-rp-a{border-top:1px solid var(--lvl-line);background:var(--lvl-wash);
  padding:10px 12px;gap:8px}
.lvl-rp.is-trades.is-min{top:auto;bottom:0;right:0;width:min(560px,44vw);height:auto;
  max-height:none;border-radius:var(--lvl-r) var(--lvl-r) 0 0}
/* narrow screens: it takes the width it needs rather than half a panel */
@media (max-width:1100px){
  .lvl-rp.is-trades,.lvl-rp.is-trades.is-min{width:min(460px,94vw)}
}
.lvl-tp{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);background:var(--lvl-card);
  margin-bottom:8px;overflow:hidden}
.lvl-tp.is-clear{border-color:color-mix(in srgb,var(--lvl-ok) 45%,var(--lvl-line))}
.lvl-tp.is-over{border-color:color-mix(in srgb,var(--lvl-risk) 40%,var(--lvl-line))}
.lvl-tp.is-off{opacity:.45}
.lvl-tp-h{display:flex;align-items:center;gap:8px;padding:7px 9px;background:var(--lvl-wash);
  border-bottom:1px solid var(--lvl-line-2)}
.lvl-tp-d{width:9px;height:9px;border-radius:50%;flex:none}
.lvl-tp-n{font:700 12px/1 var(--lvl-font);color:var(--lvl-ink);flex:1 1 auto;
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-tp-pk{font:700 12px/1 var(--lvl-font-n,var(--lvl-font));color:var(--lvl-ink);
  display:inline-flex;align-items:baseline;gap:3px;flex:none}
.lvl-tp-pk i{font-style:normal;color:var(--lvl-mut);font-size:11px}
.lvl-tp-pk em{font-style:normal;font-weight:600;color:var(--lvl-mut);font-size:10.5px}
.lvl-tp-b{display:flex;align-items:flex-start;gap:10px;padding:9px}
/* before is the shape you are cutting down; after is the line you get */
.lvl-tp-spark{flex:none;border:1px solid var(--lvl-line-2);border-radius:5px;
  background:var(--lvl-wash);display:block}
.lvl-tp-spark .k-before{fill:var(--lvl-mut);opacity:.20;stroke:none}
.lvl-tp-spark .k-after{fill:none;stroke:var(--lvl-green);stroke-width:1.6;
  vector-effect:non-scaling-stroke;stroke-linejoin:round}
.lvl-tp-spark .k-cap{stroke:var(--lvl-risk);stroke-width:1.2;stroke-dasharray:4 3;
  vector-effect:non-scaling-stroke}
.lvl-tp.is-over .lvl-tp-spark .k-after,
.lvl-tp.is-pushed .lvl-tp-spark .k-after{stroke:var(--lvl-risk)}
.lvl-tp-w{flex:1 1 auto;min-width:0}
.lvl-tp-k{font:600 10.5px/1.4 var(--lvl-font);color:var(--lvl-mut);margin-bottom:3px}
.lvl-tp-l{list-style:none;margin:0;padding:0}
.lvl-tp-l li{font:500 11px/1.45 var(--lvl-font);color:var(--lvl-ink);
  display:flex;gap:6px;justify-content:space-between;padding:1px 0}
.lvl-tp-l li b{font-weight:600;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-tp-l li em{font-style:normal;color:var(--lvl-mut);font-size:10.5px;flex:none}
.lvl-tp-l li.is-more{color:var(--lvl-mut);font-size:10.5px}
.lvl-tp-no{display:flex;gap:6px;align-items:flex-start;
  font:500 11px/1.45 var(--lvl-font);color:var(--lvl-mut)}
.lvl-tp-alone{margin-top:6px;padding:6px 7px;border-radius:4px;
  background:color-mix(in srgb,var(--lvl-risk) 8%,transparent);
  border:1px solid color-mix(in srgb,var(--lvl-risk) 22%,transparent)}
.lvl-tp-alone span{display:block;font:500 10.5px/1.5 var(--lvl-font);color:var(--lvl-ink)}
.lvl-tp-alone b{font-weight:700}
.lvl-tp-a{display:flex;justify-content:flex-end;padding:0 9px 8px}

/* the finish date and its consequence, as one block */
.lvl-ends{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);
  background:var(--lvl-wash);padding:8px;margin-bottom:2px}
.lvl-ends-now{display:flex;align-items:baseline;gap:6px;margin-bottom:6px}
.lvl-ends-now span{font:600 10.5px/1 var(--lvl-font);color:var(--lvl-mut);
  text-transform:uppercase;letter-spacing:.04em}
.lvl-ends-now b{font:700 12.5px/1 var(--lvl-font);color:var(--lvl-ink)}
.lvl-ends .lvl-push{margin:0}
.lvl-ends-w{display:flex;align-items:center;gap:5px;margin-top:7px;padding-top:7px;
  border-top:1px dashed var(--lvl-line-2);font:500 11px/1.3 var(--lvl-font);color:var(--lvl-mut)}
.lvl-ends-w b{font-weight:700;color:var(--lvl-ink)}

/* the page holds still while an overlay is open — see portalOverlays() */
body.lvl-locked{overflow:hidden}

/* a trade this run pushed over is the loudest card in the panel */
.lvl-tp.is-pushed{border-color:var(--lvl-risk);
  box-shadow:0 0 0 1px color-mix(in srgb,var(--lvl-risk) 30%,transparent) inset}
.lvl-tp.is-pushed .lvl-tp-h{background:color-mix(in srgb,var(--lvl-risk) 10%,var(--lvl-wash))}

/* ══ THE IMPACT, AT THE TOP OF THE PROPOSAL ════════════════════════════
   A list of activities is the change. This is what the change DOES — the
   five numbers a planner is accountable for, before on the left and after on
   the right, with a bar for the one that has a proportion worth seeing. */
.lvl-tim{border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);
  background:var(--lvl-wash);padding:9px;margin-bottom:10px}
.lvl-tim-bar{position:relative;height:20px;border-radius:10px;overflow:hidden;
  background:color-mix(in srgb,var(--lvl-risk) 16%,var(--lvl-card));margin-bottom:9px}
.lvl-tim-bar>i{position:absolute;inset:0 auto 0 0;background:var(--lvl-green);
  border-radius:10px 0 0 10px;transition:width .18s ease}
.lvl-tim-bar>span{position:relative;display:block;text-align:center;
  font:700 10.5px/20px var(--lvl-font);color:var(--lvl-ink);
  text-shadow:0 0 3px color-mix(in srgb,var(--lvl-card) 70%,transparent)}
.lvl-tim-g{display:grid;grid-template-columns:repeat(auto-fit,minmax(96px,1fr));gap:1px;
  background:var(--lvl-line);border:1px solid var(--lvl-line);border-radius:5px;overflow:hidden}
.lvl-tim-c{background:var(--lvl-card);padding:6px 8px;min-width:0}
.lvl-tim-c>span{display:block;font:700 8.5px/1 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.08em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-tim-c>b{display:flex;align-items:baseline;gap:3px;margin-top:4px;
  font:800 12.5px/1.15 var(--lvl-font);color:var(--lvl-mut);flex-wrap:wrap}
.lvl-tim-c>b i{font-style:normal;font-size:10px;color:var(--lvl-mut-2)}
.lvl-tim-c>b u{text-decoration:none;color:var(--lvl-ink)}
.lvl-tim-c>em{display:block;font-style:normal;font-size:9.5px;color:var(--lvl-mut);margin-top:2px}
.lvl-tim-c.is-ok>b u{color:var(--lvl-ok)}
.lvl-tim-c.is-warn>b u{color:var(--lvl-warn,#B7791F)}
.lvl-tim-c.is-bad>b u{color:var(--lvl-risk)}

/* the trades the brief was never looking at */
.lvl-tp-out{border:1px solid var(--lvl-risk);border-radius:var(--lvl-r-s);
  background:color-mix(in srgb,var(--lvl-risk) 7%,var(--lvl-card));padding:9px;margin-top:4px}
.lvl-tp-out-h{display:flex;flex-wrap:wrap;align-items:baseline;gap:6px}
.lvl-tp-out-h b{font:700 11.5px/1.35 var(--lvl-font);color:var(--lvl-ink);flex:1 1 auto;min-width:0}
.lvl-tp-out-h em{font-style:normal;font-size:10px;color:var(--lvl-mut);width:100%}
.lvl-tp-out-l{list-style:none;margin:7px 0;padding:0}
.lvl-tp-out-l li{display:flex;align-items:center;gap:7px;padding:3px 0;
  font:500 11px/1.35 var(--lvl-font);color:var(--lvl-ink)}
.lvl-tp-out-l li i{width:8px;height:8px;border-radius:50%;flex:none}
.lvl-tp-out-l li b{font-weight:600;flex:1 1 auto;min-width:0;
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-tp-out-l li span{font:700 11.5px/1 var(--lvl-font);color:var(--lvl-risk);flex:none}
.lvl-tp-out-l li span em{font-style:normal;font-weight:600;font-size:10px;color:var(--lvl-mut)}
.lvl-tp-out-l li u{text-decoration:none;font-size:10px;color:var(--lvl-mut);flex:none}

/* ── THE PLANS THIS RUN WEIGHED ────────────────────────────────────────
   The same block as the out-of-brief warning, without the warning: this is
   the run showing its working, not flagging a problem. So the risk border
   comes off, the chosen plan reads at full strength, and the ones it was
   measured against sit back a step — a planner can see in one glance what
   the alternative would have cost them. */
.lvl-tp-out.is-weighed{border-color:var(--lvl-line);background:var(--lvl-wash)}
.lvl-tp-out.is-weighed .lvl-tp-out-l li{padding:4px 0;border-top:1px solid var(--lvl-line);
  align-items:baseline;flex-wrap:wrap}
.lvl-tp-out.is-weighed .lvl-tp-out-l li:first-child{border-top:0}
.lvl-tp-out.is-weighed .lvl-tp-out-l li span{color:var(--lvl-mut)}
.lvl-tp-out.is-weighed .lvl-tp-out-l li u{width:100%;padding-left:0}
.lvl-tp-out.is-weighed .lvl-tp-out-l li:not(.is-win){opacity:.62}
.lvl-tp-out.is-weighed .lvl-tp-out-l li.is-win b,
.lvl-tp-out.is-weighed .lvl-tp-out-l li.is-win span{color:var(--lvl-ink)}
.lvl-tp-out.is-weighed .lvl-tp-out-l li.is-win b{font-weight:700}

/* ── THE BRIEF, MEASURED AGAINST THE PROGRAMME ─────────────────────────
   Not a warning and not a result: the run telling the planner that the
   question it was asked is not the question the programme is worst at, and
   what a lever they never granted would have been worth. It reads as advice,
   so it takes the informational colour rather than the risk one. */
.lvl-tp-out.is-advice{border-color:var(--lvl-info);background:var(--lvl-info-t)}
.lvl-tp-out.is-advice .lvl-tp-out-h em{line-height:1.45;color:var(--lvl-ink-2)}
.lvl-tp-out.is-advice .lvl-btn{margin-top:8px}
.lvl-tp-adv-l{margin-top:10px;padding-top:9px;border-top:1px solid var(--lvl-line)}
.lvl-tp-adv-l b{display:block;font:700 11.5px/1.35 var(--lvl-font);color:var(--lvl-ink)}
.lvl-tp-adv-l em{display:block;margin-top:2px;font-style:normal;font-size:10.5px;
  line-height:1.45;color:var(--lvl-ink-2)}
.lvl-tp-adv-l .lvl-btn{margin-right:6px}

/* ── THE BRIEF, ON THE BOARD THE PLANNER JUDGES THE TOOL ON ────────────
   Under the four meters, above the chart. It is not a warning — the run did
   what it was asked — so it takes the informational colour, and the button
   that changes the question sits inside it rather than somewhere else. */
.lvl-cc-fit{display:flex;align-items:flex-start;gap:9px;margin:0 0 10px;padding:9px 11px;
  border:1px solid var(--lvl-info);border-radius:var(--lvl-r-s);background:var(--lvl-info-t)}
.lvl-cc-fit > svg{flex:none;margin-top:1px;color:var(--lvl-info)}
.lvl-cc-fit-t{flex:1 1 auto;min-width:0}
.lvl-cc-fit-t b{display:block;font:700 12px/1.35 var(--lvl-font);color:var(--lvl-ink)}
.lvl-cc-fit-t em{display:block;margin-top:2px;font-style:normal;font-size:11px;
  line-height:1.5;color:var(--lvl-ink-2)}
.lvl-cc-fit .lvl-btn{flex:none;align-self:center}
/* ── ONE LINE, WHERE THE BOARD IS ABOUT THE PICTURE ────────────────
   Three lines of prose above a chart, on a board whose whole job is the
   chart. Everything the paragraph carried is still here — the figures are
   the line, the reasoning is the title, and the thing it was arguing for is
   a button rather than the last clause of a sentence. */
.lvl-cc-fit.is-line{align-items:center;gap:7px;margin-bottom:6px;padding:5px 9px;flex-wrap:nowrap}
.lvl-cc-fit.is-line > svg{margin-top:0}
.lvl-cc-fit.is-line > b{flex:0 1 auto;min-width:0;font:700 var(--lvl-t-2)/1.25 var(--lvl-font);
  color:var(--lvl-ink);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-fit.is-line > em{flex:1 1 auto;min-width:0;font-style:normal;
  font:500 var(--lvl-t-2)/1.25 var(--lvl-font);color:var(--lvl-mut);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
@container stage (max-width:700px){
  .lvl-cc-fit.is-line > em{display:none}
}
@media (max-width:720px){.lvl-cc-fit{flex-wrap:wrap}.lvl-cc-fit .lvl-btn{width:100%}}
/* what the run actually did, in numbers, under the score it produced */
.lvl-cc-effort{margin:0 0 9px;font:500 10.5px/1.5 var(--lvl-font);color:var(--lvl-mut);
  letter-spacing:.01em}
/* the same line, about a run that is no longer the one on screen */
.lvl-cc-effort.is-stale{color:var(--lvl-warn)}

/* the relief the brief declined — a price, not a problem */
.lvl-cc-fit.is-cost{border-color:var(--lvl-warn);
  background:color-mix(in srgb,var(--lvl-warn) 7%,var(--lvl-card))}
.lvl-cc-fit.is-cost > svg{color:var(--lvl-warn)}

/* ══ THE PROGRAMME, BEFORE AGAINST AFTER ═══════════════════════════════
   The workspace Gantt's geometry, twice. The label column is HTML and the
   chart is SVG, so both are drawn at the width they are given and the
   container scrolls — two boxes that scale by different factors cannot be
   made to line up by choosing a better number. */
.lvl-bap-tb{display:flex;align-items:center;gap:10px;flex-wrap:wrap;margin-bottom:8px}
.lvl-bap-key{display:inline-flex;align-items:center;gap:5px;
  font:600 10px/1 var(--lvl-font);color:var(--lvl-mut);margin-left:auto}
.lvl-bap-key i{width:16px;height:8px;border-radius:2px;display:inline-block}
.lvl-bap-key i.k-was{background:var(--lvl-line);border:1px solid var(--lvl-mut-2)}
.lvl-bap-key i.k-now{background:var(--lvl-green)}
.lvl-bap-key i+i{margin-left:8px}
.lvl-bap{display:flex;align-items:flex-start;gap:0;overflow-x:auto;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);background:var(--lvl-card)}
.lvl-bap-l{flex:none;width:250px;position:sticky;left:0;z-index:2;
  background:var(--lvl-card);border-right:1px solid var(--lvl-line)}
.lvl-bap-r{height:20px;display:flex;align-items:center;gap:5px;padding-right:8px;
  font:500 10.5px/20px var(--lvl-font);color:var(--lvl-ink);
  white-space:nowrap;overflow:hidden}
.lvl-bap-r>span{flex:1 1 auto;min-width:0;overflow:hidden;text-overflow:ellipsis}
.lvl-bap-r>i{width:7px;height:7px;border-radius:50%;flex:none}
.lvl-bap-r>u{text-decoration:none;font:700 9px/1 var(--lvl-mono,var(--lvl-font));
  color:var(--lvl-mut-2);flex:none}
/* the remove control, on the rows this session actually staged — a 20px row
   has no space to spare, so it takes the label's, and only on hover */
.lvl-bap-r>.lvl-chg-x{width:18px;height:18px;border-radius:5px;opacity:0;flex:none}
.lvl-bap-r.is-own:hover>.lvl-chg-x,.lvl-bap-r>.lvl-chg-x:focus-visible{opacity:1}
.lvl-bap-r.is-own:hover{background:var(--lvl-wash)}
/* the bar is the control too — it is what a planner is looking at when they
   decide a move is wrong, so it says so with the cursor */
.lvl-bap .lvl-ws-bar[data-lvl]{cursor:pointer}
.lvl-bap .lvl-ws-bar[data-lvl]:hover{filter:brightness(1.07)}
.lvl-bap-r.is-g{font-weight:800;background:var(--lvl-wash);color:var(--lvl-ink-2)}
.lvl-bap-r.is-same{opacity:.55}
.lvl-bap-t{flex:none}
.lvl-bap.is-split{gap:0}
.lvl-bap.is-split .lvl-bap-p{flex:none;border-left:1px solid var(--lvl-line)}
.lvl-bap.is-split .lvl-bap-p h6{margin:0;padding:5px 8px;
  font:800 9.5px/1 var(--lvl-font);letter-spacing:.09em;text-transform:uppercase;
  color:var(--lvl-mut);background:var(--lvl-wash);border-bottom:1px solid var(--lvl-line-2)}
.lvl-bap.is-split .lvl-bap-l{padding-top:0}
.lvl-bap.is-split .lvl-bap-l::before{content:"";display:block;height:22px;
  border-bottom:1px solid var(--lvl-line-2);background:var(--lvl-wash)}

/* BEFORE reads as before: one flat neutral, no pressure colouring, nothing
   that could be mistaken for a change. AFTER keeps the module's own marks. */
.lvl-ws-bar.is-was,.lvl-ws-seg.is-was .lvl-ws-bar{fill:var(--lvl-line);
  stroke:var(--lvl-before);stroke-width:1;stroke-opacity:.7}
.lvl-ws-seg.is-was .lvl-ws-seg-c{fill:var(--lvl-line);opacity:.85}
.lvl-bap-p h6 em{font-style:normal;font-weight:600;text-transform:none;
  letter-spacing:0;color:var(--lvl-mut-2);margin-left:6px}
.lvl-bap-p.is-now h6{color:var(--lvl-after)}
/* a row that changed is the one worth finding in a list of a hundred */
.lvl-bap-r.is-chg:not(.is-g){background:color-mix(in srgb,var(--lvl-after) 7%,transparent)}
.lvl-bap-r.is-chg:not(.is-g)>span{font-weight:700;color:var(--lvl-ink)}
.lvl-bap-r.is-same:not(.is-g){opacity:.55}

/* ══════════════════════════════════════════════════════════════════════
   THE CONTROL CENTRE — A COCKPIT

   One screen, four fixed regions, one stage that changes. The whole shell
   becomes viewport-height while it is on: nothing here scrolls, because a
   control surface you have to scroll is a document with buttons on it.
   min-height:0 on every flex child is what makes that true rather than
   aspirational — without it a child refuses to shrink below its content and
   the overflow reappears at the bottom of the page.
   ══════════════════════════════════════════════════════════════════════ */
.lvl.is-cc{height:calc(100dvh - var(--lvl-cc-top, 0px));
  max-height:calc(100dvh - var(--lvl-cc-top, 0px));
  display:flex;flex-direction:column;overflow:hidden}
.lvl.is-cc>.lvl-main{flex:1 1 auto;min-height:0;overflow:hidden;padding:0}
.lvl.is-cc .lvl-foot{flex:0 0 auto}
.lvl-cc{height:100%;min-height:0;display:flex;flex-direction:column;gap:8px;padding:8px 10px 10px}

/* ROW 0's identity band is gone — it repeated the toolbar chip above it and
   cost 44px of a viewport this page is always short of. Its rules went with
   it rather than being left to match nothing. */

/* ── ROW 1 · THE STATE, IN FIVE NUMBERS ───────────────────────────
   FIVE CARDS, NOT FIVE CELLS OF A TABLE. They were cells of one bordered
   block divided by hairlines, which is how you draw a table — and a table is
   what the eye reads it as: five equal readings to work through in order.
   These are five separate claims about the same programme, and each one is
   the loudest thing in its own box: a card with its own edge, its own ground
   and its own shadow, a figure big enough to be read across a desk, and the
   CHANGE stated as a coloured chip rather than a grey sentence.
   Each is still a door — it opens the board that explains it. */
/* THE FIRST CARD IS WIDER, BECAUSE IT IS THE ONE THE PAGE IS ABOUT. The
   deployment shape is the single number that says whether this programme can
   be built the way it is drawn; the other four are the evidence for it. Equal
   widths said all five ranked the same. */
.lvl-cc-keys{flex:0 0 auto;display:grid;grid-template-columns:1.45fr repeat(4,1fr);gap:var(--lvl-sp-2)}
.lvl-cc-k{min-width:0;display:flex;flex-direction:column;justify-content:flex-start;gap:5px;
  text-align:left;padding:11px 13px 12px;cursor:pointer;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r);background:var(--lvl-card);
  box-shadow:var(--lvl-sh);
  transition:border-color .12s ease,box-shadow .12s ease,transform .12s ease}
.lvl-cc-k:hover{border-color:var(--lvl-mut-2);box-shadow:var(--lvl-sh-2)}
/* the open board's card carries a coloured edge rather than a wash: a tinted
   card among four white ones changes its own figure's contrast, and the
   figure is the thing being read */
.lvl-cc-k.is-on{border-color:var(--lvl-green);box-shadow:var(--lvl-sh-2),inset 0 3px 0 var(--lvl-green)}
/* ── THE LEAD CARD ────────────────────────────────────────────────
   Wider, on its own tinted ground, with the figure a step larger and a meter
   thick enough to read as a gauge. It is the verdict on the programme; the
   four beside it are why. */
.lvl-cc-k.is-lead{padding:12px 16px 13px;background:var(--lvl-wash)}
.lvl-cc-k.is-lead .lvl-cc-k-v{font-size:var(--lvl-t-7)}
.lvl-cc-k.is-lead .lvl-cc-k-m{height:7px;border-radius:4px}
.lvl-cc-k.is-lead .lvl-cc-k-m>i{border-radius:4px}
.lvl-cc-k.is-lead.is-good{background:color-mix(in srgb,var(--lvl-ok) 7%,var(--lvl-card));
  border-color:color-mix(in srgb,var(--lvl-ok) 32%,var(--lvl-line))}
.lvl-cc-k.is-lead.is-warn{background:color-mix(in srgb,var(--lvl-warn) 9%,var(--lvl-card));
  border-color:color-mix(in srgb,var(--lvl-warn) 32%,var(--lvl-line))}
.lvl-cc-k.is-lead.is-bad{background:color-mix(in srgb,var(--lvl-risk) 7%,var(--lvl-card));
  border-color:color-mix(in srgb,var(--lvl-risk) 32%,var(--lvl-line))}
/* the grade sits beside the score rather than under it — there is room */
.lvl-cc-k.is-lead .lvl-cc-k-d{font-size:var(--lvl-t-3);padding:3px 9px}
.lvl-cc-k-l{font:700 var(--lvl-t-1)/1.15 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
/* a value that is a DATE, not a figure — a step down, because "7 Feb 28 →
   30 Nov 27" set at the headline size is 260px of card and it pushed its own
   chip onto a second line and the card past its four neighbours */
.lvl-cc-k-v.is-tight{font-size:var(--lvl-t-5);letter-spacing:0}
.lvl-cc-k-v.is-tight .lvl-cc-k-was{font-size:var(--lvl-t-3)}
.lvl-cc-k-v.is-tight .lvl-cc-k-to{font-size:var(--lvl-t-2)}
.lvl-cc-k-v{font:800 var(--lvl-t-6)/1 var(--lvl-head);color:var(--lvl-ink);
  display:flex;align-items:baseline;gap:2px;min-width:0;white-space:nowrap;letter-spacing:-.015em}
.lvl-cc-k-v i{font-style:normal;font-size:var(--lvl-t-4);font-weight:700;color:var(--lvl-mut-2)}
/* the old value, stepped down to the new one — a pair is one reading, so the
   "before" is deliberately quieter and smaller than the "after" beside it */
.lvl-cc-k-was{display:inline;font-size:var(--lvl-t-5);font-weight:700;color:var(--lvl-mut-2)}
.lvl-cc-k-to{font-style:normal;font-size:var(--lvl-t-4);font-weight:700;color:var(--lvl-mut-2);
  margin:0 3px}
.lvl-cc-k.is-good .lvl-cc-k-v{color:var(--lvl-ok)}
.lvl-cc-k.is-warn .lvl-cc-k-v{color:var(--lvl-warn)}
.lvl-cc-k.is-bad .lvl-cc-k-v{color:var(--lvl-risk)}
.lvl-cc-k .lvl-cc-k-was{color:var(--lvl-mut-2)}
/* THE CHANGE IS A CHIP, NOT A SENTENCE. "27 fewer at the peak · −31%" set in
   grey beside four other grey notes is a line to read; the same words on a
   tinted pill are a verdict you take in without reading. */
.lvl-cc-k-d{align-self:flex-start;display:inline-flex;align-items:center;gap:4px;
  padding:2px 7px;border-radius:999px;
  font:700 var(--lvl-t-2)/1.25 var(--lvl-font);
  background:var(--lvl-line-2);color:var(--lvl-ink-2)}
.lvl-cc-k-d.is-good{background:color-mix(in srgb,var(--lvl-ok) 13%,transparent);color:var(--lvl-ok)}
.lvl-cc-k-d.is-bad{background:color-mix(in srgb,var(--lvl-risk) 12%,transparent);color:var(--lvl-risk)}
.lvl-cc-k-d.is-warn{background:color-mix(in srgb,var(--lvl-warn) 15%,transparent);color:var(--lvl-warn)}
.lvl-cc-k-m{display:block;height:4px;border-radius:2px;background:var(--lvl-line);overflow:hidden}
.lvl-cc-k-m>i{display:block;height:100%;background:var(--lvl-mut-2);border-radius:2px}
.lvl-cc-k.is-good .lvl-cc-k-m>i{background:var(--lvl-ok)}
.lvl-cc-k.is-warn .lvl-cc-k-m>i{background:var(--lvl-warn)}
.lvl-cc-k.is-bad .lvl-cc-k-m>i{background:var(--lvl-risk)}
/* TWO LINES, RESERVED. The note wraps at one width and not at another, so
   without a reserved box the five cards were 119px on a 1920 screen and
   134px on a 1440 one — a headline row that changes height as the window
   does, and every measurement under it moving with it. It always occupies
   two lines; it just does not always fill them. */
/* THE SENTENCE IS GONE FROM THE CARD. Five cards each carrying a label, a
   figure, a chip AND two lines of prose is five paragraphs where the page
   promised five numbers — and it cost 34px of a viewport that was already
   losing the chart. What the sentence explained now lives on the card's
   title, where it is one hover away and costs nothing. */
.lvl-cc-k-n{display:none}

/* the row says what it IS, once, above the cards — the mockup's own
   "BEFORE vs AFTER (this simulation)" band, which is the thing that turns
   five numbers into one statement */
.lvl-cc-keys-h{flex:0 0 auto;display:flex;align-items:baseline;gap:8px;
  margin:2px 2px -2px}
.lvl-cc-keys-h>b{font:700 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.13em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-keys-h>em{font-style:normal;font:500 var(--lvl-t-2)/1 var(--lvl-font);color:var(--lvl-mut-2)}

/* ══ THE CHANGE REGISTER WINDOW ═════════════════════════════════════════
   Opens over the page rather than replacing it: the question "what changed"
   is asked while looking at the five numbers and the Apply button that the
   answer informs, and leaving the page to answer it loses both.
   ═══════════════════════════════════════════════════════════════════════ */
.lvl-drawer.is-chg{width:min(720px,96vw);display:flex;flex-direction:column}
.lvl-chg-f-row{flex:0 0 auto;padding:10px var(--lvl-sp-4) 0}
.lvl-chg-f-row .lvl-cc-cmp{align-self:stretch;flex-wrap:wrap}
.lvl-cc-cmp-b>u{text-decoration:none;margin-left:5px;font-size:var(--lvl-t-1);
  font-weight:800;color:var(--lvl-mut-2)}
.lvl-cc-cmp-b.is-on>u{color:var(--lvl-green-d)}

.lvl-chg-g{margin:0 0 var(--lvl-sp-4)}
.lvl-chg-g>h4{display:flex;align-items:baseline;gap:8px;margin:0 0 6px;
  font:800 var(--lvl-t-4)/1.2 var(--lvl-head);color:var(--lvl-ink)}
.lvl-chg-g>h4>span{flex:none;padding:2px 8px;border-radius:999px;background:var(--lvl-line);
  font:800 var(--lvl-t-1)/1.3 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ink-2)}
.lvl-chg-g>h4>em{flex:1 1 auto;min-width:0;font-style:normal;
  font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut-2)}

/* ONE ROW, FIVE COLUMNS, AND EVERY ONE OF THEM A REASON TO ACCEPT OR REFUSE
   THE MOVE: which trade, which bar, where it was and went, how far, and what
   it spent. A register that lists only what moved is a list; a register that
   prices each line is a decision. */
/* ── ONE ROW, AND THE MOVE IS DRAWN ON IT ──────────────────────────
   A shared time axis across every row, so the moves compare with each other
   down the column instead of each being a subtraction the reader performs. */
/* the last track is the remove control — every row that lists a change can
   take that change out of the session, from the register and the workspace
   alike, and neither of them acts on the first click */
.lvl-chg-r{display:grid;grid-template-columns:minmax(140px,1.15fr) minmax(140px,1.25fr) 68px 58px 22px;
  align-items:center;gap:12px;width:100%;text-align:left;
  padding:6px 9px;border:0;border-radius:var(--lvl-r-s);background:none;cursor:pointer;
  transition:background .12s ease}
.lvl-chg-r:hover{background:var(--lvl-wash)}
.lvl-chg-r.is-static{cursor:default}
.lvl-chg-r.is-static:hover{background:none}
.lvl-chg-n{min-width:0}
.lvl-chg-n>b{display:block;font:600 var(--lvl-t-3)/1.3 var(--lvl-font);color:var(--lvl-ink);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-chg-n>em{display:flex;align-items:center;gap:5px;font-style:normal;
  font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut-2);
  white-space:nowrap;overflow:hidden}
.lvl-chg-n>em>i{width:6px;height:6px;border-radius:50%;flex:none}

/* THE TRACK. `u` is where the bar was, `i` is where it went. The ghost is an
   outline and the move is solid, so the eye reads the pair as one bar that
   travelled rather than as two unrelated marks. */
.lvl-chg-t{position:relative;display:block;height:18px;border-radius:4px;
  background:var(--lvl-wash);border:1px solid var(--lvl-line-2);overflow:hidden}
/* AN OUTLINE 3px WIDE IS NOT A BAR, IT IS A CHARACTER. At the scale a short
   activity occupies on a two-year axis the hollow ghost rendered as a tiny
   "0" on every row. It is filled slate now, with a floor wide enough to read
   as a bar, and the new position sits under it in the accent. */
.lvl-chg-t>u,.lvl-chg-t>i{position:absolute;height:6px;border-radius:3px;min-width:7px}
.lvl-chg-t>u{top:2px;background:var(--lvl-before);opacity:.75}
.lvl-chg-t>i{bottom:2px;background:var(--lvl-after)}
.lvl-chg-t.is-dur>i{background:var(--lvl-warn)}
.lvl-chg-t.is-logic>i{background:var(--lvl-warn)}
.lvl-chg-r:hover .lvl-chg-t{border-color:var(--lvl-line-3)}

/* the axis is stated once per group, not once per row */
.lvl-chg-ax{display:flex;align-items:center;gap:10px;margin:0 9px 4px;padding-bottom:5px;
  border-bottom:1px dashed var(--lvl-line)}
.lvl-chg-ax>s{text-decoration:none;flex:none;
  font:600 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-mut-2)}
.lvl-chg-ax>em{flex:1 1 auto;display:flex;align-items:center;justify-content:center;gap:6px;
  font-style:normal;font:500 var(--lvl-t-1)/1 var(--lvl-font);color:var(--lvl-mut-2)}
.lvl-chg-ax>em>i{width:14px;height:5px;border-radius:3px;flex:none;margin-left:6px}
.lvl-chg-ax>em>i:first-child{margin-left:0}
.lvl-chg-ax .is-was{background:var(--lvl-before);opacity:.75}
.lvl-chg-ax .is-now{background:var(--lvl-after)}

.lvl-chg-s{font:800 var(--lvl-t-3)/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-after);
  text-align:right;white-space:nowrap}
.lvl-chg-s>u{text-decoration:none;font-size:9px;font-weight:600;color:var(--lvl-mut-2);margin-left:1px}
/* how far it went, against the furthest thing this run moved */
.lvl-chg-sh{display:flex;flex-direction:column;align-items:flex-end;gap:3px}
.lvl-chg-sh>b{font:800 var(--lvl-t-3)/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-after);
  white-space:nowrap}
.lvl-chg-sh>b>u{text-decoration:none;font-size:9px;font-weight:600;color:var(--lvl-mut-2);margin-left:1px}
.lvl-chg-sh>s{display:block;width:100%;height:4px;border-radius:2px;
  background:var(--lvl-line-2);text-decoration:none;overflow:hidden}
.lvl-chg-sh>s>i{display:block;height:100%;border-radius:2px;background:var(--lvl-after);opacity:.65}
.lvl-chg-f{font:700 var(--lvl-t-2)/1.15 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ok);
  text-align:right;white-space:nowrap}
/* a bar that spent every day of float it had is one nudge from the critical
   path, and the register is where a planner would want to be told */
.lvl-chg-f.is-tight{color:var(--lvl-risk)}
.lvl-chg-f>u{display:block;text-decoration:none;font-size:9px;font-weight:600;
  color:var(--lvl-mut-2)}
.lvl-chg-f.is-tight>u{color:var(--lvl-risk);opacity:.8}
@media (max-width:640px){
  .lvl-chg-r{grid-template-columns:minmax(0,1fr) 72px;row-gap:3px}
  .lvl-chg-t{grid-column:1/-1}
  .lvl-chg-f{display:none}
}

/* the "what changed" rows carry a chevron, because they OPEN something
   rather than reporting it. The third column has to be declared: left to
   auto-placement the chevron landed in the label's cell and sat on top of
   the words. */
.lvl-cc-chg-r{grid-template-columns:38px minmax(0,1fr) 14px}
.lvl-cc-chg-r>svg{grid-column:3;grid-row:1/3;align-self:center;color:var(--lvl-mut-2)}
.lvl-cc-chg-r:hover>svg{color:var(--lvl-ink-2)}

/* ── ROW 2 · THE EVIDENCE, AND THE CALL ───────────────────────────
   Who is over on the left, one picture in the middle, the decision on the
   right. Three regions, none of which restates another, and the whole row
   is one screen tall — every list inside it scrolls in its own box. */
/* ── THE SIDE COLUMNS SCALE, THEY ARE NOT TWO FIXED SLABS ──────────
   268px and 300px whatever the screen: on a 1280 laptop that is 44% of the
   window spent on two columns, and on a 2560 monitor the call panel is the
   only thing on the page that did not grow. They scale with the viewport
   between a floor that keeps a trade name readable and a ceiling past which
   more width buys nothing. */
.lvl-cc-body{flex:1 1 auto;min-height:0;display:grid;
  grid-template-columns:clamp(224px,17vw,292px) minmax(0,1fr) clamp(248px,20vw,340px);
  gap:var(--lvl-sp-2)}
/* ── AND IT FOLDS, SO THE BOARD CAN HAVE THE WIDTH ─────────────────
   Shut, the decision column is a rail the width of one button. Everything
   it was carrying that cannot wait — the action and the alarm — is on the
   rail; everything else is one click away. */
.lvl-cc-body.is-rail-shut{grid-template-columns:clamp(224px,17vw,292px) minmax(0,1fr) 46px}

/* ── THE RAIL ─────────────────────────────────────────────────────────
   ONE TAB, NOT FOUR FLOATING SHAPES. The first version was a white card
   with a coloured arc on its top edge, a circle, another circle and a line
   of type — four marks in a 46px column, none of them touching anything,
   which reads as debris rather than as a control. It is a tab now: a
   tinted ground in the state's own colour, a handle at the head, the
   sentence down the middle, the action seated at the foot. */
.lvl-cc-side.is-shut{overflow:visible}
.lvl-cc-rail{flex:1 1 auto;min-height:0;display:flex;flex-direction:column;align-items:center;
  gap:var(--lvl-sp-2);padding:var(--lvl-sp-2) 3px;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r);
  background:var(--lvl-wash);
  transition:background .12s ease,border-color .12s ease}
.lvl-cc-rail:hover{border-color:var(--lvl-mut-2)}
.lvl-cc-rail.is-ok{background:color-mix(in srgb,var(--lvl-ok) 7%,var(--lvl-card));
  border-color:color-mix(in srgb,var(--lvl-ok) 28%,var(--lvl-line))}
.lvl-cc-rail.is-warn{background:color-mix(in srgb,var(--lvl-warn) 8%,var(--lvl-card));
  border-color:color-mix(in srgb,var(--lvl-warn) 30%,var(--lvl-line))}
.lvl-cc-rail.is-risk{background:color-mix(in srgb,var(--lvl-risk) 8%,var(--lvl-card));
  border-color:color-mix(in srgb,var(--lvl-risk) 30%,var(--lvl-line))}
.lvl-cc-rail.is-sim{background:color-mix(in srgb,var(--lvl-after) 8%,var(--lvl-card));
  border-color:color-mix(in srgb,var(--lvl-after) 30%,var(--lvl-line))}
/* the handle, pointing back at the board it is giving the room to */
.lvl-cc-rail-x{flex:0 0 auto;width:26px;height:26px;display:flex;align-items:center;
  justify-content:center;border:0;border-radius:7px;
  background:color-mix(in srgb,var(--lvl-ink) 6%,transparent);color:var(--lvl-mut);cursor:pointer;
  transform:rotate(180deg);transition:background .12s ease,color .12s ease}
.lvl-cc-rail-x:hover{background:color-mix(in srgb,var(--lvl-ink) 12%,transparent);color:var(--lvl-ink)}
/* the sentence the column would have opened with, set on its side — it is
   what tells a planner whether opening it is worth doing */
.lvl-cc-rail-t{flex:1 1 auto;min-height:0;width:100%;display:flex;align-items:center;
  justify-content:center;border:0;background:none;cursor:pointer;padding:0;overflow:hidden}
.lvl-cc-rail-t>span{writing-mode:vertical-rl;transform:rotate(180deg);
  font:700 var(--lvl-t-2)/1 var(--lvl-font);color:var(--lvl-mut);
  letter-spacing:.04em;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;max-height:100%}
.lvl-cc-rail-t:hover>span{color:var(--lvl-ink)}
.lvl-cc-rail.is-warn .lvl-cc-rail-t>span{color:var(--lvl-warn)}
.lvl-cc-rail.is-risk .lvl-cc-rail-t>span{color:var(--lvl-risk)}
.lvl-cc-rail.is-sim .lvl-cc-rail-t>span{color:var(--lvl-after)}
/* the one action, seated at the foot at full contrast — a folded column
   that hides the button is a folded column nobody dares fold */
.lvl-cc-rail-go{flex:0 0 auto;position:relative;width:32px;height:32px;min-width:0;
  padding:0;gap:0;display:flex;align-items:center;justify-content:center;
  border:0;border-radius:9px;cursor:pointer;box-shadow:var(--lvl-sh)}
.lvl-cc-rail-go:hover{transform:translateY(-1px)}
.lvl-cc-rail-go[disabled]{opacity:.45;cursor:not-allowed;box-shadow:none;transform:none}
.lvl-cc-rail-go>em{position:absolute;top:-5px;right:-6px;min-width:15px;height:15px;padding:0 3px;
  display:flex;align-items:center;justify-content:center;border-radius:999px;
  font:800 var(--lvl-t-1)/1 var(--lvl-font);font-style:normal;
  background:var(--lvl-ink);color:#fff;border:2px solid var(--lvl-card)}
/* and the control that folds it again, on the head of the panel it folds */
.lvl-cc-call-f2{flex:none;margin-left:auto;width:22px;height:22px;display:flex;align-items:center;
  justify-content:center;border:1px solid var(--lvl-line);border-radius:50%;
  background:var(--lvl-wash);color:var(--lvl-mut-2);cursor:pointer}
.lvl-cc-call-f2:hover{background:var(--lvl-card);color:var(--lvl-ink);border-color:var(--lvl-mut-2)}
/* ── A COLUMN NEVER PUSHES THE PAGE ────────────────────────────────
   The call card sizes to its content and the content grows with the run — a
   trade-off sentence, a blocker, four buttons and three rules. On a short or
   narrow window that is taller than the row, and with no scroller of its own
   the column simply grew and took the shell with it: the reporter's screen
   showed the brief cut off at the bottom edge and the whole page scrolling.
   The COLUMN scrolls now, so the fit is the same on every screen. */
.lvl-cc-side{min-width:0;min-height:0;display:flex;flex-direction:column;gap:var(--lvl-sp-2);
  overflow-y:auto;overscroll-behavior:contain}
/* ── AND IT OPENS LIKE SOMETHING THAT WAS PUT AWAY ─────────────────
   Swapping the rail for the panel in one frame is a substitution, and it
   reads as one: the column was not there and now it is. A drawer that was
   FOLDED comes back the way it went — out of its own edge, sliding, with
   the content fading in behind the movement. Transform and opacity only,
   so it costs one compositor layer and no layout. */
.lvl-cc-side.is-anim.is-open{animation:lvl-rail-out .24s cubic-bezier(.22,.9,.3,1) both}
.lvl-cc-side.is-anim.is-shut{animation:lvl-rail-in .2s cubic-bezier(.22,.9,.3,1) both}
@keyframes lvl-rail-out{
  from{opacity:0;transform:translateX(14%) scaleX(.94);transform-origin:100% 50%}
  to{opacity:1;transform:none}
}
@keyframes lvl-rail-in{
  from{opacity:.4;transform:translateX(-6%);transform-origin:100% 50%}
  to{opacity:1;transform:none}
}
@media (prefers-reduced-motion:reduce){
  .lvl-cc-side.is-anim{animation:none}
}
/* the left column's ladder is already an internal scroller, so it keeps its
   own behaviour and never double-scrolls */
.lvl-cc-side.is-left{overflow:hidden}

/* what the run actually did, in kinds — three counts before three hundred
   rows, and the register that holds the rows is one click away */
.lvl-cc-chg{flex:0 0 auto;display:flex;flex-direction:column;gap:var(--lvl-sp-1);
  padding:var(--lvl-sp-2) var(--lvl-sp-3) var(--lvl-sp-2);
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r);
  background:var(--lvl-card);box-shadow:var(--lvl-sh)}
/* ── A BREAKDOWN, NOT THREE SENTENCES ──────────────────────────────
   "48 / rescheduled / activities given a later start" three times over is a
   list of paragraphs. One run broken into the kinds of change it made is a
   COMPOSITION, so it is drawn as one: the total leads, each kind keeps the
   colour it is drawn in everywhere else on this page, and a bar under each
   row states its share — which is the thing a planner reads first and was
   not on the card at all. */
.lvl-cc-chg-h{flex:0 0 auto;display:flex;align-items:baseline;gap:6px;
  padding-bottom:var(--lvl-sp-1);border-bottom:1px solid var(--lvl-line-2)}
.lvl-cc-chg-h>b{flex:1 1 auto;font:700 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.12em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-chg-h>span{font:800 var(--lvl-t-5)/1 var(--lvl-head);color:var(--lvl-after)}
.lvl-cc-chg-h>em{font-style:normal;font:600 var(--lvl-t-2)/1 var(--lvl-font);color:var(--lvl-mut-2)}
.lvl-cc-chg-l{flex:0 1 auto;min-height:0;display:flex;flex-direction:column;gap:2px;
  overflow-y:auto;overscroll-behavior:contain}
.lvl-cc-chg-r{position:relative;display:grid;
  grid-template-columns:auto minmax(0,1fr) auto;align-items:baseline;
  column-gap:7px;padding:5px 7px 8px;border:0;border-radius:6px;
  background:none;cursor:pointer;text-align:left;
  transition:background .12s ease}
.lvl-cc-chg-r:hover{background:var(--lvl-wash)}
.lvl-cc-chg-r>b{font:800 var(--lvl-t-5)/1 var(--lvl-head);color:var(--lvl-ink)}
.lvl-cc-chg-r>span{min-width:0;font:600 var(--lvl-t-3)/1.2 var(--lvl-font);color:var(--lvl-mut);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-chg-r>u{text-decoration:none;font:700 var(--lvl-t-2)/1 var(--lvl-mono,var(--lvl-font));
  color:var(--lvl-mut-2)}
.lvl-cc-chg-r>u>s{text-decoration:none;font-size:.85em;opacity:.7}
/* the share, drawn under the row it belongs to */
.lvl-cc-chg-r>i{position:absolute;left:7px;bottom:3px;height:3px;border-radius:2px;
  background:var(--lvl-mut-2);max-width:calc(100% - 14px)}
.lvl-cc-chg-r::after{content:"";position:absolute;left:7px;right:7px;bottom:3px;height:3px;
  border-radius:2px;background:var(--lvl-line);z-index:-1}
.lvl-cc-chg-r.is-move>b{color:var(--lvl-after)}
.lvl-cc-chg-r.is-move>i{background:var(--lvl-after)}
.lvl-cc-chg-r.is-dur>b{color:var(--lvl-warn)}
.lvl-cc-chg-r.is-dur>i{background:var(--lvl-warn)}
.lvl-cc-chg-r.is-logic>b{color:var(--lvl-ok)}
.lvl-cc-chg-r.is-logic>i{background:var(--lvl-ok)}
.lvl-cc-chg-all{flex:0 0 auto;margin-top:1px;display:flex;align-items:center;justify-content:center;
  gap:5px;padding:5px;border:1px dashed var(--lvl-line);border-radius:var(--lvl-r-s);
  background:none;cursor:pointer;
  font:600 var(--lvl-t-2)/1 var(--lvl-font);color:var(--lvl-mut)}
.lvl-cc-chg-all:hover{border-color:var(--lvl-mut-2);color:var(--lvl-ink);background:var(--lvl-wash)}

/* ── THE CALL ─────────────────────────────────────────────────────
   The only primary action on the control centre. The situation, then the
   button that answers it, then the rules the run will obey — in that order,
   because a page that offers the button before it has made its case is
   asking for a decision it has not argued for.
   It FILLS its column: a card that stops halfway down leaves a third of the
   page empty beside a chart that would gladly have taken it. */
/* SIZED TO ITS CONTENT, NOT STRETCHED. Stretched to the column it put the
   rules at the very bottom and left a 300px hole in the middle of the card,
   which reads as something failing to load. A compact card at the head of the
   column is what a sidebar is. */
.lvl-cc-call{flex:0 0 auto;min-height:0;display:flex;flex-direction:column;gap:var(--lvl-sp-2);
  padding:var(--lvl-sp-3) var(--lvl-sp-4);
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r);
  background:var(--lvl-card);border-top:4px solid var(--lvl-mut-2);box-shadow:var(--lvl-sh);
  overflow-y:auto;overscroll-behavior:contain}
.lvl-cc-call.is-ok{border-top-color:var(--lvl-ok)}
.lvl-cc-call.is-warn{border-top-color:var(--lvl-warn)}
.lvl-cc-call.is-risk{border-top-color:var(--lvl-risk)}
.lvl-cc-call.is-sim{border-top-color:var(--lvl-after)}
.lvl-cc-call-h{flex:0 0 auto;display:flex;align-items:flex-start;gap:7px}
.lvl-cc-call-h>svg{flex:none;margin-top:1px;color:var(--lvl-mut)}
.lvl-cc-call.is-ok .lvl-cc-call-h>svg{color:var(--lvl-ok)}
.lvl-cc-call.is-warn .lvl-cc-call-h>svg{color:var(--lvl-warn)}
.lvl-cc-call.is-risk .lvl-cc-call-h>svg{color:var(--lvl-risk)}
.lvl-cc-call.is-sim .lvl-cc-call-h>svg{color:var(--lvl-after)}
.lvl-cc-call-h>b{font:800 var(--lvl-t-5)/1.25 var(--lvl-head);color:var(--lvl-ink)}
.lvl-cc-call-p{flex:0 0 auto;margin:0;font:500 var(--lvl-t-3)/1.45 var(--lvl-font);color:var(--lvl-mut)}
.lvl-cc-call-x{flex:0 0 auto;display:grid;grid-template-columns:auto 1fr;gap:2px 7px;
  padding:8px 9px;border-radius:var(--lvl-r-s);
  background:color-mix(in srgb,var(--lvl-risk) 8%,transparent)}
.lvl-cc-call-x>svg{grid-row:1/4;margin-top:1px;color:var(--lvl-risk)}
.lvl-cc-call-x>b{font:700 var(--lvl-t-3)/1.25 var(--lvl-font);color:var(--lvl-risk)}
.lvl-cc-call-x>em{font-style:normal;font:500 var(--lvl-t-2)/1.35 var(--lvl-font);color:var(--lvl-mut)}
/* ── AND THE WAY OUT OF IT ─────────────────────────────────────────
   The blocker used to state itself and stop. Every error here is raised BY
   a staged change, so the fix that always exists is to take those changes
   back out — and that is a button, not a paragraph. */
.lvl-cc-call-x>.lvl-cc-call-xa{grid-column:2;display:flex;flex-wrap:wrap;gap:5px;margin-top:6px}
.lvl-cc-call-x .lvl-btn{flex:0 1 auto}
.lvl-cc-sess-a{display:flex;flex-wrap:wrap;gap:5px}
.lvl-cc-call-a{flex:0 0 auto;display:flex;flex-direction:column;gap:6px}
.lvl-cc-call-a .lvl-btn{width:100%;justify-content:center}
/* the rules the run will obey, read off the same brief the run reads */
/* the rules sit at the FOOT of the column — they are the fine print under
   the decision, not a second thing competing with it */
.lvl-cc-call-b{flex:0 0 auto;margin-top:2px;padding-top:var(--lvl-sp-3);
  border-top:1px solid var(--lvl-line)}
.lvl-cc-call-bh{display:flex;align-items:baseline;gap:8px;margin-bottom:5px}
.lvl-cc-call-bh>b{flex:1 1 auto;font:700 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.1em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-call-bh .lvl-link{flex:none;font:600 var(--lvl-t-2)/1 var(--lvl-font)}
.lvl-cc-call-f{display:flex;align-items:baseline;justify-content:space-between;gap:8px;
  padding:4px 0;border-bottom:1px dotted var(--lvl-line)}
.lvl-cc-call-f:last-child{border-bottom:0}
.lvl-cc-call-f>span{font:500 var(--lvl-t-2)/1.2 var(--lvl-font);color:var(--lvl-mut)}
.lvl-cc-call-f>b{font:700 var(--lvl-t-3)/1.2 var(--lvl-font);color:var(--lvl-ink);text-align:right}

/* ── A BOARD IS LAID OUT BY THE ROOM IT HAS, NOT BY THE WINDOW ─────
   Every board rule below used to key off the WINDOW width. But a board lives
   in the stage, and the stage is the window minus two side columns — so a
   1900px window can hand a board 700px and nothing fires, while a 1240px
   window fires the narrow rules on a board that has more room than that.
   The same table was laid out differently for reasons unrelated to how much
   space it actually had, which is exactly what "the views are not consistent
   with the screen" describes. The stage is a query container; the boards ask
   IT. */
.lvl-cc-stage{min-height:0;display:flex;flex-direction:column;
  container-type:inline-size;container-name:stage;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r);background:var(--lvl-card);
  box-shadow:var(--lvl-sh);overflow:hidden}
/* ── THE BOARD PICKER IS A SEGMENTED CONTROL, NOT A FILING CABINET ─────
   Six full-height cells divided by hard rules, edge to edge, under a row of
   cards that are already divided cells: the eye met two grids stacked and
   read the second as more structure to parse rather than as a control. It is
   a pill now — one track, floating buttons inside it, the open one lifted on
   white. Nothing is divided from anything, so there is one grid on the page
   and this reads as what it is: a switch. */
.lvl-cc-tabs{flex:0 0 auto;display:flex;flex-wrap:wrap;gap:3px;padding:5px;
  border-bottom:1px solid var(--lvl-line);background:var(--lvl-wash)}
/* SIZED TO THEIR LABELS, NOT TO EACH OTHER. `flex:1 1 0` gave six equal
   widths, so "Change log" sat in slack while "Deployment curve" — the one
   that opens by default — was the one cut. They take what they need; the row
   is 780px of content in 1130px of stage, and the leftover goes to the right
   of the last tab where it costs nothing. */
.lvl-cc-tab{flex:0 1 auto;min-width:0;text-align:center;padding:7px 13px;border:0;
  border-radius:var(--lvl-r-s);
  background:none;cursor:pointer;position:relative;
  transition:background .12s ease,color .12s ease,box-shadow .12s ease}
.lvl-cc-tab b{display:flex;align-items:center;justify-content:center;gap:6px;
  font:600 var(--lvl-t-3)/1.25 var(--lvl-font);color:var(--lvl-mut);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
/* THE CAPTION WRAPS, IT DOES NOT GET CUT. Four of the six ended in an
   ellipsis at every width this app is used at, and half a sentence costs the
   same 13px as a whole one while telling the planner nothing. Two lines is
   the ceiling; the full sentence is on the tab's title either way. */
.lvl-cc-tab em{display:-webkit-box;-webkit-box-orient:vertical;-webkit-line-clamp:2;line-clamp:2;
  overflow:hidden;font-style:normal;font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut-2);
  margin-top:1px}
.lvl-cc-tab-n{text-decoration:none;flex:none;min-width:17px;height:17px;padding:0 5px;
  display:inline-flex;align-items:center;justify-content:center;border-radius:9px;
  background:var(--lvl-line);color:var(--lvl-mut);
  font:800 9.5px/1 var(--lvl-mono,var(--lvl-font))}
.lvl-cc-tab-n.is-risk{background:color-mix(in srgb,var(--lvl-risk) 16%,transparent);color:var(--lvl-risk)}
.lvl-cc-tab:hover{background:color-mix(in srgb,var(--lvl-ink) 5%,transparent)}
.lvl-cc-tab:hover b{color:var(--lvl-ink)}
.lvl-cc-tab.is-on{background:var(--lvl-card);box-shadow:var(--lvl-sh)}
.lvl-cc-tab.is-on b{color:var(--lvl-ink);font-weight:700}
/* the open board is marked by the lift and a short underline INSIDE the
   pill, not by a rule spanning the whole cell — a full-width bar under a
   floating button is the old filing-cabinet tab wearing a new shape */
.lvl-cc-tab.is-on::after{content:"";position:absolute;left:13px;right:13px;bottom:4px;
  height:2px;border-radius:1px;background:var(--lvl-green)}
.lvl-cc-board{flex:1 1 auto;min-height:0;overflow:hidden;padding:var(--lvl-sp-3)}
.lvl-cc-board:focus-visible{outline-offset:-2px}

/* ── board: the curve ─────────────────────────────────────────────── */
/* AND WHEN EVEN THE FLOOR DOES NOT FIT, IT SCROLLS RATHER THAN CLIPS.
   The board above is `overflow:hidden`, so a floor that the window cannot
   pay for does not shrink the picture — it pushes it out of the box and the
   box cuts it off. Measured at 1180x760 under an open apply panel: the board
   was 275px for 407px of content and the chart's foot was simply gone. A
   scroll here costs a planner one gesture; clipping costs them the picture. */
.lvl-cc-curve{height:100%;min-height:0;display:flex;flex-direction:column;gap:8px;
  overflow-y:auto;overscroll-behavior:contain}
.lvl-cc-curve-hd{flex:0 0 auto;display:flex;gap:var(--lvl-sp-3);align-items:stretch}
/* the score card that stood here is gone: the headline row states the shape
   score, and this board is 300px under it. The meters below are what the
   board adds — the components the score is made of. */
.lvl-cc-meters{flex:1 1 auto;min-width:0;display:grid;grid-template-columns:repeat(4,1fr);gap:1px;
  background:var(--lvl-line);border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);overflow:hidden}
.lvl-cc-meter{background:var(--lvl-card);padding:8px 11px;min-width:0}
/* DIRECT CHILD. As `.lvl-cc-meter span` this also matched the "before" span
   inside the figure below it and made it display:block, which is why a pair
   that fits on one line was rendering as two. */
.lvl-cc-meter>span{display:block;font:700 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.07em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-meter b{display:block;font:800 17px/1.15 var(--lvl-head);margin-top:3px;
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
/* the master's value, stepped down to this one — quieter, because the pair
   is one reading and the reading is the number on the right */
.lvl-cc-was{display:inline;font-size:var(--lvl-t-4);font-weight:700;color:var(--lvl-mut-2)}
.lvl-cc-meter b>i{font-style:normal;font-size:var(--lvl-t-2);font-weight:700;
  color:var(--lvl-mut-2);margin:0 3px}
.lvl-cc-meter.is-ok b{color:var(--lvl-ok)}
.lvl-cc-meter.is-bad b{color:var(--lvl-risk)}
.lvl-cc-meter em{display:block;font-style:normal;font:500 9.5px/1.3 var(--lvl-font);color:var(--lvl-mut);margin-top:2px}
/* ── WHICH SCHEDULE AM I LOOKING AT ───────────────────────────────
   Sits directly above the picture it governs, because a control for a chart
   that is anywhere else is a control nobody finds. */
/* ── THE SWITCH SITS ON THE PICTURE, NOT ABOVE IT ──────────────────
   As its own row it took 34px off a chart that is already the first thing to
   lose height on a short window. It floats in the plot's top-left corner —
   over the area every deployment curve leaves empty, because a mobilise /
   build / demobilise profile is low at the start. */
.lvl-cc-cmp{position:absolute;top:8px;left:10px;z-index:2;
  display:flex;align-items:center;gap:3px;padding:3px;border-radius:999px;
  border:1px solid var(--lvl-line);background:color-mix(in srgb,var(--lvl-card) 88%,transparent);
  backdrop-filter:blur(6px);box-shadow:var(--lvl-sh)}
/* inside the drawer it is a normal block again — there is no chart under it */
.lvl-chg-f-row .lvl-cc-cmp{position:static;backdrop-filter:none;box-shadow:none;
  background:var(--lvl-wash)}
.lvl-cc-cmp>span{padding:0 8px 0 7px;font:700 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.1em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-cmp-b{border:0;border-radius:999px;padding:5px 12px;cursor:pointer;background:none;
  font:600 var(--lvl-t-2)/1 var(--lvl-font);color:var(--lvl-mut);
  transition:background .12s ease,color .12s ease,box-shadow .12s ease}
.lvl-cc-cmp-b:hover{color:var(--lvl-ink);background:color-mix(in srgb,var(--lvl-ink) 5%,transparent)}
.lvl-cc-cmp-b.is-on{background:var(--lvl-card);color:var(--lvl-ink);font-weight:700;
  box-shadow:var(--lvl-sh)}
/* a pane that is holding an error says so on the switch, not only inside */
.lvl-cc-cmp-b.is-bad{color:var(--lvl-risk)}
.lvl-cc-cmp-b.is-bad>u{color:var(--lvl-risk)}
.lvl-cc-cmp-b.is-bad.is-on{box-shadow:var(--lvl-sh),inset 0 -2px 0 var(--lvl-risk)}
/* inside a board it is a normal block that starts the region */
.lvl-cc-cmp.is-panes{position:static;align-self:flex-start;margin:0 0 10px;
  backdrop-filter:none;box-shadow:none;background:var(--lvl-wash);flex-wrap:wrap}
/* drawn alone, the master is the BEFORE state and wears its colour, so the
   planner is never in doubt about which of the two is on screen */
.lvl-cc-curve-art.is-was .lvl-shape-b{fill:var(--lvl-before);opacity:.55}
.lvl-cc-curve-art.is-was .lvl-shape-b.is-over,
.lvl-cc-curve-art.is-was .lvl-shape-b.is-under{fill:var(--lvl-before);opacity:.55}

.lvl-cc-curve-art{position:relative;flex:1 1 auto;min-height:0;overflow-y:auto;overscroll-behavior:contain;
  padding-right:4px;display:block;
  border:1px solid var(--lvl-line-2);border-radius:var(--lvl-r-s);background:var(--lvl-wash);padding:6px 8px 4px}
.lvl-cc-foot{flex:0 0 auto;margin:0;font:500 10.5px/1.35 var(--lvl-font);color:var(--lvl-mut)}

/* ── board: the crews ─────────────────────────────────────────────── */
.lvl-cc-crews{height:100%;min-height:0;display:flex;flex-direction:column;gap:6px}
.lvl-cc-crews-h{flex:0 0 auto;display:flex;align-items:baseline;gap:8px}
.lvl-cc-crews-h b{font:700 12px/1 var(--lvl-font);color:var(--lvl-ink)}
.lvl-cc-crews-h span{font:500 10.5px/1 var(--lvl-font);color:var(--lvl-mut-2);flex:1 1 auto}
/* the trades that are OVER are the ones that must be on screen without
   reaching for a scrollbar; the rest of the board is the work they cause */
/* tighter rows and a taller list: eleven of twenty-two trades on screen was
   half a register, and the board under it is one line of drivers */
.lvl-cc-crews-l{flex:0 1 auto;min-height:0;max-height:62%;
  overflow-y:auto;overscroll-behavior:contain;display:flex;flex-direction:column;gap:1px}
.lvl-cc-crews-l{gap:2px}
/* the caption row — same grid as a row, so each label sits over its column */
.lvl-cc-crew-hd{flex:0 0 auto;padding-top:2px;padding-bottom:3px;cursor:default;
  border-bottom:1px solid var(--lvl-line);border-radius:0;margin-bottom:2px}
.lvl-cc-crew-hd>span,.lvl-cc-crew-hd>b{min-width:0;
  font:700 var(--lvl-t-1)/1.15 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.07em;text-transform:uppercase;color:var(--lvl-mut-2);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
/* on a narrow board the captions are wider than the columns they name, and a
   caption row that has to be scrolled sideways to read is not a caption row.
   The sentence beside the heading says the same thing in one line. */
@container stage (max-width:760px){
  .lvl-cc-crew.lvl-cc-crew-hd{display:none}
  /* ── AND THE BOARD HEADING STOPS FIGHTING ITSELF ────────────────────
     A heading, a sentence and a link on one row in 500px is three columns
     of 160px: "1 of 22 trades over their / ceiling", "bar is the peak, the
     notch is / the limit", "Ceilings & / crews →". Every one of them broken
     mid-phrase. Stacked, each gets the whole width and reads as written. */
  .lvl-cc-crews-h{flex-direction:column;align-items:flex-start;gap:2px}
  .lvl-cc-crews-h span{flex:0 0 auto}
  .lvl-cc-crews-h .lvl-link{align-self:flex-start}
}
.lvl-cc-crew-hd>b{text-align:right}
.lvl-cc-crew-hd:hover{background:none}
.lvl-cc-crew{flex:0 0 auto;display:grid;
  grid-template-columns:10px minmax(84px,1fr) minmax(80px,1.5fr) 88px minmax(180px,3fr) 96px;
  align-items:center;gap:9px;padding:3px 6px;border:0;border-radius:4px;background:none;
  cursor:pointer;text-align:left;width:100%}
/* WHEN each trade breaches, on one shared axis — three crews breaching the
   same month is a sequencing problem, and it is invisible as three sentences */
.lvl-cc-when{position:relative;display:block;height:11px;border-radius:3px;
  background:var(--lvl-wash);border:1px solid var(--lvl-line-2);overflow:hidden}
.lvl-cc-when>i{position:absolute;top:0;bottom:0;background:var(--lvl-risk);opacity:.85;border-radius:1px}
.lvl-cc-when.is-clear{background:var(--lvl-line);opacity:.35;border-color:transparent}
.lvl-cc-crews-f{flex:0 0 auto;display:flex;align-items:center;gap:8px;padding-top:5px;margin-top:2px;
  border-top:1px dashed var(--lvl-line-2)}
.lvl-cc-crews-f span{font:600 9.5px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-mut-2)}
.lvl-cc-crews-f em{flex:1 1 auto;text-align:center;font-style:normal;
  font:500 9.5px/1 var(--lvl-font);color:var(--lvl-mut-2)}
.lvl-cc-crew:hover{background:var(--lvl-wash)}
.lvl-cc-crew.is-over{background:color-mix(in srgb,var(--lvl-risk) 5%,transparent)}
.lvl-cc-crew.is-over:hover{background:color-mix(in srgb,var(--lvl-risk) 10%,transparent)}
.lvl-cc-crew-d{width:8px;height:8px;border-radius:50%}
.lvl-cc-crew-n{font:600 11px/1.2 var(--lvl-font);color:var(--lvl-ink);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-crew-b{position:relative;height:9px;border-radius:5px;background:var(--lvl-line);overflow:visible}
.lvl-cc-crew-b>i{position:absolute;inset:0 auto 0 0;border-radius:5px;opacity:.9}
.lvl-cc-crew-b>u{position:absolute;top:-3px;bottom:-3px;width:2px;background:var(--lvl-ink-2);border-radius:1px}
.lvl-cc-crew-v{font:800 11.5px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ink);text-align:right}
.lvl-cc-crew.is-over .lvl-cc-crew-v{color:var(--lvl-risk)}
.lvl-cc-crew-v em{font-style:normal;font-weight:600;font-size:10.5px;color:var(--lvl-mut-2)}
.lvl-cc-crew-x{font:500 10.5px/1.2 var(--lvl-font);color:var(--lvl-mut);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}

/* ── board: rules and room ────────────────────────────────────────── */
/* ── THE BRIEF IS ONE COLUMN, NOT TWO HALVES ───────────────────────
   Split down the middle, the nine rules had a 470px column to live in, which
   is two cards across and five rows deep — the same wall of text the cards
   were meant to replace, just in boxes. Across the FULL width they are four
   or five to a row and two rows deep: a panel you scan.
   The room it has to spend follows underneath, where it reads as the answer
   to the rules above it rather than as a second, competing column. */
.lvl-cc-rules{height:100%;min-height:0;display:flex;flex-direction:column;gap:var(--lvl-sp-3);
  overflow-y:auto;overscroll-behavior:contain}
/* FLEX ITEMS SHRINK BY DEFAULT, AND A SHRUNK BLOCK WITH VISIBLE OVERFLOW
   DOES NOT CLIP — IT LAPS. The rules section was allowed to shrink below the
   height its wrapped grid needs, so the ninth card was drawn on top of the
   section beneath it. Neither section shrinks. */
.lvl-cc-rules-a,.lvl-cc-rules-b{flex:0 0 auto;min-height:0}
.lvl-cc-rules-b{padding-top:var(--lvl-sp-3);border-top:1px solid var(--lvl-line)}
/* THE HEADING AND ITS CAPTION WERE COMPETING FOR THE SAME SPACE. Both were
   `flex:1 1 auto`, so the two-word heading wrapped onto a second line while
   the sentence beside it — the one that says what the list underneath means —
   was cut at "the date will not stay put o…". The heading takes what it needs
   and does not wrap; the caption takes the rest and wraps to two lines rather
   than losing its ending. */
.lvl-cc-h{display:flex;align-items:baseline;flex-wrap:wrap;gap:4px 8px;margin:0 0 6px}
.lvl-cc-h b{font:700 var(--lvl-t-3)/1.25 var(--lvl-font);color:var(--lvl-ink);
  flex:0 1 auto;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-sess{height:100%;min-height:0;overflow-y:auto;overscroll-behavior:contain}
.lvl-cc-empty{height:100%;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:6px;
  color:var(--lvl-mut)}
.lvl-cc-empty b{font:700 13px/1.2 var(--lvl-font);color:var(--lvl-ink-2)}
.lvl-cc-empty span{font:500 11px/1.4 var(--lvl-font);max-width:38ch;text-align:center}

/* the trades ladder now lives in the rail — its rules are with the rail,
   under "THE UTILISATION LADDER" below. The pill-shaped strip that used to
   sit here was replaced by that ladder and its rules were never removed;
   they were still tinting the over-allocated rows from three screens away. */
/* ── THE RULE THAT BROKE THE TABLET ────────────────────────────────────
   This said `236px 1fr` — two columns — and it was right when the body WAS
   two columns, a rail and a stage. The body is three now, and a third child
   in a two-column grid does not disappear: it wraps onto the next row, under
   the ladder, in the 236px column. Measured on the reporter's own tablet
   between 1024 and 1180: the call card stacked under the utilisation list,
   the pair of them made the row taller than the window, the shell clipped,
   and the deployment curve — the picture the board exists for — was simply
   not on the screen.
   Three columns here too, just narrower. The band layout starts at 1024,
   where it is genuinely needed. */
@media (max-width:1180px){
  .lvl-cc-body{grid-template-columns:236px minmax(0,1fr) 264px}
  .lvl-cc-call{padding:var(--lvl-sp-3)}
}

/* what is driving the breaches — the board ends on the work, not the reading */
.lvl-cc-drivers{flex:1 1 auto;min-height:0;display:flex;flex-direction:column;
  margin-top:8px;padding-top:8px;border-top:1px solid var(--lvl-line)}
.lvl-cc-drivers-l{flex:1 1 auto;min-height:0;overflow-y:auto;overscroll-behavior:contain;
  display:flex;flex-direction:column;gap:1px}
.lvl-cc-driver{flex:0 0 auto;display:grid;
  grid-template-columns:9px minmax(140px,3fr) minmax(64px,1fr) 78px 118px 84px;
  align-items:center;gap:9px;padding:4px 6px;border:0;border-radius:4px;background:none;
  cursor:pointer;text-align:left;width:100%}
.lvl-cc-driver:hover{background:var(--lvl-wash)}
.lvl-cc-driver>i{width:8px;height:8px;border-radius:50%}
.lvl-cc-driver-n{font:600 11px/1.2 var(--lvl-font);color:var(--lvl-ink);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-driver-r{font:500 10.5px/1.2 var(--lvl-font);color:var(--lvl-mut);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-driver>b{font:800 11.5px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ink);text-align:right}
.lvl-cc-driver>b em{font-style:normal;font-weight:600;font-size:9.5px;color:var(--lvl-mut-2)}
.lvl-cc-driver-d{font:500 10.5px/1.2 var(--lvl-font);color:var(--lvl-mut)}
.lvl-cc-driver-f{font:700 9.5px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ok);text-align:right}
.lvl-cc-driver-f.is-none{color:var(--lvl-risk)}


/* ══════════════════════════════════════════════════════════════════════
   THE COCKPIT, SECOND PASS
   Six boards, three of which used to be tabs of their own. The rule that
   decides every measurement below: the verdict, the rail and the tab row
   never move, and a board scrolls INSIDE itself — so the window never does.
   ═══════════════════════════════════════════════════════════════════ */

/* the curve board: the real chart, and the S-curve under it */
.lvl-cc-curve-art .lvl-chart{margin:0 0 4px}
.lvl-cc-curve-art .lvl-svg{width:100%;height:auto}
.lvl-cc-curve-art .lvl-q-parts{margin-top:4px}
/* the profile chart carries its own legend row; a heading that follows it
   must clear it, or the two are drawn on top of each other */
.lvl-cc-curve-art>.lvl-cc-h{margin:14px 0 6px;padding-top:10px;border-top:1px solid var(--lvl-line-2)}
.lvl-cc-curve-art>.lvl-cc-h:first-child{margin-top:0;padding-top:0;border-top:0}
.lvl-cc-curve-art .lvl-scale{margin-bottom:2px}
.lvl-cc-curve-art .lvl-note{margin:6px 0 2px}

/* ── the over-allocation board, split by a selected trade ───────────── */
.lvl-cc-crew.is-on{background:color-mix(in srgb,var(--lvl-green) 10%,transparent);
  box-shadow:inset 2px 0 0 var(--lvl-green)}
.lvl-cc-crews.is-split{display:grid;column-gap:12px;row-gap:5px;
  grid-template-columns:minmax(280px,33%) 1fr;grid-template-rows:auto 1fr auto;
  grid-template-areas:"h d" "l d" "f d"}
.lvl-cc-crews.is-split>.lvl-cc-crews-h{grid-area:h}
.lvl-cc-crews.is-split>.lvl-cc-crews-l{grid-area:l;max-height:none}
.lvl-cc-crews.is-split>.lvl-cc-crews-f{grid-area:f}
.lvl-cc-crews.is-split>.lvl-cc-rd{grid-area:d;min-height:0}
.lvl-cc-crews.is-split .lvl-cc-crews-h span,
.lvl-cc-crews.is-split .lvl-cc-crews-h .lvl-link{display:none}
/* in the split the NAME gets the room, same rule as everywhere else: at
   1fr against a 1.1fr bar it came out "Soft Lands…", "Commissio…",
   "Sewerage …" — a list of trades whose trades cannot be told apart */
.lvl-cc-crews.is-split .lvl-cc-crew{grid-template-columns:10px minmax(70px,1.9fr) minmax(40px,.7fr) 58px}
/* and the caption row goes: it has no grid-area in the split, so it was
   auto-placed at the very bottom of the board, captioning nothing */
.lvl-cc-crews.is-split .lvl-cc-crew.lvl-cc-crew-hd{display:none}
.lvl-cc-crews.is-split .lvl-cc-crew-hd>span:nth-of-type(3),
.lvl-cc-crews.is-split .lvl-cc-crew-hd>span:nth-of-type(4),
.lvl-cc-crews.is-split .lvl-cc-when,
.lvl-cc-crews.is-split .lvl-cc-crew-x,
.lvl-cc-crews.is-split .lvl-cc-crews-f em{display:none}
.lvl-cc-crews.is-split>.lvl-cc-crews-f{justify-content:space-between}

/* ── the trade, in place ────────────────────────────────────────────── */
.lvl-cc-rd{min-height:0;display:flex;flex-direction:column;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);background:var(--lvl-card);overflow:hidden}
/* ── THE TRADE'S OWN HEADER, ON TWO LINES WHEN IT NEEDS THEM ───────
   Four things on one row in a 480px pane came out "Electrical W…" · "111%
   OF ITS CEILING" · "4 activities" · "504 man-d…" — the trade's NAME cut to
   make room for a caption, which is the wrong thing to lose. The name and
   the ratio hold the first line with the close button; the counts drop to
   their own line and keep the whole width. */
.lvl-cc-rd-h{flex:0 0 auto;display:grid;
  grid-template-columns:9px minmax(0,1fr) auto auto;
  align-items:center;gap:3px 8px;padding:6px 8px 7px 10px;
  border-bottom:1px solid var(--lvl-line);background:var(--lvl-wash)}
.lvl-cc-rd-h>i{width:9px;height:9px;border-radius:50%;flex:none}
.lvl-cc-rd-h>b{min-width:0;font:800 var(--lvl-t-4)/1.2 var(--lvl-head);color:var(--lvl-ink);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-rd-h>.lvl-tag{justify-self:end}
.lvl-cc-rd-h>em{grid-column:2/-1;min-width:0;font-style:normal;
  font:500 var(--lvl-t-2)/1.3 var(--lvl-font);
  color:var(--lvl-mut);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-rd-h>.lvl-icobtn{grid-row:1;grid-column:4}
.lvl-cc-rd-b{flex:1 1 auto;min-height:0;display:grid;grid-template-columns:minmax(240px,42%) 1fr;gap:0}
.lvl-cc-rd-l{min-height:0;overflow-y:auto;overscroll-behavior:contain;padding:8px 10px;
  border-right:1px solid var(--lvl-line)}
.lvl-cc-rd-r{min-height:0;overflow-y:auto;overscroll-behavior:contain;padding:8px 10px;
  display:flex;flex-direction:column}
.lvl-cc-rd-k{display:grid;grid-template-columns:repeat(2,1fr);gap:1px;background:var(--lvl-line);
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);overflow:hidden;margin-bottom:9px}
.lvl-cc-rd-k>div{background:var(--lvl-card);padding:6px 8px}
.lvl-cc-rd-k span{display:block;font:700 9.5px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-rd-k b{display:block;font:800 17px/1.1 var(--lvl-head);color:var(--lvl-ink);margin-top:3px}
.lvl-cc-rd-k b.is-risk{color:var(--lvl-risk)}
.lvl-cc-rd-f{display:grid;grid-template-columns:repeat(2,1fr);gap:7px;margin-bottom:9px}
.lvl-cc-fld{display:flex;flex-direction:column;gap:3px;min-width:0}
.lvl-cc-fld>span{font:700 9.5px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-fld>em{font-style:normal;font:500 9.5px/1.3 var(--lvl-font);color:var(--lvl-mut-2)}
.lvl-cc-fld .lvl-num,.lvl-cc-fld .lvl-sel-s{width:100%}
.lvl-cc-rd-w{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:1px}
.lvl-cc-rd-w>li{display:grid;grid-template-columns:1fr 64px 52px;align-items:center;gap:8px;
  padding:4px 6px;border-radius:4px;background:color-mix(in srgb,var(--lvl-risk) 6%,transparent)}
.lvl-cc-rd-w time{font:600 10.5px/1.2 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ink-2)}
.lvl-cc-rd-w b{font:800 11px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-risk);text-align:right}
.lvl-cc-rd-w b em{font-style:normal;font-weight:600;font-size:9.5px;color:var(--lvl-mut-2)}
.lvl-cc-rd-w span{font:500 9.5px/1.2 var(--lvl-font);color:var(--lvl-mut);text-align:right}
.lvl-cc-rd-r .lvl-cc-drivers{margin-top:8px}
/* the drivers list is drawn for a full board; inside the trade pane it has
   half the width, so it drops the columns it can afford to lose rather than
   running its rows off the edge */
.lvl-cc-rd-r .lvl-cc-driver{grid-template-columns:9px minmax(110px,2.6fr) minmax(36px,1fr) 60px 84px 58px;gap:7px}
.lvl-cc-rd-r .lvl-cc-driver-g{display:none}
.lvl-cc-rd-r .lvl-cc-driver-d,.lvl-cc-rd-r .lvl-cc-driver-f{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}

/* ── the drivers, with a share bar and a date ───────────────────────── */
.lvl-cc-driver{grid-template-columns:9px minmax(150px,3fr) minmax(60px,1.3fr) 74px 106px 74px 16px}
.lvl-cc-driver-n u{display:block;text-decoration:none;font:500 9.5px/1.3 var(--lvl-font);
  color:var(--lvl-mut-2);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-driver-s{position:relative;display:block;height:6px;border-radius:3px;
  background:var(--lvl-line);overflow:hidden}
.lvl-cc-driver-s>i{position:absolute;inset:0 auto 0 0;border-radius:3px;opacity:.85}
.lvl-cc-driver-g{display:flex;justify-content:flex-end;color:var(--lvl-mut-2);opacity:0;transition:opacity .12s}
.lvl-cc-driver:hover .lvl-cc-driver-g{opacity:1}

/* ── the brief ──────────────────────────────────────────────────────── */
.lvl-cc-lead{margin:0 0 7px;font:600 12px/1.4 var(--lvl-font);color:var(--lvl-ink-2)}
.lvl-cc-h span{flex:1 1 200px;min-width:0;font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut-2);
  display:-webkit-box;-webkit-box-orient:vertical;-webkit-line-clamp:2;line-clamp:2;overflow:hidden}
.lvl-cc-h.is-lead{padding-bottom:7px;margin-bottom:8px;border-bottom:1px solid var(--lvl-line)}
.lvl-cc-h.is-lead b{font:800 14px/1.2 var(--lvl-head);flex:none}

/* how much room the brief grants, before the chart of how it is spread */
/* three cells, not four: "bars that may move" and the float total are on the
   headline card, and this board is about how that float is SPREAD */
.lvl-cc-room{display:grid;grid-template-columns:repeat(auto-fit,minmax(180px,1fr));gap:var(--lvl-sp-2);
  background:none;border:0;border-radius:0;overflow:visible;margin-bottom:var(--lvl-sp-3)}
.lvl-cc-room>div{background:var(--lvl-card);padding:10px 13px 11px;
  border:1px solid var(--lvl-line);border-top:3px solid var(--lvl-line-3);
  border-radius:var(--lvl-r);box-shadow:var(--lvl-sh)}
.lvl-cc-room>div.is-ok{border-top-color:var(--lvl-ok)}
.lvl-cc-room>div.is-warn{border-top-color:var(--lvl-warn)}
.lvl-cc-room>div.is-risk{border-top-color:var(--lvl-risk)}
.lvl-cc-room span{display:block;font:700 9.5px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-room b{display:block;font:800 var(--lvl-t-5)/1.15 var(--lvl-head);color:var(--lvl-ink);margin-top:3px}
.lvl-cc-room b i{font-style:normal;font-size:11px;font-weight:700;color:var(--lvl-mut-2)}
.lvl-cc-room>div.is-warn b{color:var(--lvl-warn)}
.lvl-cc-room>div.is-risk b{color:var(--lvl-risk)}
.lvl-cc-room em{display:block;font-style:normal;font:500 9.5px/1.3 var(--lvl-font);color:var(--lvl-mut);margin-top:2px}

/* ══ THE UTILISATION LADDER ═════════════════════════════════════════════
   It was a full-width footer under the stage with `max-height:74px` — three
   rows of space for a register that is five rows on this project and nine on
   a real one. What that produced on screen was a row sliced through the
   middle at the bottom edge of the window: content hidden with nothing
   saying so, which is the one failure mode a scroll container must not have.

   It is a COLUMN now, at the foot of the rail, taking every pixel the six
   signals do not need. Three things follow from that: on a 22-trade project
   it shows twelve to fourteen rows instead of three; the trades are sorted
   worst-first, so the ones a planner must see are the ones that never need
   scrolling; and where there IS more, the scroll shadows below say so.
   ═══════════════════════════════════════════════════════════════════════ */
/* content-height now: it lists the trades that need dealing with, and on a
   clean programme that is nothing at all — a card stretched to a column it
   has no rows for is the emptiest thing on the page */
/* IT FILLS THE COLUMN. `flex:0 1 auto` sized it to its content, so a ladder
   showing seven trades left 400px of empty column under it while its own
   "18 more" sat folded away — the page's largest blank space was directly
   under the list it was hiding rows from. */
.lvl-cc-strip{flex:1 1 auto;min-height:0;display:flex;flex-direction:column;gap:6px;
  padding:10px 5px 7px 11px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r);
  background:var(--lvl-card);box-shadow:var(--lvl-sh);overflow:hidden}
.lvl-cc-strip-h{flex:0 0 auto;display:flex;align-items:baseline;gap:6px;flex-wrap:wrap;padding-right:5px}
.lvl-cc-strip-h b{font:700 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.12em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-strip-h em{font-style:normal;font:700 var(--lvl-t-2)/1 var(--lvl-font);color:var(--lvl-ink-2)}
.lvl-cc-strip-h em.is-over{color:var(--lvl-risk)}
/* the reading key drops to its own line rather than being squeezed against
   the count — right-aligned in a 264px column it collided with it */
.lvl-cc-strip-h u{text-decoration:none;flex:1 0 100%;
  font:500 var(--lvl-t-1)/1.3 var(--lvl-font);color:var(--lvl-mut-2)}
/* THE SCROLL SAYS THAT IT SCROLLS. The two `local` gradients paint the
   container's own top and bottom; the two `scroll` radials sit on the
   viewport edge and are only visible while the local ones have been pushed
   away — so a shadow appears at exactly the edge that has content beyond it,
   and at neither edge when everything fits. */
.lvl-cc-strip-l{flex:1 1 auto;min-height:0;display:flex;flex-direction:column;gap:1px;
  max-height:none;overflow-y:auto;overscroll-behavior:contain;padding-right:5px;
  background:
    linear-gradient(var(--lvl-card) 30%,rgba(255,255,255,0)) top/100% 14px no-repeat local,
    linear-gradient(rgba(255,255,255,0),var(--lvl-card) 70%) bottom/100% 14px no-repeat local,
    radial-gradient(farthest-side at 50% 0,rgba(20,32,42,.13),rgba(20,32,42,0)) top/100% 6px no-repeat scroll,
    radial-gradient(farthest-side at 50% 100%,rgba(20,32,42,.13),rgba(20,32,42,0)) bottom/100% 6px no-repeat scroll}
/* THE NAME GETS THE ROOM, BECAUSE THE NAME IS WHAT IS BEING READ.
   At 1.3fr against a .75fr bar, "Sewerage Network" came out "Sewerage Net"
   and "Commissioning" came out "Commissionin" — a register of trades whose
   trades cannot be told apart. The bar is a comparison, and a comparison
   reads fine at 40px; a truncated name reads as nothing. */
.lvl-cc-chip{flex:0 0 auto;display:grid;grid-template-columns:minmax(0,1.9fr) minmax(34px,.6fr) 34px;
  align-items:center;gap:8px;min-height:23px;padding:2px 5px;border:0;border-radius:5px;
  background:none;cursor:pointer;text-align:left}
.lvl-cc-chip:hover{background:var(--lvl-wash)}
.lvl-cc-chip.is-on{background:var(--lvl-green-t);box-shadow:inset 2px 0 0 var(--lvl-green)}
/* an over-allocated trade is a RED ROW, not a red number at the end of one */
.lvl-cc-chip.is-over{background:color-mix(in srgb,var(--lvl-risk) 7%,transparent)}
.lvl-cc-chip.is-over:hover{background:color-mix(in srgb,var(--lvl-risk) 12%,transparent)}
/* THE RULE BETWEEN THE TRADES THAT ARE OVER AND THE ONES THAT ARE NOT.
   Sorting already put them first; a line SAYS so, and turns a list of
   twenty-two into a group of three and a tail nobody has to read. */
.lvl-cc-chip.is-first-inside{margin-top:7px;padding-top:7px;
  border-top:1px solid var(--lvl-line);border-radius:0 0 5px 5px}
.lvl-cc-chip-n{display:flex;align-items:center;gap:6px;min-width:0;
  font:600 var(--lvl-t-2)/1.25 var(--lvl-font);color:var(--lvl-mut);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
/* the trade keeps its own hue HERE, on the dot, where identity belongs and
   where it is not competing with the reading */
.lvl-cc-chip-n i{width:7px;height:7px;border-radius:50%;flex:none}
.lvl-cc-chip-b{position:relative;display:block;height:7px;border-radius:4px;
  background:var(--lvl-line-2);overflow:visible}
/* PAINTED BY STATE, NOT BY TRADE. Twenty-two categorical hues in one column
   is a rainbow, and the one thing this column is for — which of these do I
   have to deal with — was left to a red percentage at the far right. */
.lvl-cc-chip-b>i{position:absolute;inset:0 auto 0 0;border-radius:4px;
  background:var(--lvl-mut-2)}
.lvl-cc-chip.is-over .lvl-cc-chip-b>i{background:var(--lvl-risk)}
/* the ceiling: a full-height tick in the ink colour, so "past the line" is
   the reading rather than "longer than the others" */
.lvl-cc-chip-b>u{position:absolute;top:-3px;bottom:-3px;width:2px;
  background:var(--lvl-ink-2);border-radius:1px;opacity:.55}
.lvl-cc-chip>b{font:700 var(--lvl-t-2)/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-mut);
  text-align:right;white-space:nowrap}
.lvl-cc-chip>b>s{text-decoration:none;font-size:9px;color:var(--lvl-mut-2);margin-left:1px}
.lvl-cc-chip.is-over>b{color:var(--lvl-risk);font-weight:800}
.lvl-cc-chip.is-over .lvl-cc-chip-n{color:var(--lvl-ink);font-weight:700}
/* the rest of the register, one click away and saying how many it is */
.lvl-cc-strip-more{flex:0 0 auto;display:flex;align-items:center;justify-content:center;gap:6px;
  margin-top:5px;padding:6px 8px;border:1px dashed var(--lvl-line-3);border-radius:var(--lvl-r-s);
  background:none;cursor:pointer;color:var(--lvl-mut);
  font:600 var(--lvl-t-2)/1 var(--lvl-font);transition:background .12s ease,color .12s ease}
.lvl-cc-strip-more:hover{background:var(--lvl-wash);color:var(--lvl-ink);border-color:var(--lvl-mut-2)}

/* ── ASKED OF THE STAGE, NOT OF THE WINDOW ─────────────────────────
   These used to be `@media (max-width:1240px)`. A board does not live in the
   window; it lives in the stage, which is the window minus two side columns.
   The trade detail is a two-pane split at 700px of stage on a 1900px window
   and a single column at 700px of stage on a 1240px one — the same board,
   the same room, two layouts, for a reason that has nothing to do with it. */
@container stage (max-width:820px){
  .lvl-cc-rd-b{grid-template-columns:1fr}
  .lvl-cc-rd-l{border-right:0;border-bottom:1px solid var(--lvl-line)}
  .lvl-cc-crews.is-split{grid-template-columns:minmax(250px,40%) 1fr}
  .lvl-cc-2{grid-template-columns:1fr}
  .lvl-cc-hist-k{grid-template-columns:repeat(2,1fr)}
}
/* ── AND WHERE THE ROOM IS GENUINELY TIGHT, THE SPLIT STOPS PRETENDING ──
   Two panes in 560px is 280px each, which is not two panes; it is two
   columns of ellipsis. The crews board stacks its list and the trade it has
   open, and the trade keeps the width it needs to be read. */
/* ── AND THE ROW SHEDS COLUMNS BEFORE IT SHEDS THE SIDE OF THE BOARD ──
   Six tracks with a 569px floor in a 448px board is 121px of row hanging off
   the edge with no way to reach it. The two widest are the ones a planner
   can do without at this size: the timeline strip (its own footer says the
   span) and the man-days tail (the peak/limit pair beside it says the same
   thing in the units the ceiling is set in). */
@container stage (max-width:760px){
  .lvl-cc-crew{grid-template-columns:10px minmax(64px,1.4fr) minmax(56px,1fr) 62px}
  .lvl-cc-crew .lvl-cc-when,.lvl-cc-crew-x{display:none}
}
@container stage (max-width:640px){
  .lvl-cc-crews.is-split{grid-template-columns:1fr;grid-template-rows:auto auto 1fr;
    grid-template-areas:"h" "l" "d"}
  .lvl-cc-crews.is-split>.lvl-cc-crews-f{display:none}
  .lvl-cc-meters{grid-template-columns:repeat(2,1fr)}
  .lvl-ba-cards,.lvl-imp,.lvl-rules{grid-template-columns:1fr 1fr}
}


/* ══════════════════════════════════════════════════════════════════════
   THE COCKPIT, THIRD PASS — the boards that were "weak"
   The rule everywhere below: a board never scrolls vertically. Where it has
   more to say than fits, it says it one pane at a time and you step sideways.
   ═══════════════════════════════════════════════════════════════════ */

/* ── STEPPING BETWEEN PICTURES, UNDER THE PICTURE ─────────────────────
   A full-width row of labelled panes directly beneath the board's own tab
   row read as a second set of tabs, and two tab rows stacked is a page that
   looks like it has twelve destinations when it has five. This is one small
   control, under the chart where the thing it changes is, and it says which
   of how many you are looking at. */
.lvl-cc-flip{flex:0 0 auto;display:flex;align-items:center;gap:8px;padding:5px 2px 0}
.lvl-cc-flip-b{flex:none;width:26px;height:26px;display:flex;align-items:center;justify-content:center;
  border:1px solid var(--lvl-line);border-radius:6px;background:var(--lvl-card);
  color:var(--lvl-mut);cursor:pointer}
.lvl-cc-flip-b:hover{border-color:var(--lvl-mut-2);color:var(--lvl-ink);background:var(--lvl-wash)}
.lvl-cc-flip-l{flex:1 1 auto;min-width:0}
.lvl-cc-flip-l b{display:block;font:700 12px/1.2 var(--lvl-font);color:var(--lvl-ink)}
.lvl-cc-flip-l em{display:block;font-style:normal;font:500 10.5px/1.3 var(--lvl-font);color:var(--lvl-mut-2);margin-top:1px}
.lvl-cc-flip-n{flex:none;display:flex;gap:4px;align-items:center}
.lvl-cc-flip-n>i{width:6px;height:6px;border-radius:50%;background:var(--lvl-line);cursor:pointer;
  border:0;padding:0;display:block}
.lvl-cc-flip-n>i.is-on{background:var(--lvl-green)}
.lvl-cc-flip>.lvl-link{flex:none}

/* the session board keeps a labelled row: its four panes are four different
   questions, not four views of one picture, so naming them earns the space */
.lvl-cc-steps{flex:0 0 auto;display:flex;align-items:stretch;gap:1px;margin:8px 0 8px;
  background:var(--lvl-line);border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);overflow:hidden}
.lvl-cc-step{flex:1 1 0;min-width:0;text-align:left;padding:6px 11px;border:0;cursor:pointer;
  background:var(--lvl-wash);position:relative}
.lvl-cc-step b{display:block;font:700 var(--lvl-t-4)/1.2 var(--lvl-font);color:var(--lvl-mut);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
/* the same rule the board tabs follow: a caption wraps, it is not cut */
.lvl-cc-step em{display:-webkit-box;-webkit-box-orient:vertical;-webkit-line-clamp:2;line-clamp:2;
  overflow:hidden;font-style:normal;font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut-2);
  margin-top:1px}
.lvl-cc-step.is-on em{color:var(--lvl-mut)}
.lvl-cc-step:hover{background:var(--lvl-card)}
.lvl-cc-step.is-on{background:var(--lvl-card)}
.lvl-cc-step.is-on b{color:var(--lvl-ink)}
.lvl-cc-step.is-on::after{content:"";position:absolute;left:0;right:0;bottom:0;height:2px;background:var(--lvl-green)}
.lvl-cc-step.is-bad.is-on::after{background:var(--lvl-risk)}
.lvl-cc-step.is-bad b{color:var(--lvl-risk)}

/* ── the curve board: one picture, full height, no scroll ─────────────
   AND A FLOOR UNDER IT, BECAUSE `min-height:0` GOES ALL THE WAY DOWN.
   The picture is a flex child of a flex child, every level carrying
   `min-height:0` so the board can shrink — and the svg's own height is
   100% of that. Three levels of "you may be zero" means the picture IS
   zero the moment anything above it grows: an extra advisory line, a
   shortfall banner and an effort line that wraps to three, and the chart
   collapsed to a sliver pinned to the left of an empty box. It reads as
   "the curve is gone", which is what it looked like on a real board.

   The score, the meters and the advisories are all things a planner can
   scroll past. The picture is the one thing on this board that cannot be
   allowed to disappear, so it gets a floor. The layout still gives it
   every pixel that is going spare; it just may not give it none. */
/* the advisories take the height that is going spare and scroll inside it,
   so the chart's floor is never paid for by clipping the chart */
.lvl-cc-advis{flex:0 1 auto;min-height:0;overflow-y:auto;overscroll-behavior:contain;
  display:flex;flex-direction:column;gap:8px}
.lvl-cc-curve-art{flex:1 1 auto;min-height:150px;overflow:hidden;display:flex;flex-direction:column;
  margin-top:8px;border:1px solid var(--lvl-line-2);border-radius:var(--lvl-r-s);
  background:var(--lvl-wash);padding:6px 8px}
.lvl-cc-curve-art .lvl-chart{flex:1 1 auto;min-height:130px;margin:0;overflow:hidden;display:flex;align-items:center}
.lvl-cc-curve-art .lvl-svg{width:100%;height:100%;min-height:120px;max-height:100%}
.lvl-cc-curve-art .lvl-scale{flex:0 0 auto}

/* ── the ceilings register, read down a column ──────────────────────── */
.lvl-cc-lim{height:100%;min-height:0;display:flex;flex-direction:column;gap:6px}
.lvl-cc-lim-h{flex:0 0 auto;display:flex;align-items:center;flex-wrap:wrap;gap:8px 12px}
.lvl-cc-lim-h b{font:700 12.5px/1.2 var(--lvl-font);color:var(--lvl-ink)}
.lvl-cc-lim-h span{font:500 10.5px/1.3 var(--lvl-font);color:var(--lvl-mut-2);flex:1 1 auto;min-width:0}
.lvl-cc-lim-hd,.lvl-cc-lrow{display:grid;
  grid-template-columns:minmax(130px,1.4fr) minmax(160px,2.1fr) 68px 78px 82px minmax(100px,1fr) 58px;
  gap:10px;align-items:center}
/* the three numbers that MAKE the ceiling belong together and say so */
.lvl-cc-lim-hd i.g{color:var(--lvl-ink-2)}
.lvl-cc-lim-hd i.g1{border-left:1px solid var(--lvl-line);padding-left:8px;margin-left:-8px}
.lvl-cc-lim-hd{flex:0 0 auto;padding:0 8px 5px;border-bottom:1px solid var(--lvl-line)}
.lvl-cc-lim-hd i{font-style:normal;font:700 9.5px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-lim-hd i.n{text-align:right}
.lvl-cc-lim-l{flex:1 1 auto;min-height:0;overflow-y:auto;overscroll-behavior:contain;
  display:flex;flex-direction:column;gap:1px;padding-right:2px}
.lvl-cc-lrow{flex:0 0 auto;padding:5px 8px;border-radius:5px;border-left:3px solid transparent}
.lvl-cc-lrow:hover{background:var(--lvl-wash)}
.lvl-cc-lrow.is-over{background:color-mix(in srgb,var(--lvl-risk) 5%,transparent);border-left-color:var(--lvl-risk)}
.lvl-cc-lrow.is-on{box-shadow:inset 0 0 0 1px var(--lvl-green)}
.lvl-cc-lname{display:flex;align-items:center;gap:7px;min-width:0;border:0;background:none;
  cursor:pointer;text-align:left;padding:0;flex-wrap:wrap}
.lvl-cc-lname>i{width:8px;height:8px;border-radius:50%;flex:none}
.lvl-cc-lname>b{font:700 11.5px/1.2 var(--lvl-font);color:var(--lvl-ink);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis;max-width:100%}
.lvl-cc-lname>em{flex:1 0 100%;font-style:normal;font:500 9.5px/1.2 var(--lvl-font);color:var(--lvl-mut-2);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis;padding-left:15px}
.lvl-cc-lrow.is-over .lvl-cc-lname>em{color:var(--lvl-risk)}
.lvl-cc-lbar{display:grid;grid-template-columns:1fr 62px 40px;gap:8px;align-items:center;min-width:0}
.lvl-cc-lbar>u{text-decoration:none;position:relative;display:block;height:9px;border-radius:5px;
  background:var(--lvl-line);overflow:visible}
.lvl-cc-lbar>u>i{position:absolute;inset:0 auto 0 0;border-radius:5px;opacity:.9}
.lvl-cc-lbar>u>s{position:absolute;top:-3px;bottom:-3px;width:2px;background:var(--lvl-ink-2);border-radius:1px}
.lvl-cc-lbar>b{font:800 11.5px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ink);text-align:right}
.lvl-cc-lbar>b em{font-style:normal;font-weight:600;font-size:10.5px;color:var(--lvl-mut-2)}
.lvl-cc-lpct{font:800 11px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-mut);text-align:right}
.lvl-cc-lpct.is-over{color:var(--lvl-risk)}
.lvl-cc-lrow .lvl-num{width:100%;text-align:right}
.lvl-cc-lsrc{min-width:0}
.lvl-cc-lsrc em{display:block;font-style:normal;font:500 9.5px/1.2 var(--lvl-font);color:var(--lvl-mut-2);margin-top:2px}

/* ── this session: the decision on top, the evidence behind it ──────── */
.lvl-cc-sess{height:100%;min-height:0;display:flex;flex-direction:column}
.lvl-cc-sess-h{flex:0 0 auto;display:flex;align-items:center;gap:11px;padding:9px 11px;
  border:1px solid color-mix(in srgb,var(--lvl-after) 35%,var(--lvl-line));border-radius:var(--lvl-r-s);
  background:color-mix(in srgb,var(--lvl-after) 6%,var(--lvl-card))}
.lvl-cc-sess-h.is-blocked{border-color:color-mix(in srgb,var(--lvl-risk) 40%,var(--lvl-line));
  background:color-mix(in srgb,var(--lvl-risk) 7%,var(--lvl-card))}
.lvl-cc-sess-h>i{flex:none;display:flex;color:var(--lvl-after)}
.lvl-cc-sess-h.is-blocked>i{color:var(--lvl-risk)}
.lvl-cc-sess-h>div{flex:1 1 auto;min-width:0}
.lvl-cc-sess-h b{display:block;font:800 14px/1.2 var(--lvl-head);color:var(--lvl-ink)}
.lvl-cc-sess-h em{display:block;font-style:normal;font:500 11px/1.4 var(--lvl-font);color:var(--lvl-mut);margin-top:2px}
.lvl-cc-sess-a{flex:none;display:flex;gap:6px;align-items:center}
.lvl-cc-sess-b{flex:1 1 auto;min-height:0;overflow-y:auto;overscroll-behavior:contain;padding-right:4px}
.lvl-cc-sess-b>*{margin-bottom:9px}
.lvl-cc-3{display:grid;grid-template-columns:repeat(3,1fr);gap:14px;align-items:start}
.lvl-cc-1{display:flex;flex-direction:column;gap:10px}
.lvl-cc-3 h5,.lvl-cc-2 h5{margin:0 0 5px;font:700 10.5px/1 var(--lvl-font);color:var(--lvl-mut);
  text-transform:uppercase;letter-spacing:.05em}

/* ── the change log: four facts and two buttons ─────────────────────── */
.lvl-cc-hist{height:100%;min-height:0;display:flex;flex-direction:column;gap:8px}
.lvl-cc-hist-k{flex:0 0 auto;display:grid;grid-template-columns:repeat(4,1fr);gap:1px;
  background:var(--lvl-line);border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);overflow:hidden}
.lvl-cc-hist-k>div{background:var(--lvl-card);padding:7px 10px}
.lvl-cc-hist-k span{display:block;font:700 9.5px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-hist-k b{display:block;font:800 20px/1.1 var(--lvl-head);color:var(--lvl-ink);margin-top:3px}
.lvl-cc-hist-k b.is-warn{color:var(--lvl-warn)}
.lvl-cc-hist-k b.is-date{font-size:14px;font-family:var(--lvl-mono,var(--lvl-head))}
.lvl-cc-hist-k em{display:block;font-style:normal;font:500 9.5px/1.3 var(--lvl-font);
  color:var(--lvl-mut);margin-top:2px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-hist-k .lvl-link{margin-top:3px;font-size:9.5px}
.lvl-cc-hist-l{flex:1 1 auto;min-height:0;overflow-y:auto;overscroll-behavior:contain;
  display:flex;flex-direction:column;gap:6px;padding-right:4px}
/* ── WHY EVERY LOG ENTRY RENDERED AS AN EMPTY STRIPE ─────────────────
   A flex column shrinks its children to fit before it will scroll, and the
   default flex-shrink is 1. With twenty-one entries in a 500px board every
   article was squashed to 21px against its own 42px header, and overflow
   hidden did the rest: twenty-one blank white bars, every one of them a
   correctly-rendered entry nobody could see. The rule for every scrolling
   list in this file: the rows keep their height and the CONTAINER scrolls. */
.lvl-cc-ent{flex:0 0 auto;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);
  background:var(--lvl-card);border-left:3px solid var(--lvl-ok);overflow:hidden}
.lvl-cc-ent.is-off{border-left-color:var(--lvl-mut-2);opacity:.72}
.lvl-cc-ent-h{display:flex;align-items:center;gap:9px;padding:7px 10px;flex-wrap:wrap}
.lvl-cc-ent-h time{font:600 9.5px/1 var(--lvl-mono,var(--lvl-font));color:var(--lvl-mut-2);flex:none}
.lvl-cc-ent-h>b{font:700 12.5px/1.2 var(--lvl-font);color:var(--lvl-ink);flex:1 1 auto;min-width:0;
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-ent-a{flex:none;display:flex;gap:5px}
.lvl-cc-ent-m{display:grid;grid-template-columns:repeat(5,1fr);gap:1px;background:var(--lvl-line);
  border-top:1px solid var(--lvl-line)}
.lvl-cc-fact{background:var(--lvl-card);padding:6px 10px}
.lvl-cc-fact span{display:block;font:700 9.5px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-fact b{display:block;font:700 12px/1.2 var(--lvl-font);color:var(--lvl-ink);margin-top:3px}
.lvl-cc-fact.is-good b{color:var(--lvl-ok)}
.lvl-cc-fact.is-bad b{color:var(--lvl-warn)}
.lvl-cc-ent-d{padding:9px 10px;border-top:1px solid var(--lvl-line);background:var(--lvl-wash)}
.lvl-cc-ent-x{display:grid;grid-template-columns:repeat(auto-fit,minmax(180px,1fr));gap:8px 14px;margin-bottom:9px}
.lvl-cc-ent-x span{display:block;font:700 9.5px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-ent-x b{display:block;font:500 10.5px/1.35 var(--lvl-font);color:var(--lvl-ink-2);margin-top:2px}
.lvl-cc-mt{max-height:210px;overflow:auto;overscroll-behavior:contain;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);background:var(--lvl-card);margin-bottom:8px}
.lvl-cc-mt table{width:100%}
.lvl-cc-mt thead th{position:sticky;top:0;z-index:2;background:var(--lvl-wash)}

/* ── the room, and the float ladder under it ────────────────────────── */
/* ── THE SPREAD IS ONE MARK, AND THE BANDS ARE ITS KEY ────────────────
   Four separate bars, each measured against the same total, is four charts
   the reader has to add up — and the question is a COMPOSITION: how much of
   this programme can move at all. One stacked bar answers it at a glance;
   the bands become a legend under it, two by two, and the figure a planner
   came for leads the block instead of sitting in a paragraph below it. */
.lvl-cc-spread{margin-bottom:var(--lvl-sp-3);padding:var(--lvl-sp-3);
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r);background:var(--lvl-card)}
.lvl-cc-spread-h{display:flex;align-items:baseline;gap:8px;flex-wrap:wrap;
  margin-bottom:var(--lvl-sp-2)}
.lvl-cc-spread-h>b{flex:0 0 auto;font:700 var(--lvl-t-1)/1 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.12em;text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-cc-spread-h>span{flex:1 1 auto;min-width:0;text-align:right;
  font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut)}
.lvl-cc-spread-h u{text-decoration:none;font:800 var(--lvl-t-4)/1 var(--lvl-head);color:var(--lvl-ink)}
/* the composition itself */
.lvl-cc-spread-b{display:flex;height:14px;border-radius:7px;overflow:hidden;
  background:var(--lvl-line);box-shadow:inset 0 1px 2px rgba(20,32,42,.06)}
.lvl-cc-spread-b>i{display:block;height:100%;min-width:3px}
.lvl-cc-spread-b>i+i{box-shadow:inset 1px 0 0 rgba(255,255,255,.75)}
.lvl-cc-spread-b>i.is-risk{background:var(--lvl-risk)}
.lvl-cc-spread-b>i.is-warn{background:var(--lvl-warn)}
.lvl-cc-spread-b>i.is-ok{background:var(--lvl-ok)}
.lvl-cc-spread-b>i.is-good{background:var(--lvl-after)}
/* its key: two by two, so four bands cost two rows instead of four */
.lvl-cc-spread-k{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));
  gap:2px var(--lvl-sp-2);margin-top:var(--lvl-sp-2)}
.lvl-cc-rung{display:grid;grid-template-columns:9px auto auto minmax(0,1fr);
  align-items:baseline;gap:2px 7px;padding:5px 6px;border:0;border-radius:6px;
  background:none;cursor:pointer;text-align:left}
.lvl-cc-rung:hover{background:var(--lvl-wash)}
.lvl-cc-rung.is-nil{opacity:.45}
.lvl-cc-rung>i{grid-row:1;width:9px;height:9px;border-radius:50%;align-self:center;
  background:var(--lvl-line-2)}
.lvl-cc-rung.is-risk>i{background:var(--lvl-risk)}
.lvl-cc-rung.is-warn>i{background:var(--lvl-warn)}
.lvl-cc-rung.is-ok>i{background:var(--lvl-ok)}
.lvl-cc-rung.is-good>i{background:var(--lvl-after)}
.lvl-cc-rung>b{font:800 var(--lvl-t-5)/1 var(--lvl-head);color:var(--lvl-ink)}
.lvl-cc-rung.is-risk>b{color:var(--lvl-risk)}
.lvl-cc-rung>s{text-decoration:none;font:700 var(--lvl-t-2)/1 var(--lvl-mono,var(--lvl-font));
  color:var(--lvl-mut-2)}
.lvl-cc-rung>span{min-width:0;font:600 var(--lvl-t-3)/1.2 var(--lvl-font);color:var(--lvl-ink-2);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lvl-cc-rung>em{grid-column:2/-1;min-width:0;font-style:normal;
  font:500 var(--lvl-t-2)/1.25 var(--lvl-font);color:var(--lvl-mut-2);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
@container stage (max-width:620px){
  .lvl-cc-spread-k{grid-template-columns:minmax(0,1fr)}
}

/* the bars nothing holds -------------------------------------------------- */
.lvl-loose{display:flex;flex-direction:column;gap:5px;margin-top:8px}
.lvl-loose-r{flex:0 0 auto;display:grid;
  grid-template-columns:minmax(120px,1.5fr) minmax(140px,2fr) auto;
  gap:9px;align-items:center;padding:7px 9px;border-radius:8px;
  border:1px solid var(--lvl-line);background:var(--lvl-card)}
.lvl-loose-n{display:block;min-width:0;text-align:left;padding:0;border:0;
  background:none;cursor:pointer}
.lvl-loose-n>b{display:block;font:600 11px/1.25 var(--lvl-font);color:var(--lvl-ink);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-loose-n>em{display:block;font:500 9.5px/1.3 var(--lvl-font);color:var(--lvl-mut-2);
  font-style:normal;margin-top:2px}
.lvl-loose-n:hover>b{color:var(--lvl-info)}
.lvl-loose-s{min-width:0}
.lvl-loose-s>span{display:block;font:600 9px/1 var(--lvl-font);color:var(--lvl-mut-2);
  letter-spacing:.06em;text-transform:uppercase}
.lvl-loose-s>b{display:block;font:600 11px/1.25 var(--lvl-font);color:var(--lvl-ink);
  margin-top:3px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.lvl-loose-s>em{display:block;font:500 9.5px/1.35 var(--lvl-font);color:var(--lvl-mut);
  font-style:normal;margin-top:2px}
@media (max-width:900px){
  .lvl-loose-r{grid-template-columns:1fr auto}
  .lvl-loose-s{grid-column:1/-1}
}

/* THE CEILINGS TABLE IS SEVEN COLUMNS WITH A 736px FLOOR. Whether that fits
   is a question about the STAGE — it was being asked of the window, so the
   table kept all seven in a 700px stage on a wide monitor and dropped one in
   a 900px stage on a narrow laptop. Where it came from goes first (it is on
   the row's title), then the crew makeup: the trade, its peak against its
   ceiling and the ceiling itself never go. */
@container stage (max-width:860px){
  .lvl-cc-3{grid-template-columns:1fr}
  .lvl-cc-ent-m{grid-template-columns:repeat(3,1fr)}
  /* the last column holds a button, and 56px is not a button: it was
     overflowing its own cell by 23px on every one of twenty-two rows */
  /* ── A HIDDEN GRID ITEM IS NOT A ZERO COLUMN, IT IS ONE FEWER ITEM ────
     `display:none` takes the element out of the grid entirely, so every item
     after it shifts one track left. Hiding "where it came from" and leaving a
     `0` track for it put the action button in that zero-width track and left
     the real last track empty — which is why the button was clipped on every
     one of twenty-two rows while the row's own template looked correct. Six
     items, six tracks, and the action column is `auto`: whatever the widest
     button needs, which cannot be wrong. */
  .lvl-cc-lim-hd,.lvl-cc-lrow{grid-template-columns:minmax(110px,1.4fr) minmax(130px,2fr) 50px 54px 58px auto;
    gap:8px}
  .lvl-cc-lim-hd i:nth-child(6),.lvl-cc-lsrc{display:none}
  .lvl-cc-lrow>.lvl-btn{padding:0 9px;font-size:10.5px}
}
/* tighter still: the crew makeup goes (it is editable on the trade's own
   panel), and four items leave four tracks — the trade, its peak against its
   ceiling, the ceiling itself, and the way in */
@container stage (max-width:660px){
  .lvl-cc-lim-hd,.lvl-cc-lrow{grid-template-columns:minmax(90px,1.3fr) minmax(100px,1.8fr) 56px auto;
    gap:7px}
  .lvl-cc-lim-hd i:nth-child(3),.lvl-cc-lim-hd i:nth-child(4),
  .lvl-cc-lrow>.lvl-num.is-crew{display:none}
}

/* the back arrow is the same glyph, turned round */
.lvl-cc-flip-b.is-back .lvl-ic{transform:rotate(180deg)}
/* two-line column captions in the register header */
.lvl-cc-lim-hd i{line-height:1.25}

/* ── the dates, all of them, in one block ───────────────────────────── */
.lvl-dates{display:flex;flex-direction:column;gap:8px;padding:10px;margin-bottom:4px;
  border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);background:var(--lvl-wash)}
.lvl-dates-r{display:flex;align-items:flex-end;flex-wrap:wrap;gap:8px}
.lvl-dates-f{display:flex;flex-direction:column;gap:3px;min-width:0}
.lvl-dates-f>span{font:700 8px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-dates-f>em{font-style:normal;font:500 9.5px/1.3 var(--lvl-font);color:var(--lvl-mut-2)}
.lvl-dates-now{margin-left:auto;text-align:right}
.lvl-dates-now span{display:block;font:700 8px/1 var(--lvl-mono,var(--lvl-font));letter-spacing:.09em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-dates-now b{display:block;font:800 15px/1.2 var(--lvl-head);color:var(--lvl-ink);margin-top:3px}

/* an apply the validator refused, named so it can be acted on ------------- */
.lvl-blockapply{display:flex;flex-direction:column;gap:8px;margin:0 0 10px;padding:10px 12px}
.lvl-blockapply-h{display:flex;align-items:center;gap:8px;flex-wrap:wrap}
.lvl-blockapply-h>b{font:700 12px/1.3 var(--lvl-font);color:var(--lvl-risk)}
.lvl-blockapply-h>span{flex:1 1 auto;font:500 10px/1.35 var(--lvl-font);color:var(--lvl-mut)}
.lvl-blockapply-l{display:flex;flex-direction:column;gap:4px;max-height:180px;overflow-y:auto;
  overscroll-behavior:contain}
.lvl-blockapply-r{flex:0 0 auto;padding:5px 8px;border-radius:6px;background:var(--lvl-card);
  border:1px solid var(--lvl-line)}
.lvl-blockapply-r>b{display:block;font:600 10.5px/1.35 var(--lvl-font);color:var(--lvl-ink)}
.lvl-blockapply-r>em{display:block;font:500 9.5px/1.3 var(--lvl-mono,var(--lvl-font));
  color:var(--lvl-mut-2);font-style:normal;margin-top:2px}
.lvl-blockapply>.lvl-btn{align-self:flex-start}
.lvl-blockapply-n{font:500 10px/1.4 var(--lvl-font);color:var(--lvl-mut)}

/* ══ A SEARCH THAT BLOCKS THE THREAD, SHOWN HONESTLY ════════════════════
   The run is synchronous: no timer fires, no event runs and nothing the main
   thread paints can change while it is going. The old banner said so in
   words and then sat there, which reads exactly like a crash.

   A CSS animation on TRANSFORM or OPACITY is not run by the main thread —
   the compositor owns it, and it keeps running while JavaScript is blocked
   solid. So the ring really turns and the bar really sweeps, for the whole
   minute, on the frozen thread. Everything here animates one of those two
   properties and nothing else; anything that would need the thread (a
   percentage, an elapsed count) is deliberately absent, because that is the
   part that genuinely cannot tick.
   ═══════════════════════════════════════════════════════════════════════ */
body.lvl-is-busy{cursor:progress}
body.lvl-is-busy button,body.lvl-is-busy a,body.lvl-is-busy input,
body.lvl-is-busy select{cursor:progress}
.lvl-busy{position:fixed;inset:0;z-index:120;display:flex;align-items:center;
  justify-content:center;padding:24px;
  background:color-mix(in srgb,var(--lvl-bg) 68%,transparent);
  backdrop-filter:blur(2px);
  animation:lvl-busy-in .18s ease-out both}
@keyframes lvl-busy-in{from{opacity:0}to{opacity:1}}
.lvl-busy-c{width:min(420px,92vw);display:flex;flex-direction:column;align-items:center;
  gap:var(--lvl-sp-2);padding:var(--lvl-sp-4) var(--lvl-sp-4) var(--lvl-sp-3);
  border-radius:var(--lvl-r);border:1px solid var(--lvl-line);
  background:var(--lvl-card);box-shadow:var(--lvl-sh-2);text-align:center}
/* the ring: a conic sweep masked to a 3px band, turning on the compositor */
.lvl-busy-ring{position:relative;width:38px;height:38px;flex:none}
.lvl-busy-ring>i{position:absolute;inset:0;border-radius:50%;
  background:conic-gradient(from 0deg,transparent 0deg,var(--lvl-green) 300deg,transparent 360deg);
  -webkit-mask:radial-gradient(farthest-side,transparent calc(100% - 3.5px),#000 calc(100% - 3.5px));
  mask:radial-gradient(farthest-side,transparent calc(100% - 3.5px),#000 calc(100% - 3.5px));
  animation:lvl-busy-spin 1.1s linear infinite;will-change:transform}
@keyframes lvl-busy-spin{to{transform:rotate(360deg)}}
.lvl-busy-t{font:800 var(--lvl-t-5)/1.25 var(--lvl-head);color:var(--lvl-ink)}
.lvl-busy-n{font:500 var(--lvl-t-2)/1.5 var(--lvl-font);color:var(--lvl-mut)}
/* the sweep: one bar travelling the width of its track, also on transform */
.lvl-busy-bar{position:relative;width:100%;height:4px;margin-top:2px;border-radius:3px;
  background:var(--lvl-line);overflow:hidden}
.lvl-busy-bar>i{position:absolute;top:0;bottom:0;left:0;width:38%;border-radius:3px;
  background:linear-gradient(90deg,transparent,var(--lvl-green),transparent);
  animation:lvl-busy-sweep 1.4s cubic-bezier(.5,0,.5,1) infinite;will-change:transform}
@keyframes lvl-busy-sweep{
  from{transform:translateX(-100%)}
  to{transform:translateX(300%)}
}
@media (prefers-reduced-motion:reduce){
  .lvl-busy-ring>i,.lvl-busy-bar>i{animation-duration:3s}
}

/* ══ SMALL SCREENS AND PHONES ═══════════════════════════════════════════
   The cockpit's smallest breakpoint was 900px, so below that there was no
   layout at all — just a desktop one clipped. Measured on the control
   centre before this existed:

     phone 390x844   curve chart overhangs by 779px
                     crews rows overhang by 406px
                     limits board 36 controls entirely off screen
                     rules board  11 controls entirely off screen
     tablet 768x1024 crews and rules already overhanging

   Nothing scrolled sideways to reach them — the shell clipped, so the
   content was simply unreachable. Below 1024 the cockpit stops pretending
   to be two columns; below 720 every wide row becomes a stack, and the
   charts scroll inside their own box rather than off the side of the page. */
@media (max-width:1024px){
  /* the rail stops being a column and becomes a band above the board */
  /* THE CALL COMES OFF ITS COLUMN BEFORE THE EVIDENCE DOES. At this width
     three columns leaves the chart under 400px, and the chart is the reason
     the board exists. The decision moves under the headline row, where it is
     still above the fold, and the evidence keeps the full width. */
  /* five cards still fit one row at 1024 — 200px each, and the longest
     caption is 150px. They break only when they genuinely cannot. */
  /* ── UNLESS IT IS ALREADY FOLDED ────────────────────────────────────
     This moves the decision column out of the row and lays it across the
     top, which is the right answer for a 300px panel in a 768px window and
     the wrong one for a 46px rail: it left an empty 46px track down the
     side AND a full-width band across the top carrying one sideways word. */
  .lvl-cc-body:not(.is-rail-shut){grid-template-columns:268px minmax(0,1fr);
    grid-template-rows:auto 1fr}
  .lvl-cc-body:not(.is-rail-shut) .lvl-cc-side.is-right{grid-column:1/-1;grid-row:1}
  .lvl-cc-body:not(.is-rail-shut) .lvl-cc-side.is-left{grid-row:2}
  .lvl-cc-body:not(.is-rail-shut) .lvl-cc-stage{grid-row:2}
  /* folded, the rail simply stays where it is and the left column narrows */
  .lvl-cc-body.is-rail-shut{grid-template-columns:minmax(0,216px) minmax(0,1fr) 42px}
  /* and in 216px the trade NAME is the column, not the bar beside it */
  .lvl-cc-chip{grid-template-columns:minmax(0,2.6fr) minmax(24px,.4fr) 30px;gap:6px}
  .lvl-cc-call{flex-direction:row;flex-wrap:wrap;align-items:flex-start;overflow:visible}
  .lvl-cc-call-h,.lvl-cc-call-p{flex:1 1 240px}
  .lvl-cc-call-a{flex:0 0 auto;flex-direction:row}
  .lvl-cc-call-a .lvl-btn{width:auto}
  /* the brief folds onto ONE line with its caption inline, instead of a
     headed block: stacked it took 90px of a 768px screen to say three words,
     and the evidence underneath is what the planner came for */
  .lvl-cc-call{padding:9px var(--lvl-sp-3);gap:6px}
  .lvl-cc-call-b{flex:1 1 100%;margin-top:0;padding-top:6px;
    display:flex;align-items:baseline;flex-wrap:wrap;gap:2px 14px}
  .lvl-cc-call-bh{margin-bottom:0;flex:0 0 auto}
  .lvl-cc-call-b .lvl-cc-call-f{display:inline-flex;margin-right:0;border-bottom:0;padding:0}
  .lvl-cc-meters{grid-template-columns:repeat(2,1fr)}
  .lvl-cc-rules{grid-template-columns:1fr}
  .lvl-cc-crews.is-split{grid-template-columns:1fr;grid-template-rows:auto auto 1fr}
  .lvl-cc-rd-b{grid-template-columns:1fr}
  /* the ladder stays a COLUMN here. It went back to a capped grid when this
     breakpoint turned the old rail into a horizontal band; the left column
     survives at this width now, so capping the list at 104px only cut a row
     in half and left white space under it. */
}
/* ══ THE FIT IS THE SAME ON EVERY SCREEN, SO THE CHROME GIVES WAY ══════
   On a 1280x720 laptop under the app's own 96px band the shell is 624px, and
   a five-card row, a two-line tab strip, four meters, a chart, its key and a
   footer do not all get to be generous. The PICTURE is what the board exists
   for, so everything around it is what gets tighter — rather than the chart
   collapsing to 200px and its key spilling out of the box, which is what the
   reporter's screen showed.
   ═══════════════════════════════════════════════════════════════════════ */
@media (max-width:1400px){
  /* six labels in a 744px stage: tighter padding fits them on ONE row, and a
     row that wraps costs 45px of chart to say nothing new */
  .lvl-cc-tab{padding:7px 9px}
  .lvl-cc-tab b{font-size:var(--lvl-t-2);gap:4px}
  .lvl-cc-tab.is-on::after{left:9px;right:9px}
}
/* the chart is the one thing that must not be the loser: on any window, it
   keeps a floor and the boards scroll around it rather than squeezing it */
.lvl-cc-curve-art{min-height:190px}

@media (max-height:900px){
  /* THE CARDS GIVE WAY BEFORE THE GRAPH DOES. On the reporter's screen they
     were 110px against a 190px chart — a headline row taking more than a
     third of what the chart got, to state five numbers that need a fifth of
     it. Everything here is a step down, and nothing below the 48px
     legibility floor the cockpit test holds them to. */
  /* THE TYPE IS NOT SET HERE ANY MORE — it was, at 21px, 9.5px, 25px and
     15px, and those fought the scale above, which already reads the shorter
     of the two dimensions and steps the whole page down together. What is
     left is what a ratio cannot know: the fixed chrome around the cards. */
  .lvl-cc-k{padding:7px 11px 8px;gap:2px}
  .lvl-cc-k-m{height:3px}
  .lvl-cc-keys-h{margin-bottom:-4px}
  .lvl-cc-k.is-lead{padding:8px 13px 9px}
  .lvl-cc-k.is-lead .lvl-cc-k-m{height:5px}
  .lvl-cc-k-d{padding:1px 7px}
  .lvl-cc-meter{padding:6px 10px}
  .lvl-cc-board{padding:9px 10px}
  .lvl-cc-curve{gap:6px}
  /* the key is one line of small print, not two of body copy */
  .lvl-cc-curve-art .lvl-scale{font-size:9.5px;gap:5px 9px}
}

/* between the two: three across, and the fifth card takes the empty cell the
   other two leave rather than sitting beside a grey hole */
@media (max-width:940px){
  .lvl-cc-keys{grid-template-columns:repeat(3,1fr)}
  .lvl-cc-k:nth-child(5){grid-column:span 2}
  .lvl-cc-k.is-lead .lvl-cc-k-v{font-size:var(--lvl-t-6)}
}
@media (max-width:720px){
  /* one column, and the board is allowed to be as tall as it needs.
     THE CAP GOES WITH THE HEIGHT. `height:auto` on its own left the shell's
     `max-height:100dvh` in force, so the page still could not grow past the
     viewport — it just squeezed instead: the utilisation ladder came out a
     51px card with its header and none of its seven trades in it. A phone
     scrolls; that is what a phone is for. */
  .lvl.is-cc{height:auto;min-height:0;max-height:none;overflow:visible}
  .lvl-cc-body{display:flex;flex-direction:column;gap:10px}
  .lvl-cc-board,.lvl-cc-stage{min-height:0;overflow:visible}
  /* nowrap matters: the band above inherits flex-wrap:wrap, and a WRAPPING
     COLUMN lays its items out in further columns to the right — which is
     precisely the 146px of unreachable content this was measured at */
  .lvl-cc-keys{grid-template-columns:repeat(2,1fr)}
  .lvl-cc-k:nth-child(5){grid-column:span 2}
  .lvl-cc-body{display:flex;flex-direction:column}
  /* THE CALL COMES BEFORE THE EVIDENCE ON A PHONE. As the last column it is
     the last thing in the DOM, which on one column puts the only button on
     the page below a chart, a ladder and a board — three screens of scroll
     to reach the thing the five numbers above have just argued for. */
  .lvl-cc-side.is-right{order:-1}
  /* ── A RAIL IS A SIDE THING, AND A PHONE HAS NO SIDE ────────────────
     Stacked into one column the rail became a full-width block with its
     label still set vertically — 350px of sideways type running off the
     left edge of a 390px screen. On one column it is a normal strip: the
     handle, the sentence upright, the action at the end of it. */
  .lvl-cc-rail{flex-direction:row;align-items:center;padding:6px 8px}
  .lvl-cc-rail-x{transform:rotate(90deg)}
  .lvl-cc-rail-t{flex:1 1 auto;width:auto;justify-content:flex-start}
  .lvl-cc-rail-t>span{writing-mode:horizontal-tb;transform:none;white-space:normal;
    max-height:none;text-align:left}
  /* NOWRAP MATTERS, AND THIS MODULE HAS PAID FOR IT ONCE ALREADY. The band
     above sets flex-wrap:wrap for its row layout; turning the direction back
     to column without clearing the wrap gives a WRAPPING COLUMN, which lays
     whatever does not fit into further columns to the RIGHT — measured here
     at 757px off the side of a 390px phone, with the brief and its three
     rules simply unreachable. */
  .lvl-cc-call{flex-direction:column;flex-wrap:nowrap;overflow:visible}
  .lvl-cc-call-h,.lvl-cc-call-p{flex:0 0 auto}
  .lvl-cc-call-a{flex-direction:column}
  .lvl-cc-call-a .lvl-btn{width:100%}
  .lvl-cc-call-b{flex:0 0 auto;margin-top:2px}
  .lvl-cc-call-b .lvl-cc-call-f{display:flex;margin-right:0;
    border-bottom:1px dotted var(--lvl-line)}
  .lvl-cc-meters{grid-template-columns:1fr}
  /* the rows are two lines tall at this width, so 150px was a row and a half
     — enough to show that the list is cut and not enough to read it */
  .lvl-cc-strip-l{grid-template-columns:1fr;max-height:260px}

  /* every wide row stacks: the label and figure on one line, the bar under */
  .lvl-cc-crew,.lvl-cc-driver,.lvl-cc-chip,.lvl-cc-lrow{
    grid-template-columns:1fr auto!important;gap:4px 8px}
  /* a two-row chip cannot be one row tall — the bar was being cut off the
     bottom of every trade on a phone */
  .lvl-cc-chip{height:auto;padding:4px 5px 5px}
  .lvl-cc-crew>*,.lvl-cc-driver>*,.lvl-cc-chip>*,.lvl-cc-lrow>*{min-width:0}
  .lvl-cc-when,.lvl-cc-driver-s,.lvl-cc-chip-b{grid-column:1/-1}
  .lvl-cc-room,.lvl-cc-rd-k,.lvl-cc-rd-f{grid-template-columns:1fr}
  .lvl-cc-rd-w>li{grid-template-columns:1fr auto}

  /* charts scroll inside their own box instead of off the side of the page */
  .lvl-cc-curve,.lvl-cc-board svg,.lvl-ws-wrap,.lvl-ba{max-width:100%}
  .lvl-cc-board>div,.lvl-cc-curve{overflow-x:auto;overscroll-behavior-x:contain}
  .lvl-cc-tabs{overflow-x:auto;overscroll-behavior-x:contain;flex-wrap:nowrap}
  .lvl-cc-tab{flex:0 0 auto}

  /* the verdict and its actions wrap rather than push each other off */
  .lvl-verdict{flex-wrap:wrap;grid-template-columns:1fr!important}
  .lvl-verdict-a{width:100%;justify-content:flex-start;flex-wrap:wrap}

  /* a finger needs a target, and the panels stop being fixed-width */
  .lvl-cc-board .lvl-btn,.lvl-cc-board button.lvl-link{min-height:32px}
  .lvl-blockapply,.lvl-searching{max-width:calc(100vw - 24px)}
  .lvl-fit-subr{grid-template-columns:1fr auto;padding-left:22px}
  .lvl-fit-more{padding-left:22px}
}

/* ══ THE EXECUTION WINDOW ══════════════════════════════════════════════
   What Apply is about to do to the programme, before it does it. A planner
   approving a levelling plan is approving a set of SCHEDULE CHANGES — a
   relationship becoming SS with a lag, a bar getting a predecessor from the
   package next door, a duration and the crew per day that follows it — and
   every one of those has to be readable at a glance and checkable against
   what they know of the job.

   The layout carries the argument: the counter row says how much of the plan
   is held by logic rather than by a date (the number a P6 reviewer asks
   about first), then the operations, grouped by the lever they pull, each
   one a single sentence with the mechanism on the left and the consequence
   underneath. Nothing is a table of dates.
   ═══════════════════════════════════════════════════════════════════════ */
.lvl-drawer.is-xplan{width:min(680px,96vw)}
.lvl-xp-b{padding:var(--lvl-sp-4) var(--lvl-sp-4) var(--lvl-sp-3)}

/* ── THE FOUR NUMBERS THE DECISION TURNS ON ───────────────────────── */
.lvl-xp-sum{display:grid;grid-template-columns:repeat(auto-fit,minmax(120px,1fr));gap:8px;
  margin:var(--lvl-sp-2) 0 var(--lvl-sp-3)}
.lvl-xp-s{padding:9px 11px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);
  background:var(--lvl-wash)}
.lvl-xp-s>i{display:block;font:800 var(--lvl-t-5,17px)/1.1 var(--lvl-head);font-style:normal;
  color:var(--lvl-ink);font-variant-numeric:tabular-nums}
.lvl-xp-s>span{display:block;margin-top:3px;font:500 var(--lvl-t-1)/1.35 var(--lvl-font);
  color:var(--lvl-mut)}
.lvl-xp-s.is-good{border-left:3px solid var(--lvl-ok);background:var(--lvl-ok-t)}
.lvl-xp-s.is-good>i{color:var(--lvl-ok)}
.lvl-xp-s.is-warn{border-left:3px solid var(--lvl-warn);background:var(--lvl-warn-t)}
.lvl-xp-s.is-warn>i{color:var(--lvl-warn)}

/* the verdict line is a SENTENCE, so it is laid out as one — a flex row
   here made the bold lead its own column and wrapped it two words wide */
.lvl-xp-b>.lvl-note{display:block;padding:9px 11px;
  border-radius:var(--lvl-r-s);margin:0 0 var(--lvl-sp-3);line-height:1.55;
  font-size:var(--lvl-t-2)}
.lvl-xp-b>.lvl-note .lvl-ic{vertical-align:-3px;margin-right:5px}
.lvl-xp-b>.lvl-note.is-good{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-xp-b>.lvl-note.is-warn{background:var(--lvl-warn-t);color:var(--lvl-warn)}
.lvl-xp-b>.lvl-note b{color:inherit}

/* ── ONE GROUP PER LEVER ──────────────────────────────────────────── */
.lvl-xp-g{margin:0 0 var(--lvl-sp-4)}
.lvl-xp-g>h4{display:flex;align-items:center;gap:7px;margin:0 0 2px;
  font:700 var(--lvl-t-1)/1.2 var(--lvl-mono,var(--lvl-font));letter-spacing:.11em;
  text-transform:uppercase;color:var(--lvl-mut-2)}
.lvl-xp-g>h4>u{text-decoration:none;font-variant-numeric:tabular-nums;
  background:var(--lvl-line-2);color:var(--lvl-ink-2);border-radius:20px;padding:1px 7px;
  letter-spacing:0}
.lvl-xp-g>p{margin:0 0 8px;font:500 var(--lvl-t-2)/1.45 var(--lvl-font);color:var(--lvl-mut)}
.lvl-xp-l{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:6px}

/* ── ONE OPERATION, AS A SENTENCE ─────────────────────────────────── */
.lvl-xp-r{display:grid;grid-template-columns:auto 1fr;gap:2px 10px;align-items:baseline;
  padding:9px 11px;border:1px solid var(--lvl-line);border-radius:var(--lvl-r-s);
  border-left:3px solid var(--lvl-after);background:var(--lvl-card)}
.lvl-xp-r.is-add{border-left-color:var(--lvl-ok)}
.lvl-xp-r.is-dur{border-left-color:var(--lvl-info)}
.lvl-xp-r.is-pin{border-left-color:var(--lvl-warn);background:var(--lvl-warn-t)}
.lvl-xp-k{grid-column:1;font:700 var(--lvl-t-1)/1.2 var(--lvl-mono,var(--lvl-font));
  letter-spacing:.08em;text-transform:uppercase;color:var(--lvl-mut-2);white-space:nowrap}
.lvl-xp-n{grid-column:2;display:flex;align-items:center;gap:4px;flex-wrap:wrap;
  font:700 var(--lvl-t-3)/1.3 var(--lvl-head);color:var(--lvl-ink)}
.lvl-xp-n .lvl-ic{color:var(--lvl-mut-2)}
.lvl-xp-d{grid-column:2;display:flex;align-items:center;gap:5px;flex-wrap:wrap;margin-top:2px;
  font:600 var(--lvl-t-2)/1.3 var(--lvl-mono,var(--lvl-font));color:var(--lvl-ink-2)}
.lvl-xp-d>s{text-decoration:line-through;color:var(--lvl-before)}
.lvl-xp-d>u{text-decoration:none;color:var(--lvl-after);font-weight:800}
.lvl-xp-d>u.is-new{color:var(--lvl-ok)}
.lvl-xp-w{grid-column:2;display:block;margin-top:4px;font-style:normal;
  font:500 var(--lvl-t-2)/1.5 var(--lvl-font);color:var(--lvl-mut)}
.lvl-xp-w.is-warn{color:var(--lvl-warn);display:flex;align-items:flex-start;gap:5px}
.lvl-xp-w.is-warn .lvl-ic{flex:0 0 auto;margin-top:2px}
.lvl-xp-ft{margin-top:var(--lvl-sp-3);padding-top:var(--lvl-sp-3);border-top:1px solid var(--lvl-line)}
.lvl-xp-ft .lvl-note{display:flex;align-items:flex-start;gap:6px;margin:0 0 6px}
.lvl-xp-ft .lvl-note .lvl-ic{flex:0 0 auto;margin-top:2px}
.lvl-xp-ft .lvl-note.is-bad{color:var(--lvl-risk)}

body[data-gantt-theme="dark"] .lvl-portal .lvl-xp-r{background:var(--lvl-card)}

/* a pin the network already satisfies — read, and deliberately not written */
.lvl-xp-g.is-inert>h4>u{background:var(--lvl-ok-t);color:var(--lvl-ok)}
.lvl-xp-r.is-noop{border-left-color:var(--lvl-line-3);background:var(--lvl-wash);
  grid-template-columns:auto 1fr auto;align-items:center}
.lvl-xp-r.is-noop .lvl-xp-d{grid-column:3;margin-top:0;justify-self:end;
  font:500 var(--lvl-t-2)/1.3 var(--lvl-font);color:var(--lvl-mut)}
.lvl-xp-r.is-noop .lvl-xp-d>u{color:var(--lvl-ink-2);font-weight:700}
.lvl-xp-more{list-style:none;padding:4px 11px;font:500 var(--lvl-t-2)/1.4 var(--lvl-font);
  color:var(--lvl-mut-2)}

/* styles/tabs/cost.css */
/* ===========================================================================
   COST & CASH FLOW — DESIGN SYSTEM
   A commercial-control workspace. Built for Cost specifically and scoped to
   #tp-cost / .cost-portal, so nothing here can reach another tab.

   THE RULES THAT PRODUCED IT

   1. A NUMBER IS THE INTERFACE. Everything else — labels, chrome, borders —
      exists to make figures comparable. Money is monospaced with tabular
      figures so digits align in a column, and it carries WEIGHT hierarchy:
      the figure a row is about is 700 and dark, its supporting figures are
      500 and grey. A table where every number looks the same is a table
      nobody can read.

   2. NO NATIVE CONTROLS. A default checkbox or a browser <select> chevron is
      the single loudest signal that a screen is unfinished — it is the one
      element that looks different on every machine. Every control here is
      drawn.

   3. HIERARCHY IS STRUCTURAL, NOT DECORATIVE. A WBS row is not "bold text";
      it is a tinted band with a depth rail, so the tree is legible at a
      glance from three metres away. Indentation alone is not hierarchy.

   4. ENCODE, DO NOT JUST PRINT. A percentage gets a bar behind it, a share
      gets a rail. The eye finds the outlier before it reads the digits.

   5. DENSITY IS TIGHT SPACING, NEVER SMALL TYPE. 32px rows, 12px figures.
      Nothing below 10px, and nothing below 4.5:1 contrast.
   ========================================================================= */

/* .cost-menu is in this list because it is appended to document.body — a
   fixed-position overlay cannot live inside a scrolling table cell. Outside
   this selector every var(--c-*) below resolves to nothing, and the menu
   renders as bare text over the page with no surface at all. */
#tp-cost, .cost-portal, .cost-menu {
  /* ── ink ramp: five steps, each a real jump ───────────────────────── */
  --c-ink:#0A0F1A; --c-ink-2:#28323F; --c-ink-3:#47525F;
  --c-mut:#69747F; --c-mut-2:#939DA8;
  /* ── surfaces ─────────────────────────────────────────────────────── */
  --c-surface:#FFFFFF; --c-wash:#F7F9FB; --c-canvas:#EDF1F5; --c-sunken:#E4EAF0;
  --c-line:#E2E8EE; --c-line-2:#EDF1F5; --c-line-3:#CFD8E1; --c-line-4:#B8C4D0;
  /* ── brand (Nexora green, kept) ───────────────────────────────────── */
  --c-brand:#24B47E; --c-brand-d:#128A5E; --c-brand-dd:#0B6647;
  --c-brand-t:#E7F7F0; --c-brand-t2:#CFEFE2;
  /* ── financial semantics. One meaning each, never decorative. ─────── */
  --c-pos:#12855E; --c-pos-t:#E6F6EF;       /* money in, within budget   */
  --c-neg:#C03B32; --c-neg-t:#FBECEA;       /* money out, over budget    */
  --c-warn:#B57619; --c-warn-t:#FCF3E3;     /* under-allocated, at limit */
  --c-info:#2B59C3; --c-info-t:#EAEFFB;     /* net, proposal, scenario   */
  --c-gap:#C98A1E;                           /* funding requirement       */
  /* ── categorical: assigned by entity, never by rank ───────────────── */
  --c-s1:#2B59C3; --c-s2:#E06B2E; --c-s3:#12A374; --c-s4:#D9A016;
  --c-s5:#D2649B; --c-s6:#0F7A46; --c-s7:#4634A0; --c-s8:#CF4038;
  --c-s9:#0E93A3; --c-s10:#9A5E11; --c-s11:#A93A9E; --c-s12:#5F7D11;
  /* ── radii: controls are crisp, not pills ─────────────────────────── */
  --c-r:10px; --c-r-s:7px; --c-r-xs:5px; --c-r-pill:999px;
  /* ── elevation ────────────────────────────────────────────────────── */
  --c-sh-1:0 1px 2px rgba(10,15,26,.05);
  --c-sh-2:0 1px 3px rgba(10,15,26,.07),0 4px 12px rgba(10,15,26,.05);
  --c-sh-3:0 8px 28px rgba(10,15,26,.10),0 2px 6px rgba(10,15,26,.06);
  --c-sh-in:inset 0 1px 2px rgba(10,15,26,.06);
  /* ── type ─────────────────────────────────────────────────────────── */
  --c-font:"Inter","Segoe UI",system-ui,-apple-system,sans-serif;
  --c-head:"Plus Jakarta Sans","Inter","Segoe UI",sans-serif;
  --c-mono:"JetBrains Mono","SFMono-Regular",Consolas,"Liberation Mono",monospace;
  /* ── density ──────────────────────────────────────────────────────── */
  --c-row:32px; --c-row-h:34px; --c-ctl:32px; --c-ctl-sm:26px;
  --c-gut:18px;
  background:var(--c-canvas); color:var(--c-ink);
  font-family:var(--c-font);
  -webkit-font-smoothing:antialiased; -moz-osx-font-smoothing:grayscale;
  font-feature-settings:"cv05" 1,"ss01" 1;
}
#tp-cost *,#tp-cost *::before,#tp-cost *::after,
.cost-portal,.cost-portal *,.cost-portal *::before,.cost-portal *::after{box-sizing:border-box}
#costOut{font-size:13px;line-height:1.45;color:var(--c-ink)}
.cost{display:flex;flex-direction:column;min-height:100%;background:var(--c-canvas)}

/* focus: one ring, everywhere, visible on every surface */
#tp-cost :focus-visible,.cost-portal :focus-visible{
  outline:2px solid var(--c-brand);outline-offset:1px;border-radius:var(--c-r-xs)}

/* figures: one class, used on every number in the module */
.cost-n{font-family:var(--c-mono);font-variant-numeric:tabular-nums lining-nums;
  letter-spacing:-.02em;font-feature-settings:"tnum" 1,"lnum" 1}

/* ═══ 1. TOP BAR ═════════════════════════════════════════════════════ */
.cost-top{display:flex;align-items:center;justify-content:space-between;gap:16px;flex-wrap:wrap;
  padding:11px var(--c-gut);background:var(--c-surface);
  border-bottom:1px solid var(--c-line);position:sticky;top:0;z-index:30}
.cost-top-l{display:flex;align-items:center;gap:14px;min-width:0;flex-wrap:wrap}
.cost-title{display:flex;align-items:center;gap:10px}
.cost-title-mark{width:30px;height:30px;border-radius:var(--c-r-s);flex:0 0 auto;
  background:linear-gradient(145deg,var(--c-brand),var(--c-brand-dd));
  display:grid;place-items:center;color:#fff;box-shadow:0 1px 2px rgba(11,102,71,.3)}
.cost-title-mark svg{width:16px;height:16px}
.cost-title h1{margin:0;font:700 15px/1.1 var(--c-head);letter-spacing:-.015em;color:var(--c-ink)}
.cost-title p{margin:2px 0 0;font:600 9.5px/1 var(--c-font);letter-spacing:.1em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-crumbs{display:flex;align-items:center;gap:7px;font-size:12px;color:var(--c-mut);
  padding-left:14px;border-left:1px solid var(--c-line);min-width:0}
.cost-crumbs span{overflow:hidden;text-overflow:ellipsis;white-space:nowrap;max-width:30ch}
.cost-crumbs .sep{color:var(--c-line-4)}
.cost-crumbs .is-cur{color:var(--c-ink);font-weight:600}
.cost-top-r{display:flex;align-items:center;gap:7px;flex-wrap:wrap}

/* ═══ 2. CONTROLS — every one of them drawn ══════════════════════════ */
.cost-btn{display:inline-flex;align-items:center;justify-content:center;gap:6px;
  height:var(--c-ctl);padding:0 12px;border-radius:var(--c-r-s);
  border:1px solid var(--c-line-3);background:var(--c-surface);color:var(--c-ink-2);
  font:600 12.5px/1 var(--c-font);cursor:pointer;white-space:nowrap;
  box-shadow:var(--c-sh-1);
  transition:background .15s ease,border-color .15s ease,color .15s ease,box-shadow .15s ease}
.cost-btn svg{width:14px;height:14px;flex:0 0 auto}
.cost-btn:hover{background:var(--c-wash);border-color:var(--c-line-4);color:var(--c-ink)}
.cost-btn:active{box-shadow:var(--c-sh-in);transform:translateY(.5px)}
.cost-btn.is-primary{background:var(--c-brand-d);border-color:var(--c-brand-d);color:#fff;
  box-shadow:0 1px 2px rgba(11,102,71,.25)}
.cost-btn.is-primary:hover{background:var(--c-brand-dd);border-color:var(--c-brand-dd);color:#fff}
.cost-btn.is-ghost{background:transparent;border-color:transparent;box-shadow:none;color:var(--c-mut)}
.cost-btn.is-ghost:hover{background:var(--c-sunken);color:var(--c-ink)}
.cost-btn.is-danger{background:var(--c-neg);border-color:var(--c-neg);color:#fff}
.cost-btn.is-danger:hover{filter:brightness(.93)}
.cost-btn.is-sm{height:var(--c-ctl-sm);padding:0 9px;font-size:11.5px;border-radius:var(--c-r-xs)}
.cost-btn.is-sm svg{width:12px;height:12px}
.cost-btn[disabled]{opacity:.4;cursor:not-allowed;box-shadow:none}
.cost-icobtn{display:inline-grid;place-items:center;width:28px;height:28px;flex:0 0 auto;
  border-radius:var(--c-r-xs);border:1px solid transparent;background:none;
  color:var(--c-mut);cursor:pointer;transition:background .15s,color .15s}
.cost-icobtn svg{width:15px;height:15px}
.cost-icobtn:hover{background:var(--c-sunken);color:var(--c-ink)}
.cost-link{background:none;border:0;padding:0;font:inherit;font-weight:600;
  color:var(--c-brand-d);cursor:pointer;text-align:left;border-bottom:1px solid transparent}
.cost-link:hover{border-bottom-color:currentColor}

/* segmented control */
.cost-seg{display:inline-flex;padding:2px;gap:2px;background:var(--c-sunken);
  border-radius:var(--c-r-s);border:1px solid var(--c-line)}
.cost-seg-b{height:26px;padding:0 11px;border:0;border-radius:var(--c-r-xs);background:none;
  font:600 11.5px/1 var(--c-font);color:var(--c-mut);cursor:pointer;
  transition:background .15s,color .15s,box-shadow .15s}
.cost-seg-b:hover{color:var(--c-ink-2)}
.cost-seg-b.is-on{background:var(--c-surface);color:var(--c-ink);box-shadow:var(--c-sh-1)}

.cost-chip{height:26px;padding:0 10px;border-radius:var(--c-r-pill);
  border:1px solid var(--c-line-3);background:var(--c-surface);
  font:600 11.5px/1 var(--c-font);color:var(--c-ink-3);cursor:pointer;
  display:inline-flex;align-items:center;gap:5px;transition:background .15s,border-color .15s,color .15s}
.cost-chip:hover{border-color:var(--c-line-4);background:var(--c-wash)}
.cost-chip.is-on{background:var(--c-brand-t);border-color:var(--c-brand-t2);color:var(--c-brand-dd)}
.cost-chip.is-static{cursor:default}

/* search */
.cost-search{display:flex;align-items:center;gap:7px;background:var(--c-wash);
  border:1px solid var(--c-line-3);border-radius:var(--c-r-s);padding:0 10px;
  height:var(--c-ctl);color:var(--c-mut-2);min-width:210px;
  transition:border-color .15s,background .15s,box-shadow .15s}
.cost-search:focus-within{border-color:var(--c-brand);background:var(--c-surface);
  box-shadow:0 0 0 3px rgba(36,180,126,.12)}
.cost-search svg{width:14px;height:14px;flex:0 0 auto}
.cost-search input{border:0;background:none;outline:0;font:500 12.5px/1 var(--c-font);
  color:var(--c-ink);width:100%;height:100%}
.cost-search input::placeholder{color:var(--c-mut-2)}

/* ── CHECKBOX. Drawn, not native. ───────────────────────────────────── */
.cost-cb{position:relative;display:inline-grid;place-items:center;flex:0 0 auto;
  width:16px;height:16px;cursor:pointer}
.cost-cb input{position:absolute;inset:0;opacity:0;margin:0;cursor:pointer}
.cost-cb i{width:16px;height:16px;border-radius:4px;border:1.5px solid var(--c-line-4);
  background:var(--c-surface);display:block;
  transition:background .15s,border-color .15s,box-shadow .15s}
.cost-cb:hover i{border-color:var(--c-brand)}
.cost-cb input:checked+i{background:var(--c-brand-d);border-color:var(--c-brand-d);
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none' stroke='white' stroke-width='2.4' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpolyline points='3.5 8.5 6.5 11.5 12.5 5'/%3E%3C/svg%3E");
  background-size:100%;background-repeat:no-repeat}
.cost-cb input:indeterminate+i{background:var(--c-brand-d);border-color:var(--c-brand-d);
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Crect x='4' y='7.2' width='8' height='1.8' rx='.9' fill='white'/%3E%3C/svg%3E");
  background-size:100%;background-repeat:no-repeat}
.cost-cb input:focus-visible+i{box-shadow:0 0 0 3px rgba(36,180,126,.22)}

/* ── SELECT. appearance:none + our own chevron. ─────────────────────── */
.cost-sel{appearance:none;-webkit-appearance:none;-moz-appearance:none;
  height:var(--c-ctl-sm);padding:0 26px 0 9px;border-radius:var(--c-r-xs);
  border:1px solid var(--c-line-3);background-color:var(--c-surface);color:var(--c-ink-2);
  font:600 11.5px/1 var(--c-font);cursor:pointer;max-width:100%;width:100%;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none' stroke='%2369747F' stroke-width='1.9' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpolyline points='4 6.5 8 10.5 12 6.5'/%3E%3C/svg%3E");
  background-repeat:no-repeat;background-position:right 7px center;background-size:13px;
  transition:border-color .15s,box-shadow .15s,background-color .15s}
.cost-sel:hover{border-color:var(--c-line-4);background-color:var(--c-wash)}
.cost-sel:focus{outline:0;border-color:var(--c-brand);background-color:var(--c-surface);
  box-shadow:0 0 0 3px rgba(36,180,126,.14)}
.cost-sel.is-lg{height:var(--c-ctl);font-size:12.5px;padding:0 30px 0 11px;border-radius:var(--c-r-s)}

/* ── TOGGLE ─────────────────────────────────────────────────────────── */
.cost-sw{position:relative;width:36px;height:20px;border-radius:var(--c-r-pill);
  background:var(--c-line-4);border:0;cursor:pointer;flex:0 0 auto;padding:0;
  transition:background .18s ease}
.cost-sw::after{content:"";position:absolute;top:2px;left:2px;width:16px;height:16px;
  border-radius:50%;background:#fff;box-shadow:0 1px 2px rgba(10,15,26,.25);
  transition:transform .18s cubic-bezier(.3,.8,.4,1)}
.cost-sw.is-on{background:var(--c-brand-d)}
.cost-sw.is-on::after{transform:translateX(16px)}
.cost-sw:focus-visible{box-shadow:0 0 0 3px rgba(36,180,126,.25)}

/* ═══ 3. RAIL NAV ════════════════════════════════════════════════════ */
.cost-rail{display:flex;align-items:center;gap:2px;flex-wrap:wrap;
  padding:0 var(--c-gut);background:var(--c-surface);
  border-bottom:1px solid var(--c-line);position:sticky;top:53px;z-index:29}
.cost-rail-b{position:relative;display:inline-flex;align-items:center;gap:7px;
  height:40px;padding:0 13px;border:0;background:none;color:var(--c-mut);
  font:600 12.5px/1 var(--c-font);cursor:pointer;transition:color .15s}
.cost-rail-b i{font:700 9.5px/1 var(--c-mono);color:var(--c-mut-2);font-style:normal;
  letter-spacing:0;transition:color .15s}
.cost-rail-b::after{content:"";position:absolute;left:8px;right:8px;bottom:0;height:2px;
  border-radius:2px 2px 0 0;background:transparent;transition:background .15s}
.cost-rail-b:hover{color:var(--c-ink-2)}
.cost-rail-b:hover::after{background:var(--c-line-3)}
.cost-rail-b.is-on{color:var(--c-ink)}
.cost-rail-b.is-on i{color:var(--c-brand-d)}
.cost-rail-b.is-on::after{background:var(--c-brand)}

/* ═══ 4. STATE BAR — the reconciliation strip ════════════════════════ */
.cost-state{display:flex;align-items:stretch;gap:0;flex-wrap:wrap;
  background:var(--c-surface);border-bottom:1px solid var(--c-line);
  padding:0 var(--c-gut)}
.cost-state-tag{display:flex;align-items:center;gap:7px;padding:9px 14px 9px 0;
  margin-right:14px;border-right:1px solid var(--c-line-2);
  font:700 11.5px/1 var(--c-font);white-space:nowrap}
.cost-state-tag .dot{width:7px;height:7px;border-radius:50%;flex:0 0 auto}
.cost-state.is-ok .cost-state-tag{color:var(--c-pos)}
.cost-state.is-ok .dot{background:var(--c-pos);box-shadow:0 0 0 3px var(--c-pos-t)}
.cost-state.is-warn .cost-state-tag{color:var(--c-warn)}
.cost-state.is-warn .dot{background:var(--c-warn);box-shadow:0 0 0 3px var(--c-warn-t)}
.cost-state.is-risk .cost-state-tag{color:var(--c-neg)}
.cost-state.is-risk .dot{background:var(--c-neg);box-shadow:0 0 0 3px var(--c-neg-t)}
.cost-state.is-sim .cost-state-tag{color:var(--c-info)}
.cost-state.is-sim .dot{background:var(--c-info);box-shadow:0 0 0 3px var(--c-info-t)}
.cost-state-fig{display:flex;flex-direction:column;gap:1px;padding:7px 18px 7px 0;justify-content:center}
.cost-state-fig span{font:600 8.5px/1 var(--c-font);letter-spacing:.1em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-state-fig b{font:700 12.5px/1.1 var(--c-mono);font-variant-numeric:tabular-nums;
  color:var(--c-ink-2);letter-spacing:-.02em}
.cost-state-fig.is-pos b{color:var(--c-pos)}
.cost-state-fig.is-warn b{color:var(--c-warn)}
.cost-state-fig.is-risk b{color:var(--c-neg)}
.cost-state-sp{flex:1 1 auto;min-width:8px}
.cost-state-r{display:flex;align-items:center;gap:8px;padding:7px 0}

/* ═══ 5. BODY & SECTIONS ═════════════════════════════════════════════ */
.cost-body{padding:16px var(--c-gut) 44px;display:flex;flex-direction:column;gap:16px}
.cost-sect{display:flex;flex-direction:column;gap:10px}
.cost-sect-h{display:flex;align-items:center;justify-content:space-between;gap:12px;flex-wrap:wrap}
.cost-sect-h h2{margin:0;font:700 11px/1 var(--c-font);letter-spacing:.11em;
  text-transform:uppercase;color:var(--c-mut)}
.cost-sect-h .cost-top-r{gap:7px}
.cost-grid-2{display:grid;grid-template-columns:1fr 1fr;gap:16px;align-items:start}
.cost-grid-3{display:grid;grid-template-columns:repeat(3,1fr);gap:16px;align-items:start}
.cost-grid-2-1{display:grid;grid-template-columns:1.8fr 1fr;gap:16px;align-items:start}

/* ═══ 6. CARDS ═══════════════════════════════════════════════════════ */
.cost-card{background:var(--c-surface);border:1px solid var(--c-line);
  border-radius:var(--c-r);box-shadow:var(--c-sh-1);overflow:hidden}
.cost-card-h{display:flex;align-items:flex-start;justify-content:space-between;gap:14px;
  padding:13px 15px 11px;border-bottom:1px solid var(--c-line-2)}
.cost-card-h h3{margin:0;font:700 13.5px/1.3 var(--c-head);letter-spacing:-.012em;color:var(--c-ink)}
.cost-card-h p{margin:4px 0 0;font-size:11.5px;line-height:1.5;color:var(--c-mut);max-width:84ch}
.cost-card-h p b{color:var(--c-ink-3);font-weight:600}
.cost-card-h-r{display:flex;align-items:center;gap:6px;flex-shrink:0}
.cost-card-b{padding:14px 15px 15px}
.cost-card-b>h4{margin:18px 0 9px;font:700 10px/1 var(--c-font);letter-spacing:.1em;
  text-transform:uppercase;color:var(--c-mut)}
.cost-card-b>h4:first-child{margin-top:0}
.cost-card-b>h4 small{font-weight:500;text-transform:none;letter-spacing:0;
  margin-left:8px;color:var(--c-mut-2)}
.cost-card-b.is-flush{padding:0}

/* ═══ 7. KPI TILES ═══════════════════════════════════════════════════ */
.cost-kpis{display:grid;grid-template-columns:repeat(auto-fit,minmax(158px,1fr));
  gap:1px;background:var(--c-line);border:1px solid var(--c-line);
  border-radius:var(--c-r);overflow:hidden;box-shadow:var(--c-sh-1)}
.cost-kpis.is-sm{grid-template-columns:repeat(auto-fit,minmax(136px,1fr))}
.cost-kpi{background:var(--c-surface);padding:12px 14px 11px;display:flex;flex-direction:column;
  gap:2px;position:relative;min-width:0;transition:background .15s}
.cost-kpi:hover{background:var(--c-wash)}
.cost-kpi-l{display:flex;align-items:center;gap:5px;font:600 9px/1.2 var(--c-font);
  letter-spacing:.11em;text-transform:uppercase;color:var(--c-mut-2);white-space:nowrap;
  overflow:hidden;text-overflow:ellipsis}
.cost-kpi-v{font:800 21px/1.15 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.035em;color:var(--c-ink);margin-top:2px;
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.cost-kpi-v small{font-size:12px;font-weight:600;color:var(--c-mut);letter-spacing:0}
.cost-kpi-v .cur{font-size:11px;font-weight:600;color:var(--c-mut-2);margin-right:3px;
  font-family:var(--c-font);letter-spacing:.02em}
.cost-kpi-s{font-style:normal;font-size:10.5px;line-height:1.35;color:var(--c-mut);
  margin-top:2px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
/* the accent is a left keyline, not a top border — it reads as a category
   marker rather than as an underline belonging to the tile above */
.cost-kpi::before{content:"";position:absolute;left:0;top:11px;bottom:11px;width:2.5px;
  border-radius:0 2px 2px 0;background:transparent;transition:background .15s}
.cost-kpi.is-ok::before{background:var(--c-pos)}
.cost-kpi.is-ok .cost-kpi-v{color:var(--c-pos)}
.cost-kpi.is-warn::before{background:var(--c-warn)}
.cost-kpi.is-warn .cost-kpi-v{color:var(--c-warn)}
.cost-kpi.is-risk::before{background:var(--c-neg)}
.cost-kpi.is-risk .cost-kpi-v{color:var(--c-neg)}
.cost-kpi.is-info::before{background:var(--c-info)}
.cost-kpi.is-info .cost-kpi-v{color:var(--c-info)}
/* an editable KPI: the figure itself is the input */
.cost-kpi-in{font:800 19px/1.2 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.035em;color:var(--c-ink);background:none;border:0;border-bottom:1.5px dashed var(--c-line-3);
  padding:1px 0;width:100%;outline:0;margin-top:2px;transition:border-color .15s,background .15s}
.cost-kpi-in:hover{border-bottom-color:var(--c-line-4)}
.cost-kpi-in:focus{border-bottom-color:var(--c-brand);border-bottom-style:solid}

/* ═══ 8. TABLES ══════════════════════════════════════════════════════ */
.cost-tbl-wrap{overflow:auto;border:1px solid var(--c-line);border-radius:var(--c-r);
  background:var(--c-surface);box-shadow:var(--c-sh-1)}
.cost-tbl-wrap.is-tall{max-height:min(70vh,780px)}
.cost-tbl-wrap.is-mid{max-height:min(46vh,500px)}
.cost-tbl{width:100%;border-collapse:separate;border-spacing:0;font-size:12px}

.cost-tbl thead th{position:sticky;top:0;z-index:3;height:var(--c-row-h);
  background:var(--c-wash);font:700 9.5px/1.2 var(--c-font);letter-spacing:.085em;
  text-transform:uppercase;color:var(--c-mut);text-align:left;padding:0 10px;
  border-bottom:1px solid var(--c-line-3);white-space:nowrap;vertical-align:middle}
.cost-tbl thead th.n,.cost-tbl td.n,.cost-tbl th.n{text-align:right}
.cost-tbl thead th.c,.cost-tbl td.c{text-align:center}

.cost-tbl tbody th,.cost-tbl tbody td{height:var(--c-row);padding:0 10px;
  border-bottom:1px solid var(--c-line-2);vertical-align:middle;color:var(--c-ink-3);
  white-space:nowrap}
.cost-tbl tbody th{text-align:left;font-weight:500;color:var(--c-ink-2)}
.cost-tbl tbody td.n{font-family:var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.02em;font-size:11.5px}
/* THE FIGURE THE ROW IS ABOUT is heavier and darker than its neighbours */
.cost-tbl td.n.is-key{font-weight:700;color:var(--c-ink);font-size:12px}
.cost-tbl td.n.is-soft{color:var(--c-mut)}
.cost-tbl td.n.is-nil{color:var(--c-line-4)}
.cost-tbl td.n.is-pos{color:var(--c-pos)}
.cost-tbl td.n.is-neg{color:var(--c-neg);font-weight:600}
.cost-tbl td.n.is-warn{color:var(--c-warn);font-weight:600}
.cost-tbl tbody tr{transition:background .12s}
.cost-tbl tbody tr:hover>*{background:var(--c-wash)}
.cost-tbl tbody tr.is-sel>*{background:var(--c-info-t)}
.cost-tbl tbody tr.is-sel:hover>*{background:#DFE8FA}

/* sticky identity column */
.cost-tbl .is-stick{position:sticky;left:0;z-index:2;background:var(--c-surface)}
.cost-tbl thead .is-stick{z-index:4;background:var(--c-wash)}
.cost-tbl tbody tr:hover .is-stick{background:var(--c-wash)}
.cost-tbl tbody tr.is-sel .is-stick{background:var(--c-info-t)}
/* the shadow that tells the reader the column is pinned, only while scrolled */
.cost-tbl .is-stick::after{content:"";position:absolute;top:0;bottom:0;right:0;width:1px;
  background:var(--c-line)}
.cost-tbl-wrap.is-scrolled .cost-tbl .is-stick::after{
  box-shadow:6px 0 8px -6px rgba(10,15,26,.22)}

/* ── WBS BANDING — PAINTED FROM THE LIVE APPEARANCE PALETTE ───────────
   No hex lives here. cost-views.js asks AppearancePalette for the level's
   colour at render time — the same call the Gantt makes — and stamps
   --rowbg / --rowfg / --rowdv / --rowsoft / --rowtrack onto the row. Change
   the palette in Appearance settings and both tabs repaint together, on the
   same aipe:appearance-changed event.

   AND THE BAND RUNS THE WHOLE ROW. It used to stop at the name column with
   the figures sitting on a faint tint behind it, which read as a label glued
   to the left edge rather than as the row's own identity. */
.cost-tbl tr.cost-row-w>th,
.cost-tbl tr.cost-row-w>td{background:var(--rowbg);color:var(--rowfg);
  border-bottom-color:var(--rowdv)}
.cost-tbl tr.cost-row-w>th.is-stick{background:var(--rowbg)}
.cost-tbl tr.cost-row-w>th.is-stick::after{background:var(--rowdv)}
/* a filter or a transform on a sticky cell stops it sticking, so the hover
   lift is an inset shadow rather than brightness() */
.cost-tbl tr.cost-row-w:hover>th,
.cost-tbl tr.cost-row-w:hover>td{box-shadow:inset 0 0 0 999px rgba(255,255,255,.08)}
.cost-tbl tr.cost-row-w>td.n{color:var(--rowfg);font-weight:700}
.cost-tbl tr.cost-row-w>td.n.is-nil,
.cost-tbl tr.cost-row-w>td.n.is-soft{color:var(--rowsoft)}
.cost-tbl tr.cost-row-w .cost-nm-t{color:var(--rowfg);font:700 12.5px/1 var(--c-head);letter-spacing:-.01em}
.cost-tbl tr.cost-row-w .cost-code.is-id{color:var(--rowsoft);border-right-color:var(--rowdv)}
.cost-tbl tr.cost-row-w .cost-kind{color:var(--rowfg);opacity:.88}
.cost-tbl tr.cost-row-w .cost-tg{color:var(--rowfg);opacity:.82}
.cost-tbl tr.cost-row-w .cost-tg:hover{background:var(--rowtrack);opacity:1}
.cost-tbl tr.cost-row-w .cost-rails i::before{background:var(--rowtrack)}
.cost-tbl tr.cost-row-w .cost-lock{color:var(--rowsoft)}
.cost-tbl tr.cost-row-w .cost-lock:hover{background:var(--rowtrack);color:var(--rowfg)}
.cost-tbl tr.cost-row-w .cost-rail-bar em{color:var(--rowsoft)}
.cost-tbl tr.cost-row-w .cost-rail-bar u{background:var(--rowtrack)}
.cost-tbl tr.cost-row-w .cost-rail-bar u>b{background:var(--rowfg);opacity:.9}
.cost-tbl tr.cost-row-w .cost-cb i{border-color:var(--rowtrack);background:rgba(255,255,255,.16)}
.cost-tbl tr.cost-row-w .cost-cb:hover i{border-color:var(--rowfg)}
.cost-tbl tr.cost-row-w .cost-b.is-mut{background:var(--rowtrack);color:var(--rowfg);border-color:var(--rowdv)}
/* an editable figure on a coloured row keeps the row's ink until it is
   focused, when it takes the surface back so typing is legible */
#tp-cost .cost-tbl tr.cost-row-w .cost-in,
#tp-cost .cost-tbl tr.cost-row-w .cost-in.is-derived{color:var(--rowfg)!important}
#tp-cost .cost-tbl tr.cost-row-w .cost-in:hover{background-color:rgba(255,255,255,.16)!important;
  border-color:var(--rowtrack)!important}
#tp-cost .cost-tbl tr.cost-row-w .cost-in:focus{background-color:var(--c-surface)!important;
  color:var(--c-ink)!important;border-color:var(--c-brand)!important}

/* ── the name cell: rail + twisty + icon + label ────────────────────── */
.cost-nm{display:flex;align-items:center;gap:6px;min-width:0;height:100%}
.cost-rails{display:flex;flex:0 0 auto;align-self:stretch}
.cost-rails i{width:14px;flex:0 0 auto;position:relative}
.cost-rails i::before{content:"";position:absolute;left:6px;top:0;bottom:0;width:1px;
  background:var(--c-line-2)}
.cost-tg{width:17px;height:17px;flex:0 0 auto;border:0;background:none;padding:0;
  cursor:pointer;color:var(--c-mut);display:inline-grid;place-items:center;border-radius:4px;
  transition:background .12s,color .12s}
.cost-tg:hover{background:var(--c-line-2);color:var(--c-ink)}
.cost-tg svg{width:11px;height:11px;transition:transform .15s ease}
.cost-tg.is-open svg{transform:rotate(90deg)}
.cost-tg.is-leaf{visibility:hidden}
.cost-kind{width:15px;height:15px;flex:0 0 auto;color:var(--c-mut-2)}
tr.is-ms .cost-kind{color:var(--c-s7)}
.cost-nm-t{overflow:hidden;text-overflow:ellipsis;white-space:nowrap;min-width:0}
.cost-code{font:500 10.5px/1 var(--c-mono);color:var(--c-mut-2);white-space:nowrap;
  letter-spacing:-.02em}

/* ── the data bar: a proportion drawn behind the figure ─────────────── */
.cost-dbar{position:relative;display:block;padding:3px 0}
.cost-dbar>i{position:absolute;right:0;top:50%;transform:translateY(-50%);height:15px;
  border-radius:2px;background:var(--c-brand-t);z-index:0;pointer-events:none}
.cost-dbar>span{position:relative;z-index:1}
.cost-dbar.is-warn>i{background:var(--c-warn-t)}
.cost-dbar.is-neg>i{background:var(--c-neg-t)}

/* ── a share rail: 100% of the cell, filled to the share ────────────── */
.cost-rail-bar{display:flex;align-items:center;gap:7px;justify-content:flex-end}
.cost-rail-bar em{font-style:normal;font-family:var(--c-mono);font-size:11px;
  font-variant-numeric:tabular-nums;color:var(--c-mut);min-width:38px;text-align:right}
.cost-rail-bar u{text-decoration:none;display:block;width:42px;height:4px;border-radius:99px;
  background:var(--c-line-2);overflow:hidden;flex:0 0 auto}
.cost-rail-bar u>b{display:block;height:100%;border-radius:99px;background:var(--c-brand);
  transition:width .2s ease}
.cost-rail-bar.is-warn u>b{background:var(--c-warn)}
.cost-rail-bar.is-neg u>b{background:var(--c-neg)}

.cost-tbl tfoot td,.cost-tbl tfoot th{position:sticky;bottom:0;z-index:3;
  height:var(--c-row-h);background:var(--c-sunken);color:var(--c-ink);
  font-weight:800;padding:0 10px;border-top:1.5px solid var(--c-line-4);
  font-family:var(--c-mono);font-variant-numeric:tabular-nums;white-space:nowrap}
.cost-tbl tfoot th{font-family:var(--c-font);font-size:9.5px;letter-spacing:.1em;
  text-transform:uppercase;color:var(--c-ink-2)}
.cost-tbl tfoot .is-stick{z-index:4;background:var(--c-sunken)}
.cost-tbl .empty-row td{height:120px;text-align:center;color:var(--c-mut);font-size:12.5px}

/* ── inline editing inside a cell ───────────────────────────────────── */
.cost-in{width:100%;min-width:56px;border:1px solid transparent;background:none;
  font:600 11.5px/1 var(--c-mono);font-variant-numeric:tabular-nums;letter-spacing:-.02em;
  text-align:right;padding:3px 5px;border-radius:var(--c-r-xs);color:var(--c-ink);
  transition:background .12s,border-color .12s,box-shadow .12s}
.cost-in:hover{border-color:var(--c-line-3);background:var(--c-surface)}
.cost-in:focus{border-color:var(--c-brand);background:var(--c-surface);outline:0;
  box-shadow:0 0 0 3px rgba(36,180,126,.14)}
.cost-in.is-derived{color:var(--c-mut);border-color:transparent;background:none;
  cursor:default;pointer-events:none}
.cost-lock{width:22px;height:22px;border:0;background:none;cursor:pointer;color:var(--c-line-4);
  display:inline-grid;place-items:center;border-radius:4px;transition:background .12s,color .12s}
.cost-lock svg{width:13px;height:13px}
.cost-lock:hover{background:var(--c-line-2);color:var(--c-ink-3)}
.cost-lock.is-on{color:var(--c-warn)}

/* ═══ 9. BADGES ══════════════════════════════════════════════════════ */
.cost-b{display:inline-flex;align-items:center;gap:4px;height:19px;padding:0 7px;
  border-radius:var(--c-r-xs);font:700 9.5px/1 var(--c-font);letter-spacing:.05em;
  text-transform:uppercase;white-space:nowrap;border:1px solid transparent}
.cost-b.is-ok{background:var(--c-pos-t);color:var(--c-pos);border-color:#CFEADF}
.cost-b.is-warn{background:var(--c-warn-t);color:var(--c-warn);border-color:#F0DFC0}
.cost-b.is-risk{background:var(--c-neg-t);color:var(--c-neg);border-color:#F3D4D0}
.cost-b.is-info{background:var(--c-info-t);color:var(--c-info);border-color:#D3DEF7}
.cost-b.is-mut{background:var(--c-sunken);color:var(--c-mut);border-color:var(--c-line)}

/* ═══ 10. THE ALLOCATION WORKSPACE ═══════════════════════════════════ */

/* ── breadcrumb: walking the tree is the primary navigation here ─────── */
.cost-bread{display:flex;align-items:center;gap:2px;flex-wrap:wrap;margin-bottom:2px}
.cost-bread-b{display:inline-flex;align-items:center;gap:6px;height:28px;padding:0 9px;
  border:0;background:none;border-radius:var(--c-r-xs);cursor:pointer;
  font:600 12px/1 var(--c-font);color:var(--c-mut);transition:background .12s,color .12s}
.cost-bread-b svg{width:14px;height:14px}
.cost-bread-b:hover{background:var(--c-sunken);color:var(--c-ink)}
.cost-bread-b.is-cur{color:var(--c-ink);font-weight:700;background:var(--c-sunken)}
.cost-bread-sep{display:inline-grid;place-items:center;color:var(--c-line-4);width:14px}
.cost-bread-sep svg{width:10px;height:10px}

/* ── the scope header and its split bar ─────────────────────────────── */
.cost-scope{background:var(--c-surface);border:1px solid var(--c-line);
  border-radius:var(--c-r);box-shadow:var(--c-sh-1);overflow:hidden}
.cost-scope-h{display:flex;align-items:flex-start;justify-content:space-between;gap:16px;
  padding:14px 16px 12px}
.cost-scope-t h3{margin:0;font:700 17px/1.2 var(--c-head);letter-spacing:-.018em;color:var(--c-ink)}
.cost-scope-t p{margin:4px 0 0;font-size:11.5px;color:var(--c-mut)}
.cost-scope-v{display:flex;flex-direction:column;align-items:flex-end;gap:1px;flex:0 0 auto}
.cost-scope-v span{font:600 9px/1 var(--c-font);letter-spacing:.11em;text-transform:uppercase;
  color:var(--c-mut-2)}
.cost-scope-v b{font:800 24px/1.1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.035em;color:var(--c-ink)}
.cost-scope-v u{text-decoration:none;font:600 10px/1 var(--c-font);color:var(--c-mut-2);
  letter-spacing:.06em}

/* THE BAR IS THE MODEL: one segment per child, and what is left over */
.cost-split{display:flex;height:46px;margin:0 16px;border-radius:var(--c-r-s);overflow:hidden;
  background:var(--c-sunken);border:1px solid var(--c-line)}
.cost-split>i{position:relative;display:flex;flex-direction:column;justify-content:center;
  padding:0 9px;min-width:2px;overflow:hidden;
  border-right:1px solid rgba(255,255,255,.55);
  transition:width .22s cubic-bezier(.3,.8,.4,1)}
.cost-split>i:last-child{border-right:0}
.cost-split>i>b{font:700 11px/1.2 var(--c-font);color:#fff;white-space:nowrap;
  overflow:hidden;text-overflow:ellipsis;text-shadow:0 1px 1px rgba(10,15,26,.22)}
.cost-split>i>em{font:600 10px/1.2 var(--c-mono);font-style:normal;color:rgba(255,255,255,.9);
  font-variant-numeric:tabular-nums}
.cost-split>i.is-free{background:repeating-linear-gradient(45deg,
  var(--c-sunken),var(--c-sunken) 6px,var(--c-canvas) 6px,var(--c-canvas) 12px)}
.cost-split>i.is-free>b{color:var(--c-mut);text-shadow:none}
.cost-split>i.is-free>em{color:var(--c-mut-2)}

.cost-scope-f{display:flex;align-items:center;gap:16px;flex-wrap:wrap;padding:11px 16px 13px}
.cost-scope-fig{display:inline-flex;align-items:center;gap:7px;font-size:11.5px;color:var(--c-mut)}
.cost-scope-fig>i{width:9px;height:9px;border-radius:2.5px;flex:0 0 auto}
.cost-scope-fig>b{font:700 12.5px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  color:var(--c-ink);letter-spacing:-.025em}
.cost-scope-fig.is-warn>b{color:var(--c-warn)}
.cost-scope-fig.is-risk>b{color:var(--c-neg)}
.cost-scope-sp{flex:1 1 auto}

/* ── tools that say what they will do ───────────────────────────────── */
.cost-tools{display:flex;flex-direction:column;gap:9px;padding:13px 15px;
  background:var(--c-surface);border:1px solid var(--c-line);border-radius:var(--c-r);
  box-shadow:var(--c-sh-1)}
.cost-tools-g{display:flex;align-items:center;gap:12px;flex-wrap:wrap}
.cost-tools-l{font-size:12px;color:var(--c-mut);flex:0 0 auto;min-width:160px}
.cost-tools-l b{font:700 12.5px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  color:var(--c-ink);letter-spacing:-.025em}
.cost-tools-b{display:flex;align-items:center;gap:6px;flex-wrap:wrap}

/* ── one card per child ─────────────────────────────────────────────── */
.cost-kids{display:flex;flex-direction:column;gap:8px}
.cost-kid{display:grid;grid-template-columns:4px minmax(0,1fr) 208px 236px;
  align-items:center;gap:14px;background:var(--c-surface);border:1px solid var(--c-line);
  border-radius:var(--c-r-s);box-shadow:var(--c-sh-1);padding:0 14px 0 0;overflow:hidden;
  transition:border-color .15s,box-shadow .15s}
.cost-kid:hover{border-color:var(--c-line-3);box-shadow:var(--c-sh-2)}
.cost-kid.is-wbs .cost-kid-top .cost-kind{color:var(--kidbg)}
.cost-kid.is-locked{background:linear-gradient(90deg,var(--c-warn-t),var(--c-surface) 180px)}
.cost-kid.is-over{border-color:#EFC5BE;background:linear-gradient(90deg,var(--c-neg-t),var(--c-surface) 180px)}
.cost-kid-swatch{align-self:stretch;width:4px}
.cost-kid-main{display:flex;flex-direction:column;gap:7px;padding:12px 0;min-width:0}
.cost-kid-top{display:flex;align-items:center;gap:7px;min-width:0}
.cost-kid-top .cost-kind{color:var(--c-mut-2)}
.cost-kid-n{font:600 13px/1.2 var(--c-font);color:var(--c-ink);overflow:hidden;
  text-overflow:ellipsis;white-space:nowrap;min-width:0}
.cost-kid-slide{display:flex;align-items:center}

/* the slider: drawn, because the native one is a different control on every
   platform and this is the primary edit in the view */
.cost-range{-webkit-appearance:none;appearance:none;width:100%;height:18px;background:none;
  cursor:pointer;padding:0;margin:0;border:0!important;min-height:0}
.cost-range::-webkit-slider-runnable-track{height:6px;border-radius:99px;
  background:linear-gradient(90deg,var(--c,var(--c-brand)) 0 var(--fill,0%),var(--c-line-2) var(--fill,0%) 100%)}
.cost-range::-moz-range-track{height:6px;border-radius:99px;background:var(--c-line-2)}
.cost-range::-moz-range-progress{height:6px;border-radius:99px;background:var(--c,var(--c-brand))}
.cost-range::-webkit-slider-thumb{-webkit-appearance:none;appearance:none;width:16px;height:16px;
  margin-top:-5px;border-radius:50%;background:#fff;border:2px solid var(--c,var(--c-brand));
  box-shadow:0 1px 3px rgba(10,15,26,.24);transition:transform .12s}
.cost-range::-moz-range-thumb{width:16px;height:16px;border-radius:50%;background:#fff;
  border:2px solid var(--c,var(--c-brand));box-shadow:0 1px 3px rgba(10,15,26,.24)}
.cost-range:hover::-webkit-slider-thumb{transform:scale(1.12)}
.cost-range:active::-webkit-slider-thumb{transform:scale(1.2)}
.cost-range:focus-visible::-webkit-slider-thumb{box-shadow:0 0 0 4px rgba(36,180,126,.25)}
.cost-range[disabled]{opacity:.45;cursor:not-allowed}

.cost-kid-figs{display:flex;align-items:center;gap:8px;justify-content:flex-end}
.cost-kid-pct{position:relative;display:flex;align-items:center;width:82px}
.cost-kid-pct>input{text-align:right;padding-right:18px}
.cost-kid-pct>u{position:absolute;right:5px;text-decoration:none;font:600 10.5px/1 var(--c-font);
  color:var(--c-mut-2);pointer-events:none}
.cost-kid-amt{width:118px}
.cost-kid-amt>input{text-align:right}
.cost-kid-act{display:flex;align-items:center;gap:7px;justify-content:flex-end}
.cost-kid-act .cost-sel{width:126px;flex:0 0 auto}
.cost-kid-leaf{font:600 9.5px/1 var(--c-font);letter-spacing:.09em;text-transform:uppercase;
  color:var(--c-line-4);width:58px;text-align:center}

@media (max-width:1180px){
  .cost-kid{grid-template-columns:4px minmax(0,1fr) 186px;row-gap:0}
  .cost-kid-act{grid-column:2/-1;padding:0 0 12px;justify-content:flex-start}
}
@media (max-width:760px){
  .cost-kid{grid-template-columns:4px minmax(0,1fr)}
  .cost-kid-figs{grid-column:2/-1;justify-content:flex-start;padding-bottom:10px}
  .cost-split{height:38px}
  .cost-scope-v b{font-size:19px}
}

/* ── the allocation meter ───────────────────────────────────────────── */
.cost-meter{display:flex;align-items:center;gap:0;padding:0;background:var(--c-surface);
  border:1px solid var(--c-line);border-radius:var(--c-r);flex-wrap:wrap;
  box-shadow:var(--c-sh-1);overflow:hidden}
.cost-meter-f{display:flex;flex-direction:column;gap:2px;padding:11px 16px;min-width:128px;
  border-right:1px solid var(--c-line-2)}
.cost-meter-f span{font:600 9px/1 var(--c-font);letter-spacing:.11em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-meter-f b{font:800 17px/1.1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.035em;color:var(--c-ink)}
.cost-meter-f.is-ok b{color:var(--c-pos)}
.cost-meter-f.is-warn b{color:var(--c-warn)}
.cost-meter-f.is-risk b{color:var(--c-neg)}
.cost-meter-bar{flex:1 1 220px;height:10px;margin:0 16px;border-radius:99px;
  background:var(--c-line-2);overflow:hidden;display:flex;min-width:140px}
.cost-meter-bar i{display:block;height:100%;transition:width .25s ease}

/* ═══ 11. FORMS ══════════════════════════════════════════════════════ */
.cost-form{display:grid;grid-template-columns:repeat(auto-fit,minmax(210px,1fr));gap:13px 16px}
.cost-form.is-2{grid-template-columns:repeat(2,minmax(0,1fr))}
.cost-f{display:flex;flex-direction:column;gap:5px;min-width:0}

/* ── ADDING COST ASKS ONCE, IN BOTH CURRENCIES OF THIS SCREEN ─────────
   An amount or a share of what the scope already holds — "another 15% on
   Procurement" is how the addition usually arrives, and converting it by
   hand before typing it is work the screen can do. */
.cost-ac-ask{display:grid;grid-template-columns:1.35fr 1fr;gap:12px;align-items:end}
.cost-ac-ask .cost-f.is-pct{position:relative}
.cost-ac-ask .cost-f.is-pct>u{position:absolute;right:11px;bottom:10px;text-decoration:none;
  font:700 11px/1 var(--c-font);color:var(--c-mut-2);pointer-events:none}
.cost-ac-ask .cost-f.is-pct input{padding-right:26px}
@media (max-width:560px){.cost-ac-ask{grid-template-columns:1fr}}
.cost-f>span{font:600 10.5px/1.2 var(--c-font);color:var(--c-ink-3);letter-spacing:.005em}
.cost-f>em{font-style:normal;font-size:10.5px;line-height:1.4;color:var(--c-mut-2)}
.cost-f input[type=text],.cost-f input[type=number],.cost-f input[type=date],.cost-f select{
  height:var(--c-ctl);border:1px solid var(--c-line-3);border-radius:var(--c-r-s);
  background:var(--c-surface);padding:0 10px;font:600 13px/1 var(--c-font);
  color:var(--c-ink);outline:0;width:100%;
  transition:border-color .15s,box-shadow .15s,background .15s}
.cost-f input[type=number],.cost-f input[type=date]{font-family:var(--c-mono);
  font-variant-numeric:tabular-nums;letter-spacing:-.02em}
.cost-f input:hover,.cost-f select:hover{border-color:var(--c-line-4)}
.cost-f input:focus,.cost-f select:focus{border-color:var(--c-brand);
  box-shadow:0 0 0 3px rgba(36,180,126,.14)}
.cost-f input::-webkit-outer-spin-button,.cost-f input::-webkit-inner-spin-button{
  -webkit-appearance:none;margin:0}
.cost-f input[type=number]{-moz-appearance:textfield}
/* the unit lives inside the field, so a percentage never reads as a count */
.cost-f-wrap{position:relative;display:block}
.cost-f-wrap>input{padding-right:38px!important}
.cost-f-wrap>u{position:absolute;right:11px;top:50%;transform:translateY(-50%);
  text-decoration:none;font:600 11px/1 var(--c-font);color:var(--c-mut-2);pointer-events:none}
.cost-f-wrap.is-prefix>input{padding-right:10px!important;padding-left:42px!important}
.cost-f-wrap.is-prefix>u{right:auto;left:11px}
/* a field that does not apply is dimmed and inert, not merely annotated */
.cost-f.is-off{opacity:.42}
.cost-f.is-off input,.cost-f.is-off select{pointer-events:none;background:var(--c-wash)}
.cost-f.is-switch{flex-direction:row;align-items:center;gap:10px;
  grid-column:1/-1;padding:9px 12px;background:var(--c-wash);
  border:1px solid var(--c-line-2);border-radius:var(--c-r-s)}
.cost-f.is-switch>span{font-size:12.5px;font-weight:600;color:var(--c-ink-2);letter-spacing:0}
.cost-f.is-wide{grid-column:1/-1}
/* a date field: our own calendar glyph, and the native one hidden */
.cost-f input[type=date]::-webkit-calendar-picker-indicator{
  opacity:0;position:absolute;right:0;width:34px;height:100%;cursor:pointer}
.cost-f .cost-date{position:relative;display:block}
.cost-f .cost-date>svg{position:absolute;right:10px;top:50%;transform:translateY(-50%);
  width:15px;height:15px;color:var(--c-mut-2);pointer-events:none}
.cost-f .cost-date>input{padding-right:34px!important}

/* the result strip under a rules card */
.cost-result{display:flex;align-items:center;gap:0;flex-wrap:wrap;margin-top:13px;
  background:var(--c-wash);border:1px solid var(--c-line-2);border-radius:var(--c-r-s);overflow:hidden}
.cost-result-f{display:flex;flex-direction:column;gap:1px;padding:9px 14px;min-width:104px;
  border-right:1px solid var(--c-line-2)}
.cost-result-f:last-child{border-right:0}
.cost-result-f span{font:600 8.5px/1 var(--c-font);letter-spacing:.1em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-result-f b{font:700 13px/1.1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.025em;color:var(--c-ink)}

/* a row of sub-fields (release stages, deductions, material splits) */
.cost-rows{display:flex;flex-direction:column;gap:6px}
.cost-row{display:grid;gap:7px;align-items:center;
  grid-template-columns:minmax(0,1.5fr) 92px 84px minmax(0,1.2fr) 30px}
.cost-row>input,.cost-row>select{height:30px;border:1px solid var(--c-line-3);
  border-radius:var(--c-r-xs);background:var(--c-surface);padding:0 9px;
  font:600 12px/1 var(--c-font);color:var(--c-ink);outline:0;width:100%;
  transition:border-color .15s,box-shadow .15s}
.cost-row>input[type=number]{font-family:var(--c-mono);text-align:right;
  font-variant-numeric:tabular-nums}
.cost-row>input:focus,.cost-row>select:focus{border-color:var(--c-brand);
  box-shadow:0 0 0 3px rgba(36,180,126,.14)}
.cost-row>input[disabled]{background:var(--c-wash);color:var(--c-mut-2);border-style:dashed}
.cost-row-h{display:grid;gap:7px;
  grid-template-columns:minmax(0,1.5fr) 92px 84px minmax(0,1.2fr) 30px;
  font:700 9px/1 var(--c-font);letter-spacing:.1em;text-transform:uppercase;
  color:var(--c-mut-2);margin-bottom:7px}
.cost-row-h span:nth-child(2),.cost-row-h span:nth-child(3){text-align:right}

/* ═══ 12. VALIDATION ═════════════════════════════════════════════════ */
.cost-checks{display:flex;flex-direction:column}
.cost-chk{display:flex;align-items:flex-start;gap:10px;padding:9px 14px;
  border-bottom:1px solid var(--c-line-2);font-size:12px}
.cost-chk:last-child{border-bottom:0}
.cost-chk-i{width:17px;height:17px;flex:0 0 auto;margin-top:1px}
.cost-chk.is-pass .cost-chk-i{color:var(--c-pos)}
.cost-chk.is-fail .cost-chk-i{color:var(--c-neg)}
.cost-chk.is-warn .cost-chk-i{color:var(--c-warn)}
.cost-chk b{font-weight:600;color:var(--c-ink);display:block}
.cost-chk span{display:block;color:var(--c-mut);font-size:11px;margin-top:2px;line-height:1.45}
.cost-ready{display:flex;align-items:center;gap:11px;padding:14px 16px;
  border-radius:var(--c-r-s);font:700 13px/1 var(--c-font);letter-spacing:.02em}
.cost-ready svg{width:20px;height:20px;flex:0 0 auto}
.cost-ready.is-ok{background:var(--c-pos-t);color:var(--c-pos);border:1px solid #CFEADF}
.cost-ready.is-no{background:var(--c-neg-t);color:var(--c-neg);border:1px solid #F3D4D0}

/* ═══ 13. CHARTS ═════════════════════════════════════════════════════ */
.cost-chart{width:100%;display:block;overflow:visible}
.cost-chart text{font-family:var(--c-font);fill:var(--c-mut)}
.cost-chart .gr{stroke:var(--c-line-2);stroke-width:1}
.cost-chart .ax{stroke:var(--c-line-3);stroke-width:1}
.cost-chart .zero{stroke:var(--c-mut-2);stroke-width:1;stroke-dasharray:3 3}
.cost-chart .lbl{font-size:9.5px;font-weight:500}
.cost-chart .lbl-y{font-size:9.5px;font-weight:500;font-family:var(--c-mono)}
.cost-chart .ttl{font-size:10px;font-weight:700;fill:var(--c-ink-2)}
.cost-legend{display:flex;align-items:center;gap:14px;flex-wrap:wrap;
  padding:10px 15px 2px;font-size:11px;color:var(--c-mut)}
.cost-legend b{display:inline-flex;align-items:center;gap:6px;font-weight:500;color:var(--c-ink-3)}
.cost-legend i{width:10px;height:10px;border-radius:3px;display:inline-block;flex:0 0 auto}
.cost-legend i.is-line{height:3px;width:16px;border-radius:2px}

/* ═══ 14. EMPTY / NOTE / ERROR ═══════════════════════════════════════ */
.cost-empty{display:flex;flex-direction:column;align-items:center;justify-content:center;
  gap:12px;padding:72px 24px;text-align:center;color:var(--c-mut)}
.cost-empty-ic{width:52px;height:52px;border-radius:var(--c-r);display:grid;place-items:center;
  background:var(--c-sunken);color:var(--c-mut-2);margin-bottom:2px}
.cost-empty-ic svg{width:24px;height:24px}
.cost-empty h3{margin:0;font:700 16px/1.3 var(--c-head);color:var(--c-ink);letter-spacing:-.015em}
.cost-empty p{margin:0;font-size:12.5px;max-width:48ch;line-height:1.65;color:var(--c-mut)}
.cost-note{font-size:11.5px;color:var(--c-mut);line-height:1.6;background:var(--c-wash);
  border:1px solid var(--c-line-2);border-radius:var(--c-r-s);padding:11px 13px}
.cost-note b{color:var(--c-ink-3);font-weight:600}
.cost-note.is-warn{background:var(--c-warn-t);border-color:#F0DFC0;color:#7A5210}
.cost-err{margin:24px;padding:16px;border:1px solid #F3D4D0;background:var(--c-neg-t);
  color:var(--c-neg);border-radius:var(--c-r-s);font-size:12.5px}

/* ═══ 15. DRAWER ═════════════════════════════════════════════════════ */
.cost-portal{position:fixed;inset:0;z-index:9000;display:flex;justify-content:flex-end;
  background:rgba(10,15,26,.32);backdrop-filter:blur(1.5px);
  font-family:var(--c-font);font-size:13px;color:var(--c-ink);
  animation:costFade .16s ease}
@keyframes costFade{from{opacity:0}to{opacity:1}}
.cost-dr{width:min(580px,96vw);background:var(--c-surface);height:100%;
  display:flex;flex-direction:column;box-shadow:var(--c-sh-3);
  animation:costSlide .2s cubic-bezier(.3,.8,.4,1)}
@keyframes costSlide{from{transform:translateX(16px);opacity:.6}to{transform:none;opacity:1}}
.cost-dr-h{display:flex;align-items:flex-start;justify-content:space-between;gap:14px;
  padding:16px 18px;border-bottom:1px solid var(--c-line)}
.cost-dr-h h3{margin:0;font:700 15px/1.25 var(--c-head);letter-spacing:-.015em}
.cost-dr-h p{margin:5px 0 0;font-size:11.5px;color:var(--c-mut);line-height:1.55;max-width:62ch}
.cost-dr-b{flex:1;overflow:auto;padding:16px 18px;display:flex;flex-direction:column;gap:16px}
.cost-dr-f{display:flex;align-items:center;justify-content:flex-end;gap:8px;
  padding:13px 18px;border-top:1px solid var(--c-line);background:var(--c-wash)}
.cost-dr-f .cost-dr-note{margin-right:auto;font-size:10.5px;color:var(--c-mut);
  max-width:46ch;line-height:1.5}
.cost-dr-b>h4{margin:0 0 8px;font:700 10px/1 var(--c-font);letter-spacing:.1em;
  text-transform:uppercase;color:var(--c-mut)}

/* assignment editor */
.cost-asg-h,.cost-asg{display:grid;gap:7px;align-items:center;
  grid-template-columns:minmax(0,1fr) 118px 86px 104px 30px}
.cost-asg-h{font:700 9px/1 var(--c-font);letter-spacing:.1em;text-transform:uppercase;
  color:var(--c-mut-2);margin-bottom:7px}
.cost-asg-h span:nth-child(n+2){text-align:right}
.cost-asg+.cost-asg{margin-top:6px}
.cost-asg input,.cost-asg select{height:30px;border:1px solid var(--c-line-3);
  border-radius:var(--c-r-xs);background:var(--c-surface);padding:0 9px;
  font:600 12px/1 var(--c-font);color:var(--c-ink);outline:0;width:100%}
.cost-asg input[type=number]{font-family:var(--c-mono);text-align:right;
  font-variant-numeric:tabular-nums}
.cost-asg input:focus,.cost-asg select:focus{border-color:var(--c-brand);
  box-shadow:0 0 0 3px rgba(36,180,126,.14)}

/* AI operation card */
.cost-ai-op{border:1px solid var(--c-line);border-radius:var(--c-r-s);padding:11px 13px;
  background:var(--c-surface);box-shadow:var(--c-sh-1)}
.cost-ai-op+.cost-ai-op{margin-top:8px}
.cost-ai-op b{display:block;font:600 12.5px/1.35 var(--c-font);color:var(--c-ink)}
.cost-ai-op span{display:block;font-size:11.5px;color:var(--c-mut);margin-top:3px;line-height:1.5}
.cost-delta{font-family:var(--c-mono);font-size:11.5px;margin-top:6px;
  font-variant-numeric:tabular-nums}
.cost-delta s{color:var(--c-mut-2);text-decoration:line-through}
.cost-delta b{display:inline;color:var(--c-info)}
.cost-ai-q{border:1px solid var(--c-line-3);border-radius:var(--c-r-s);padding:9px 11px;
  font:inherit;font-size:12.5px;resize:vertical;outline:0;color:var(--c-ink);
  background:var(--c-surface);min-height:66px;transition:border-color .15s,box-shadow .15s}
.cost-ai-q:focus{border-color:var(--c-brand);box-shadow:0 0 0 3px rgba(36,180,126,.14)}

/* audit */
.cost-audit{display:flex;flex-direction:column;font-size:11.5px}
.cost-audit-r{display:grid;grid-template-columns:118px 1fr auto;gap:12px;
  padding:8px 14px;border-bottom:1px solid var(--c-line-2);align-items:center}
.cost-audit-r:last-child{border-bottom:0}
.cost-audit-r:hover{background:var(--c-wash)}
.cost-audit-r time{font:500 10px/1 var(--c-mono);color:var(--c-mut-2)}
.cost-audit-r b{font-weight:600;color:var(--c-ink-2)}

/* ═══ 16. RESPONSIVE ═════════════════════════════════════════════════ */
@media (max-width:1240px){
  .cost-grid-3{grid-template-columns:repeat(2,1fr)}
  .cost-grid-2-1{grid-template-columns:1fr}
}
@media (max-width:960px){
  #tp-cost{--c-gut:12px}
  .cost-grid-2,.cost-grid-3{grid-template-columns:1fr}
  .cost-top,.cost-rail{position:static}
  .cost-search{min-width:150px}
  .cost-cn-head,.cost-cn{grid-template-columns:minmax(130px,1.5fr) 100px 74px 120px;gap:8px}
  .cost-cn>.cost-flow,.cost-cn>.cost-cn-act{display:none}
  .cost-cn-head>span:nth-child(4),.cost-cn-head>span:nth-child(6){display:none}
  .cost-asg,.cost-asg-h{grid-template-columns:minmax(0,1fr) 92px 72px 86px 28px}
  .cost-row,.cost-row-h{grid-template-columns:minmax(0,1.3fr) 76px 70px minmax(0,1fr) 28px}
}
/* a coarse pointer needs a 44px target even in a dense table */
@media (pointer:coarse){
  #tp-cost{--c-ctl:38px;--c-ctl-sm:32px;--c-row:40px}
  .cost-cb,.cost-tg,.cost-lock,.cost-icobtn{min-width:32px;min-height:32px}
}
@media (prefers-reduced-motion:reduce){
  #tp-cost *,.cost-portal *{animation-duration:.01ms!important;transition-duration:.01ms!important}
}

/* ═══ 17. PRINT ══════════════════════════════════════════════════════
   The report, not the app. Everything interactive is chrome and chrome on
   paper is noise. */
#costPrintReport{display:none}
@media print{
  body>*{display:none!important}
  body>#costPrintReport{display:block!important}
  @page{size:A4 landscape;margin:12mm 10mm}
  #costPrintReport{font-family:"Inter","Segoe UI",system-ui,sans-serif;color:#0A0F1A;
    font-size:9.5pt;line-height:1.42}
  #costPrintReport .pr-cover{page-break-after:always;padding-top:50mm;text-align:center}
  #costPrintReport .pr-mark{font:800 11pt/1 "Plus Jakarta Sans",sans-serif;
    letter-spacing:.24em;color:#128A5E}
  #costPrintReport .pr-cover h1{margin:10mm 0 3mm;font:800 27pt/1.12 "Plus Jakarta Sans",sans-serif;
    letter-spacing:-.02em}
  #costPrintReport .pr-cover .pr-sub{margin:0;font-size:11pt;color:#69747F}
  #costPrintReport .pr-cover .pr-meta{margin:16mm auto 0;max-width:158mm;
    border-top:.6pt solid #E2E8EE;padding-top:6mm;display:grid;
    grid-template-columns:1fr 1fr;gap:2.4mm 10mm;text-align:left;font-size:9.5pt}
  #costPrintReport .pr-cover .pr-meta b{color:#69747F;font-weight:600}
  #costPrintReport .pr-sect{margin-bottom:7mm}
  #costPrintReport .pr-sect>h2{font:800 12pt/1.2 "Plus Jakarta Sans",sans-serif;margin:0 0 3mm;
    padding-bottom:1.6mm;border-bottom:1.6pt solid #24B47E;page-break-after:avoid}
  #costPrintReport .pr-sect>h3{font:700 10pt/1.2 "Plus Jakarta Sans",sans-serif;
    margin:5mm 0 2mm;page-break-after:avoid}
  #costPrintReport table{width:100%;border-collapse:collapse;font-size:8pt}
  #costPrintReport thead{display:table-header-group}
  #costPrintReport tfoot{display:table-footer-group}
  #costPrintReport th,#costPrintReport td{padding:1.5mm 2mm;border-bottom:.4pt solid #E2E8EE;
    text-align:left;vertical-align:top}
  #costPrintReport thead th{background:#EDF1F5!important;font-weight:700;font-size:7.2pt;
    letter-spacing:.07em;text-transform:uppercase;color:#28323F;border-bottom:.9pt solid #CFD8E1;
    -webkit-print-color-adjust:exact;print-color-adjust:exact}
  #costPrintReport td.n,#costPrintReport th.n{text-align:right;
    font-family:"JetBrains Mono",Consolas,monospace;font-variant-numeric:tabular-nums}
  #costPrintReport tr{page-break-inside:avoid}
  /* the printed WBS band uses the palette the planner actually chose —
     cost-export.js stamps --rowbg/--rowfg from AppearancePalette, the same
     values the screen uses, so a report matches the tab it came from */
  #costPrintReport tr.wbs>*{font-weight:700;
    background:var(--rowbg,#E3EAF2)!important;color:var(--rowfg,#0A0F1A)!important;
    -webkit-print-color-adjust:exact;print-color-adjust:exact}
  #costPrintReport tr.wbs.d0>*{font-weight:800}
  #costPrintReport tr.tot>*{font-weight:800;border-top:.9pt solid #0A0F1A;
    border-bottom:.9pt solid #0A0F1A}
  #costPrintReport .pr-kpis{display:grid;grid-template-columns:repeat(5,1fr);gap:2.4mm;
    margin-bottom:4mm}
  #costPrintReport .pr-kpi{border:.4pt solid #E2E8EE;border-left:1.4pt solid #24B47E;padding:2.2mm}
  #costPrintReport .pr-kpi span{display:block;font-size:6.8pt;letter-spacing:.09em;
    text-transform:uppercase;color:#939DA8;font-weight:700}
  #costPrintReport .pr-kpi b{display:block;font:800 12pt/1.15 "JetBrains Mono",Consolas,monospace;
    margin-top:.7mm;letter-spacing:-.03em}
  #costPrintReport .pr-kpi em{display:block;font-style:normal;font-size:7.4pt;color:#69747F}
  #costPrintReport .pr-chart{width:100%;height:auto;max-height:95mm;page-break-inside:avoid;
    margin-bottom:3mm}
  #costPrintReport .pr-foot{margin-top:6mm;padding-top:2mm;border-top:.4pt solid #E2E8EE;
    font-size:7.4pt;color:#939DA8}
  #costPrintReport .pr-note{font-size:7.8pt;color:#69747F;margin:2mm 0 0;line-height:1.5}
}

/* ===========================================================================
   18. THE GLOBAL CONTROL RESET, NEUTRALISED INSIDE THIS MODULE

   styles/core/nexora-premium-redesign.css carries a bare-element rule:

       input, textarea, select { min-height:44px;
         border-radius:…!important; background:#FFFFFF!important;
         border:1px solid …!important; color:…!important }

   It is a theme-wide reset and it is not this module's to change — other
   tabs are built on top of it. But it wins over any class a tab declares,
   because `.cost-in` (0-1-0) loses to an `!important` declaration on
   `input` (0-0-1) no matter how carefully the class is written.

   Three things followed, and all three were visible on screen:
     · min-height:44px inflated every inline cell editor into a pill taller
       than the 32px row it sits in — the single ugliest thing in the table
     · `background` is a SHORTHAND, so `background:#FFFFFF` erased the
       background-image that draws the select chevron, putting the browser's
       own native arrow back
     · the border and radius were the theme's, not the module's, so the
       controls could never match the tables they sit in

   Re-asserted here at #tp-cost specificity (1-1-0 beats 0-0-1) so the
   module's own controls win INSIDE the module and nothing changes outside
   it. This is the one place in the module that needs !important; it is
   answering !important, not creating it.
   ========================================================================= */
#tp-cost input,#tp-cost select,#tp-cost textarea,
.cost-portal input,.cost-portal select,.cost-portal textarea{
  min-height:0;border-radius:var(--c-r-xs)!important;
  background-color:var(--c-surface)!important;border:1px solid var(--c-line-3)!important;
  color:var(--c-ink)!important;font-family:var(--c-font)}

/* the cell editor: as tall as its row, never taller */
#tp-cost .cost-in,.cost-portal .cost-in{
  min-height:0;height:22px;border-radius:var(--c-r-xs)!important;
  background-color:transparent!important;border:1px solid transparent!important;
  color:var(--c-ink)!important;font-family:var(--c-mono)!important}
#tp-cost .cost-in:hover,.cost-portal .cost-in:hover{
  border-color:var(--c-line-3)!important;background-color:var(--c-surface)!important}
#tp-cost .cost-in:focus,.cost-portal .cost-in:focus{
  border-color:var(--c-brand)!important;background-color:var(--c-surface)!important}
#tp-cost .cost-in.is-derived,.cost-portal .cost-in.is-derived{
  border-color:transparent!important;background-color:transparent!important;color:var(--c-mut)!important}

/* the headline figure editors on the Cost Plan */
#tp-cost .cost-kpi-in{min-height:0;height:26px;border-radius:0!important;
  background-color:transparent!important;color:var(--c-ink)!important;
  border:0!important;border-bottom:1.5px dashed var(--c-line-3)!important;
  font-family:var(--c-mono)!important}
#tp-cost .cost-kpi-in:hover{border-bottom-color:var(--c-line-4)!important}
#tp-cost .cost-kpi-in:focus{border-bottom-color:var(--c-brand)!important;border-bottom-style:solid!important}

/* SELECTS keep their drawn chevron: background-color only, never the
   shorthand, so the background-image survives */
#tp-cost .cost-sel,.cost-portal .cost-sel{
  min-height:0;height:var(--c-ctl-sm);border-radius:var(--c-r-xs)!important;
  background-color:var(--c-surface)!important;border:1px solid var(--c-line-3)!important;
  color:var(--c-ink-2)!important;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='none' stroke='%2369747F' stroke-width='1.9' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpolyline points='4 6.5 8 10.5 12 6.5'/%3E%3C/svg%3E")!important;
  background-repeat:no-repeat!important;background-position:right 7px center!important;
  background-size:13px!important}
#tp-cost .cost-sel.is-lg{height:var(--c-ctl);border-radius:var(--c-r-s)!important}
#tp-cost .cost-sel:focus,.cost-portal .cost-sel:focus{border-color:var(--c-brand)!important}

/* form fields, drawer fields and the small sub-row inputs */
#tp-cost .cost-f input,#tp-cost .cost-f select,
.cost-portal .cost-f input,.cost-portal .cost-f select{
  min-height:0;height:var(--c-ctl);border-radius:var(--c-r-s)!important;
  background-color:var(--c-surface)!important;border:1px solid var(--c-line-3)!important;
  color:var(--c-ink)!important}
#tp-cost .cost-f input:focus,#tp-cost .cost-f select:focus,
.cost-portal .cost-f input:focus,.cost-portal .cost-f select:focus{
  border-color:var(--c-brand)!important}
#tp-cost .cost-f.is-off input,#tp-cost .cost-f.is-off select{
  background-color:var(--c-wash)!important}
#tp-cost .cost-row>input,#tp-cost .cost-row>select,
#tp-cost .cost-asg input,#tp-cost .cost-asg select,
.cost-portal .cost-row>input,.cost-portal .cost-row>select,
.cost-portal .cost-asg input,.cost-portal .cost-asg select{
  min-height:0;height:30px;border-radius:var(--c-r-xs)!important;
  background-color:var(--c-surface)!important;border:1px solid var(--c-line-3)!important;
  color:var(--c-ink)!important}
#tp-cost .cost-row>input[disabled],.cost-portal .cost-row>input[disabled]{
  background-color:var(--c-wash)!important;color:var(--c-mut-2)!important;border-style:dashed!important}
#tp-cost .cost-search input,.cost-portal .cost-search input{
  min-height:0;height:100%;border:0!important;background-color:transparent!important;
  border-radius:0!important;color:var(--c-ink)!important}
#tp-cost .cost-ai-q,.cost-portal .cost-ai-q{
  min-height:66px;border-radius:var(--c-r-s)!important;
  background-color:var(--c-surface)!important;border:1px solid var(--c-line-3)!important;
  color:var(--c-ink)!important;font-family:var(--c-font)!important}

/* the drawn checkbox: the real input is invisible and must stay that way */
#tp-cost .cost-cb input,.cost-portal .cost-cb input{
  min-height:0;height:100%;width:100%;border:0!important;background-color:transparent!important;
  border-radius:0!important;-webkit-appearance:none;appearance:none}

/* ── ranked bars: real HTML, so the labels are at their real size ────────
   The SVG twin (byCategorySvg) still exists for the PDF and the deck; on
   screen a scaled viewBox rendered every caption at two thirds of its
   stated size inside a half-width card. */
.cost-ranked{display:flex;flex-direction:column}
.cost-ranked-r{display:grid;grid-template-columns:minmax(96px,148px) 1fr 64px 46px;
  align-items:center;gap:11px;padding:6px 0;border-bottom:1px solid var(--c-line-2)}
.cost-ranked-r:last-child{border-bottom:0}
.cost-ranked-l{font-size:11.5px;color:var(--c-ink-2);font-weight:500;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cost-ranked-t{display:block;height:14px;border-radius:3px;background:var(--c-line-2);
  overflow:hidden;position:relative}
.cost-ranked-t>i{display:block;height:100%;border-radius:3px;
  transition:width .25s cubic-bezier(.3,.8,.4,1)}
.cost-ranked-v{font:700 11.5px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.025em;color:var(--c-ink);text-align:right}
.cost-ranked-p{font:500 11px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  color:var(--c-mut);text-align:right}
@media (max-width:600px){
  .cost-ranked-r{grid-template-columns:minmax(80px,1fr) 1.4fr 56px;gap:8px}
  .cost-ranked-p{display:none}
}

/* the identifier leads the name cell: monospace, fixed width, never wrapping,
   so a column of ids reads as a column even though it shares a cell */
.cost-code.is-id{flex:0 0 auto;min-width:58px;text-align:left;
  font:600 10.5px/1 var(--c-mono);letter-spacing:-.02em;color:var(--c-mut);
  padding-right:8px;margin-right:2px;border-right:1px solid var(--c-line-2)}

/* the range slider, kept clear of the theme-wide control reset (section 18) */
#tp-cost input[type=range],.cost-portal input[type=range]{
  min-height:0;height:18px;border:0!important;background-color:transparent!important;
  border-radius:0!important;padding:0}

/* ══════════════════════════════════════════════════════════════════════
   19 — THE GRID

   A cost plan is worked, not read. What follows gives the table the three
   things that separate a worked grid from a printed one: a cell you can
   see the cursor on, a header that says how it is sorted, and an edit that
   opens in place instead of sitting permanently open in forty rows at once.

   The cursor is a RING, not a fill. A filled cell fights the WBS banding —
   the bands carry meaning here (they are the level colours from the Gantt)
   and a selection colour painted over them would read as a different level.
   ══════════════════════════════════════════════════════════════════════ */

.cost-tbl.is-grid{outline:none}
.cost-tbl.is-grid:focus-visible{outline:none}
.cost-tbl.is-grid [data-c]{position:relative}

/* the active cell */
.cost-tbl.is-grid [data-c].is-cur::after{
  content:"";position:absolute;inset:0;pointer-events:none;z-index:3;
  border:2px solid var(--c-brand-d);border-radius:2px;
  box-shadow:0 0 0 1px rgba(255,255,255,.55) inset}
.cost-tbl.is-grid:focus-within [data-c].is-cur::after{
  box-shadow:0 0 0 1px rgba(255,255,255,.55) inset,0 0 0 3px var(--c-brand-t2)}
.cost-tbl.is-grid th.is-stick[data-c].is-cur::after{border-radius:2px}

/* a cell that CAN be edited says so on hover, and only on hover — forty
   permanent affordances is noise, none at all is a guessing game */
.cost-tbl.is-grid td[data-edit]{cursor:cell}
.cost-tbl.is-grid td[data-edit]:hover::before{
  content:"";position:absolute;inset:1px;border-radius:3px;pointer-events:none;
  border:1px dashed var(--c-line-4)}
/* A SET FIGURE IS DARKER THAN A DERIVED ONE — except on a painted WBS
   band, where "darker" is the one thing it must not be: --rowfg is the
   band's own ink, and near-black on navy is unreadable. */
.cost-tbl.is-grid td[data-edit].is-set{font-weight:650;color:var(--rowfg,var(--c-ink))}
.cost-row-w td[data-edit].is-set::before{background:var(--rowfg,var(--c-brand));opacity:.55}
.cost-row-w td[data-edit]:hover::before{border-color:var(--rowdv,var(--c-line-4))}
.cost-tbl.is-grid .cost-row-w [data-c].is-cur::after{
  border-color:var(--rowfg,var(--c-brand-d));
  box-shadow:0 0 0 1px rgba(0,0,0,.25) inset}
.cost-tbl.is-grid td[data-edit].is-set::before{
  content:"";position:absolute;left:0;top:0;bottom:0;width:2px;
  background:var(--c-brand);border:0;border-radius:0;opacity:.75}

/* the in-place editor */
#tp-cost .cost-tbl input.cg-edit,.cost-portal .cost-tbl input.cg-edit{
  width:100%;min-height:0;height:22px;padding:0 5px;margin:0;
  border:1px solid var(--c-brand-d)!important;border-radius:3px!important;
  background:var(--c-surface)!important;color:var(--c-ink)!important;
  font:600 12px/1 var(--c-mono)!important;font-variant-numeric:tabular-nums;
  text-align:right;box-shadow:0 0 0 3px var(--c-brand-t2);outline:none}
.cost-tbl td.is-editing{padding-top:2px;padding-bottom:2px}

/* ── sortable headers ────────────────────────────────────────────────── */
.cost-tbl th.is-sortable{cursor:pointer;user-select:none}
.cost-tbl th.is-sortable:hover{color:var(--c-ink)}
.cost-tbl th.is-sortable:focus-visible{outline:2px solid var(--c-brand);outline-offset:-2px}
.cost-th{display:inline-flex;align-items:center;gap:5px}
.cost-tbl th.n .cost-th{flex-direction:row-reverse}
.cost-sortmark{width:8px;height:10px;flex:0 0 auto;position:relative;opacity:0;
  transition:opacity .15s ease}
.cost-tbl th.is-sortable:hover .cost-sortmark{opacity:.35}
.cost-sortmark.is-asc,.cost-sortmark.is-desc{opacity:1}
.cost-sortmark::before{content:"";position:absolute;left:1px;top:3px;
  border-left:3px solid transparent;border-right:3px solid transparent;
  border-bottom:4px solid currentColor}
.cost-sortmark.is-desc::before{border-bottom:0;border-top:4px solid currentColor}
.cost-tbl th.is-sorted{color:var(--c-brand-dd)}

/* ── allocation status chip ──────────────────────────────────────────── */
.cost-st{display:inline-block;padding:2px 7px;border-radius:var(--c-r-pill);
  font:600 10.5px/1.5 var(--c-font);letter-spacing:.005em;white-space:nowrap;
  border:1px solid transparent}
.cost-st.is-key{background:var(--c-brand-t);color:var(--c-brand-dd);border-color:var(--c-brand-t2)}
.cost-st.is-ok{background:var(--c-pos-t);color:var(--c-pos);border-color:#CBE9DC}
.cost-st.is-warn{background:var(--c-warn-t);color:var(--c-warn);border-color:#F0DFC0}
.cost-st.is-info{background:#EAF1FB;color:#2A5CA8;border-color:#D3E2F6}
.cost-st.is-mut{background:var(--c-wash);color:var(--c-mut);border-color:var(--c-line)}
.cost-st.is-nil{background:transparent;color:var(--c-mut-2);border-color:var(--c-line-2)}
/* on a painted WBS row the chip borrows the row's own ink so it does not
   punch a light hole through the band */
.cost-row-w .cost-st{background:rgba(255,255,255,.14);color:var(--rowfg,inherit);
  border-color:var(--rowdv,transparent)}

.cost-tbl td.is-trunc{max-width:170px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}

/* ── bulk action bar ─────────────────────────────────────────────────── */
.cost-bulk{display:flex;align-items:center;gap:8px;flex-wrap:wrap;
  padding:9px 12px;margin:0 0 10px;border-radius:var(--c-r-s);
  background:var(--c-brand-t);border:1px solid var(--c-brand-t2);
  box-shadow:var(--c-sh-1)}
.cost-bulk-n{font:700 12px/1 var(--c-font);color:var(--c-brand-dd);
  padding-right:4px;margin-right:2px;border-right:1px solid var(--c-brand-t2)}
.cost-bulk-sp{flex:1 1 auto}
.cost-bulk .cost-btn{background:var(--c-surface)}

/* ── the cell menu ───────────────────────────────────────────────────── */
.cost-menu{position:fixed;z-index:9200;min-width:236px;max-width:320px;
  padding:5px;border-radius:var(--c-r-s);background:var(--c-surface);
  border:1px solid var(--c-line-3);box-shadow:var(--c-sh-3);
  font-family:var(--c-font);animation:costMenuIn .1s ease-out}
@keyframes costMenuIn{from{opacity:0;transform:translateY(-3px)}to{opacity:1;transform:none}}
.cost-menu-h{padding:6px 9px 7px;margin:-1px -1px 4px;font:600 10.5px/1.4 var(--c-font);
  letter-spacing:.02em;color:var(--c-mut);border-bottom:1px solid var(--c-line-2);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cost-menu-sep{height:1px;margin:4px 6px;background:var(--c-line-2)}
.cost-menu-b{display:flex;align-items:flex-start;justify-content:space-between;gap:10px;
  width:100%;padding:7px 9px;border:0;border-radius:var(--c-r-xs);background:transparent;
  color:var(--c-ink-2);font:500 12.5px/1.35 var(--c-font);text-align:left;cursor:pointer}
.cost-menu-b:hover,.cost-menu-b:focus-visible{background:var(--c-wash);color:var(--c-ink);outline:none}
.cost-menu-b em{display:block;margin-top:2px;font-style:normal;
  font-size:11px;color:var(--c-mut);line-height:1.4}
.cost-menu-b kbd{flex:0 0 auto;padding:1px 5px;border-radius:3px;
  background:var(--c-wash);border:1px solid var(--c-line);
  font:600 10px/1.5 var(--c-mono);color:var(--c-mut)}

@media (max-width:760px){
  .cost-bulk{gap:6px;padding:8px}
  .cost-bulk-n{width:100%;border-right:0;padding-right:0}
  .cost-menu{min-width:0;max-width:calc(100vw - 24px)}
}

/* ══════════════════════════════════════════════════════════════════════
   20 — THE RESOLUTION BAR

   This is the only place in the module where an out-of-balance figure is
   allowed to appear, and it appears for as long as it takes to answer one
   question. It sits directly under the state bar because it BLOCKS: the
   edit behind it is not written until one of these is chosen.
   ══════════════════════════════════════════════════════════════════════ */
.cost-pending{margin:0 var(--c-gut) 12px;padding:14px 16px 12px;
  border-radius:var(--c-r);background:var(--c-surface);
  border:1px solid #F0DFC0;border-left:3px solid var(--c-warn);
  box-shadow:var(--c-sh-2);animation:costPendIn .14s ease-out}
@keyframes costPendIn{from{opacity:0;transform:translateY(-4px)}to{opacity:1;transform:none}}
.cost-pending-h{margin-bottom:11px}
.cost-pending-tag{display:inline-block;margin-bottom:6px;padding:2px 8px;
  border-radius:var(--c-r-pill);background:var(--c-warn-t);color:var(--c-warn);
  border:1px solid #F0DFC0;font:700 9.5px/1.6 var(--c-font);
  letter-spacing:.09em;text-transform:uppercase}
.cost-pending-h h3{margin:0;font:600 15px/1.4 var(--c-font);color:var(--c-ink);
  letter-spacing:-.01em}
.cost-pending-h h3 b{font-weight:700;font-family:var(--c-mono);
  font-variant-numeric:tabular-nums;letter-spacing:-.02em;color:var(--c-warn)}
.cost-pending-h p{margin:5px 0 0;font-size:12px;line-height:1.6;color:var(--c-mut)}

.cost-pending-opts{display:grid;gap:8px;
  grid-template-columns:repeat(auto-fit,minmax(240px,1fr))}
.cost-pending-o{display:block;width:100%;padding:10px 12px;text-align:left;
  border:1px solid var(--c-line-3);border-radius:var(--c-r-s);
  background:var(--c-wash);cursor:pointer;font-family:var(--c-font);
  transition:background .14s ease,border-color .14s ease,box-shadow .14s ease}
.cost-pending-o:hover{background:var(--c-surface);border-color:var(--c-brand);
  box-shadow:0 0 0 3px var(--c-brand-t)}
.cost-pending-o:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}
.cost-pending-o b{display:block;font:600 12.5px/1.4 var(--c-font);color:var(--c-ink)}
.cost-pending-o em{display:block;margin-top:3px;font-style:normal;
  font-size:11.5px;line-height:1.55;color:var(--c-mut)}
.cost-pending-f{margin-top:10px;display:flex;justify-content:flex-end}

/* the state bar's own reconcile button, shown only on a store that was
   written before an edit had to close the scope it touched */
.cost-state .cost-btn[data-act="reconcile"]{margin-left:2px}

@media (max-width:700px){
  .cost-pending{margin:0 10px 10px;padding:12px}
  .cost-pending-opts{grid-template-columns:1fr}
}

/* the row an unapplied edit belongs to */
.cost-tbl tr.is-pending>th,.cost-tbl tr.is-pending>td{
  box-shadow:inset 0 0 0 999px var(--c-warn-t)}
.cost-tbl tr.cost-row-w.is-pending>th,.cost-tbl tr.cost-row-w.is-pending>td{
  box-shadow:inset 0 0 0 999px rgba(247,205,130,.22)}

/* ══════════════════════════════════════════════════════════════════════
   21 — THE ALLOCATION STUDIO

   Two bars on ONE scale, a grid between them, and the money-movement
   column that makes the point the bars only imply: nothing appears, it
   comes from a sibling.
   ══════════════════════════════════════════════════════════════════════ */

.cost-ba{display:grid;grid-template-columns:1fr 26px 1fr;align-items:end;gap:10px;
  padding:12px 14px 13px;border-top:1px solid var(--c-line-2)}
/* ONE DIVISION, ONE BAR. With nothing pending and the activities carrying
   what they were allocated, there is no second figure to draw — and the
   same bar twice with an arrow between them said there was. */
.cost-ba.is-one{grid-template-columns:1fr}
.cost-ba-col{min-width:0}
.cost-ba-h{display:flex;align-items:baseline;justify-content:space-between;gap:8px;
  margin-bottom:6px}
.cost-ba-h span{font:700 9.5px/1 var(--c-font);letter-spacing:.1em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-ba-h b{font:700 13px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.02em;color:var(--c-ink)}
.cost-ba-col.is-ok .cost-ba-h b{color:var(--c-pos)}
.cost-ba-col.is-warn .cost-ba-h b{color:var(--c-warn)}
.cost-ba-col.is-ok .cost-split{box-shadow:0 0 0 2px var(--c-pos-t)}
.cost-ba-col.is-warn .cost-split{box-shadow:0 0 0 2px var(--c-warn-t)}
.cost-ba-arrow{display:grid;place-items:center;height:34px;color:var(--c-mut-2)}
.cost-ba-arrow svg{width:18px;height:18px}

.cost-bread-draft{margin-left:auto;padding:2px 9px;border-radius:var(--c-r-pill);
  background:var(--c-warn-t);color:var(--c-warn);border:1px solid #F0DFC0;
  font:600 10.5px/1.6 var(--c-font);white-space:nowrap}

/* the movement column */
.cost-mv{display:inline-block;width:0;height:0;
  border-left:4.5px solid transparent;border-right:4.5px solid transparent}
.cost-mv.is-up{border-bottom:6px solid var(--c-pos)}
.cost-mv.is-down{border-top:6px solid var(--c-neg)}
.cost-mv.is-flat{width:9px;height:1.5px;border:0;background:var(--c-line-3);
  border-radius:1px;vertical-align:middle}
.cost-tbl td.is-pos{color:var(--c-pos);font-weight:650}
.cost-tbl.is-studio tr.is-edited>th,.cost-tbl.is-studio tr.is-edited>td{
  box-shadow:inset 0 0 0 999px rgba(36,180,126,.10)}
.cost-tbl.is-studio tr.cost-row-w.is-edited>th,.cost-tbl.is-studio tr.cost-row-w.is-edited>td{
  box-shadow:inset 0 0 0 999px rgba(140,240,200,.16)}
.cost-tbl.is-studio tr.is-locked .cost-lock.is-on{color:var(--c-warn)}
.cost-tbl.is-studio .cost-kid-swatch{flex:0 0 auto;width:8px;height:16px;
  border-radius:2px;margin-right:2px}
.cost-tbl.is-studio .cost-sel{width:100%;max-width:172px}

/* ── the impact panel ────────────────────────────────────────────────── */
.cost-imp .cost-imp-r{display:grid;grid-template-columns:1.6fr .9fr .9fr .9fr;
  gap:10px;align-items:baseline;padding:8px 14px;
  border-bottom:1px solid var(--c-line-2)}
.cost-imp .cost-imp-r:last-child{border-bottom:0}
.cost-imp-r.is-head{padding-top:9px;padding-bottom:7px;background:var(--c-wash)}
.cost-imp-r.is-head span{font:700 9.5px/1 var(--c-font);letter-spacing:.09em;
  text-transform:uppercase;color:var(--c-mut-2);text-align:right}
.cost-imp-r.is-head .cost-imp-l{text-align:left}
.cost-imp-l{font-size:12.5px;color:var(--c-ink-2);font-weight:500}
.cost-imp-l em{display:block;margin-top:2px;font-style:normal;font-size:11px;
  color:var(--c-mut);line-height:1.45}
.cost-imp-b,.cost-imp-a,.cost-imp-d{text-align:right;
  font:600 12.5px/1.4 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.02em}
.cost-imp-b{color:var(--c-mut)}
.cost-imp-a{color:var(--c-ink)}
.cost-imp-d{font-size:11.5px;font-weight:650}
.cost-imp-d.is-pos,.cost-imp-a.is-pos{color:var(--c-pos)}
.cost-imp-d.is-neg,.cost-imp-a.is-neg{color:var(--c-neg)}
.cost-imp-d.is-nil{color:var(--c-mut-2);font-family:var(--c-font);font-weight:500}

/* ── review and apply ────────────────────────────────────────────────── */
.cost-apply{margin:12px var(--c-gut) 0;padding:13px 15px;border-radius:var(--c-r);
  background:var(--c-surface);border:1px solid var(--c-line-3);
  box-shadow:var(--c-sh-2)}
.cost-apply.is-ok{border-left:3px solid var(--c-pos)}
.cost-apply.is-warn{border-left:3px solid var(--c-warn)}
.cost-apply-t b{display:block;font:600 13.5px/1.4 var(--c-font);color:var(--c-ink)}
.cost-apply-t span{display:block;margin-top:3px;font-size:12px;line-height:1.6;
  color:var(--c-mut)}
.cost-apply-opts{display:grid;gap:8px;margin-top:11px;
  grid-template-columns:repeat(auto-fit,minmax(230px,1fr))}
.cost-apply-b{display:flex;justify-content:flex-end;gap:8px;margin-top:11px}

@media (max-width:820px){
  .cost-ba{grid-template-columns:1fr;gap:8px}
  .cost-ba-arrow{height:14px;transform:rotate(90deg)}
  .cost-imp .cost-imp-r{grid-template-columns:1fr .8fr .8fr;gap:7px}
  .cost-imp-d{display:none}
  .cost-apply-opts{grid-template-columns:1fr}
}

.cost-imp-none{padding:12px 14px 13px;border-top:1px solid var(--c-line-2);
  background:var(--c-wash)}
.cost-imp-none b{display:block;font:600 12.5px/1.4 var(--c-font);color:var(--c-ink-2)}
.cost-imp-none span{display:block;margin-top:3px;font-size:11.5px;line-height:1.6;
  color:var(--c-mut)}

/* ══════════════════════════════════════════════════════════════════════
   22 — THE CONTRACT MODEL FLOW

   The order of these stages IS the arithmetic — retention off the gross,
   recovery off what is left — so the chain is drawn as a chain. Each stage
   carries its own figure and opens the rule that produced it.
   ══════════════════════════════════════════════════════════════════════ */

.cost-flow-card{margin-bottom:12px}
.cost-flow-per{display:flex;flex-wrap:wrap;gap:5px;padding:10px 14px 0}
.cost-flow-per .cost-seg-b{border:1px solid var(--c-line-3);border-radius:var(--c-r-pill);
  padding:3px 10px;background:var(--c-surface)}
.cost-flow-per .cost-seg-b.is-on{background:var(--c-brand-d);border-color:var(--c-brand-d);color:#fff}

.cost-flow{display:flex;align-items:stretch;gap:0;padding:12px 14px 4px;
  overflow-x:auto;scrollbar-width:thin}
.cost-flow-s{flex:1 1 0;min-width:132px;padding:10px 11px 11px;
  border:1px solid var(--c-line);border-radius:var(--c-r-s);
  background:var(--c-wash);position:relative;transition:background .14s,border-color .14s}
.cost-flow-s[data-act]{cursor:pointer}
.cost-flow-s[data-act]:hover{background:var(--c-surface);border-color:var(--c-brand);
  box-shadow:0 0 0 3px var(--c-brand-t)}
.cost-flow-s[data-act]:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}
.cost-flow-s.is-strong{background:var(--c-surface);border-color:var(--c-line-3);
  box-shadow:var(--c-sh-1)}
.cost-flow-t{display:block;font:700 9.5px/1.3 var(--c-font);letter-spacing:.08em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-flow-v{display:block;margin-top:5px;font:700 15px/1.15 var(--c-mono);
  font-variant-numeric:tabular-nums;letter-spacing:-.03em;color:var(--c-ink)}
.cost-flow-s.is-minus .cost-flow-v{color:var(--c-neg)}
.cost-flow-s.is-strong .cost-flow-v{color:var(--c-brand-dd);font-size:16px}
.cost-flow-r{display:block;margin-top:5px;font-style:normal;font-size:10.5px;
  line-height:1.5;color:var(--c-mut)}
.cost-flow-go{display:block;margin-top:7px;font:600 10.5px/1 var(--c-font);
  color:var(--c-brand-d);opacity:0;transition:opacity .14s}
.cost-flow-s[data-act]:hover .cost-flow-go,
.cost-flow-s[data-act]:focus-visible .cost-flow-go{opacity:1}
.cost-flow-j{flex:0 0 auto;display:grid;place-items:center;width:18px;
  color:var(--c-line-4)}
.cost-flow-j svg{width:13px;height:13px}
.cost-flow-foot{margin:0;padding:6px 14px 13px;font-size:11.5px;color:var(--c-mut)}

/* the rule card the flow just sent you to */
.cost-card.is-flash{animation:costFlash 1.4s ease-out}
@keyframes costFlash{
  0%,55%{box-shadow:0 0 0 3px var(--c-brand-t2),var(--c-sh-2)}
  100%{box-shadow:var(--c-sh-1)}
}

@media (max-width:760px){
  .cost-flow{padding:10px 10px 4px}
  .cost-flow-s{min-width:118px}
}

/* the payment schedule's date columns read as dates, not as prose */
.cost-tbl td.d,.cost-tbl th.d{font:500 11.5px/1.4 var(--c-mono);
  font-variant-numeric:tabular-nums;letter-spacing:-.01em;
  color:var(--c-ink-2);text-align:right;white-space:nowrap}
.cost-tbl th.d{font:700 9.5px/1 var(--c-font);letter-spacing:.07em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-tbl.is-pay td.d.is-key{color:var(--c-ink);font-weight:650}
.cost-tbl.is-pay tbody tr:hover>td,.cost-tbl.is-pay tbody tr:hover>th{
  box-shadow:inset 0 0 0 999px rgba(36,180,126,.05)}

/* ══════════════════════════════════════════════════════════════════════
   23 — COMMERCIAL EXCEPTIONS
   A KPI says what a number is. This says which number is a problem.
   ══════════════════════════════════════════════════════════════════════ */
.cost-exc-r{display:grid;grid-template-columns:20px 1fr auto auto;gap:11px;
  align-items:center;padding:10px 14px;border-bottom:1px solid var(--c-line-2)}
.cost-exc-r:last-child{border-bottom:0}
.cost-exc-i{display:grid;place-items:center;width:20px;height:20px}
.cost-exc-i svg{width:17px;height:17px}
.cost-exc-r.is-risk .cost-exc-i{color:var(--c-neg)}
.cost-exc-r.is-warn .cost-exc-i{color:var(--c-warn)}
.cost-exc-r.is-info .cost-exc-i{color:var(--c-brand-d)}
.cost-exc-t b{display:block;font:600 12.5px/1.4 var(--c-font);color:var(--c-ink)}
.cost-exc-t span{display:block;margin-top:2px;font-size:11.5px;line-height:1.55;
  color:var(--c-mut)}
.cost-exc-v{font:700 13px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.03em;color:var(--c-ink);white-space:nowrap;text-align:right}
.cost-exc-r.is-risk .cost-exc-v{color:var(--c-neg)}
.cost-exc-r.is-warn .cost-exc-v{color:var(--c-warn)}
.cost-exc-none{display:flex;align-items:flex-start;gap:11px}
.cost-exc-none svg{width:19px;height:19px;flex:0 0 auto;color:var(--c-pos);margin-top:1px}
.cost-exc-none b{display:block;font:600 12.5px/1.4 var(--c-font);color:var(--c-ink)}
.cost-exc-none span{display:block;margin-top:3px;font-size:11.5px;line-height:1.6;
  color:var(--c-mut)}
@media (max-width:700px){
  .cost-exc-r{grid-template-columns:20px 1fr;gap:8px}
  .cost-exc-v{grid-column:2;text-align:left}
  .cost-exc-r>.cost-btn,.cost-exc-r>button{grid-column:2;justify-self:start}
}

/* the XER export gate: every blocker names its fix */
.cost-gate{border:1px solid #F3CFC9;border-radius:var(--c-r-s);background:var(--c-neg-t);
  overflow:hidden}
.cost-gate-r{display:grid;grid-template-columns:18px 1fr auto;gap:10px;align-items:start;
  padding:10px 12px;border-bottom:1px solid rgba(192,59,50,.14)}
.cost-gate-r:last-child{border-bottom:0}
.cost-gate-r>svg{width:17px;height:17px;color:var(--c-neg);margin-top:1px}
.cost-gate-r b{display:block;font:600 12.5px/1.4 var(--c-font);color:var(--c-ink)}
.cost-gate-r span{display:block;margin-top:2px;font-size:11.5px;line-height:1.55;
  color:var(--c-ink-3)}
.cost-gate-r em{display:block;margin-top:5px;font-style:normal;font-size:11.5px;
  line-height:1.55;color:var(--c-neg);font-weight:500}
.cost-gate-r .cost-btn{white-space:nowrap}
@media (max-width:620px){
  .cost-gate-r{grid-template-columns:18px 1fr}
  .cost-gate-r .cost-btn{grid-column:2}
}

/* ══════════════════════════════════════════════════════════════════════
   24 — A CHOICE STATED IN THE LANGUAGE OF THE CONTRACT
   ══════════════════════════════════════════════════════════════════════ */
.cost-choice{display:grid;gap:8px;grid-template-columns:repeat(auto-fit,minmax(230px,1fr));
  margin-bottom:11px}
.cost-choice-b{display:block;width:100%;padding:11px 13px;text-align:left;cursor:pointer;
  border:1px solid var(--c-line-3);border-radius:var(--c-r-s);background:var(--c-wash);
  font-family:var(--c-font);transition:background .14s,border-color .14s,box-shadow .14s}
.cost-choice-b:hover{background:var(--c-surface);border-color:var(--c-line-4)}
.cost-choice-b:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}
.cost-choice-b.is-on{background:var(--c-brand-t);border-color:var(--c-brand);
  box-shadow:0 0 0 3px var(--c-brand-t2)}
.cost-choice-b b{display:block;font:600 13px/1.35 var(--c-font);color:var(--c-ink)}
.cost-choice-b.is-on b{color:var(--c-brand-dd)}
.cost-choice-b em{display:block;margin-top:4px;font-style:normal;font-size:11.5px;
  line-height:1.55;color:var(--c-mut)}

/* a derived KPI is DRAWN as derived, not as an input waiting to be typed in */
.cost-kpi.is-derived .cost-kpi-v{display:block;padding:4px 0 3px;
  font:700 19px/1.1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.035em;color:var(--c-ink)}
.cost-link{border:0;background:none;padding:0;cursor:pointer;font:inherit;
  color:var(--c-brand-d);text-decoration:underline;text-underline-offset:2px}
.cost-link:hover{color:var(--c-brand-dd)}

/* ── retention release stages ────────────────────────────────────────── */
.cost-stages{display:grid;gap:9px}
.cost-stage{padding:11px 12px 12px;border:1px solid var(--c-line);
  border-radius:var(--c-r-s);background:var(--c-wash)}
.cost-stage-h{display:flex;align-items:center;gap:8px;margin-bottom:9px}
#tp-cost input.cost-stage-n,.cost-portal input.cost-stage-n{
  flex:1 1 auto;min-height:0;height:28px;padding:0 9px;
  font:600 12.5px/1 var(--c-font)!important;color:var(--c-ink)!important;
  background:var(--c-surface)!important;border:1px solid var(--c-line-3)!important}
.cost-stage .cost-form.is-3{display:grid;gap:9px;
  grid-template-columns:repeat(auto-fit,minmax(140px,1fr))}
.cost-stage-r{display:flex;flex-wrap:wrap;align-items:baseline;gap:5px;margin-top:9px;
  padding-top:9px;border-top:1px dashed var(--c-line-3);font-size:11.5px;color:var(--c-mut)}
.cost-stage-r b{font:700 12px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.02em;color:var(--c-ink)}

/* ══════════════════════════════════════════════════════════════════════
   25 — A TABLE THAT FITS, AND SAYS WHAT CAN BE TYPED IN

   Two failures this fixes. The name column took a quarter of the width
   because nothing bounded it, and an editable cell announced itself only
   on hover — so a planner who never happened to hover concluded, fairly,
   that the table could not be edited at all.
   ══════════════════════════════════════════════════════════════════════ */

.cost-tbl.is-fixed{table-layout:fixed;width:100%}
.cost-tbl.is-fixed th,.cost-tbl.is-fixed td{overflow:hidden;text-overflow:ellipsis}
.cost-tbl.is-fixed .cost-nm-t{min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}

/* the grip on the name column */
.cost-colgrip{position:absolute;top:0;right:-3px;bottom:0;width:7px;cursor:col-resize;
  z-index:6}
.cost-colgrip::after{content:"";position:absolute;top:22%;bottom:22%;left:3px;width:1px;
  background:var(--c-line-3);transition:background .14s}
.cost-colgrip:hover::after{background:var(--c-brand);width:2px;left:2.5px}
/* NOTE: do not set position:relative here — it overrides the sticky
   header (line 322) and the month labels then scroll away while the
   first column stays pinned. `sticky` is already a containing block for
   the absolutely positioned resize grip. */
body.cost-resizing{cursor:col-resize;user-select:none}

/* AN EDITABLE CELL SAYS SO WITHOUT BEING HOVERED. A hairline down the
   leading edge, permanent and quiet — enough to read as a column of
   inputs, not enough to compete with the figures. */
.cost-tbl.is-grid td[data-edit]::before{
  content:"";position:absolute;left:0;top:3px;bottom:3px;width:2px;border:0;border-radius:0;
  background:var(--c-line-3);opacity:.9;transition:background .14s,opacity .14s}
.cost-tbl.is-grid td[data-edit]:hover::before{background:var(--c-brand);opacity:1}
.cost-tbl.is-grid td[data-edit].is-set::before{background:var(--c-brand);opacity:.8}
.cost-row-w td[data-edit]::before{background:var(--rowfg,var(--c-line-3));opacity:.4}
.cost-row-w td[data-edit]:hover::before,.cost-row-w td[data-edit].is-set::before{
  background:var(--rowfg,var(--c-brand));opacity:.95}

/* ── the column chooser ──────────────────────────────────────────────── */
.cost-colpick{display:flex;flex-wrap:wrap;align-items:center;gap:6px;
  padding:9px 11px;margin:0 0 10px;border-radius:var(--c-r-s);
  background:var(--c-wash);border:1px solid var(--c-line)}
.cost-colpick-sp{flex:1 1 auto}
.cost-colpick-b{display:inline-flex;align-items:center;gap:6px;padding:4px 10px 4px 6px;
  border-radius:var(--c-r-pill);border:1px solid var(--c-line-3);background:var(--c-surface);
  font:500 12px/1.3 var(--c-font);color:var(--c-mut);cursor:pointer;
  transition:background .14s,border-color .14s,color .14s}
.cost-colpick-b:hover{border-color:var(--c-line-4);color:var(--c-ink-2)}
.cost-colpick-b.is-on{background:var(--c-brand-t);border-color:var(--c-brand-t2);
  color:var(--c-brand-dd);font-weight:600}
.cost-cbm{display:grid;place-items:center;width:14px;height:14px;flex:0 0 auto;
  border-radius:3px;border:1.5px solid var(--c-line-4);background:var(--c-surface)}
.cost-cbm.is-on{border-color:var(--c-brand-d);background:var(--c-brand-d);color:#fff}
.cost-cbm svg{width:11px;height:11px}
.cost-cbm.is-on svg circle{display:none}

/* the trailing column that absorbs the slack — it carries nothing and must
   never take a cursor, a border or a hover */
.cost-tbl .cost-sp{padding:0;border-left:0;background:transparent;pointer-events:none}

/* ══════════════════════════════════════════════════════════════════════
   26 — THE STUDIO'S TOOLBAR AND ITS NESTED ROWS
   Eleven buttons across the top were eleven buttons a planner did not
   want on most visits. One opens them, and says what they would move.
   ══════════════════════════════════════════════════════════════════════ */
.cost-toolbar{display:flex;align-items:center;gap:9px;flex-wrap:wrap;
  padding:9px 14px;margin:12px var(--c-gut) 0;border-radius:var(--c-r-s);
  background:var(--c-surface);border:1px solid var(--c-line)}
.cost-toolbar-l{font-size:12px;color:var(--c-mut)}
.cost-toolbar-l b{font:700 12.5px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.02em;color:var(--c-warn)}
.cost-toolbar-sp{flex:1 1 auto}

/* a row that is context rather than the thing being edited */
.cost-tbl.is-studio tr.is-sub>td{color:var(--c-mut)}
.cost-tbl.is-studio tr.is-sub .cost-nm-t{font-weight:500}
.cost-tbl.is-studio tr.is-sub td[data-c="proposed"]{font-weight:500;color:var(--c-ink-3)}
.cost-tbl.is-studio td[data-c="open"] .cost-icobtn svg{width:13px;height:13px}
.cost-tbl.is-studio td[data-c="open"] .cost-icobtn{opacity:.45}
.cost-tbl.is-studio tr:hover td[data-c="open"] .cost-icobtn{opacity:1}

/* THE ID CHIP WAS TAKING 58px OF THE NAME CELL and the name was getting 91.
   An id is four or five characters; it does not need a fifth of the column. */
.cost-tbl.is-fixed .cost-code.is-id{min-width:0;max-width:64px;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap;padding-right:6px}
.cost-tbl.is-fixed .cost-nm{gap:5px}
.cost-tbl.is-fixed .cost-rails{flex:0 0 auto}
.cost-tbl.is-fixed .cost-rails i{width:11px}

/* the spacer must carry the header and footer surface, or the table looks
   sliced off halfway across the pane */
.cost-tbl thead th.cost-sp,.cost-tbl tfoot td.cost-sp{
  background:inherit;border-bottom:inherit}
.cost-tbl thead th.cost-sp{background:var(--c-wash)}

/* ══════════════════════════════════════════════════════════════════════
   27 — COMMERCIAL RULES: CARDS, A LIST, AND ONE OPEN TERM

   Six forms stacked down a page is not a screen. A commercial manager
   works one term at a time and needs to know, before opening anything,
   which terms are on and what each is worth.
   ══════════════════════════════════════════════════════════════════════ */

.cost-rulecards{display:grid;gap:9px;margin:0 var(--c-gut) 12px;
  grid-template-columns:repeat(auto-fit,minmax(168px,1fr))}
.cost-rulecard{display:block;text-align:left;padding:11px 13px 12px;cursor:pointer;
  border:1px solid var(--c-line);border-radius:var(--c-r-s);background:var(--c-surface);
  box-shadow:var(--c-sh-1);font-family:var(--c-font);
  transition:border-color .14s,box-shadow .14s,background .14s}
.cost-rulecard:hover{border-color:var(--c-line-4)}
.cost-rulecard:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}
.cost-rulecard.is-cur{border-color:var(--c-brand);box-shadow:0 0 0 3px var(--c-brand-t),var(--c-sh-1)}
.cost-rulecard.is-off{background:var(--c-wash);box-shadow:none}
.cost-rulecard.is-off .cost-rulecard-v,.cost-rulecard.is-off .cost-rulecard-a{color:var(--c-mut-2)}
.cost-rulecard-t{display:block;font:700 9.5px/1.3 var(--c-font);letter-spacing:.08em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-rulecard-v{display:block;margin-top:5px;font:700 18px/1.1 var(--c-mono);
  font-variant-numeric:tabular-nums;letter-spacing:-.035em;color:var(--c-ink)}
.cost-rulecard-a{display:block;margin-top:3px;font:600 11.5px/1.3 var(--c-mono);
  font-variant-numeric:tabular-nums;letter-spacing:-.02em;color:var(--c-ink-3)}
.cost-rulecard-s{display:block;margin-top:4px;font-style:normal;font-size:11px;
  line-height:1.45;color:var(--c-mut)}

/* ── the list and the pane ───────────────────────────────────────────── */
.cost-rulepane{display:grid;grid-template-columns:236px minmax(0,1fr);gap:12px;
  margin:0 var(--c-gut)}
.cost-rulelist{display:flex;flex-direction:column;gap:2px;padding:6px;align-self:start;
  border:1px solid var(--c-line);border-radius:var(--c-r);background:var(--c-surface);
  box-shadow:var(--c-sh-1);position:sticky;top:8px}
.cost-rulelist-r{display:flex;align-items:center;gap:8px;padding:2px 4px 2px 6px;
  border-radius:var(--c-r-xs)}
.cost-rulelist-r.is-cur{background:var(--c-brand-t)}
.cost-rulelist-b{flex:1 1 auto;min-width:0;text-align:left;border:0;background:none;
  padding:7px 4px;cursor:pointer;font-family:var(--c-font)}
.cost-rulelist-b b{display:block;font:600 12.5px/1.3 var(--c-font);color:var(--c-ink-2)}
.cost-rulelist-r.is-cur .cost-rulelist-b b{color:var(--c-brand-dd)}
.cost-rulelist-r.is-off .cost-rulelist-b b{color:var(--c-mut)}
.cost-rulelist-b em{display:block;margin-top:2px;font-style:normal;font-size:11px;
  color:var(--c-mut);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cost-rulelist-b:focus-visible{outline:2px solid var(--c-brand);outline-offset:-2px;
  border-radius:var(--c-r-xs)}
.cost-rulepane-r>.cost-card{margin:0}
.cost-sw.is-sm{width:30px;height:17px;flex:0 0 auto}
.cost-sw.is-sm::after{width:13px;height:13px}
.cost-sw.is-sm.is-on::after{transform:translateX(13px)}
.cost-sw.is-fixed{background:var(--c-line-2);border-color:var(--c-line-2);cursor:default;
  opacity:.5}

@media (max-width:860px){
  .cost-rulepane{grid-template-columns:1fr}
  .cost-rulelist{position:static;flex-direction:row;flex-wrap:wrap}
  .cost-rulelist-r{flex:0 1 auto}
  .cost-rulelist-b em{display:none}
}

/* a term that is always on: present, not switchable */
.cost-rulelist-dot{flex:0 0 auto;width:30px;display:grid;place-items:center}
.cost-rulelist-dot::after{content:"";width:5px;height:5px;border-radius:50%;
  background:var(--c-line-4)}
.cost-rulelist-r.is-cur .cost-rulelist-dot::after{background:var(--c-brand-d)}

/* the S-curve's axis titles, and the per-period hover band */
.cost-chart .lbl-ax{font:600 8.5px/1 var(--c-font);letter-spacing:.07em;
  text-transform:uppercase;fill:var(--c-mut-2)}
.cost-chart .hot{cursor:crosshair}
.cost-chart .hot:hover{fill:rgba(36,180,126,.07)}

/* periods across: the measure column stays put and the totals column reads
   as the total rather than as another month */
.cost-tbl.is-matrix th.is-stick{min-width:150px}
.cost-tbl.is-matrix .is-tot{background:var(--c-wash);font-weight:700;color:var(--c-ink)}
.cost-tbl.is-matrix thead th.is-tot{color:var(--c-ink-2)}

/* ══════════════════════════════════════════════════════════════════════
   28 — THE CASH FLOW SECTION

   Two components and nothing else: a chart of money in against money out
   with the running position over it, and one table saying the same thing
   period by period. The KPI strip, the second summary and the caption row
   that used to sit between them all restated figures the table already
   carried, and a figure stated twice is a figure that has to be reconciled
   before either can be trusted.

   COLOUR IS ASSIGNED BY MEANING AND NEVER BY RANK. Retention is the same
   soft red wherever it appears, amortisation the same amber, profit the
   same purple — and profit is the one row here that is NOT cash, which is
   exactly why it is the one row that does not share a hue with anything
   that moves. Saturation is spent on the four figures that get argued
   about — the net invoice, the total in, the position and the funding
   requirement — and withheld everywhere else, because a table where every
   row shouts has no emphasis left to give.
   ══════════════════════════════════════════════════════════════════════ */
.cost-cf{
  --cf-out:#C03B32;      /* cost leaving                                */
  --cf-in:#12855E;       /* money arriving                              */
  --cf-ret:#D4645C;      /* retention held back — a soft red, not alarm */
  --cf-ap:#BE7C17;       /* advance amortisation                        */
  --cf-profit:#6A4CC4;   /* margin. NOT a cash movement.                */
  --cf-net:#0C7A55;      /* the certificate's net — the figure argued over */
  --cf-adv:#2B59C3;      /* the advance itself                          */
  --cf-rel:#0C8B9B;      /* retention coming back                       */
  --cf-pos:#2B59C3;      /* the running position                        */
  --cf-need:#B57619;     /* money the business has to find              */
  gap:14px;
}

/* ── THE CHART ──────────────────────────────────────────────────────── */
.cost-cf-chart{background:var(--c-surface);border:1px solid var(--c-line);
  border-radius:var(--c-r);box-shadow:var(--c-sh-1);overflow:hidden}
.cost-cf-chart-h{display:grid;grid-template-columns:1fr auto;align-items:start;
  gap:10px 18px;padding:14px 16px 10px}
.cost-cf-chart-h h3{grid-column:1;margin:0;font:700 14px/1.25 var(--c-head);
  letter-spacing:-.015em;color:var(--c-ink)}
.cost-cf-chart-h p{grid-column:1;margin:4px 0 0;font-size:11.5px;line-height:1.55;
  color:var(--c-mut);max-width:70ch;min-height:2.1em}
/* the switcher and the legend share the right-hand column: the control
   that changes the reading, and the key to the reading it changed to */
.cost-cf-tools{grid-column:2;grid-row:1/span 2;display:flex;flex-direction:column;
  align-items:flex-end;gap:9px;padding-top:1px}
.cost-cf-seg{flex:0 0 auto}
.cost-cf-chart-b{padding:2px 8px 8px}
/* the chart is the smaller half of the section: it frames the question,
   the table answers it */
.cost-cf-chart-b .cost-chart{display:block;width:100%;height:auto;
  max-height:clamp(220px,38vh,340px)}

/* a legend on one line, in the header — not a block of its own */
.cost-cf-key{display:flex;align-items:center;justify-content:flex-end;
  gap:13px;flex-wrap:wrap}
.cost-cf-k{display:inline-flex;align-items:center;gap:6px;
  font:500 11px/1 var(--c-font);color:var(--c-mut);white-space:nowrap}
.cost-cf-k>i{width:9px;height:9px;border-radius:2px;flex:0 0 auto}
.cost-cf-k>i.is-line{width:14px;height:2.5px;border-radius:2px}

/* ── THE TABLE HEADER ───────────────────────────────────────────────── */
.cost-cf-tbl-h{display:flex;align-items:baseline;gap:10px;flex-wrap:wrap;
  padding:2px 2px 0}
.cost-cf-tbl-h h3{margin:0;font:700 11px/1 var(--c-font);letter-spacing:.11em;
  text-transform:uppercase;color:var(--c-mut)}
.cost-cf-tbl-h p{margin:0;font-size:11px;color:var(--c-mut-2)}
.cost-cf-tbl-h .cost-btn{margin-left:auto;align-self:center}

/* ── THE TABLE ────────────────────────────────────────────────────────
   A STATEMENT, NOT A SPREADSHEET. Three things do most of the work here:
   a rail down the left of every row saying which section it belongs to,
   so a reader who has scrolled past the band still knows where they are;
   a faint tint on alternate columns, the same rhythm the chart uses, so
   the eye holds its month across a table that is wider than the screen;
   and a hairline crosshair on hover, because finding the intersection of
   a row and a month in a thirteen-column matrix is otherwise a task. */
.cost-cf-wrap{max-height:min(62vh,760px)}
.cost-cf-t{font-size:12px}
.cost-cf-t tbody th.is-stick{padding-left:12px;min-width:252px}
.cost-cf-t tbody th,.cost-cf-t tbody td{height:33px}

/* THE MONTH HEADER CARRIES THE TABLE, so it is allowed to look like it:
   full ink rather than a grey, a real rule under it, and a ground that
   separates it from the statement instead of dissolving into it. */
.cost-cf-t thead th{height:38px;font-size:10px;font-weight:750;letter-spacing:.085em;
  color:var(--c-ink);background:var(--c-canvas);
  border-bottom:2px solid var(--c-ink-3)}
.cost-cf-t thead th.is-stick{background:var(--c-canvas)}
.cost-cf-t thead th.is-tot{background-color:var(--c-sunken);color:var(--c-ink)}

/* NO BANDING ON THE COLUMNS. Tinting every other month was meant to help
   the eye hold its column; what it actually did was give a table of money
   a stripe pattern, so the columns read as two different KINDS of month
   rather than as one row of them. The crosshair already does that job,
   and it does it only for the column somebody is actually pointing at. */
.cost-cf-t tbody td.is-tot,.cost-cf-t thead th.is-tot{background-color:var(--c-wash)}

/* THE SECTION RAIL. Four pixels of the band's own colour, carried down
   every row underneath it. */
.cost-cf-t tbody tr.sect-out>th.is-stick{box-shadow:inset 3px 0 0 rgba(192,59,50,.55)}
.cost-cf-t tbody tr.sect-in>th.is-stick{box-shadow:inset 3px 0 0 rgba(18,133,94,.55)}
.cost-cf-t tbody tr.sect-pos>th.is-stick{box-shadow:inset 3px 0 0 rgba(43,89,195,.55)}
/* THE TOTAL IS PINNED, LIKE THE MONTH NAME. A programme long enough to
   scroll is exactly the programme whose total nobody can see, and a
   statement whose bottom line is off the right-hand edge is a statement
   that has to be scrolled to be believed. */
.cost-cf-t thead th.is-tot,.cost-cf-t tbody td.is-tot{
  position:sticky;right:0;background:var(--c-wash);
  border-left:1px solid var(--c-line-3)}
.cost-cf-t tbody td.is-tot{z-index:2}
.cost-cf-t thead th.is-tot{z-index:4}
.cost-cf-t td.is-tot::before{content:"";position:absolute;top:0;bottom:0;left:-1px;
  width:1px;background:var(--c-line-3)}

/* ── A SECTION BAND ───────────────────────────────────────────────────
   THE THREE LINES THE WHOLE STATEMENT COMES DOWN TO. Everything else on
   this table is working; these are the answers, so they are the one place
   the section's colour is spent at full strength — a solid rail, a tinted
   ground, the name in its own hue and the figures at full weight. A
   summary line that looks like the rows underneath it is not a summary. */
.cost-tbl tr.cost-cf-b>th,.cost-tbl tr.cost-cf-b>td{background:var(--c-sunken);
  border-top:1.5px solid var(--c-line-3);border-bottom:1.5px solid var(--c-line-3)}
.cost-tbl tr.cost-cf-b>th{padding:0}
.cost-cf-t tr.cost-cf-b>td.is-tot{background:var(--c-sunken)}
.cost-tbl tr.cost-cf-b:first-child>th,.cost-tbl tr.cost-cf-b:first-child>td{border-top:0}
.cost-cf-b .cost-cf-v{font-weight:800;font-size:12.5px}

/* each band in its own colour, ground and all */
.cost-tbl tr.cost-cf-b.is-out>th,.cost-tbl tr.cost-cf-b.is-out>td{
  background:var(--c-neg-t);border-top-color:rgba(192,59,50,.34);
  border-bottom-color:rgba(192,59,50,.34)}
.cost-tbl tr.cost-cf-b.is-in>th,.cost-tbl tr.cost-cf-b.is-in>td{
  background:var(--c-pos-t);border-top-color:rgba(18,133,94,.34);
  border-bottom-color:rgba(18,133,94,.34)}
.cost-tbl tr.cost-cf-b.is-pos>th,.cost-tbl tr.cost-cf-b.is-pos>td{
  background:var(--c-info-t);border-top-color:rgba(43,89,195,.34);
  border-bottom-color:rgba(43,89,195,.34)}
.cost-cf-b.is-out .cost-cf-tg>span{color:#8E2B24}
.cost-cf-b.is-in .cost-cf-tg>span{color:#0A5C41}
.cost-cf-b.is-pos .cost-cf-tg>span{color:#1E3F8C}
.cost-cf-b.is-out .cost-cf-tg>i.cost-tg{color:var(--cf-out)}
.cost-cf-b.is-in .cost-cf-tg>i.cost-tg{color:var(--cf-in)}
.cost-cf-b.is-pos .cost-cf-tg>i.cost-tg{color:var(--cf-pos)}
.cost-cf-b.is-out .cost-cf-tg:hover{background:rgba(192,59,50,.07)}
.cost-cf-b.is-in .cost-cf-tg:hover{background:rgba(18,133,94,.07)}
.cost-cf-b.is-pos .cost-cf-tg:hover{background:rgba(43,89,195,.07)}
/* the total column keeps the band's ground rather than reverting to grey */
.cost-cf-t tr.cost-cf-b.is-out>td.is-tot{background:#F7E2DF}
.cost-cf-t tr.cost-cf-b.is-in>td.is-tot{background:#DCF0E7}
.cost-cf-t tr.cost-cf-b.is-pos>td.is-tot{background:#E0E8F9}
.cost-cf-tg{display:flex;align-items:center;gap:9px;width:100%;padding:8px 12px;
  border:0;background:none;cursor:pointer;text-align:left;font-family:var(--c-font)}
.cost-cf-tg:hover{background:rgba(10,15,26,.045)}
.cost-cf-tg:focus-visible{outline:2px solid var(--c-brand);outline-offset:-2px}
.cost-cf-tg>span{font:700 9.5px/1.4 var(--c-font);letter-spacing:.11em;
  text-transform:uppercase;color:var(--c-ink-3)}

.cost-cf-tg>i.cost-tg{flex:0 0 auto;width:15px;height:15px;display:grid;place-items:center;
  color:var(--c-mut);transition:transform .14s}
.cost-cf-tg>i.cost-tg svg{width:11px;height:11px}
/* the band carries the meaning of everything under it, on its left edge —
   four solid pixels, against the three translucent ones on its rows */
.cost-tbl tr.cost-cf-b>th{box-shadow:inset 4px 0 0 var(--c-line-3)}
.cost-tbl tr.cost-cf-b.is-out>th{box-shadow:inset 4px 0 0 var(--cf-out)}
.cost-tbl tr.cost-cf-b.is-in>th{box-shadow:inset 4px 0 0 var(--cf-in)}
.cost-tbl tr.cost-cf-b.is-pos>th{box-shadow:inset 4px 0 0 var(--cf-pos)}

/* ── A ROW ──────────────────────────────────────────────────────────── */
.cost-cf-r>th.is-stick{display:table-cell;white-space:nowrap}
.cost-cf-lb{font:500 12px/1.5 var(--c-font);color:var(--c-ink-2)}
/* a four-pixel chip carrying the row's meaning — so retention and
   amortisation are told apart at the left edge, before the label is read */
.cost-cf-dot{display:inline-block;width:4px;height:4px;border-radius:50%;
  margin-right:8px;vertical-align:1px;background:var(--c-line-4)}
.cost-cf-r.is-out .cost-cf-dot{background:var(--cf-out)}
.cost-cf-r.is-in .cost-cf-dot{background:var(--cf-in)}
.cost-cf-r.is-ret .cost-cf-dot{background:var(--cf-ret)}
.cost-cf-r.is-ap .cost-cf-dot{background:var(--cf-ap)}
.cost-cf-r.is-profit .cost-cf-dot{background:var(--cf-profit)}
.cost-cf-r.is-net .cost-cf-dot{background:var(--cf-net)}
.cost-cf-r.is-adv .cost-cf-dot{background:var(--cf-adv)}
.cost-cf-r.is-rel .cost-cf-dot{background:var(--cf-rel)}
.cost-cf-r.is-pos .cost-cf-dot{background:var(--cf-pos)}
.cost-cf-r.is-need .cost-cf-dot{background:var(--cf-need)}
/* "not a cash movement" belongs on the row that is not one, not in a
   footnote at the bottom of a table that scrolls */
.cost-cf-nt{display:inline-block;margin-left:8px;font-style:normal;
  font:500 10px/1.4 var(--c-font);color:var(--c-mut-2);letter-spacing:.005em}

/* ── A FIGURE ─────────────────────────────────────────────────────────
   THE DOTS CARRY THE TAXONOMY, THE DIGITS CARRY ONLY DIRECTION.

   Ten hues on ten rows of numbers is not a hierarchy, it is a paint
   chart: nothing stands out because everything does, and the reader ends
   up matching shades instead of reading money. So the ten stay, at four
   pixels each, on the chip beside every label — where they still tell
   retention from amortisation at a glance — and the figures themselves
   are ink unless there is something about the DIRECTION of the money
   that the digits have to say:

     · cash out is red, because it is leaving
     · the net invoice and the total in are green, because they arrive
       and because they are the two figures anyone argues about
     · profit is purple, because it is the one row that is not cash
     · the funding requirement is amber, because it is a warning
     · the position takes its colour from its sign, because on a running
       balance the sign IS the message

   Everything else — the gross, the deductions, the advance, the release,
   the packages — is ink, and a deduction is known by its brackets. */
.cost-cf-v{font-family:var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.02em;font-weight:550;color:var(--c-ink-2)}
.cost-cf-v.is-out{color:var(--cf-out)}
.cost-cf-v.is-profit{color:var(--cf-profit)}
.cost-cf-v.is-net{color:var(--cf-net)}
.cost-cf-v.is-need{color:var(--cf-need);font-weight:650}
/* green is spent on the two lines that are the section's answer, not on
   every row that happens to sit in the cash-in block */
.cost-cf-r.is-tot .cost-cf-v.is-in,.cost-cf-b.is-in .cost-cf-v{color:var(--cf-in)}
/* the position is the one row where the sign is the message */
.cost-cf-r.is-pos .cost-cf-v,.cost-cf-b.is-pos .cost-cf-v{color:var(--cf-in)}
.cost-cf-r.is-pos .cost-cf-v.is-brk,.cost-cf-b.is-pos .cost-cf-v.is-brk{color:var(--cf-out)}
.cost-cf-nil{color:var(--c-line-4);font-weight:400}

/* ── EMPHASIS: TWO LEVELS, AND ONLY TWO ─────────────────────────────
   The net invoice is the figure a certificate is argued about; the total
   in is the figure the month is judged on. Everything else is working. */
.cost-cf-r.is-sub>th,.cost-cf-r.is-sub>td{background:var(--c-wash)}
.cost-cf-r.is-sub .cost-cf-lb{font-weight:650;color:var(--c-ink)}
.cost-cf-r.is-sub .cost-cf-v{font-weight:700;font-size:12px}
.cost-cf-r.is-tot>th,.cost-cf-r.is-tot>td{background:var(--c-wash);
  border-top:1px solid var(--c-line-3);border-bottom:1px solid var(--c-line-3)}
.cost-cf-r.is-tot .cost-cf-lb{font-weight:750;color:var(--c-ink)}
.cost-cf-r.is-tot .cost-cf-v{font-weight:800;font-size:12.5px}
.cost-cf-r>td.is-tot .cost-cf-v{font-weight:700}

/* a funding requirement is money you must FIND: amber, and stated as a
   positive, because it is not an amount leaving */
.cost-cf-r.is-need>th,.cost-cf-r.is-need>td{background:var(--c-warn-t)}
.cost-cf-r.is-need>th.is-stick{background:var(--c-warn-t)}
.cost-cf-r.is-need .cost-cf-lb{font-weight:650;color:#8A5A11}
.cost-cf-r.is-need>td.is-tot{background:#F9E9CC}

.cost-tbl tr.cost-cf-r:hover>td{box-shadow:inset 0 0 0 999px rgba(43,89,195,.045)}
/* the row rail must survive the hover wash, so the row's th layers both */
.cost-cf-t tbody tr.cost-cf-r:hover>th.is-stick{
  box-shadow:inset 0 0 0 999px rgba(43,89,195,.045),inset 3px 0 0 var(--c-line-3)}
.cost-cf-t tbody tr.sect-out:hover>th.is-stick{
  box-shadow:inset 0 0 0 999px rgba(43,89,195,.045),inset 3px 0 0 rgba(192,59,50,.45)}
.cost-cf-t tbody tr.sect-in:hover>th.is-stick{
  box-shadow:inset 0 0 0 999px rgba(43,89,195,.045),inset 3px 0 0 rgba(18,133,94,.45)}
.cost-cf-t tbody tr.sect-pos:hover>th.is-stick{
  box-shadow:inset 0 0 0 999px rgba(43,89,195,.045),inset 3px 0 0 rgba(43,89,195,.45)}

/* THE COLUMN HALF OF THE CROSSHAIR. A tall pseudo-element on the hovered
   cell, clipped by the scroll wrapper — no script, no per-column classes,
   and it costs nothing when nobody is pointing at anything.
   NOTE: position:relative goes on the plain money cells ONLY. The sticky
   first column and the pinned total are positioned already, and taking
   that away puts the month labels back on top of the rows. */
.cost-cf-wrap{position:relative}
.cost-cf-t tbody td.n:not(.is-tot){position:relative}
.cost-cf-t tbody td.n:not(.is-tot):hover::before{content:"";position:absolute;
  left:0;right:0;top:-2000px;bottom:-2000px;background:rgba(43,89,195,.05);
  pointer-events:none;z-index:0}
.cost-cf-t tbody td.n>*{position:relative;z-index:1}

/* ── A FIGURE THAT EXPLAINS ITSELF ──────────────────────────────────
   Every money cell with something behind it is a real button: it takes
   focus, it takes Enter and Space, and it says so on hover rather than
   only on the pointer arriving. A cell that cannot be reached from a
   keyboard is a figure nobody using one can defend. */
.cost-cf-t td.is-drill{padding:0}
.cost-cf-cell{display:block;width:100%;height:100%;padding:0 10px;border:0;
  background:none;font:inherit;color:inherit;text-align:right;cursor:pointer;
  border-radius:0;transition:background .12s,box-shadow .12s}
.cost-cf-cell:hover{background:rgba(43,89,195,.09);
  box-shadow:inset 0 -1.5px 0 rgba(43,89,195,.45)}
.cost-cf-cell:focus-visible{outline:2px solid var(--c-brand);outline-offset:-2px}

/* ── THE DRILL-DOWN ─────────────────────────────────────────────────
   The working behind one figure, opened from the figure. It is a
   statement, not a form: label on the left, money on the right, and one
   rule above the line the whole panel exists to prove. */
.cost-dr.is-slim{width:min(430px,96vw)}
.cost-dl{border:1px solid var(--c-line);border-radius:var(--c-r-s);
  background:var(--c-surface);overflow:hidden}
.cost-dl-r{display:flex;align-items:center;justify-content:space-between;gap:18px;
  padding:9px 13px;border-bottom:1px solid var(--c-line-2)}
.cost-dl-r:last-child{border-bottom:0}
.cost-dl-r.is-rule{border-top:1.5px solid var(--c-ink-3);background:var(--c-wash)}
.cost-dl-l{font:500 12px/1.5 var(--c-font);color:var(--c-ink-2);min-width:0}
.cost-dl-v{font-family:var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.02em;font:600 12.5px/1.4 var(--c-mono);color:var(--c-ink-2);
  white-space:nowrap}
.cost-dl-r.is-strong .cost-dl-l{font-weight:700;color:var(--c-ink)}
.cost-dl-r.is-strong .cost-dl-v{font-weight:800;font-size:13.5px}
.cost-dl-v .cost-cf-v{font-weight:inherit;font-size:inherit}
.cost-dl-note{margin:0;font-size:11.5px;line-height:1.6;color:var(--c-mut)}
.cost-dl-none{margin:0;padding:12px 13px;font-size:11.5px;color:var(--c-mut)}

/* on a narrow screen the legend drops under the title rather than
   squeezing it to two words a line */
@media (max-width:860px){
  .cost-cf-chart-h{grid-template-columns:1fr}
  .cost-cf-key{grid-column:1;grid-row:auto;padding-top:2px}
  .cost-cf-t tbody th.is-stick{min-width:180px}
  .cost-cf-nt{display:none}
}

/* ══════════════════════════════════════════════════════════════════════
   29 — COST OVER TIME

   The same rows and hierarchy as the cost plan, spread over the calendar.
   A cell's bar is its share of the busiest cell on this programme, green
   through amber to red, so the heavy months are visible before a figure
   is read.
   ══════════════════════════════════════════════════════════════════════ */
.cost-tbl.is-timeline{table-layout:auto}
.cost-tbl.is-timeline th.is-stick{min-width:260px;max-width:340px}
.cost-tbl.is-timeline thead th.n{min-width:74px}
.cost-tl-c{position:relative;padding-top:3px;padding-bottom:3px;min-width:74px}
.cost-tl-bar{position:absolute;left:4px;right:4px;bottom:3px;height:3px;border-radius:2px;
  background:var(--c-line-2);overflow:hidden;display:block}
.cost-tl-bar::after{content:"";position:absolute;left:0;top:0;bottom:0;
  width:var(--w,0%);background:var(--c);border-radius:2px}
.cost-tl-c b{display:block;font:600 11.5px/1.5 var(--c-mono);
  font-variant-numeric:tabular-nums;letter-spacing:-.02em;color:var(--c-ink-2)}
.cost-tbl.is-timeline tr.cost-row-w .cost-tl-c b{color:var(--rowfg)}
.cost-tbl.is-timeline tr.cost-row-w .cost-tl-bar{background:var(--rowtrack,rgba(255,255,255,.18))}
.cost-tbl.is-timeline td.is-tot,.cost-tbl.is-timeline th.is-tot{
  background:var(--c-wash);font-weight:750;border-left:1px solid var(--c-line-3)}
.cost-tbl.is-timeline tr.cost-row-w td.is-tot{background:var(--rowbg);color:var(--rowfg)}
.cost-tbl.is-timeline tfoot td,.cost-tbl.is-timeline tfoot th{font-weight:750}

/* the step that makes an allocation reach Primavera, offered where the
   allocation is made */
.cost-apply-load{display:flex;align-items:flex-start;gap:10px;margin-top:11px;
  padding:10px 12px;border-radius:var(--c-r-s);background:var(--c-wash);
  border:1px solid var(--c-line);cursor:pointer}
.cost-apply-load.is-off{opacity:.5}
.cost-apply-load>span{min-width:0}
.cost-apply-load b{display:block;font:600 12.5px/1.4 var(--c-font);color:var(--c-ink)}
.cost-apply-load em{display:block;margin-top:3px;font-style:normal;font-size:11.5px;
  line-height:1.55;color:var(--c-mut)}

/* ══════════════════════════════════════════════════════════════════════
   THE TWO BASES, AND THE OPERATION THAT RECONCILES THEM

   A scope's allocation is an intention; what its activities carry is what
   every period figure is actually built from. The banner states the gap
   at the top of the Distribution screen, the chip states it on the row it
   belongs to, and both are the button that closes it.
   ══════════════════════════════════════════════════════════════════════ */
.cost-basis{display:flex;flex-direction:column;gap:11px;margin:0 0 12px;
  padding:13px 15px;border-radius:var(--c-r);
  background:var(--c-warn-t);border:1px solid #F0DFC0}
.cost-basis-t b{display:block;font:700 13px/1.35 var(--c-head);color:var(--c-ink)}
.cost-basis-t span{display:block;margin-top:4px;font-size:11.5px;line-height:1.6;
  color:var(--c-ink-2);max-width:86ch}
.cost-basis-t b+span b,.cost-basis-t span b{font:700 12px/1 var(--c-mono);
  font-variant-numeric:tabular-nums;color:var(--c-ink)}
.cost-basis-l{display:flex;gap:7px;flex-wrap:wrap}
.cost-basis-b{display:flex;align-items:center;gap:9px;padding:7px 10px;cursor:pointer;
  border-radius:var(--c-r-s);background:var(--c-surface);
  border:1px solid var(--c-line-3);text-align:left}
.cost-basis-b:hover{border-color:var(--c-warn);background:var(--c-bg)}
.cost-basis-b:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}
.cost-basis-b b{font:600 12px/1.2 var(--c-font);color:var(--c-ink)}
.cost-basis-b em{font-style:normal;font-size:10.5px;color:var(--c-mut)}
.cost-basis-b u{text-decoration:none;font:700 11.5px/1 var(--c-mono);
  font-variant-numeric:tabular-nums;color:var(--c-warn)}
.cost-basis-a{display:flex;gap:8px}

/* the same fact, on the row it belongs to */
.cost-gap{display:inline-block;margin-left:7px;padding:1px 6px;cursor:pointer;
  border-radius:999px;border:1px solid #F0DFC0;background:var(--c-warn-t);
  font:700 10.5px/1.55 var(--c-mono);font-variant-numeric:tabular-nums;
  color:var(--c-warn)}
.cost-gap:hover{background:#F0DFC0;border-color:var(--c-warn)}
.cost-gap:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}

/* a drawer that asks a question rather than showing a form */
.cost-dr-sect{display:block}
.cost-dr-sect>h4{margin:0 0 8px;font:700 10px/1 var(--c-font);letter-spacing:.1em;
  text-transform:uppercase;color:var(--c-mut)}
.cost-choice.is-col{grid-template-columns:1fr}
.cost-choice.is-scroll{max-height:280px;overflow:auto;padding-right:4px}
.cost-choice-b.is-row{display:flex;align-items:baseline;gap:10px;padding:9px 12px}
.cost-choice-b.is-row b{flex:0 0 auto}
.cost-choice-b.is-row em{margin-top:0;flex:1 1 auto;text-align:right}
.cost-choice-b.is-off{opacity:.55}
.cost-imp-t{border:1px solid var(--c-line);border-radius:var(--c-r-s);overflow:hidden}
.cost-imp-t .cost-imp-r{display:grid;grid-template-columns:1.6fr .9fr .9fr .9fr;
  gap:10px;align-items:baseline;padding:9px 12px;
  border-bottom:1px solid var(--c-line)}
.cost-imp-t .cost-imp-r:last-child{border-bottom:0}

/* ══════════════════════════════════════════════════════════════════════
   THE TERMS THAT PRODUCED THE STATEMENT, ON THE STATEMENT

   A cash flow is the consequence of four or five commercial terms, and
   reading one without them is reading an answer with the question torn
   off. The strip names them and opens any of them in place.
   ══════════════════════════════════════════════════════════════════════ */
.cost-rulebar{display:flex;align-items:center;gap:12px;flex-wrap:wrap;
  margin:0 0 12px;padding:9px 12px;border-radius:var(--c-r);
  background:var(--c-wash);border:1px solid var(--c-line)}
.cost-rulebar-l{font:700 9.5px/1 var(--c-font);letter-spacing:.09em;
  text-transform:uppercase;color:var(--c-mut)}
.cost-rulebar-c{display:flex;gap:6px;flex-wrap:wrap;flex:1 1 auto}
.cost-rulechip{display:flex;align-items:baseline;gap:6px;padding:4px 9px;cursor:pointer;
  border-radius:var(--c-r-pill);background:var(--c-surface);
  border:1px solid var(--c-line-3)}
.cost-rulechip:hover{border-color:var(--c-brand);background:var(--c-brand-t)}
.cost-rulechip:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}
.cost-rulechip span{font-size:10.5px;color:var(--c-mut)}
.cost-rulechip b{font:700 11px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  color:var(--c-ink)}

/* the payment register tells its three kinds of event apart */
.cost-seg.is-wrap{flex-wrap:wrap}
.cost-seg-b.is-off{opacity:.5}
.cost-seg-b u{margin-left:5px;text-decoration:none;font:700 9.5px/1 var(--c-mono);
  font-variant-numeric:tabular-nums;opacity:.65}
.cost-tbl.is-pay tr.is-advance th.is-stick{box-shadow:inset 3px 0 0 var(--c-info)}
.cost-tbl.is-pay tr.is-release th.is-stick{box-shadow:inset 3px 0 0 var(--c-pos)}
.cost-tbl.is-pay tr.is-ipc th.is-stick{box-shadow:inset 3px 0 0 var(--c-line-4)}

/* the S-curve's own type: two scales, a present, a peak and two end
   figures all have to be told apart at a glance */
.cost-chart .lbl-y.is-soft{fill:var(--c-mut-2);font-size:9px}
.cost-chart .lbl-end{font:700 10.5px/1 var(--c-mono);font-variant-numeric:tabular-nums}
.cost-chart .lbl-end.is-cost{fill:var(--c-brand-dd)}
.cost-chart .lbl-end.is-rev{fill:var(--c-s4)}
.cost-chart .lbl.is-peak{font-weight:700;fill:var(--c-s1)}
.cost-chart .lbl-ax.is-today{fill:var(--c-neg)}

/* ══════════════════════════════════════════════════════════════════════
   THE DASHBOARD READS AS AN ARGUMENT, NOT A PILE

   Four questions in the order a commercial manager asks them, each with
   its own heading and number, and a headline band of four figures that
   carry what they are measured against.
   ══════════════════════════════════════════════════════════════════════ */
.cost-dash{display:flex;flex-direction:column;gap:26px}
.cost-dash-s{display:flex;flex-direction:column;gap:12px}
.cost-dash-h{display:flex;align-items:flex-start;gap:12px;
  padding-bottom:9px;border-bottom:1px solid var(--c-line)}
.cost-dash-h>div{flex:1 1 auto;min-width:0}
.cost-dash-h h2{margin:0;font:700 14.5px/1.25 var(--c-head);letter-spacing:-.015em;color:var(--c-ink)}
.cost-dash-h p{margin:4px 0 0;font-size:11.5px;line-height:1.6;color:var(--c-mut);max-width:92ch}
.cost-dash-n{flex:0 0 auto;display:grid;place-items:center;width:26px;height:26px;
  border-radius:var(--c-r-s);background:var(--c-sunken);
  font:700 10.5px/1 var(--c-mono);color:var(--c-mut)}

.cost-bigs{display:grid;gap:12px;grid-template-columns:repeat(auto-fit,minmax(215px,1fr))}
.cost-big{display:flex;flex-direction:column;gap:5px;padding:15px 17px;
  border-radius:var(--c-r);background:var(--c-surface);
  border:1px solid var(--c-line);box-shadow:var(--c-sh-1)}
.cost-big.is-ok{border-color:#BFE6D5}
.cost-big.is-warn{border-color:#F0DFC0}
.cost-big.is-risk{border-color:#F3D4D0}
.cost-big-l{font:700 9.5px/1 var(--c-font);letter-spacing:.09em;
  text-transform:uppercase;color:var(--c-mut)}
.cost-big-v{font:750 26px/1.05 var(--c-mono);font-variant-numeric:tabular-nums;
  letter-spacing:-.02em;color:var(--c-ink)}
.cost-big.is-risk .cost-big-v{color:var(--c-neg)}
.cost-big-s{font-style:normal;font-size:11px;line-height:1.5;color:var(--c-mut)}
.cost-big-bar{display:block;height:4px;margin-top:3px;border-radius:999px;
  background:var(--c-sunken);overflow:hidden}
.cost-big-bar>i{display:block;height:100%;background:var(--c-brand);border-radius:999px}
.cost-big-bar>i.is-ok{background:var(--c-pos)}
.cost-big-bar>i.is-warn{background:var(--c-gap)}
.cost-big-bar>i.is-risk{background:var(--c-neg)}

/* the reconciliation table: one row per join between two parts */
.cost-rec .cost-rec-dot{width:7px;height:7px;border-radius:999px;flex:0 0 auto;
  background:var(--c-line-4)}
.cost-rec tr.is-pass .cost-rec-dot{background:var(--c-pos)}
.cost-rec tr.is-fail .cost-rec-dot{background:var(--c-neg)}
.cost-rec tr.is-fail{background:var(--c-neg-t)}
.cost-rec tr.is-nil{opacity:.6}
.cost-b.is-ok{background:var(--c-pos-t);color:var(--c-pos);border-color:#BFE6D5}

/* a cash figure explains itself twice: the arithmetic, and the term that
   decided which period it falls in */
.cost-dl-rule{display:flex;align-items:center;gap:12px;margin-top:12px;
  padding:10px 12px;border-radius:var(--c-r-s);background:var(--c-wash);
  border:1px solid var(--c-line)}
.cost-dl-rule>div{flex:1 1 auto;min-width:0}
.cost-dl-rule span{display:block;font:700 9px/1 var(--c-font);letter-spacing:.09em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-dl-rule b{display:block;margin-top:3px;font:600 12.5px/1.3 var(--c-font);color:var(--c-ink)}
.cost-dl-rule em{display:block;margin-top:2px;font-style:normal;font-size:11px;
  line-height:1.55;color:var(--c-mut)}

/* ══════════════════════════════════════════════════════════════════════
   WHAT A DRAFT WOULD DO, BESIDE THE BEFORE-AND-AFTER

   This was a full-width card at the bottom of the screen with a paragraph
   and a four-column table, so the consequence of a change sat as far as
   possible from the change. Four chips under the two bars instead: one
   number moving to another, and the working on hover.
   ══════════════════════════════════════════════════════════════════════ */
.cost-imps{display:flex;gap:8px;flex-wrap:wrap;margin-top:11px;
  padding-top:11px;border-top:1px solid var(--c-line)}
.cost-ic{display:flex;flex-direction:column;gap:2px;min-width:124px;
  padding:7px 11px;border-radius:var(--c-r-s);background:var(--c-wash);
  border:1px solid var(--c-line)}
.cost-ic u{text-decoration:none;font:700 9px/1 var(--c-font);letter-spacing:.08em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-ic b{font:700 14px/1.2 var(--c-mono);font-variant-numeric:tabular-nums;color:var(--c-ink)}
.cost-ic i{font-style:normal;font:500 10px/1.3 var(--c-mono);
  font-variant-numeric:tabular-nums;color:var(--c-mut)}
.cost-ic.is-pos{background:var(--c-pos-t);border-color:#BFE6D5}
.cost-ic.is-pos b,.cost-ic.is-pos i{color:var(--c-pos)}
.cost-ic.is-neg{background:var(--c-neg-t);border-color:#F3D4D0}
.cost-ic.is-neg b,.cost-ic.is-neg i{color:var(--c-neg)}
.cost-ic.is-flat{opacity:.75}

/* an edit that does not close, stated where the edit was made */
.cost-settle{display:flex;align-items:center;gap:14px;flex-wrap:wrap;margin-top:11px;
  padding:10px 13px;border-radius:var(--c-r-s);background:var(--c-warn-t);
  border:1px solid #F0DFC0}
.cost-settle-t{flex:1 1 auto;min-width:0}
.cost-settle-t b{display:block;font:700 12.5px/1.3 var(--c-font);color:var(--c-ink)}
.cost-settle-t span{display:block;margin-top:2px;font-size:11px;color:var(--c-mut)}
.cost-settle-b{display:flex;gap:7px;flex-wrap:wrap}

/* the costing and the upload disagree — said before anything else, because
   every figure under it is affected by the answer */
.cost-upload{display:flex;align-items:center;gap:14px;flex-wrap:wrap;
  margin:0 0 2px;padding:11px 16px;background:var(--c-neg-t);
  border-bottom:1px solid #F3D4D0}
.cost-upload-t{flex:1 1 320px;min-width:0}
.cost-upload-t>b{display:block;font:700 12.5px/1.3 var(--c-font);color:var(--c-neg)}
.cost-upload-t>span{display:block;margin-top:3px;font-size:11.5px;line-height:1.6;color:var(--c-ink-2)}
.cost-upload-t>span b{font-weight:700;color:var(--c-ink)}
.cost-upload-b{display:flex;gap:7px;flex-wrap:wrap}

/* the clean-start receipt is not an alarm: nothing is wrong, something
   was prevented */
.cost-upload.is-reset{background:var(--c-info-t);border-bottom-color:#CBD8F5}
.cost-upload.is-reset .cost-upload-t>b{color:var(--c-info)}

/* ══════════════════════════════════════════════════════════════════════
   REDISTRIBUTE — the division as a picture, in the level's own colours

   Wide, centred, and quiet: a bar per level, one row per package with its
   share and its money side by side, and the levels underneath opened in
   place. Nothing here explains itself in a paragraph — the colours and
   the two figures are the explanation.
   ══════════════════════════════════════════════════════════════════════ */
.cost-portal.is-wide{align-items:center;justify-content:center}
.cost-dr.is-wide{width:min(920px,94vw);max-height:88vh;border-radius:var(--c-r);
  margin:0;box-shadow:var(--c-sh-3)}
.rd{display:flex;flex-direction:column;gap:4px}
.rd-lvl{display:flex;flex-direction:column;gap:5px}
.rd-bar{display:flex;height:30px;border-radius:var(--c-r-s);overflow:hidden;
  border:1px solid var(--c-line-2);background:var(--c-sunken)}
.rd-bar>i{display:flex;align-items:center;gap:5px;padding:0 8px;min-width:0;
  overflow:hidden;transition:width .16s ease}
.rd-bar>i b{font:650 10.5px/1 var(--c-font);color:#fff;white-space:nowrap;
  overflow:hidden;text-overflow:ellipsis;text-shadow:0 1px 1px rgba(0,0,0,.25)}
.rd-bar>i em{font-style:normal;font:700 9.5px/1 var(--c-mono);color:rgba(255,255,255,.86)}

.rd-ms{display:flex;gap:5px;flex-wrap:wrap;margin:1px 0 4px}
.rd-m{padding:3px 9px;border-radius:var(--c-r-pill);cursor:pointer;
  background:var(--c-wash);border:1px solid var(--c-line-3);
  font:600 10.5px/1.5 var(--c-font);color:var(--c-ink-2)}
.rd-m:hover{border-color:var(--c-brand);background:var(--c-brand-t);color:var(--c-brand-dd)}
.rd-m:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}

.rd-r{display:flex;align-items:center;gap:8px;padding:5px 8px;border-radius:var(--c-r-s)}
.rd-r:hover{background:var(--c-wash)}
.rd-r.is-pinned{background:var(--c-warn-t)}
.rd-sw{width:10px;height:18px;border-radius:3px;flex:0 0 auto}
.rd-tg{display:grid;place-items:center;width:18px;height:18px;flex:0 0 auto;border:0;
  background:none;color:var(--c-mut-2);cursor:pointer;border-radius:4px}
.rd-tg:hover{background:var(--c-sunken);color:var(--c-ink)}
.rd-tg.is-on svg{transform:rotate(90deg)}
.rd-tg.is-leaf{visibility:hidden}
.rd-nm{flex:1 1 auto;min-width:0;font:600 12.5px/1.35 var(--c-font);color:var(--c-ink);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.rd-f{display:flex;align-items:center;gap:3px;flex:0 0 auto}
.rd-in{width:74px;padding:4px 7px;text-align:right;border-radius:var(--c-r-xs);
  border:1px solid var(--c-line-3);background:var(--c-surface);
  font:600 12px/1.3 var(--c-mono);font-variant-numeric:tabular-nums;color:var(--c-ink)}
.rd-f.is-money .rd-in{width:112px}
.rd-in:focus{outline:none;border-color:var(--c-brand);box-shadow:0 0 0 2px var(--c-brand-t)}
.rd-f>u{text-decoration:none;font:600 10px/1 var(--c-font);color:var(--c-mut-2)}
.rd-mv{flex:0 0 96px;text-align:right;font:600 11px/1 var(--c-mono);
  font-variant-numeric:tabular-nums;color:var(--c-mut)}
.rd-mv.is-pos{color:var(--c-pos)}
.rd-mv.is-neg{color:var(--c-neg)}
.rd-mv.is-nil{color:var(--c-line-4)}
.rd-pin{border:0;background:none;padding:3px;border-radius:4px;cursor:pointer;color:var(--c-line-4)}
.rd-pin:hover{background:var(--c-sunken);color:var(--c-mut)}
.rd-pin.is-on{color:var(--c-warn)}
.rd-sub{margin:2px 0 8px;padding:8px 0 2px;border-left:2px solid var(--c-line-2);
  margin-left:14px;padding-left:12px}

/* ══════════════════════════════════════════════════════════════════════
   REDISTRIBUTE — headed columns, the level's own colours, no shake

   Two pairs of figures per row and a header that says which is which:
   what it holds NOW, and what it would hold. The band down the left is
   the WBS level's own colour, the same one the Gantt and the cost plan
   paint — a planner reads a level by its colour before its name.
   ══════════════════════════════════════════════════════════════════════ */
.rx{display:flex;flex-direction:column;gap:0}
.rx-head,.rx-r{display:grid;align-items:center;
  grid-template-columns:5px 20px minmax(150px,1fr) 58px 104px 18px 78px 124px 96px 26px;
  gap:9px}
.rx-head{padding:0 8px 7px;border-bottom:1px solid var(--c-line);
  position:sticky;top:0;z-index:2;background:var(--c-surface)}
.rx-head span{font:700 8.5px/1 var(--c-font);letter-spacing:.08em;
  text-transform:uppercase;color:var(--c-mut-2)}
.rx-h-nm{grid-column:1 / span 3}
.rx-h-b,.rx-h-f,.rx-h-mv{text-align:right}
.rx-h-f{color:var(--c-brand-dd)!important}

.rx-body{display:flex;flex-direction:column;gap:2px;padding-top:8px}
.rx-r{padding:4px 8px;border-radius:var(--c-r-s)}
.rx-r:hover{background:var(--c-wash)}
.rx-r.is-pinned{background:var(--c-warn-t)}
.rx-r.is-act .rx-nm b{font-weight:500;color:var(--c-ink-2)}
.rx-band{height:20px;border-radius:2px}

/* ── THE LEVEL'S COLOUR IS THE ROW ────────────────────────────────────
   A 5px stripe was carrying the WBS level on a window whose whole subject
   is levels. The row is painted the level's own colour now, with the same
   --rowbg / --rowfg / --rowdv / --rowsoft / --rowtrack the cost plan and
   the distribution grid use, so one change of palette moves all three. */
.rx-r.is-paint{background:var(--rowbg);padding:6px 9px}
.rx-r.is-paint:hover{background:var(--rowbg);box-shadow:inset 0 0 0 1px var(--rowdv)}
.rx-r.is-paint .rx-nm b{color:var(--rowfg)}
.rx-r.is-paint .rx-nm em{color:var(--rowsoft)}
.rx-r.is-paint .rx-b{color:var(--rowsoft)}
.rx-r.is-paint .rx-ar{color:var(--rowtrack)}
.rx-r.is-paint .rx-tg{color:var(--rowfg);opacity:.85}
.rx-r.is-paint .rx-tg:hover{background:var(--rowtrack);opacity:1}
.rx-r.is-paint .rx-pin{color:var(--rowsoft)}
.rx-r.is-paint .rx-pin:hover{background:var(--rowtrack);color:var(--rowfg)}
.rx-r.is-paint .rx-pin.is-on{color:var(--c-warn)}
.rx-r.is-paint .rx-f>u{color:var(--rowsoft)}
/* the two fields stay white paper on the band — they are the one thing
   on the row a planner types into, and they have to look it */
.rx-r.is-paint .rx-in{border-color:transparent;background:rgba(255,255,255,.94);color:var(--c-ink)}
.rx-r.is-paint .rx-in:hover{background:#fff}
.rx-r.is-paint .rx-in:focus{background:#fff;border-color:var(--c-brand);
  box-shadow:0 0 0 2px rgba(255,255,255,.55)}
.rx-r.is-paint .rx-mv.is-nil{color:var(--rowtrack)}
.rx-r.is-paint.is-pinned{box-shadow:inset 0 0 0 2px var(--c-warn)}
/* an activity is a lighter weight of the same band, not another colour */
.rx-r.is-paint.is-act{background:color-mix(in srgb,var(--rowbg) 82%,#fff)}
.rx-r.is-paint.is-act .rx-nm b{font-weight:600;color:var(--rowfg)}

/* ── WHAT IS OPEN IS THE SUBJECT; THE REST STEPS BACK ─────────────────
   Not hidden — the packages beside it are exactly what the open level is
   being compared against — but quieter, so the level a planner just asked
   to see is the one their eye lands on. Hover and focus bring a dimmed
   row all the way back, because stepping back is not the same as being
   out of reach. */
.rx-r.is-dim,.rx-lvl.is-dim{opacity:.42;filter:saturate(.72);
  transition:opacity .16s ease,filter .16s ease}
.rx-r.is-dim:hover,.rx-r.is-dim:focus-within,
.rx-lvl.is-dim:hover,.rx-lvl.is-dim:focus-within{opacity:1;filter:none}
.rx-tg{display:grid;place-items:center;width:20px;height:20px;border:0;background:none;
  color:var(--c-mut-2);cursor:pointer;border-radius:4px}
.rx-tg:hover{background:var(--c-sunken);color:var(--c-ink)}
.rx-tg.is-on svg{transform:rotate(90deg)}
.rx-tg.is-leaf{visibility:hidden}
.rx-nm{min-width:0;display:flex;align-items:baseline;gap:7px}
.rx-nm b{font:600 12.5px/1.35 var(--c-font);color:var(--c-ink);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.rx-nm em{font-style:normal;font:600 8.5px/1 var(--c-font);letter-spacing:.07em;
  text-transform:uppercase;color:var(--c-mut-2)}
.rx-b{text-align:right;font:500 11.5px/1 var(--c-mono);font-variant-numeric:tabular-nums;
  color:var(--c-mut)}
.rx-ar{display:grid;place-items:center;color:var(--c-line-4)}
.rx-f{display:flex;align-items:center;gap:3px;justify-content:flex-end}
.rx-in{width:100%;padding:5px 8px;text-align:right;border-radius:var(--c-r-xs);
  border:1px solid var(--c-line-3);background:var(--c-surface);
  font:700 12px/1.3 var(--c-mono);font-variant-numeric:tabular-nums;color:var(--c-ink)}
.rx-in:hover{border-color:var(--c-line-4)}
.rx-in:focus{outline:none;border-color:var(--c-brand);box-shadow:0 0 0 2px var(--c-brand-t)}
.rx-f>u{text-decoration:none;font:600 10px/1 var(--c-font);color:var(--c-mut-2)}
.rx-mv{text-align:right;font:600 11px/1 var(--c-mono);font-variant-numeric:tabular-nums}
.rx-mv.is-pos{color:var(--c-pos)} .rx-mv.is-neg{color:var(--c-neg)}
.rx-mv.is-nil{color:var(--c-line-4)}
.rx-pin{border:0;background:none;padding:4px;border-radius:4px;cursor:pointer;color:var(--c-line-4)}
.rx-pin:hover{background:var(--c-sunken);color:var(--c-mut)}
.rx-pin.is-on{color:var(--c-warn)}

/* a level: its bar, and the ways of splitting it */
.rx-lvl{display:flex;flex-direction:column;gap:6px;margin:10px 0 6px}
.rx-bar{display:flex;height:34px;border-radius:var(--c-r-s);overflow:hidden;
  border:1px solid var(--c-line-2);background:var(--c-sunken)}
.rx-bar>i{display:flex;flex-direction:column;justify-content:center;gap:1px;
  padding:0 9px;min-width:2px;overflow:hidden;transition:width .14s ease;
  border-right:1px solid rgba(255,255,255,.55)}
.rx-bar>i:last-child{border-right:0}
.rx-bar>i.is-free{background:repeating-linear-gradient(45deg,
  var(--c-sunken),var(--c-sunken) 6px,var(--c-canvas) 6px,var(--c-canvas) 12px)}
.rx-bar>i b{font:650 10.5px/1.15 var(--c-font);color:#fff;white-space:nowrap;
  overflow:hidden;text-overflow:ellipsis;text-shadow:0 1px 1px rgba(0,0,0,.28)}
.rx-bar>i em{font-style:normal;font:700 9px/1 var(--c-mono);color:rgba(255,255,255,.85)}
.rx-ms{display:flex;align-items:center;gap:6px;flex-wrap:wrap}
.rx-ms-l{font:700 8.5px/1 var(--c-font);letter-spacing:.08em;text-transform:uppercase;
  color:var(--c-mut-2)}
.rx-m{padding:4px 11px;border-radius:var(--c-r-pill);cursor:pointer;
  background:var(--c-surface);border:1px solid var(--c-line-3);
  font:600 11px/1.5 var(--c-font);color:var(--c-ink-2)}
.rx-m:hover{border-color:var(--c-brand);background:var(--c-brand-t);color:var(--c-brand-dd)}
.rx-m:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}

.rx-foot{display:flex;align-items:center;justify-content:space-between;gap:14px;
  margin-top:12px;padding-top:10px;border-top:1px solid var(--c-line);
  font-size:11.5px;color:var(--c-mut)}
.rx-foot b{color:var(--c-ink);font-weight:700}
.rx-sum{font:700 11.5px/1 var(--c-mono);font-variant-numeric:tabular-nums}
.rx-sum.is-ok{color:var(--c-pos)} .rx-sum.is-off{color:var(--c-neg)}

/* the difference carries its own direction — a separate arrow column was
   a column of arrows and nothing else */
.cost-dir{display:inline-block;width:0;height:0;margin-right:5px;vertical-align:1px}
.cost-dir.is-up{border-left:4px solid transparent;border-right:4px solid transparent;
  border-bottom:6px solid var(--c-pos)}
.cost-dir.is-down{border-left:4px solid transparent;border-right:4px solid transparent;
  border-top:6px solid var(--c-neg)}

/* ══════════════════════════════════════════════════════════════════════
   WHERE THE MONEY COMES FROM — drawn, not described

   A list of names and figures makes a planner build the picture in their
   head before they can choose. The level is a bar: what each package
   holds, the one being edited marked, and the piece that has to come from
   somewhere shown as the hole it is.
   ══════════════════════════════════════════════════════════════════════ */
.cost-sos{display:flex;flex-direction:column;gap:7px}
.cost-so{display:flex;align-items:center;gap:12px;width:100%;padding:11px 13px;cursor:pointer;
  text-align:left;border-radius:var(--c-r-s);background:var(--c-surface);
  border:1px solid var(--c-line-3)}
.cost-so:hover{border-color:var(--c-line-4);background:var(--c-wash)}
.cost-so.is-on{border-color:var(--c-brand);background:var(--c-brand-t);box-shadow:0 0 0 1px var(--c-brand)}
.cost-so-t{flex:1 1 auto;min-width:0}
.cost-so-t b{display:block;font:650 13px/1.35 var(--c-font);color:var(--c-ink)}
.cost-so.is-on .cost-so-t b{color:var(--c-brand-dd)}
.cost-so-t em{display:block;margin-top:2px;font-style:normal;font-size:11.5px;
  line-height:1.5;color:var(--c-mut)}
.cost-so-n{flex:0 0 auto;text-decoration:none;font:700 13px/1 var(--c-mono);
  font-variant-numeric:tabular-nums;color:var(--c-mut-2)}
.cost-so.is-on .cost-so-n{color:var(--c-brand-dd)}

.cost-sb{display:flex;height:38px;margin:2px 0 12px;border-radius:var(--c-r-s);
  overflow:hidden;border:1px solid var(--c-line-2);background:var(--c-sunken)}
.cost-sb-seg{display:flex;flex-direction:column;justify-content:center;gap:1px;
  padding:0 9px;min-width:0;overflow:hidden;transition:width .16s ease}
.cost-sb-seg b{font:650 10.5px/1.15 var(--c-font);color:#fff;white-space:nowrap;
  overflow:hidden;text-overflow:ellipsis;text-shadow:0 1px 1px rgba(0,0,0,.28)}
.cost-sb-seg em{font-style:normal;font:700 9px/1 var(--c-mono);color:rgba(255,255,255,.85)}
.cost-sb-seg.is-edited{box-shadow:inset 0 0 0 2px #fff}
.cost-sb-seg.is-giving{opacity:.55}
.cost-sb-hole{display:grid;place-items:center;background:
  repeating-linear-gradient(45deg,var(--c-warn-t) 0 7px,#F3E6CC 7px 14px);
  border-left:2px dashed var(--c-warn)}
.cost-sb-hole b{font:700 10.5px/1 var(--c-mono);color:var(--c-warn)}

.cost-sd{display:flex;flex-direction:column;gap:1px}
.cost-sd-r{display:grid;grid-template-columns:10px 1fr 96px 16px 96px 96px;gap:9px;
  align-items:center;padding:7px 6px;border-radius:var(--c-r-xs)}
.cost-sd-r:hover{background:var(--c-wash)}
.cost-sd-sw{width:10px;height:16px;border-radius:2px}
.cost-sd-n{font:600 12.5px/1.3 var(--c-font);color:var(--c-ink);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cost-sd-b,.cost-sd-a,.cost-sd-d{text-align:right;font:600 11.5px/1 var(--c-mono);
  font-variant-numeric:tabular-nums}
.cost-sd-b{color:var(--c-mut)}
.cost-sd-a{color:var(--c-ink);font-weight:700}
.cost-sd-ar{text-align:center;color:var(--c-line-4)}
.cost-sd-d.is-pos{color:var(--c-pos)} .cost-sd-d.is-neg{color:var(--c-neg)}
.cost-sd-d.is-nil{color:var(--c-line-4)}

/* the donors, as cards you pick from */
.cost-sp{display:grid;gap:8px;grid-template-columns:repeat(auto-fit,minmax(220px,1fr))}
.cost-sp-c{display:flex;flex-wrap:wrap;align-items:center;gap:7px;padding:11px 13px;cursor:pointer;
  text-align:left;border-radius:var(--c-r-s);background:var(--c-surface);
  border:1px solid var(--c-line-3)}
.cost-sp-c:hover{border-color:var(--c-line-4);background:var(--c-wash)}
.cost-sp-c.is-on{border-color:var(--c-brand);background:var(--c-brand-t);box-shadow:0 0 0 1px var(--c-brand)}
.cost-sp-c.is-short{opacity:.7}
.cost-sp-sw{width:10px;height:16px;border-radius:2px;flex:0 0 auto}
.cost-sp-c>b{flex:1 1 auto;min-width:0;font:650 12.5px/1.3 var(--c-font);color:var(--c-ink);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cost-sp-f{flex:1 1 100px;display:flex;flex-direction:column;gap:1px;
  font:700 12px/1.2 var(--c-mono);font-variant-numeric:tabular-nums;color:var(--c-ink)}
.cost-sp-f u{text-decoration:none;font:700 8.5px/1 var(--c-font);letter-spacing:.07em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-sp-f.is-after{color:var(--c-brand-dd)}
.cost-sp-w{flex:1 1 100%;font-style:normal;font-size:10.5px;color:var(--c-warn)}

/* ══════════════════════════════════════════════════════════════════════
   STEP 2 — how a changed branch divides underneath

   Numbered, because the settle window now asks two questions in order:
   where the money comes from, then how it spreads below. The methods are
   chips with one clearly on; the children are rows with a swatch, a share
   and an amount, and a thin bar says the same thing at a glance.
   ══════════════════════════════════════════════════════════════════════ */
.cost-step{display:inline-grid;place-items:center;width:20px;height:20px;margin-right:8px;
  border-radius:999px;background:var(--c-brand);color:#fff;font:700 11px/1 var(--c-font)}
.cost-under{display:flex;flex-direction:column;gap:9px;padding:12px 13px;
  border-radius:var(--c-r-s);border:1px solid var(--c-line);background:var(--c-wash)}
.cost-under-h{display:flex;align-items:center;flex-wrap:wrap;gap:4px 0}
.cost-under-h b{font:650 13px/1.3 var(--c-font);color:var(--c-ink)}
.cost-under-h em{flex:1 1 100%;margin-left:28px;font-style:normal;font-size:11.5px;color:var(--c-mut)}
.cost-ucs{display:flex;flex-wrap:wrap;gap:6px}
.cost-uc{padding:5px 11px;border-radius:999px;cursor:pointer;background:var(--c-surface);
  border:1px solid var(--c-line-3);font:600 11.5px/1.4 var(--c-font);color:var(--c-ink-2)}
.cost-uc:hover{border-color:var(--c-brand);color:var(--c-brand-dd)}
.cost-uc.is-on{background:var(--c-brand);border-color:var(--c-brand);color:#fff}
.cost-uc:focus-visible{outline:2px solid var(--c-brand);outline-offset:1px}
.cost-sb.is-thin{height:10px;margin:0}
.cost-urs{display:flex;flex-direction:column;gap:2px}
.cost-ur{display:grid;grid-template-columns:10px 1fr 92px 110px;gap:9px;align-items:center;
  padding:6px 6px;border-radius:var(--c-r-xs);background:var(--c-surface)}
.cost-ur-sw{width:10px;height:16px;border-radius:2px}
.cost-ur-n{display:flex;align-items:center;gap:6px;min-width:0;font:600 12px/1.3 var(--c-font);
  color:var(--c-ink);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cost-ur-n svg{flex:0 0 auto;color:var(--c-mut-2)}
.cost-ur-p,.cost-ur-a{text-align:right;font:600 11.5px/1 var(--c-mono);font-variant-numeric:tabular-nums}
.cost-ur-p{color:var(--c-mut)}
.cost-ur-a{color:var(--c-ink);font-weight:700}
.cost-ur-in{display:flex;align-items:center;gap:3px;justify-content:flex-end}
.cost-ur-in input{width:70px;padding:4px 7px;text-align:right;border-radius:var(--c-r-xs);
  border:1px solid var(--c-line-3);font:700 11.5px/1.3 var(--c-mono);color:var(--c-ink)}
.cost-ur-in input:focus{outline:none;border-color:var(--c-brand);box-shadow:0 0 0 2px var(--c-brand-t)}
.cost-ur-in u{text-decoration:none;font-size:10px;color:var(--c-mut-2)}

/* the inline chip on a changed branch in the grid */
.cost-under-chip{margin-left:8px;padding:2px 8px;border-radius:999px;cursor:pointer;
  background:rgba(255,255,255,.85);border:1px solid var(--c-line-3);
  font:600 10.5px/1.4 var(--c-font);color:var(--c-brand-dd);white-space:nowrap}
.cost-under-chip:hover{background:#fff;border-color:var(--c-brand)}

/* ══════════════════════════════════════════════════════════════════════
   THE WIZARD — one question per screen

   Dots for where the planner is in the sequence, a breadcrumb for which
   level the step is about, and a sum line under the rows that always reads
   100% of what the parent holds.
   ══════════════════════════════════════════════════════════════════════ */
.cost-wiz-dots{display:flex;align-items:center;gap:5px;margin:0 0 12px}
.cost-wiz-dots i{width:18px;height:4px;border-radius:2px;background:var(--c-line-3)}
.cost-wiz-dots i.is-done{background:var(--c-brand-t2)}
.cost-wiz-dots i.is-on{background:var(--c-brand);width:28px}
.cost-wiz-dots span{margin-left:8px;font:700 9.5px/1 var(--c-font);letter-spacing:.08em;
  text-transform:uppercase;color:var(--c-mut-2)}
.cost-wiz-crumb{margin:0 0 10px;font:600 11.5px/1.4 var(--c-font);color:var(--c-mut)}
.cost-wiz-crumb u{text-decoration:none;color:var(--c-line-4);margin:0 4px}
.cost-ur{grid-template-columns:10px 1fr 92px 120px}
.cost-ur.is-typed{box-shadow:inset 2px 0 0 var(--c-brand)}
.cost-ur-in.is-money input{width:110px}
.cost-ur-sum{display:grid;grid-template-columns:1fr 92px 120px;gap:9px;align-items:center;
  padding:7px 6px 0;border-top:1px solid var(--c-line)}
.cost-ur-sum span{font:700 9px/1 var(--c-font);letter-spacing:.08em;text-transform:uppercase;color:var(--c-mut-2)}
.cost-ur-sum b{text-align:right;font:700 12px/1 var(--c-mono);font-variant-numeric:tabular-nums;color:var(--c-ink)}

