/* instrument-cluster theme: graphite panels, amber/red accents, mono readouts */

@import url('https://fonts.googleapis.com/css2?family=Bahnschrift&family=Archivo:wght@500;600;700;800;900&family=JetBrains+Mono:wght@400;500;700&display=swap');

:root {
  --bg: #0a0d11;
  --panel: #11161c;
  --panel-2: #161d25;
  --raised: #1d262f;
  --line: #263039;
  --line-bright: #36444f;
  --ink: #e7edf2;
  --ink-dim: #8d9aa6;
  --ink-faint: #5b6772;
  --amber: #ff9e2c;       /* caution */
  --amber-soft: #c9831f;
  --red: #ff4242;         /* FAIL */
  --green: #38e08a;       /* OK */
  --cyan: #4fd2ff;        /* live data */
  --shadow: 0 18px 40px -18px rgba(0,0,0,.8);
  --display: 'Archivo', system-ui, sans-serif;
  --mono: 'JetBrains Mono', ui-monospace, monospace;
  /* scrollbar: graphite thumb, amber on hover */
  --sb-size: 10px; --sb-radius: 8px; --sb-track: rgba(255,255,255,.02);
  --sb-thumb: #2c3742; --sb-thumb-hover: var(--amber);
  /* gauge: amber fill on dark track */
  --gauge-track: #0c1218; --gauge-fill: var(--amber);
  /* the two zones analogout declares: the good band, and the rest of the
     scale. INPA paints these green and red on every bar that carries them. */
  --gauge-ok: #1f7a4d; --gauge-warn: #7a2020; --gauge-mark: #05080b;
  /* logo */
  --logo-bg: #11161c;
  --logo-border: #9aa6b2;
  --logo-quad-1: #eef2f5;
  --logo-quad-2: #ff9e2c;
  --logo-inner-border: #0a0d11;
}

* { box-sizing: border-box; margin: 0; padding: 0; }

html, body {
  height: 100%;
  background:
    radial-gradient(1200px 600px at 80% -10%, #16202b 0%, transparent 60%),
    radial-gradient(900px 500px at -10% 110%, #131a22 0%, transparent 55%),
    var(--bg);
  color: var(--ink);
  font-family: var(--display);
  -webkit-font-smoothing: antialiased;
  overflow: hidden;
  user-select: none;
}

/* film grain + scanlines */
.grain {
  position: fixed; inset: 0; pointer-events: none; z-index: 9999;
  opacity: .035;
  background-image:
    repeating-linear-gradient(0deg, #fff 0 1px, transparent 1px 3px);
  mix-blend-mode: overlay;
}

/* top bar */
.topbar {
  height: 56px;
  -webkit-app-region: drag;          /* drag window by topbar */
  display: grid;
  grid-template-columns: auto auto 1fr auto;
  align-items: center;
  gap: 18px;
  padding: 0 18px 0 14px;
  background: linear-gradient(180deg, #131a22, #0d1217);
  border-bottom: 1px solid var(--line);
}
/* the web build removes .win-controls, which left the 1fr column on
   .topbar-right and dragged everything leftward; re-shape the grid so the
   breadcrumbs take the slack and the right group stays right */
html.web .topbar { grid-template-columns: auto 1fr auto; }

/* custom traffic-light controls (frameless window) */
.win-controls { -webkit-app-region: no-drag; display: flex; align-items: center; gap: 8px; }
.win-dot {
  width: 12px; height: 12px; border-radius: 50%; border: none; padding: 0;
  cursor: pointer; position: relative; transition: filter .12s;
}
.win-close { background: #ff5f57; }
.win-min   { background: #febc2e; }
.win-zoom  { background: #28c840; }
.win-dot:hover { filter: brightness(.85); }
/* glyphs on hover */
.win-controls:hover .win-dot::after {
  position: absolute; inset: 0; display: flex; align-items: center; justify-content: center;
  font-size: 9px; font-weight: 700; color: rgba(0,0,0,.55); line-height: 1;
}
.win-controls:hover .win-close::after { content: '\00d7'; }
.win-controls:hover .win-min::after   { content: '\2013'; }
.win-controls:hover .win-zoom::after  { content: '\2b1a'; font-size: 7px; }
.brand { display: flex; align-items: center; gap: 9px; white-space: nowrap; }
.brand-logo { width: 22px; height: 22px; display: block; }
.brand-logo .logo-ring { fill: var(--logo-bg); stroke: var(--logo-border); stroke-width: 3px; }
.brand-logo .logo-quad-white { fill: var(--logo-quad-1); }
.brand-logo .logo-quad-color { fill: var(--logo-quad-2); }
.brand-logo .logo-inner-ring { fill: none; stroke: var(--logo-inner-border); stroke-width: 2px; }
.brand-mark { color: var(--amber); font-size: 16px; }
.brand-name { font-weight: 900; letter-spacing: .08em; font-size: 15px; line-height: 1; }

/* boot splash. covers the window until the sidecar answers, then fades out.
   logo reuses the theme logo vars so it tracks the selected skin. */
.splash {
  position: fixed; inset: 0; z-index: 9999;
  display: flex; align-items: center; justify-content: center;
  background: radial-gradient(120% 120% at 50% 35%, var(--panel-2) 0%, var(--bg) 70%);
  -webkit-app-region: drag;
  opacity: 1; transition: opacity .5s ease;
}
.splash.hide { opacity: 0; pointer-events: none; }
.splash-inner {
  display: flex; flex-direction: column; align-items: center;
  gap: 4px; transform: translateY(-4px);
}
.splash-logo {
  width: 128px; height: 128px; display: block; margin-bottom: 18px;
  filter: drop-shadow(0 14px 30px rgba(0,0,0,.55));
  animation: splash-pop .6s cubic-bezier(.2,.9,.25,1.1) both;
}
.splash-logo .logo-ring { fill: var(--logo-bg); stroke: var(--logo-border); stroke-width: 3px; }
.splash-logo .logo-quad-white { fill: var(--logo-quad-1); }
.splash-logo .logo-quad-color { fill: var(--logo-quad-2); }
.splash-logo .logo-inner-ring { fill: none; stroke: var(--logo-inner-border); stroke-width: 2px; }
.splash-name {
  font-family: var(--display); font-weight: 900; letter-spacing: .14em;
  font-size: 30px; color: var(--ink); text-transform: none;
  animation: splash-fade .6s ease .1s both;
}
.splash-tag {
  font-family: var(--mono); font-size: 11px; letter-spacing: .04em;
  color: var(--ink-dim); margin-top: 2px; margin-bottom: 22px;
  animation: splash-fade .6s ease .2s both;
}
.splash-bar {
  width: 188px; height: 3px; border-radius: 999px;
  background: var(--line); overflow: hidden; position: relative;
  animation: splash-fade .6s ease .25s both;
}
.splash-bar-fill {
  position: absolute; inset: 0; width: 38%; border-radius: 999px;
  background: var(--gauge-fill);
  animation: splash-sweep 1.15s ease-in-out infinite;
}
.splash-status {
  font-family: var(--mono); font-size: 10.5px; letter-spacing: .03em;
  color: var(--ink-faint); margin-top: 12px; min-height: 1em;
  animation: splash-fade .6s ease .3s both;
}
@keyframes splash-pop {
  0% { opacity: 0; transform: scale(.82) translateY(8px); }
  100% { opacity: 1; transform: scale(1) translateY(0); }
}
@keyframes splash-fade { from { opacity: 0; transform: translateY(6px); } to { opacity: 1; transform: translateY(0); } }
@keyframes splash-sweep {
  0% { left: -40%; } 100% { left: 100%; }
}
.brand-dot { color: var(--amber); }
.brand-sub {
  font-family: var(--mono); font-size: 9px; letter-spacing: .16em;
  color: var(--ink-faint); text-transform: uppercase; white-space: nowrap;
  padding-left: 10px; margin-left: 2px; border-left: 1px solid var(--line);
}
.breadcrumbs {
  -webkit-app-region: no-drag;
  display: flex; align-items: center; gap: 8px;
  font-family: var(--mono); font-size: 11px; color: var(--ink-dim);
  overflow: hidden; white-space: nowrap; text-overflow: ellipsis;
}
.crumb { cursor: pointer; color: var(--ink-dim); transition: color .15s; }
.crumb:hover { color: var(--amber); }
.crumb.active { color: var(--ink); }
.crumb-sep { color: var(--ink-faint); }

.status {
  -webkit-app-region: no-drag;
  display: flex; align-items: center; gap: 8px;
  font-family: var(--mono); font-size: 11px; color: var(--ink-dim);
  padding: 6px 12px; border: 1px solid var(--line);
  border-radius: 4px; background: var(--panel);
}
.topbar-right { -webkit-app-region: no-drag; display: flex; align-items: center; gap: 10px; }
/* Battery / Ignition indicators */
.kl-state { display: flex; align-items: center; gap: 14px; padding: 5px 12px;
  border: 1px solid var(--line); border-radius: 4px; background: var(--panel); }
.kl { display: flex; align-items: center; gap: 6px; }
/* outline ring, fills solid when on (no glow) */
.kl-led { width: 10px; height: 10px; border-radius: 50%; background: transparent;
  border: 1.5px solid var(--ink); flex: none; }
.kl-led.on { background: var(--ink); border-color: var(--ink); }
.kl-led.off { background: transparent; }
.kl-lbl { font-family: var(--mono); font-size: 10px; letter-spacing: .04em; color: var(--ink-dim); }
.kl-val { font-family: var(--mono); font-size: 11px; font-weight: 700; color: var(--ink); min-width: 32px; }
.icon-btn {
  -webkit-app-region: no-drag; cursor: pointer;
  font-family: var(--mono); font-size: 10px; letter-spacing: .1em; text-transform: uppercase;
  color: var(--ink-dim); background: var(--panel); border: 1px solid var(--line);
  border-radius: 4px; padding: 7px 11px; transition: all .15s;
}
.icon-btn:hover { color: var(--amber); border-color: var(--amber); }
#flash-btn:hover { color: var(--red); border-color: var(--red); }

/* settings */
/* wide enough for the widest row: the offline copy carries a picker, a
   checkbox and a button side by side */
.settings-list { display: grid; gap: 12px; max-width: 860px; }

/* INPA-style settings: the same rows, laid out the way INPA laid out
   everything -- monospace, one per line, ruled rather than carded. Matches
   the ECU Hauptmenue so the two screens do not look like different apps. */
/* wide enough for the widest row: the offline copy carries a picker, a
   checkbox and a button in one cell */
.inpa-settings { gap: 0; max-width: 860px; }
.inpa-settings .setting-row {
  background: none; border: none; border-radius: 0;
  border-bottom: 1px dotted var(--line);
  padding: 9px 6px; cursor: pointer;
  /* the Hauptmenue's vertical key list: key | text | control per row.
     A 4th auto column takes the Download row's extra button. */
  /* the text column gets a floor: an "auto" control column will otherwise
     take what it likes and squeeze a title into one word per line */
  display: grid; grid-template-columns: 150px minmax(20ch, 1fr) auto;
  column-gap: 16px; align-items: baseline;
}
.inpa-settings .setting-row > .inpa-fn-key { font-size: 12px; }
.inpa-settings .setting-row:hover { background: rgba(127, 127, 127, .07); }
.inpa-settings .setting-title {
  font-family: var(--mono); font-size: 13px; font-weight: 400;
  letter-spacing: .02em;
}
.inpa-settings .setting-desc {
  font-family: var(--mono); font-size: 11px; color: var(--ink-dim);
  margin-top: 2px;
}
/* the theme swatches stay a grid: a list of colour names would be worse.
   the swatches drop under the text, in the text column */
.inpa-settings .theme-row { border-bottom: 1px dotted var(--line);
  grid-template-columns: 150px 1fr; }
.inpa-settings .theme-row .theme-grid { grid-column: 2; }
.inpa-settings .combo-btn,
.inpa-settings .btn {
  font-family: var(--mono); font-size: 12px; border-radius: 0;
}
.setting-row {
  display: flex; align-items: center; gap: 20px; justify-content: space-between;
  border: 1px solid var(--line); border-radius: 4px; padding: 16px 20px;
  background: linear-gradient(180deg, var(--panel-2), var(--panel));
}
.setting-title { font-weight: 700; font-size: 15px; }
.setting-desc { color: var(--ink-dim); font-size: 12.5px; margin-top: 4px; max-width: 46ch; }
/* dropdown setting (chassis picker) */
.setting-select {
  flex: none; min-width: 180px; cursor: pointer;
  font-family: var(--mono); font-size: 13px; color: var(--ink);
  background: var(--bg); border: 1px solid var(--line-bright); border-radius: 4px;
  padding: 9px 12px; outline: none;
}
.setting-select:focus { border-color: var(--amber); }
/* searchable custom dropdown (startup vehicle) */
.combo { position: relative; flex: none; min-width: 200px; }
.combo-btn {
  width: 100%; cursor: pointer; display: flex; align-items: center; justify-content: space-between; gap: 8px;
  font-family: var(--mono); font-size: 13px; color: var(--ink);
  background: var(--bg); border: 1px solid var(--line-bright); border-radius: 4px; padding: 9px 12px;
}
.combo-btn:hover { border-color: var(--ink-dim); }
.combo.open .combo-btn { border-color: var(--amber); }
.combo-caret { color: var(--ink-faint); font-size: 10px; transition: transform .15s; }
.combo.open .combo-caret { transform: rotate(180deg); }
.combo-pop {
  position: absolute; top: calc(100% + 4px); right: 0; z-index: 60; width: max(200px, 100%);
  background: var(--panel-2); border: 1px solid var(--line-bright); border-radius: 5px;
  box-shadow: 0 18px 40px -14px rgba(0,0,0,.7); overflow: hidden;
}
/* open upward when there isn't room below */
.combo.drop-up .combo-pop { top: auto; bottom: calc(100% + 4px); }
/* the stagger entrance (fill: forwards) leaves every row a permanent stacking
   context, so the pop's z-index only counts inside its own row and later
   sibling rows paint over it — lift the row that owns the open combo */
.setting-row:has(.combo.open) { position: relative; z-index: 60; }
.combo-search {
  width: 100%; box-sizing: border-box; border: none; border-bottom: 1px solid var(--line);
  background: var(--bg); color: var(--ink); font-family: var(--mono); font-size: 13px;
  padding: 10px 12px; outline: none;
}
.combo-list { max-height: 240px; overflow-y: auto; padding: 4px; }
.combo-item {
  width: 100%; text-align: left; cursor: pointer; display: block;
  font-family: var(--mono); font-size: 13px; color: var(--ink);
  background: none; border: none; border-radius: 3px; padding: 8px 10px;
}
.combo-item:hover { background: var(--raised); }
.combo-item.active { color: #1a1206; background: linear-gradient(180deg, var(--amber), var(--amber-soft)); font-weight: 700; }
/* INPA theme highlights with navy, so the selected item needs white text */
html[data-theme="inpa"] .combo-item.active { color: #fff; background: #000080; }
.combo-empty { padding: 12px; text-align: center; font-family: var(--mono); font-size: 12px; color: var(--ink-faint); }
/* version footer under the settings list */
.settings-version { max-width: 720px; margin: 16px auto 0; text-align: center;
  font-family: var(--mono); font-size: 11px; letter-spacing: .05em; color: var(--ink-faint); }

/* opacity slider */
.opacity-control { display: flex; align-items: center; gap: 10px; flex: none; min-width: 280px; }
.opacity-end { font-family: var(--mono); font-size: 10px; letter-spacing: .06em;
  text-transform: uppercase; color: var(--ink-faint); }
.opacity-pct { font-family: var(--mono); font-size: 12px; font-weight: 700;
  color: var(--amber); min-width: 38px; text-align: right; }
.opacity-control input[type="range"] {
  -webkit-appearance: none; appearance: none; flex: 1; height: 4px; border-radius: 4px;
  background: var(--line-bright); outline: none; cursor: pointer;
}
.opacity-control input[type="range"]::-webkit-slider-thumb {
  -webkit-appearance: none; appearance: none; width: 16px; height: 16px; border-radius: 50%;
  background: var(--amber); border: 2px solid var(--panel); box-shadow: 0 1px 3px rgba(0,0,0,.4);
  cursor: pointer;
}
.setting-row.disabled { opacity: .45; }
.setting-row.disabled .opacity-control { pointer-events: none; }
.seg { display: inline-flex; border: 1px solid var(--line-bright); border-radius: 4px; overflow: hidden; flex: none; }
.seg-btn {
  cursor: pointer; font-family: var(--display); font-weight: 600; font-size: 12.5px;
  padding: 9px 16px; background: var(--panel); color: var(--ink-dim); border: 0;
  border-right: 1px solid var(--line); transition: all .12s; white-space: nowrap;
}
.seg-btn:last-child { border-right: 0; }
.seg-btn:hover { color: var(--ink); }
.seg-btn.active { background: linear-gradient(180deg, var(--amber), var(--amber-soft)); color: #1a1206; }

/* connection light, styled like the Battery/Ignition circles: outline when
   inactive, filled white when active (cable connected). */
.led { width: 10px; height: 10px; border-radius: 50%; background: transparent;
       border: 1.5px solid var(--ink); flex: none; transition: all .2s; }
.led.ok   { background: var(--ink); border-color: var(--ink); }
.led.idle { background: transparent; }
.led.off  { background: transparent; }

/* view */
.view {
  position: absolute; inset: 56px 0 52px 0;
  padding: 38px 44px; overflow-y: auto;
}
/* scrollbars: theme vars override per skin in themes.css */
.view::-webkit-scrollbar,
.modal::-webkit-scrollbar,
.live-panel::-webkit-scrollbar,
.split-list::-webkit-scrollbar { width: var(--sb-size, 10px); height: var(--sb-size, 10px); }
.view::-webkit-scrollbar-track,
.modal::-webkit-scrollbar-track,
.live-panel::-webkit-scrollbar-track,
.split-list::-webkit-scrollbar-track { background: var(--sb-track, transparent); }
.view::-webkit-scrollbar-thumb,
.modal::-webkit-scrollbar-thumb,
.live-panel::-webkit-scrollbar-thumb,
.split-list::-webkit-scrollbar-thumb {
  background: var(--sb-thumb, var(--line));
  border-radius: var(--sb-radius, 8px);
  border: var(--sb-thumb-border, none);
}
.view::-webkit-scrollbar-thumb:hover,
.modal::-webkit-scrollbar-thumb:hover,
.live-panel::-webkit-scrollbar-thumb:hover,
.split-list::-webkit-scrollbar-thumb:hover { background: var(--sb-thumb-hover, var(--line-bright)); }
.view::-webkit-scrollbar-corner { background: var(--sb-track, transparent); }

.screen-head { margin-bottom: 30px; }
.eyebrow {
  font-family: var(--mono); font-size: 11px; letter-spacing: .26em;
  text-transform: uppercase; color: var(--amber-soft); margin-bottom: 10px;
}
.title { font-size: 38px; font-weight: 800; letter-spacing: -.02em; line-height: 1; }
.subtitle { color: var(--ink-dim); margin-top: 10px; font-size: 14px; max-width: 60ch; }

/* staggered entrance */
@keyframes rise { from { opacity: 0; transform: translateY(14px); } to { opacity: 1; transform: none; } }
.stagger > * { opacity: 0; animation: rise .5s cubic-bezier(.2,.7,.2,1) forwards; }

/* chassis grid (start screen) */
.chassis-grid {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
  gap: 14px;
}
.chassis-card {
  position: relative; cursor: pointer;
  background: linear-gradient(160deg, var(--panel-2), var(--panel));
  border: 1px solid var(--line); border-radius: 4px;
  padding: 20px 18px; aspect-ratio: 1.5;
  display: flex; flex-direction: column; justify-content: space-between;
  transition: transform .18s cubic-bezier(.2,.7,.2,1), border-color .18s, box-shadow .18s;
  overflow: hidden;
}
.chassis-card::before {
  content: ''; position: absolute; inset: 0;
  background: radial-gradient(120px 80px at 80% 0%, rgba(255,158,44,.10), transparent 70%);
  opacity: 0; transition: opacity .2s;
}
.chassis-card:hover { transform: translateY(-3px); border-color: var(--line-bright);
  box-shadow: var(--shadow); }
.chassis-card:hover::before { opacity: 1; }
/* color explicitly rather than by inheritance: the wiring picker builds these
   cards as <button>, and a button does not inherit the page's text colour --
   it starts from the browser's own black, which on this background is
   invisible. The vehicle picker's <div> cards were fine and hid the bug. */
.chassis-card { color: var(--ink); font-family: inherit; text-align: left; }
.chassis-code { font-size: 30px; font-weight: 900; letter-spacing: .02em; }
.chassis-tag {
  font-family: var(--mono); font-size: 10px; letter-spacing: .14em;
  color: var(--ink-faint); text-transform: uppercase;
}
.chassis-arrow { align-self: flex-end; color: var(--amber); font-size: 18px;
  opacity: 0; transform: translateX(-6px); transition: all .2s; }
.chassis-card:hover .chassis-arrow { opacity: 1; transform: none; }

/* sections */
.section-stack { display: grid; gap: 16px; }
.section {
  border: 1px solid var(--line); border-radius: 4px;
  background: linear-gradient(180deg, var(--panel-2), var(--panel));
  overflow: hidden;
}
.section-head {
  display: flex; align-items: center; gap: 14px;
  padding: 16px 20px; border-bottom: 1px solid var(--line);
}
.section-name { font-weight: 700; font-size: 16px; letter-spacing: .01em; }
.section-count { font-family: var(--mono); font-size: 11px; color: var(--ink-faint); margin-left: auto; }
/* module cards, read like the ECU's housing label: designation stamp on top,
   application name, part number footer. the left edge carries a connector
   pin-header (three ticks) that lights amber on hover. */
.ecu-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(230px, 1fr)); gap: 12px; }
.ecu-card {
  position: relative; cursor: pointer; -webkit-app-region: no-drag;
  display: flex; flex-direction: column; gap: 5px;
  padding: 13px 16px 12px;
  background: var(--panel); border: 1px solid var(--line); border-radius: 6px;
  transition: transform .14s ease, border-color .14s ease, background .14s ease;
}
.ecu-card:hover { transform: translateY(-2px); border-color: var(--line-bright); background: var(--panel-2); }
.ecu-code {
  font: 700 10.5px var(--mono); letter-spacing: .1em; text-transform: uppercase;
  color: var(--amber-soft); transition: color .14s ease;
}
.ecu-card:hover .ecu-code { color: var(--amber); }
.ecu-name { font: 700 14px/1.35 var(--display); color: var(--ink); }
.ecu-prg { font: 400 10px var(--mono); color: var(--ink-faint); margin-top: 1px; }

/* ECU / fault dashboard */
.toolbar { display: flex; align-items: center; gap: 12px; margin-bottom: 22px; flex-wrap: wrap; }
.btn {
  -webkit-app-region: no-drag; cursor: pointer;
  font-family: var(--display); font-weight: 700; font-size: 13px; letter-spacing: .02em;
  padding: 11px 18px; border-radius: 4px; border: 1px solid var(--line-bright);
  background: var(--raised); color: var(--ink); transition: all .15s;
  display: inline-flex; align-items: center; gap: 8px;
}
.btn:hover { border-color: var(--amber); color: #fff; transform: translateY(-1px); }
.btn:active { transform: translateY(0); }
.btn.primary { background: linear-gradient(180deg, var(--amber), var(--amber-soft));
  color: #1a1206; border-color: transparent; }
.btn.danger:hover { border-color: var(--red); }
.btn[disabled] { opacity: .45; pointer-events: none; }

.pill { font-family: var(--mono); font-size: 11px; color: var(--ink-dim);
  padding: 7px 12px; border: 1px solid var(--line); border-radius: 4px; }

/* INPA-faithful screens (toggle in Settings) */
/* vehicle select: Battery / Ignition row + chassis list */
.inpa-vsel { display: block; }
.inpa-klrow { display: flex; gap: 60px; margin-bottom: 28px; padding-bottom: 20px;
  border-bottom: 1px solid var(--line); }
.inpa-kl { display: flex; align-items: center; gap: 14px; font-size: 22px; }
.inpa-kl-name { color: var(--ink); }
/* outline ring, fills solid black when on (no glow) */
.inpa-kl-led { width: 20px; height: 20px; border-radius: 50%;
  border: 2px solid var(--ink); background: transparent; flex: none; }
.inpa-kl-led.on { background: var(--ink); border-color: var(--ink); }
.inpa-kl-state { font-size: 20px; color: var(--ink-dim); min-width: 48px; }
.inpa-vlist { display: grid; gap: 2px; max-width: 640px; }
html[data-theme="inpa"] .inpa-kl-led { border-color: #000; }
html[data-theme="inpa"] .inpa-kl-led.on { background: #000; }
/* two columns: common chassis left, "Old models / Special tests" right */
.inpa-vsplit { display: grid; grid-template-columns: 1fr 1fr; gap: 40px; max-width: 900px; }
.inpa-vsplit .inpa-vlist { max-width: none; }
.inpa-vlist-right { align-content: end; }
.inpa-fn-more .inpa-fn-key { color: var(--ink-faint); }
.inpa-fn-more .inpa-fn-label { font-style: italic; color: var(--ink-dim); }
/* Fault Lookup entry in the INPA vehicle-select right column: search glyph key,
   muted italic label like "Other models …". right-align the glyph in the 64px key
   column so it sits next to the label instead of floating far left, and size it to
   match the F-key text on the rows above. */
.inpa-fn-lookup .inpa-fn-key {
  font-size: 16px; line-height: 1; color: var(--amber);
  justify-self: end; text-align: right;
}
.inpa-fn-lookup .inpa-fn-label { font-style: italic; color: var(--ink-dim); }
html[data-theme="inpa"] .inpa-fn-lookup .inpa-fn-key { color: #000080; }
/* Old-models popup list */
.inpa-pop { min-width: 360px; }
.inpa-pop-list { display: grid; gap: 1px; margin: 6px 0 18px; max-height: 50vh; overflow-y: auto; }
.inpa-pop-row { -webkit-app-region: no-drag; cursor: pointer; text-align: left;
  display: grid; grid-template-columns: 44px 1fr; gap: 12px; align-items: center;
  background: none; border: none; padding: 8px 8px; color: var(--ink); border-radius: 3px; }
.inpa-pop-row:hover { background: rgba(127,127,127,.12); }
.inpa-pop-key { font-family: var(--mono); font-size: 12px; color: var(--ink-dim); }
.inpa-pop-label { font-size: 14px; }
html[data-theme="inpa"] .inpa-pop-row:hover { background: #eef2ff; }
html[data-theme="inpa"] .inpa-pop-key { color: #000080; }

/* "Script selection" two-pane popup (Special tests) */
.inpa-script { min-width: 560px; padding: 0; overflow: hidden; }
.inpa-script-bar { padding: 9px 14px; font-family: var(--mono); font-size: 12px;
  background: var(--panel-2); border-bottom: 1px solid var(--line); color: var(--ink); }
.inpa-script-hint { color: var(--ink-faint); }
.inpa-script-panes { display: grid; grid-template-columns: 200px 1fr; min-height: 240px; }
.inpa-script-cats { border-right: 1px solid var(--line); padding: 6px; }
.inpa-script-cat { padding: 6px 10px; font-family: var(--mono); font-size: 12.5px;
  background: var(--amber); color: #1a1206; border-radius: 2px; }
.inpa-script-list { padding: 6px; display: grid; gap: 1px; align-content: start; }
.inpa-script-row { -webkit-app-region: no-drag; cursor: pointer; text-align: left;
  font-family: var(--mono); font-size: 13px; color: var(--ink);
  background: none; border: none; padding: 6px 10px; border-radius: 2px; }
.inpa-script-row:hover { background: rgba(127,127,127,.12); }
.inpa-script-row.disabled { color: var(--ink-faint); cursor: not-allowed; }
.inpa-script .modal-actions { padding: 10px 14px; border-top: 1px solid var(--line); }
html[data-theme="inpa"] .inpa-script-cat { background: #000080; color: #fff; }
html[data-theme="inpa"] .inpa-script-row:hover { background: #eef2ff; }

/* auto-scan attention badge + slide-up panel */
.att-corner {
  position: fixed; right: 18px; bottom: 64px; z-index: 9000;
  display: flex; align-items: center; gap: 7px; cursor: pointer;
  background: var(--red); color: #fff; border: none; border-radius: 999px;
  padding: 8px 13px 8px 11px; font-family: var(--mono); font-weight: 700; font-size: 13px;
  box-shadow: 0 6px 18px -4px rgba(255,66,66,.6), inset 0 1px 0 rgba(255,255,255,.25);
  transform: translateY(20px) scale(.9); opacity: 0; transition: all .2s cubic-bezier(.2,.8,.2,1);
}
.att-corner.show { transform: none; opacity: 1; }
.att-corner:hover { filter: brightness(1.08); }
.att-corner.expanded { filter: brightness(.92); }
.att-tri { font-size: 12px; animation: attPulse 1.6s ease-in-out infinite; }
@keyframes attPulse { 0%,100% { opacity: 1; transform: scale(1); } 50% { opacity: .55; transform: scale(.85); } }
.att-count { font-size: 13px; }

.att-panel {
  position: fixed; right: 18px; bottom: 108px; z-index: 9001;
  width: 380px; max-width: calc(100vw - 36px);
  background: var(--panel); border: 1px solid var(--line-bright); border-radius: 8px;
  box-shadow: var(--shadow);
  transform: translateY(14px) scale(.97); opacity: 0; pointer-events: none;
  transition: all .18s cubic-bezier(.2,.8,.2,1);
}
.att-panel.show { transform: none; opacity: 1; pointer-events: auto; }
.att-panel-head {
  display: flex; align-items: center; justify-content: space-between;
  padding: 12px 14px; border-bottom: 1px solid var(--line);
  font-weight: 700; font-size: 14px; color: var(--amber);
}
.att-x { background: none; border: none; color: var(--ink-faint); cursor: pointer; font-size: 14px; padding: 2px 6px; }
.att-x:hover { color: var(--ink); }
.att-body { max-height: 46vh; overflow-y: auto; padding: 12px 14px; display: grid; gap: 14px; }
.att-ecu { font-family: var(--mono); font-size: 11px; letter-spacing: .04em; text-transform: uppercase;
  color: var(--ink-dim); margin-bottom: 6px; }
.att-fault { border: 1px solid var(--line); border-left: 3px solid var(--ink-faint); border-radius: 3px;
  padding: 9px 12px; margin-bottom: 5px; background: var(--panel-2); }
.att-fault.present { border-left-color: var(--red); }
.att-name { font-size: 13.5px; font-weight: 600; display: flex; align-items: center; gap: 8px; }
.att-badge { font-family: var(--mono); font-size: 9px; font-weight: 700; color: #fff; background: var(--red);
  padding: 1px 6px; border-radius: 3px; letter-spacing: .06em; }
.att-meta { font-size: 12px; color: var(--ink-dim); margin-top: 3px; }
.att-panel-foot { padding: 10px 14px; border-top: 1px solid var(--line); display: flex; justify-content: flex-end; }

/* "Script selection" dialog: Win9x two-pane chassis/section picker */
.inpa-scriptsel {
  width: 620px; max-width: 92vw; background: var(--panel);
  border: 1px solid var(--line-bright); border-radius: 4px; overflow: hidden;
  box-shadow: var(--shadow); transform: translateY(8px); opacity: 0; transition: all .16s;
}
.modal-overlay.show .inpa-scriptsel { transform: none; opacity: 1; }
.inpa-ss-bar {
  padding: 8px 12px; font-family: var(--display); font-size: 13px; color: var(--ink);
  background: linear-gradient(180deg, var(--panel-2), var(--panel));
  border-bottom: 1px solid var(--line);
}
.inpa-ss-hint { color: var(--ink-faint); font-size: 12px; }
.inpa-ss-panes { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; padding: 10px; }
/* sunken white list boxes */
.inpa-ss-left, .inpa-ss-right {
  min-height: 240px; background: var(--bg);
  border: 1px solid var(--line-bright); border-radius: 2px; overflow-y: auto;
  box-shadow: inset 1px 1px 0 rgba(0,0,0,.15);
}
/* chassis name / "Functional jobs" header rows */
.inpa-ss-head {
  font-family: var(--mono); font-weight: 700; font-size: 13.5px;
  padding: 5px 8px; color: var(--ink);
}
/* header doubles as the clickable Functional Jobs entry on the chassis row */
.inpa-ss-head.func { -webkit-app-region: no-drag; cursor: pointer; color: var(--amber); }
.inpa-ss-head.func:hover { background: rgba(127,127,127,.12); }
html[data-theme="inpa"] .inpa-ss-head.func { color: #000080; }
html[data-theme="inpa"] .inpa-ss-head.func:hover { background: #e8eefc; }
/* indented section items, bold mono */
.inpa-ss-item, .inpa-ss-job {
  -webkit-app-region: no-drag; cursor: pointer; display: block; width: 100%; text-align: left;
  font-family: var(--mono); font-weight: 700; font-size: 13.5px; color: var(--ink);
  background: none; border: none; padding: 4px 8px 4px 26px;
}
.inpa-ss-item:hover, .inpa-ss-job:hover { background: rgba(127,127,127,.12); }
.inpa-ss-item.active { background: rgba(127,127,127,.18); }
/* chassis row sits flush like a header, not indented like a section */
.inpa-ss-chassis { padding-left: 8px; }
.inpa-ss-chassis.active { background: var(--amber); color: #1a1206; }
.inpa-ss-job { padding-left: 12px; }
.inpa-ss-job.func { font-weight: 700; color: var(--amber); }
html[data-theme="inpa"] .inpa-ss-job.func { color: #000080; }
.inpa-ss-empty { font-family: var(--mono); font-size: 12px; color: var(--ink-faint); padding: 8px 12px; }
/* INPA theme: navy highlight, white box */
html[data-theme="inpa"] .inpa-scriptsel { background: #d4d0c8; border-color: #808080; }
html[data-theme="inpa"] .inpa-ss-bar { background: #d4d0c8; color: #000; }
html[data-theme="inpa"] .inpa-ss-left, html[data-theme="inpa"] .inpa-ss-right { background: #fff; border-color: #808080; }
html[data-theme="inpa"] .inpa-ss-item, html[data-theme="inpa"] .inpa-ss-job { color: #000; }
html[data-theme="inpa"] .inpa-ss-item:hover, html[data-theme="inpa"] .inpa-ss-job:hover { background: #e8eefc; }
html[data-theme="inpa"] .inpa-ss-item.active { background: #cfe0ff; }
html[data-theme="inpa"] .inpa-ss-chassis.active { background: #0a246a; color: #fff; }

/* quick sweep: chassis-wide fault/ident scan */
.quick-sweep { }
.quick-bar { display: flex; align-items: center; justify-content: space-between; gap: 12px; margin-bottom: 10px; }
.quick-bar .quick-head { margin-bottom: 0; }
.quick-bar-btns { display: flex; gap: 8px; align-items: center; }
.quick-clear-all {
  -webkit-app-region: no-drag; cursor: pointer; font-family: var(--mono); font-size: 11.5px;
  color: var(--red); background: none; border: 1px solid var(--red); border-radius: 3px;
  padding: 4px 12px; white-space: nowrap;
}
.quick-clear-all:hover:not(:disabled) { background: var(--red); color: #fff; }
.quick-clear-all:disabled { opacity: .35; cursor: default; }
.quick-pdf {
  -webkit-app-region: no-drag; cursor: pointer; font-family: var(--mono); font-size: 11.5px;
  color: var(--ink-dim); background: none; border: 1px solid var(--line-bright); border-radius: 3px;
  padding: 4px 12px; white-space: nowrap;
}
.quick-pdf:hover:not(:disabled) { background: var(--raised); color: var(--ink); border-color: var(--ink-dim); }
.quick-pdf:disabled { opacity: .35; cursor: default; }
.quick-head { font-family: var(--mono); font-size: 12px; color: var(--ink-dim); margin-bottom: 10px; }
.quick-rows { display: grid; gap: 2px; }
.quick-row { display: grid; grid-template-columns: 1fr auto; gap: 16px; align-items: center;
  padding: 9px 14px; border: 1px solid var(--line); border-radius: 3px; background: var(--panel); }
.quick-ecu { font-size: 13.5px; }
.quick-status { font-family: var(--mono); font-size: 12px; color: var(--ink-dim); }
.quick-row.has-faults { border-left: 3px solid var(--red); }
.quick-row.has-faults .quick-status { color: var(--red); }
.quick-row.clean { border-left: 3px solid var(--green); }
.quick-row.noresp { opacity: .55; }
.quick-row.scanning-detail .quick-status { color: var(--amber); }
.quick-status { display: inline-flex; align-items: center; gap: 8px; }
.quick-clear {
  -webkit-app-region: no-drag; cursor: pointer; font-family: var(--mono); font-size: 10.5px;
  color: var(--red); background: none; border: 1px solid var(--red); border-radius: 3px;
  padding: 2px 8px;
}
.quick-clear:hover { background: var(--red); color: #fff; }
.quick-clearing { color: var(--amber); font-style: italic; }
.quick-cleared { color: var(--green); }
.quick-clear-fail { color: var(--red); }
/* deep-scan DTC rows, listed under a faulty module */
.quick-detail { display: grid; gap: 1px; margin: 1px 0 4px 14px;
  border-left: 3px solid var(--line-bright); }
.quick-detail-row { display: grid; grid-template-columns: 76px 1fr auto; gap: 12px;
  align-items: baseline; padding: 5px 14px; background: var(--panel-2);
  font-size: 12.5px; }
.quick-detail-code { font-family: var(--mono); font-weight: 700; color: var(--ink); }
.quick-detail-name { color: var(--ink-dim); }
.quick-detail-state { font-family: var(--mono); font-size: 10.5px; letter-spacing: .04em;
  color: var(--ink-faint); }
.quick-detail-row.present .quick-detail-code { color: var(--red); }
.quick-detail-row.present .quick-detail-state { color: var(--red); }


/* ECU main menu: SGBD subline + function list */
.inpa-haupt { display: block; }
.inpa-haupt-sub {
  font-family: var(--mono); font-size: 12px; color: var(--ink-dim);
  margin-bottom: 18px; letter-spacing: .04em;
}
.inpa-haupt-list { display: grid; gap: 2px; max-width: 560px; }
.inpa-fn {
  -webkit-app-region: no-drag; cursor: pointer; text-align: left;
  display: grid; grid-template-columns: 64px 1fr auto; gap: 16px; align-items: baseline;
  background: none; border: none; padding: 7px 6px; color: var(--ink);
  border-bottom: 1px dotted transparent; transition: background .1s;
}
.inpa-fn:hover { background: rgba(127,127,127,.10); }
.inpa-fn-key { font-family: var(--mono); font-size: 13px; color: var(--ink-dim); white-space: nowrap; }
.inpa-fn-label { font-size: 14.5px; }
.inpa-fn-count { font-family: var(--mono); font-size: 11px; color: var(--ink-faint); }
/* INPA theme: black-on-white, navy F-key */
html[data-theme="inpa"] .inpa-fn-key { color: #000080; }
html[data-theme="inpa"] .inpa-fn:hover { background: #eef2ff; }

/* fault view: labeled block per fault */
.inpa-faults { display: grid; gap: 14px; }
.inpa-fault-title { font-size: 20px; font-weight: 700; margin-bottom: 6px; }
.inpa-noerr { color: var(--ink-dim); font-size: 14px; }
.inpa-fault { border: 1px solid var(--line); border-radius: 4px; padding: 14px 18px;
  background: var(--panel); }
.inpa-fault-head { display: flex; align-items: baseline; gap: 14px; flex-wrap: wrap;
  padding-bottom: 8px; margin-bottom: 8px; border-bottom: 1px solid var(--line); }
.inpa-fault-idx { font-family: var(--mono); font-size: 12px; color: var(--ink-dim); }
.inpa-fault-nr  { font-family: var(--mono); font-size: 12px; color: var(--ink-faint); }
.inpa-fault-name { font-size: 16px; font-weight: 700; flex: 1; }
.inpa-fault-present { font-family: var(--mono); font-size: 10px; font-weight: 700;
  color: #fff; background: var(--red); padding: 2px 8px; border-radius: 3px; letter-spacing: .08em; }
.inpa-fault-freq { font-family: var(--mono); font-size: 11px; color: var(--ink-faint); margin-left: auto; }
.inpa-fault-fields { display: grid; gap: 5px; }
.inpa-ff { display: grid; grid-template-columns: 130px 1fr; gap: 14px; font-size: 13px; }
.inpa-ff-k { color: var(--ink-dim); font-family: var(--mono); font-size: 11.5px; }
.inpa-ff-v { color: var(--ink); }
.inpa-ff-v.mono { font-family: var(--mono); }
html[data-theme="inpa"] .inpa-fault { background: #fff; }
html[data-theme="inpa"] .inpa-fault-name { color: #000; }
/* environment snapshot (RPM/voltage/mileage at code entry) */
.inpa-env { margin-top: 10px; padding-top: 10px; border-top: 1px dashed var(--line); }
.inpa-env-head { font-family: var(--mono); font-size: 10.5px; letter-spacing: .04em;
  text-transform: uppercase; color: var(--ink-faint); margin-bottom: 6px; }
.inpa-uw { display: grid; grid-template-columns: 1fr auto; gap: 14px; font-size: 12.5px; padding: 2px 0; }
.inpa-uw-k { color: var(--ink-dim); }
.inpa-uw-v { font-family: var(--mono); font-weight: 700; color: var(--ink); }

.faults { display: grid; gap: 12px; }
.fault {
  display: grid; grid-template-columns: 110px 1fr auto; gap: 18px; align-items: center;
  border: 1px solid var(--line); border-left: 3px solid var(--red);
  background: linear-gradient(90deg, rgba(255,66,66,.06), var(--panel) 30%);
  border-radius: 4px; padding: 16px 20px;
}
.fault.cleared { border-left-color: var(--green);
  background: linear-gradient(90deg, rgba(56,224,138,.06), var(--panel) 30%); }
.fault-code { display: flex; flex-direction: column; gap: 3px; min-width: 0; overflow: hidden; }
.fault-hex { font-family: var(--mono); font-weight: 700; font-size: 15px; color: var(--amber);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis; max-width: 110px; }
.fault-pcode { font-family: var(--mono); font-size: 11px; color: var(--cyan); white-space: nowrap; }
.fault-main { min-width: 0; }
.fault-loc { font-size: 15px; font-weight: 600; }
.fault-symptom { font-size: 12.5px; color: var(--ink-dim); margin-top: 3px; }
/* detailed read: fields under the symptom */
.fault-detail { margin-top: 9px; padding-top: 9px; border-top: 1px solid var(--line); display: grid; gap: 4px; }
.fd-row { display: grid; grid-template-columns: 90px 1fr; gap: 12px; font-size: 12.5px; }
.fd-k { color: var(--ink-faint); font-family: var(--mono); font-size: 11px; }
.fd-v { color: var(--ink-dim); }
.fd-env-row { display: flex; flex-wrap: wrap; gap: 6px 18px; margin-top: 2px; }
.fd-env { font-size: 12px; color: var(--ink-dim); }
.fd-env-k { color: var(--ink-faint); }
.fault-flags { display: flex; gap: 6px; flex: none; }
.flag { font-family: var(--mono); font-size: 10px; letter-spacing: .08em; text-transform: uppercase;
  padding: 4px 9px; border-radius: 3px; border: 1px solid var(--line); color: var(--ink-dim); }
.flag.present { color: var(--red); border-color: rgba(255,66,66,.4); }

/* master/detail split: sections sidebar + ECU list */
.split { display: grid; grid-template-columns: 230px 1fr; gap: 18px; margin-top: 8px; }
/* system rail: flat rows, an amber edge marks the active system. the key
   number mirrors the F-key bar; the count is how many module variants the
   system carries. token-driven, so every skin inherits it. */
.split-nav { display: flex; flex-direction: column; gap: 2px; }
.sys-item {
  -webkit-app-region: no-drag; cursor: pointer; text-align: left;
  display: flex; align-items: center; gap: 10px; font: inherit;
  padding: 10px 12px 10px 13px;
  background: none; border: none; border-left: 3px solid transparent;
  border-radius: 0 6px 6px 0;
  color: var(--ink-dim); transition: background .12s, border-color .12s, color .12s;
}
.sys-item:hover { background: var(--panel); color: var(--ink); }
.sys-item.active { border-left-color: var(--amber); background: var(--panel); color: var(--ink); }
.sys-item .nav-name { font-weight: 700; font-size: 13.5px; }
.sys-item .nav-key {
  font-family: var(--mono); font-weight: 700; font-size: 11px;
  color: var(--ink-faint); min-width: 14px; text-align: center;
  transition: color .12s;
}
.sys-item.active .nav-key { color: var(--amber); }
.split-content { min-width: 0; }
.nav-count { margin-left: auto; font: 600 10.5px var(--mono); color: var(--ink-faint); }
.split-nav-item.active .nav-count { color: var(--ink-dim); }

/* flashing */
.flash-tile { border-color: rgba(255,66,66,.35); }
.flash-tile:hover { border-color: var(--red); }
.flash-tile .group-name { color: var(--red); }
.flash-tools { display: flex; flex-wrap: wrap; gap: 10px; margin: 14px 0; }
.flash-tools .btn { flex-direction: column; align-items: flex-start; gap: 3px; padding: 11px 18px; }
.flash-sub { font-family: var(--mono); font-size: 9px; font-weight: 400; letter-spacing: .04em;
  opacity: .7; text-transform: none; }
.flash-hint { align-self: center; font-family: var(--mono); font-size: 11px; color: var(--ink-faint); }
.dme-type { margin-left: auto; font-family: var(--mono); font-weight: 700; font-size: 13px;
  letter-spacing: .04em; border: 1px solid; border-radius: 4px; padding: 4px 12px; }
/* DME identity: even columns, no orphan cell */
.dme-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); }
.dme-grid .live-cell { border-top: 1px solid var(--line); border-right: 1px solid var(--line); }
.dme-grid .live-v { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.flash-job { border: 1px solid var(--line); border-radius: 4px; margin-bottom: 10px;
  background: linear-gradient(180deg, var(--panel-2), var(--panel)); }
.flash-bar { height: 10px; background: var(--bg); border: 1px solid var(--line-bright); border-radius: 999px; overflow: hidden; }
.flash-bar-fill { height: 100%; width: 0; background: linear-gradient(90deg, var(--amber), var(--green));
  transition: width .2s ease; }

/* ECU main menu: category tiles */
.group-grid {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
  gap: 12px; margin-top: 8px;
}
.group-tile {
  position: relative; cursor: pointer;
  border: 1px solid var(--line); border-radius: 4px;
  background: linear-gradient(160deg, var(--panel-2), var(--panel));
  padding: 20px; min-height: 96px;
  display: flex; flex-direction: column; gap: 6px;
  transition: transform .16s, border-color .16s, box-shadow .16s;
}
.group-tile:hover { transform: translateY(-2px); border-color: var(--amber); box-shadow: var(--shadow); }
.group-name { font-size: 18px; font-weight: 800; letter-spacing: -.01em; }
.group-count { font-family: var(--mono); font-size: 11px; color: var(--ink-faint); }
.group-arrow { position: absolute; right: 16px; bottom: 14px; color: var(--amber);
  opacity: 0; transform: translateX(-4px); transition: all .18s; }
.group-tile:hover .group-arrow { opacity: 1; transform: none; }

/* grouped functional menu (INPA-style sections) */
.menu-sections { display: grid; gap: 18px; margin-top: 8px; }
.menu-section {
  border: 1px solid var(--line); border-radius: 4px;
  background: linear-gradient(180deg, var(--panel-2), var(--panel)); overflow: hidden;
}
.menu-section-head {
  display: flex; align-items: center; gap: 10px;
  padding: 11px 16px; border-bottom: 1px solid var(--line);
}
.menu-section-name {
  font-family: var(--mono); font-size: 11px; letter-spacing: .22em; text-transform: uppercase;
  color: var(--amber-soft); font-weight: 700;
}
.menu-section-count {
  font-family: var(--mono); font-size: 10px; color: var(--ink-faint);
  border: 1px solid var(--line); border-radius: 3px; padding: 1px 7px; margin-left: auto;
}
.menu-rows { display: grid; grid-template-columns: repeat(auto-fill, minmax(320px, 1fr)); }
.menu-rows .job-row { border: 0; border-top: 1px solid transparent; border-right: 1px solid var(--line); border-radius: 0; }

/* INPA-style function (job) list */
.job-list {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(320px, 1fr));
  gap: 6px; margin-top: 8px;
}
.job-row {
  -webkit-app-region: no-drag; cursor: pointer;
  display: flex; align-items: center; gap: 11px;
  padding: 12px 15px; border: 1px solid var(--line); border-radius: 4px;
  background: var(--panel); transition: background .12s, border-color .12s;
}
.job-row:hover { background: var(--raised); border-color: var(--line-bright); }
.job-bullet { width: 6px; height: 6px; border-radius: 50%; background: var(--ink-faint); flex: none; }
.job-row:hover .job-bullet { background: var(--cyan); box-shadow: 0 0 8px var(--cyan); }
.job-row.danger:hover { border-color: var(--red); }
.job-row.danger .job-bullet { background: var(--amber-soft); }
.job-label { font-size: 13.5px; font-weight: 500; }
.job-warn {
  font-family: var(--mono); font-size: 9px; letter-spacing: .1em; text-transform: uppercase;
  color: var(--amber); border: 1px solid rgba(255,158,44,.4); border-radius: 3px; padding: 2px 6px;
  margin-left: auto;
}

/* generic result cards */
.results-panel { display: grid; gap: 10px; margin-bottom: 20px; }
.results-panel:empty { display: none; }
.result-card {
  border: 1px solid var(--line); border-left: 3px solid var(--cyan);
  border-radius: 4px; background: var(--panel); padding: 14px 18px;
}
.result-head { font-family: var(--mono); font-size: 10px; letter-spacing: .12em;
  text-transform: uppercase; color: var(--ink-faint); margin-bottom: 8px; }
.kv { display: flex; justify-content: space-between; gap: 18px; padding: 4px 0;
  border-bottom: 1px solid rgba(38,48,57,.5); }
.kv:last-child { border-bottom: 0; }
.kv-k { font-family: var(--mono); font-size: 11.5px; color: var(--ink-dim); }
.kv-v { font-family: var(--mono); font-size: 12px; color: var(--ink); text-align: right; word-break: break-word; }

/* actuator tests (activations) */
.act-warning {
  font-size: 12.5px; line-height: 1.5; color: var(--amber);
  background: rgba(255,158,44,.07); border: 1px solid rgba(255,158,44,.3);
  border-radius: 4px; padding: 12px 16px; margin-bottom: 16px;
}
.act-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(340px, 1fr)); gap: 10px; }
.act-card {
  display: flex; align-items: center; gap: 14px;
  border: 1px solid var(--line); border-radius: 4px; padding: 14px 16px;
  background: linear-gradient(180deg, var(--panel-2), var(--panel)); transition: border-color .15s;
}
.act-card.running { border-color: var(--red); background: linear-gradient(90deg, rgba(255,66,66,.08), var(--panel) 40%); }
.act-info { min-width: 0; flex: 1; }
.act-label { font-size: 14px; font-weight: 600; }
.act-jobs { font-family: var(--mono); font-size: 9.5px; color: var(--ink-faint); margin-top: 3px;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
/* STATUS_X readback after activating (the value INPA shows, e.g. fan 98 %) */
.act-readback { font-family: var(--mono); font-size: 12px; color: var(--cyan); margin-top: 5px;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.act-card.running .act-readback { color: var(--green); }
.act-btn { flex: none; min-width: 92px; justify-content: center; }
.act-btn.on { animation: actpulse 1.4s ease-in-out infinite; }
@keyframes actpulse { 0%,100% { box-shadow: 0 0 0 0 rgba(255,66,66,.5); } 50% { box-shadow: 0 0 0 4px rgba(255,66,66,0); } }

/* demo mode: simulated values, never a real reading — say so loudly */
.live-meta.demo { color: var(--amber); font-weight: 700; letter-spacing: .04em; }

/* INPA action menus: an actuator's softkey row, each key sending the exact
   value decoded from the .IPO */
.act-menu-title { font-size: 17px; font-weight: 700; margin: 4px 0 2px; }
/* INPA's own subtitle: these pages are I/O STATUS screens you can also drive
   from, so the readouts run live whether or not a key is pressed */
.act-menu-sub { font-size: 11.5px; color: var(--ink-faint); margin: 0 0 12px; }
/* Special: INPA's hex memory dump */
.mem-dump { margin-top: 6px; font-family: var(--mono); font-size: 12.5px; }
.mem-row {
  display: grid; grid-template-columns: 110px 1fr 150px; gap: 14px;
  padding: 6px 0; border-bottom: 1px solid var(--line);
}
.mem-head { color: var(--ink-faint); font-size: 11px; letter-spacing: .04em; }
.mem-addr { color: var(--cyan); }
.mem-bytes { word-break: break-all; }
.mem-ascii { color: var(--ink-faint); word-break: break-all; }

/* Special: the immobilizer-sync sequence, one row per step */
.sync-steps { margin-top: 8px; display: grid; gap: 1px; max-width: 720px; }
.sync-step {
  display: grid; grid-template-columns: 24px 1fr auto auto; gap: 12px;
  align-items: baseline; padding: 8px 0; border-bottom: 1px solid var(--line);
}
.sync-n { color: var(--ink-faint); font-family: var(--mono); font-size: 12px; }
.sync-job { font-size: 11.5px; color: var(--ink-faint); }
.sync-state { font-size: 11px; text-transform: uppercase; letter-spacing: .05em; }
.sync-step.running .sync-state, .sync-step.waiting .sync-state { color: var(--amber); }
.sync-step.ok .sync-state { color: var(--green); }
.sync-step.failed .sync-state { color: var(--red); }
.sync-step.idle .sync-state { color: var(--ink-faint); }

/* the state word on an INPA actuator row (running / needs input): text, not a
   control — the row itself is what you click */
.act-row .act-key-val { font-size: 11px; letter-spacing: .04em; color: var(--ink-faint); }
.act-row.running .act-key-val { color: var(--green); }

/* INPA's post-drive readout: it shows the signal state rather than treating
   the send as fire-and-forget, which is how it works without a stop job. */
.act-drive-note {
  margin: 6px 0 2px; font-size: 12px; color: var(--ink-faint);
  max-width: 720px; line-height: 1.5;
}
.act-state { min-height: 22px; margin: 4px 0 8px; }
.act-state-title {
  display: block; font-size: 10.5px; letter-spacing: .06em;
  color: var(--ink-faint); text-transform: uppercase;
}
.act-state-row { font-family: var(--mono); font-size: 13px; }
.act-state-row .on { color: var(--green); font-weight: 700; }
.act-state-row .off { color: var(--ink-faint); font-weight: 700; }

/* An actuator test the ECU declares but whose arguments we cannot supply:
   shown so the capability is visible, but plainly not offered as runnable. */
.act-btn.act-blocked {
  background: transparent; border: 1px dashed var(--line-bright);
  color: var(--ink-faint); cursor: not-allowed; font-size: 11px;
}
.act-blocked-card { opacity: .62; }
.act-blocked-card:hover { border-color: var(--line); }

/* Service: CBS availability drawn as a bar — full is fresh, empty is due */
.svc-bar {
  display: inline-block; width: 84px; height: 6px; margin-left: 10px;
  background: var(--line); border-radius: 3px; overflow: hidden;
  vertical-align: middle;
}
.svc-bar-fill { display: block; height: 100%; background: var(--green); }

/* Identity: the ID-data card. Long cards (18 ID fields, the CBS read) run past
   the F-key bar; the .view scrolls them, so the card itself stays a plain grid
   rather than nesting a second scrollbar. */
.ident-card { display: grid; gap: 1px; max-width: 620px; margin-top: 4px; }

/* INPA mode draws the card as its own screen does: one monospace line per
   field with the colons in a column ('BMWTeilenummer          :  0000000').
   Not a restyle of the modern grid — the label column is fixed-width so the
   colons align, which is the whole look. */
.ident-line {
  display: grid; grid-template-columns: 25ch 1ch 1fr; gap: 6px;
  font-family: var(--mono); font-size: 12.5px; padding: 2px 0;
}
.ident-lk { color: var(--ink-faint); white-space: nowrap;
            overflow: hidden; text-overflow: ellipsis; }
.ident-lc { color: var(--ink-faint); }
.ident-lv { color: var(--ink); }
/* a field the SGBD supplied that INPA's own screen does not show */
.ident-extra .ident-lk, .ident-extra .ident-k { opacity: .72; }
.ident-row {
  display: grid; grid-template-columns: 210px 1fr; gap: 14px;
  padding: 5px 0; align-items: baseline;
}
.ident-k { font-size: 12.5px; color: var(--ink-faint); }
.ident-v { font-family: var(--mono); font-size: 13px; color: var(--ink); }

/* Coding: the ECU's option flags as lamps, filled when the option is fitted */
.coding-grid {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: 2px 24px; margin-top: 4px;
}
.coding-opt { display: flex; align-items: baseline; gap: 10px; padding: 5px 0; }
.coding-lamp { font-size: 13px; color: var(--ink-faint); width: 14px; flex: none; }
.coding-opt.fitted .coding-lamp { color: var(--green); }
.coding-name { font-size: 13px; color: var(--ink-dim); }
.coding-opt.fitted .coding-name { color: var(--ink); }

/* a system check's diagnosis line — INPA prints the routine's state here */
.sc-state {
  font-family: var(--mono); font-size: 14px; font-weight: 700; color: var(--cyan);
  padding: 8px 0 10px; border-top: 1px solid var(--line); margin-top: 6px;
}
/* INPA prints its softkeys as a plain list, same shape as the Hauptmenue —
   the footer bar is what actually fires them, so these are just readable rows */
/* Compact rows: INPA fits nine keys plus every readout on one screen, so these
   are tighter than the Hauptmenue list they borrow from — no scrolling. */
.act-key-list { display: grid; gap: 0; max-width: 620px; margin-bottom: 10px; }
.act-key-row {
  grid-template-columns: 76px 1fr auto 14px; padding: 2px 6px; gap: 12px;
}
.act-key-row .inpa-fn-label { font-size: 13px; }
.act-key-val { font-family: var(--mono); font-size: 10px; color: var(--ink-faint); }
/* return arrow marking a row that opens a submenu */
.ir-enter { font-size: 12px; color: var(--ink-faint); text-align: right; }

/* INPA prints identity values on the menu screen itself, above the softkeys */
.ir-menu-head { display: flex; flex-wrap: wrap; gap: 6px 28px;
  max-width: 620px; margin: 0 0 14px; }
.ir-menu-head:empty { display: none; }

/* INPA's bar has two rows and Shift swaps between them; mark the shifted one
   so it is obvious which half is showing */
.fkeys.shifted .fkey { border-color: var(--amber-soft); }
.fkeys.shifted .fkey-num { color: var(--amber); }
/* The shifted keys live in a second column, always visible, the way INPA
   prints them beside the plain list. Only the footer bar swaps on Shift. */
.results-panel.ir-has-shift { display: grid; gap: 0 48px;
  grid-template-columns: auto auto; justify-content: start; align-items: start; }
.results-panel.ir-has-shift .ir-menu-head { grid-column: 1 / -1; }
.ir-shift-col .act-key-row { grid-template-columns: 150px 1fr auto 14px; }
.ir-head-cell { display: flex; gap: 8px; align-items: baseline;
  font-size: 12px; }
.ir-head-label { color: var(--ink-faint); text-transform: uppercase;
  letter-spacing: .04em; }
.ir-head-value { font-family: var(--mono); color: var(--ink); }
.act-key-row.danger .inpa-fn-label { color: var(--red); }
/* the live output readout INPA prints under the keys, one row per driven output
   ("Status Vanoseinlassventil  33 %") */
/* the driven outputs, drawn as bars like INPA's "Status Vanoseinlassventil".
   No padding override here: the cells must match the Status screens' gauges. */
/* the driven-output cells live inside the measurement grid so they page with
   everything else — no separate block, no rule, no stray border */
.act-menu-readback {
  font-family: var(--mono); font-size: 13px; color: var(--green); min-height: 18px;
}
.group-tile.danger { border-color: rgba(255,66,66,.45); }
.group-tile.danger .group-name { color: var(--red); }

/* INPA mode: the flat Steuern list, laid out like the Hauptmenue F-key list
   rather than the card grid. Columns: F-key, name, job, button. */
.act-inpa .inpa-haupt-list { max-width: 760px; }
.act-inpa-warn { font-size: 12px; color: var(--amber); margin: 0 0 12px; max-width: 760px; }
.act-row { grid-template-columns: 64px 1fr auto auto; gap: 4px 12px; align-items: center; }
.act-row .inpa-fn-label { text-align: left; }
.act-row-job { font-family: var(--mono); font-size: 10px; color: var(--ink-faint); }
.act-row .act-btn { min-width: 78px; padding: 3px 10px; font-size: 11.5px; pointer-events: none; }
.act-row.running .inpa-fn-label { color: var(--red); }
.act-row .act-readback { grid-column: 2 / -1; margin-top: 2px; }
html[data-theme="inpa"] .act-row.running .inpa-fn-label { color: #a00000; }

/* Status multi-watch toolbar + checkboxes */
.watch-toolbar {
  display: flex; align-items: center; gap: 12px; margin: 4px 0 14px;
  flex-wrap: wrap;
}
.watch-hint { font-family: var(--mono); font-size: 11px; color: var(--ink-faint); margin-right: auto; }
.watch-toolbar .btn { padding: 9px 15px; font-size: 12.5px; }
.job-row.selectable { cursor: pointer; }
.job-check {
  width: 15px; height: 15px; flex: none; border-radius: 3px;
  border: 1.5px solid var(--line-bright); background: var(--bg);
  display: inline-flex; align-items: center; justify-content: center; transition: all .12s;
}
.job-check:hover { border-color: var(--cyan); }
.job-row.checked { background: rgba(79,210,255,.06); border-color: rgba(79,210,255,.3); }
.job-row.checked .job-check { background: var(--cyan); border-color: var(--cyan); }
.job-row.checked .job-check::after { content: '✓'; color: #06222e; font-size: 11px; font-weight: 900; }
.live-log { font-size: 12px; padding: 7px 13px; }

/* live status value table */
.live-panel { margin-bottom: 20px; border: 1px solid var(--line); border-radius: 4px;
  background: linear-gradient(180deg, var(--panel-2), var(--panel)); overflow: hidden; }
.live-head { display: flex; align-items: center; gap: 10px; padding: 12px 16px;
  border-bottom: 1px solid var(--line); }
.live-dot { width: 8px; height: 8px; border-radius: 50%; background: var(--green);
  box-shadow: 0 0 9px var(--green); animation: pulse 1.1s ease-in-out infinite; }
@keyframes pulse { 0%,100% { opacity: 1; } 50% { opacity: .35; } }
.live-title { font-weight: 700; font-size: 14px; }
.live-meta { font-family: var(--mono); font-size: 10px; color: var(--ink-faint); }
.live-head .live-stop { margin-left: auto; padding: 7px 14px; font-size: 12px; }
.live-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); }
/* min-width:0 is load-bearing, not tidiness. A grid/flex item's default
   min-width is auto, i.e. "never shrink below my content", so a long
   nowrap label (MSD80's "MISFIRE MONITORING: TEST NOT SUPPORTED BY THIS
   MODULE = 0, SUPPORTED = 1") widened its own track and ran off the panel
   instead of ellipsing. The ellipsis below only engages once the box is
   allowed to be narrower than its text. */
.live-cell { padding: 12px 16px; border-top: 1px solid var(--line); border-right: 1px solid var(--line);
  min-width: 0; overflow: hidden; }
.live-k { font-family: var(--mono); font-size: 10px; letter-spacing: .06em; color: var(--ink-dim);
  text-transform: uppercase; margin-bottom: 5px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  min-width: 0; max-width: 100%; }
.live-v { font-family: var(--mono); font-size: 18px; font-weight: 700; color: var(--cyan); }
.live-v.flash { animation: vflash .5s ease; }
@keyframes vflash { 0% { color: #fff; text-shadow: 0 0 10px rgba(79,210,255,.8); } 100% {} }

/* INPA-style gauge bars */
.gauge-cell { padding: 11px 16px 13px; }
.gauge { margin-top: 4px; }
.gauge-track {
  position: relative; height: 14px; border-radius: 2px; overflow: hidden;
  background: var(--gauge-track, var(--green));
  border: 1px solid var(--line);
}
/* INPA draws its zones in flat saturated green and red on white */
html[data-theme="inpa"] { --gauge-ok: #00d000; --gauge-warn: #ff0000;
  --gauge-mark: #000; }
.gauge-fill {
  position: absolute; left: 0; top: 0; bottom: 0; width: 0%;
  background: var(--gauge-fill, #000);
  transition: width .25s ease;
}
/* INPA fills a zoned bar from the left up to the reading, in black over the
   coloured zones -- its VANOS page shows a -5..5 gauge black to the midpoint
   at 0.0. The fill is SHORTER than the track, so the zone it covers still
   reads as a stripe above and below it: you can see which side of the
   threshold the reading sits on without looking at the number. */
.gauge-track.zoned .gauge-fill {
  background: var(--gauge-mark); top: 12.5%; bottom: 12.5%;
}
/* the unit sits under the label on its own line, INPA-style: "[V]" */
.gauge-unit { font-family: var(--mono); font-size: 10px; color: var(--ink-faint);
  min-height: 12px; line-height: 12px; }
/* bar and value share a row; the scale ends sit under the bar. The bar takes a
   share of the column rather than all of it, so the value stays beside its bar
   instead of drifting to the far edge on a wide screen (INPA does the same). */
.gauge { display: flex; align-items: flex-start; gap: 12px; }
.gauge-bar { flex: 0 1 320px; min-width: 0; }
.gauge-foot {
  display: flex; align-items: baseline; justify-content: space-between; gap: 8px;
  margin-top: 2px; font-family: var(--mono); font-size: 10px; color: var(--ink-faint);
}
.gauge-min, .gauge-max { flex: none; min-width: 18px; }
.gauge-max { text-align: right; }
/* the threshold sits under the point where the colours meet, so the foot has
   to position it proportionally rather than space it evenly */
.gauge-foot { position: relative; }
.gauge-edge {
  position: absolute; transform: translateX(-50%);
  pointer-events: none; white-space: nowrap;
}
.gauge-edge:empty { display: none; }
.gauge-val {
  flex: none; text-align: left; font-size: 15px; font-weight: 700;
  color: var(--cyan); white-space: nowrap; line-height: 14px;
}
/* a boolean reads as INPA's filled/hollow dot, not a word or a bar */
.gauge-cell.bool .gauge-bar { display: none; }
.gauge-cell.bool .gauge-val {
  min-width: 0; font-size: 15px; color: var(--ink);
  display: flex; align-items: center; gap: 8px;
}
/* INPA two-column screens (Bank 1 / Bank 2 side by side) */
.inpa-grid.two-col { grid-template-columns: 1fr 1fr; }
/* the column divider belongs to the left cell only, and must not hang below the
   last row when an odd value count leaves the right cell empty */
.inpa-grid.two-col .gauge-cell { border-right: none; }
.inpa-grid.two-col .gauge-cell:nth-child(odd):not(:last-child) {
  border-right: 1px solid var(--line);
}
/* an odd value count leaves the right column empty on the last row, so the row
   separator would stop halfway across. Extend it over the empty slot with a
   pseudo-element the exact width of one column. */
.inpa-grid.two-col .gauge-cell { position: relative; }
.inpa-grid.two-col .gauge-cell:last-child:nth-child(odd)::after {
  content: ''; position: absolute; top: -1px; left: 100%; width: 100%;
  border-top: 1px solid var(--line); pointer-events: none;
}
.inpa-grid { grid-template-columns: 1fr; }

/* INPA 10-per-page paging: a cell outside the current page is removed from flow
   so the grid always shows exactly one page (2 cols x 5 rows). */
.live-panel.inpa-screen { position: relative; padding-bottom: 30px; }
.inpa-grid .gauge-cell.inpa-hidden { display: none; }

/* Bare readout: INPA draws measurements straight onto the window — no card, no
   cell dividers, no title bar, rows separated by whitespace alone. Declared
   after the panel/grid rules above so these overrides win the cascade. */
.live-panel.bare {
  border: none; border-radius: 0; background: none;
  margin-bottom: 0; overflow: visible;
  /* keep the room the pager arrow is absolutely positioned into */
  position: relative; padding-bottom: 34px;
}
.live-panel.bare .live-head {
  border-bottom: none; padding: 0 0 14px; background: none;
}
.live-panel.bare .live-title { font-size: 20px; font-weight: 400; }
.live-panel.bare .live-meta { margin-left: auto; }
.live-panel.bare .live-grid { border-top: none; row-gap: 20px; column-gap: 52px; }
/* INPA never scrolls a status screen — it pages. Keep the readout inside the
   viewport so the pager arrow, not a scrollbar, moves you through the values. */
.view:has(> .live-panel.bare) { overflow-y: hidden; }
/* The action-menu page nests its readout inside .act-menu, so the direct-child
   rule above misses it — it pages with the arrow, it must not scroll either.
   Bound the readout's height too: suppressing the scrollbar alone just clips
   the last row, since cells keep arriving after the pager has measured.
   Scoped to menus that actually page: the read-only card screens (ID-data, AIF,
   CBS) are plain lists with no pager, and clipping them just hides their last
   rows with no way to reach them. */
.view:has(.act-menu #act-gauges) { overflow-y: hidden; }
/* bound by the viewport, not the parent: .results-panel is an auto-height grid,
   so a percentage max-height there resolves against nothing */
.act-menu { display: flex; flex-direction: column; min-height: 0; }
.act-menu #act-gauges { flex: 1 1 auto; min-height: 0; overflow: hidden; }
/* every divider off, including the two-column separator */
.live-panel.bare .live-cell,
.live-panel.bare .gauge-cell,
.live-panel.bare .inpa-grid.two-col .gauge-cell:nth-child(odd) {
  border: none; padding: 0;
}
/* no row separators at all in the bare layout, so no filler either */
.live-panel.bare .inpa-grid.two-col .gauge-cell::after { display: none; }

/* single green scroll arrow, bottom-right, exactly like INPA's page indicator */
.inpa-pager-arrow {
  position: absolute; right: 10px; bottom: 8px; z-index: 3;
  width: 26px; height: 22px; padding: 0; line-height: 20px;
  -webkit-app-region: no-drag; cursor: pointer;
  font-size: 13px; text-align: center;
  color: #04140b; background: var(--green);
  border: 1px solid rgba(0,0,0,.35); border-radius: 3px;
  box-shadow: 0 0 8px rgba(56,224,138,.5);
}
.inpa-pager-arrow:hover { filter: brightness(1.12); }
.inpa-pager-arrow:active { transform: translateY(1px); }
/* the INPA theme uses the classic bright-green softkey look on white */
html[data-theme="inpa"] .inpa-pager-arrow {
  color: #003300; background: #00d000; border-color: #007000;
  box-shadow: none; border-radius: 0;
}
/* arrow-key paging pulses the arrow so the keyboard action is visible */
.inpa-pager-arrow.flash { animation: pagerflash .25s ease-out; }
@keyframes pagerflash { from { transform: scale(1.35); } to { transform: scale(1); } }

/* INPA status F-key category bar (Digital / Analog / VANOS / ...) */
.inpa-cat-bar { display: flex; flex-wrap: wrap; gap: 6px; margin: 0 0 14px;
  max-height: 132px; overflow-y: auto; align-content: flex-start; }
.inpa-cat-btn {
  -webkit-app-region: no-drag; cursor: pointer;
  display: flex; align-items: center; gap: 8px;
  padding: 7px 12px; font-size: 12.5px;
  color: var(--ink-dim); background: transparent;
  border: 1px solid var(--line); border-radius: 4px;
}
.inpa-cat-btn:hover { color: var(--ink); border-color: var(--ink-faint); }
.inpa-cat-btn.active { color: var(--ink); border-color: var(--amber);
  background: rgba(255,176,32,.08); }
.inpa-cat-btn.disabled { opacity: .38; cursor: not-allowed; }
.inpa-cat-key { font-family: var(--mono); font-size: 10.5px; color: var(--amber); }
.inpa-cat-btn.disabled .inpa-cat-key { color: var(--ink-faint); }
html[data-theme="inpa"] .inpa-cat-btn { border-radius: 0; }
html[data-theme="inpa"] .inpa-cat-btn.active { background: #000080; color: #fff;
  border-color: #000080; }
html[data-theme="inpa"] .inpa-cat-btn.active .inpa-cat-key { color: #9fc3ff; }
html[data-theme="inpa"] .inpa-cat-key { color: #000080; }

/* sub-tabs inside a category (one per measurement block) */
.inpa-cat-split { margin-bottom: 20px; }
.inpa-cat-split .live-panel { margin-bottom: 0; }
.inpa-subtabs { display: flex; flex-wrap: wrap; gap: 4px; margin: 0 0 8px; }
.inpa-subtab {
  -webkit-app-region: no-drag; cursor: pointer;
  padding: 5px 10px; font-size: 12px; color: var(--ink-dim);
  background: transparent; border: 1px solid var(--line); border-radius: 3px;
}
.inpa-subtab:hover { color: var(--ink); }
.inpa-subtab.active { color: var(--ink); border-color: var(--cyan);
  background: rgba(79,210,255,.08); }
html[data-theme="inpa"] .inpa-subtab { border-radius: 0; }
html[data-theme="inpa"] .inpa-subtab.active { background: #000080; color: #fff;
  border-color: #000080; }

/* non-numeric: hide bar, center text */
/* no bar: the value sits left under its label, not adrift in the value column */
.gauge-cell.text-only .gauge-bar { display: none; }
.gauge-cell.text-only .gauge-track { display: none; }
.gauge-cell.text-only .gauge-min,
.gauge-cell.text-only .gauge-max { display: none; }
.gauge-cell.text-only .gauge-val {
  font-size: 16px; color: var(--ink);
  flex: none; min-width: 0; text-align: left;
}
.live-dot.stopped { background: var(--ink-faint); box-shadow: none; animation: none; }
.live-meta.rec { color: var(--red); }
.live-meta.rec::before { content: '● '; }
/* watched rows in Status list */
.job-row.watching { border-color: var(--cyan); background: rgba(79,210,255,.08); }
.job-row.watching .job-check { border-color: var(--cyan); }

/* confirmation modal */
.modal-overlay {
  position: fixed; inset: 0; z-index: 1000;
  display: grid; place-items: center;
  background: rgba(4, 7, 10, 0); backdrop-filter: blur(0px);
  transition: background .16s ease, backdrop-filter .16s ease;
}
.modal-overlay.show { background: rgba(4, 7, 10, .62); backdrop-filter: blur(3px); }
.modal {
  width: min(440px, 86vw);
  max-height: 88vh; display: flex; flex-direction: column;
  background: linear-gradient(180deg, var(--panel-2), var(--panel));
  border: 1px solid var(--line-bright); border-radius: 6px;
  box-shadow: 0 30px 70px -20px rgba(0,0,0,.85);
  padding: 24px 24px 18px; transform: translateY(10px) scale(.98); opacity: 0;
  transition: transform .18s cubic-bezier(.2,.7,.2,1), opacity .18s;
}
.modal-title, .modal-body, .modal-actions { flex: none; }
.modal-overlay.show .modal { transform: none; opacity: 1; }
.modal.danger { border-top: 2px solid var(--red); }
.modal-title { font-size: 19px; font-weight: 800; letter-spacing: -.01em; margin-bottom: 10px; }
.modal.danger .modal-title { color: #fff; }
.modal-body { font-size: 13.5px; line-height: 1.55; color: var(--ink-dim); margin-bottom: 22px; }
.modal-body b { color: var(--ink); font-weight: 700; }
.modal-body .mono { font-family: var(--mono); font-size: 12px; color: var(--amber); }
.modal-input {
  width: 100%; margin-bottom: 20px; padding: 11px 14px;
  background: var(--bg); border: 1px solid var(--line-bright); border-radius: 4px;
  color: var(--ink); font-family: var(--mono); font-size: 14px; outline: none;
}
.modal-input:focus { border-color: var(--amber); }
.modal-input-wrap { margin-bottom: 20px; }
.modal-input-wrap .modal-input { margin-bottom: 6px; }
.modal-input-hint { font-family: var(--mono); font-size: 10.5px; color: var(--ink-faint); letter-spacing: .04em; }
.modal-input.shake { animation: inpShake .32s; border-color: var(--red); }
@keyframes inpShake { 0%,100%{transform:translateX(0)} 20%,60%{transform:translateX(-5px)} 40%,80%{transform:translateX(5px)} }
.modal-body .muted { color: var(--ink-dim); }
/* multi-field job-argument dialog (built from the _ARGUMENTS schema) */
/* scroll the field list, not the whole modal, so many-arg jobs (e.g. AIF_SCHREIBEN
   with 9 fields) stay on screen with the title and Run/Cancel fixed */
.arg-fields { margin-bottom: 18px; max-height: 52vh; overflow-y: auto; padding-right: 4px; }
.arg-row { margin-bottom: 14px; }
.arg-row:last-child { margin-bottom: 0; }
.arg-label { display: block; font-size: 12.5px; font-weight: 700; color: var(--ink); margin-bottom: 6px; }
.arg-label .arg-type { font-family: var(--mono); font-size: 10.5px; font-weight: 400; color: var(--ink-faint); }
.arg-row .modal-input { margin-bottom: 5px; }
.arg-hint { font-size: 11px; color: var(--ink-faint); line-height: 1.4; }
select.modal-input { appearance: none; cursor: pointer; }
.arg-warn { font-size: 11px; color: var(--red); line-height: 1.45; margin-top: 5px;
  border-left: 2px solid var(--red); padding-left: 8px; }
.arg-warn .mono { font-family: var(--mono); color: var(--amber); }
.modal-actions { display: flex; justify-content: flex-end; gap: 10px; }
.modal-actions .btn { display: inline-flex; align-items: center; gap: 9px; }
.modal-cancel { background: var(--panel); }
.modal-key {
  font-family: var(--mono); font-size: 9px; color: var(--ink-faint);
  border: 1px solid var(--line); border-radius: 3px; padding: 2px 5px;
}
.modal-confirm.danger .modal-key, .modal-confirm.primary .modal-key { color: inherit; border-color: currentColor; opacity: .55; }

.empty {
  display: grid; place-items: center; gap: 14px; padding: 70px 20px;
  border: 1px dashed var(--line); border-radius: 4px; color: var(--ink-dim);
}
.empty-big { font-size: 22px; font-weight: 800; color: var(--green); letter-spacing: .02em; }

.loader { display: inline-block; width: 14px; height: 14px; border-radius: 50%;
  border: 2px solid var(--line-bright); border-top-color: var(--amber);
  animation: spin .7s linear infinite; }
@keyframes spin { to { transform: rotate(360deg); } }

/* INPA-style function-key bar */
.fkeybar {
  position: absolute; bottom: 0; left: 0; right: 0; height: 52px;
  display: flex; align-items: stretch; justify-content: space-between;
  padding: 7px 14px; gap: 14px;
  background: linear-gradient(180deg, #0e141a, #090d11);
  border-top: 1px solid var(--line);
}
.fkeys { display: flex; align-items: stretch; gap: 6px; flex: 1; min-width: 0; }
.fkey {
  -webkit-app-region: no-drag; cursor: pointer;
  display: flex; align-items: center; justify-content: center; gap: 6px;
  padding: 0 8px; min-width: 0; flex: 1 1 0;     /* share width evenly, shrink */
  background: var(--panel); border: 1px solid var(--line);
  border-radius: 3px; transition: all .12s; overflow: hidden;
}
.fkey:hover { border-color: var(--amber); background: var(--raised); }
.fkey:active { transform: translateY(1px); }
.fkey-num {
  font-family: var(--mono); font-weight: 700; font-size: 11px;
  color: var(--amber); background: var(--key-bg, #0c1218); border: 1px solid var(--line-bright);
  border-radius: 3px; padding: 3px 6px; min-width: 22px; text-align: center; flex: none;
}
.fkey-label {
  font-family: var(--display); font-weight: 600; font-size: 12px;
  color: var(--ink); white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  min-width: 0;
}
/* 7+ keys: drop chip min-width, tighten */
.fkeys:has(.fkey:nth-child(7)) .fkey { padding: 0 6px; gap: 4px; }
.fkeys:has(.fkey:nth-child(7)) .fkey-num { min-width: 18px; padding: 3px 4px; }
.fkeys:has(.fkey:nth-child(7)) .fkey-label { font-size: 11px; }
/* 10+ keys (the memory screen: 4 regions + 4 address steps + go-to + back):
   at an even 1/10 split every label ellipsises to nothing, so let each key take
   only the width its own label needs and stack the chip above short captions. */
.fkeys:has(.fkey:nth-child(10)) .fkey { padding: 0 4px; gap: 3px; flex: 0 1 auto; }
.fkeys:has(.fkey:nth-child(10)) .fkey-num { min-width: 16px; padding: 2px 3px; font-size: 10px; }
.fkeys:has(.fkey:nth-child(10)) .fkey-label { font-size: 10.5px; }
.fkey.back .fkey-num { color: var(--cyan); }
/* the page you are already on, for softkeys that select rather than act */
.fkey.active { border-color: var(--green); }
.fkey.active .fkey-num { color: var(--green); }
.fkey.danger:hover { border-color: var(--red); }
.fkey.primary { background: linear-gradient(180deg, rgba(255,158,44,.16), transparent); border-color: var(--amber-soft); }
.fkey.flash { animation: fkflash .35s ease; }
@keyframes fkflash { 0% { background: var(--amber); } 100% {} }

/* Fixed width, not content width: this column sits beside the flex:1 F-key row,
   so letting it grow with its text ("sent" -> "released") squeezed every key on
   each status change. Reserve the space once and ellipsize inside it. */
.fkeybar-status {
  display: flex; flex-direction: column; justify-content: center; align-items: flex-end;
  font-family: var(--mono); font-size: 10px; color: var(--ink-faint);
  gap: 2px;
  flex: 0 0 168px; width: 168px; min-width: 0; overflow: hidden;
}
.fkeybar-status > * {
  max-width: 100%; white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}

/* first-run tutorial: spotlight ring + coach-mark tip (tour-overlay rides the
   modal-overlay class so the global action keys stand down while it's up) */
.tour-overlay { background: transparent !important; backdrop-filter: none !important; }
.tour-ring {
  position: fixed; border-radius: 12px; pointer-events: none;
  border: 1px solid var(--amber);
  box-shadow: 0 0 0 9999px rgba(4, 7, 10, .74), 0 0 22px -4px var(--amber);
  transition: left .28s ease, top .28s ease, width .28s ease, height .28s ease;
}
.tour-tip {
  position: fixed; width: min(380px, calc(100vw - 24px)); padding: 16px 18px 14px;
  background: var(--panel-2); border: 1px solid var(--line-bright);
  border-radius: 12px; box-shadow: var(--shadow);
}
.tour-title { font: 700 15px var(--display); color: var(--ink); margin-bottom: 6px; }
.tour-body { font: 400 12.5px/1.55 var(--display); color: var(--ink-dim); }
/* footer stacks: dots row, then buttons; never wider than the card */
.tour-foot { margin-top: 14px; }
.tour-dots { display: flex; gap: 5px; justify-content: center; margin-bottom: 10px; }
.tour-btns { justify-content: flex-end; }
.tour-btns .tour-skip { margin-right: auto; }
.tour-btns .btn { padding: 7px 14px; font-size: 12px; }
.tour-dot { width: 6px; height: 6px; border-radius: 50%; background: var(--line-bright); }
.tour-dot.active { background: var(--amber); }
.tour-btns { display: flex; gap: 8px; }
.tour-setting { display: flex; align-items: center; justify-content: space-between; gap: 16px; }

/* "How it works" guided explainer (centered card, stepped slides) */
.hiw-card {
  position: relative; width: min(560px, 92vw);
  background: var(--panel); border: 1px solid var(--line-bright); border-radius: 12px;
  padding: 30px 30px 20px; box-shadow: var(--shadow); text-align: center;
}
.hiw-close {
  position: absolute; top: 14px; right: 14px; -webkit-app-region: no-drag; cursor: pointer;
  width: 28px; height: 28px; border-radius: 6px; border: 1px solid var(--line);
  background: transparent; color: var(--ink-dim); font-size: 12px;
}
.hiw-close:hover { color: var(--ink); border-color: var(--ink-faint); }
.hiw-icon { font-size: 40px; line-height: 1; margin-bottom: 14px; }
.hiw-title { font-size: 20px; font-weight: 800; color: var(--ink); margin-bottom: 12px; }
.hiw-body { font-size: 14px; line-height: 1.6; color: var(--ink-dim);
  max-width: 460px; margin: 0 auto 22px; text-align: left; }
.hiw-foot { display: flex; flex-direction: column; gap: 14px; }
.hiw-dots { display: flex; gap: 6px; justify-content: center; }
.hiw-dot { width: 7px; height: 7px; border-radius: 50%; background: var(--line-bright);
  -webkit-app-region: no-drag; cursor: pointer; }
.hiw-dot.active { background: var(--amber); }
.hiw-btns { display: flex; gap: 8px; justify-content: center; }
.hiw-btns .btn { padding: 8px 20px; font-size: 13px; }
.hiw-btns .hiw-back:disabled { opacity: .4; cursor: default; }

/* whole-vehicle fault scan entry at the foot of the system rail */
.sys-scan { margin-top: 10px; border-top: 1px solid var(--line); border-radius: 0 0 6px 0; padding-top: 12px; }
.sys-scan .nav-name { color: var(--amber-soft); }
.sys-scan:hover .nav-name, .sys-scan.active .nav-name { color: var(--amber); }

/* ---- wiring diagrams (WDS) ------------------------------------------------
   A tree on the left, one document on the right. The document is either a
   vector schematic (pan/zoom by viewBox) or BMW's own description HTML. */
.wiring-split {
  /* the diagram takes the window: topbar (56) + fkey bar + padding.
     A column, not .split's grid: the panes live inside .wiring-body so the
     WDS layout can stack a toolbar above them and a footer below. */
  display: flex; flex-direction: column;
  /* fill what .view leaves: its box minus its own padding. height:100% would
     resolve against the padding box and come up short. */
  height: calc(100% - 38px); min-height: 320px;
}
.wiring-nav { display: flex; flex-direction: column; min-height: 0; }
.wiring-search {
  width: 100%; box-sizing: border-box; margin-bottom: 8px;
  font-family: var(--mono); font-size: 12px; color: var(--ink);
  background: var(--panel); border: 1px solid var(--line);
  border-radius: 4px; padding: 7px 9px;
}
.wiring-search:focus { outline: none; border-color: var(--amber); }
.wiring-tree, .wiring-results { overflow-y: auto; flex: 1; min-height: 0; }
.wiring-folder, .wiring-leaf {
  display: flex; align-items: baseline; gap: 7px; width: 100%;
  text-align: left; cursor: pointer; background: none; border: none;
  color: var(--ink); font-size: 12.5px; padding: 5px 8px; line-height: 1.35;
}
.wiring-folder { color: var(--ink-dim); font-family: var(--mono); font-size: 12px; }
.wiring-folder:hover, .wiring-leaf:hover { background: rgba(127,127,127,.10); }
.wiring-caret { display: inline-block; transition: transform .12s; font-size: 9px; }
.wiring-folder.open .wiring-caret { transform: rotate(90deg); }
.wiring-leaf-name { flex: 1; }
.wiring-trail { font-family: var(--mono); font-size: 10px; color: var(--ink-faint); }
/* a dot per document kind, so a schematic reads differently from a note */
.wiring-dot {
  width: 7px; height: 7px; border-radius: 2px; flex: none;
  background: var(--ink-faint); transform: translateY(-1px);
}
.kind-schematic  .wiring-dot { background: var(--amber); }
.kind-location   .wiring-dot { background: var(--green); }
.kind-connector  .wiring-dot { background: #6ab0ff; }
.kind-pins       .wiring-dot { background: #b98cff; border-radius: 50%; }
.kind-test       .wiring-dot { background: var(--red); }
.kind-specs      .wiring-dot { background: #ffd166; border-radius: 50%; }
.wiring-empty { color: var(--ink-dim); font-size: 12px; padding: 10px 8px; }

.wiring-view { display: flex; flex-direction: column; min-height: 0; padding: 0; }
.wiring-bar {
  display: flex; align-items: baseline; gap: 12px; flex: none;
  padding: 10px 14px; border-bottom: 1px solid var(--line);
}
.wiring-title { font-size: 14px; font-weight: 700; flex: 1; }
.wiring-kind {
  font-family: var(--mono); font-size: 10px; letter-spacing: .06em;
  text-transform: uppercase; color: var(--ink-dim);
}
.wiring-fit { font-size: 11px; padding: 4px 10px; }
/* the schematic stage: white because BMW drew these on white, and the
   strokes are black -- inverting them would misread as a different diagram */
.wiring-stage {
  flex: 1; min-height: 0; overflow: hidden; background: #fff;
  cursor: grab; touch-action: none;
}
.wiring-stage.grabbing { cursor: grabbing; }
.wiring-stage svg { width: 100%; height: 100%; display: block; }
.wiring-doc {
  flex: 1; min-height: 0; overflow-y: auto; padding: 18px 22px;
  font-size: 13.5px; line-height: 1.55; max-width: 80ch;
}
.wiring-doc h1 { font-size: 18px; margin: 0 0 12px; }
.wiring-doc h2 { font-size: 15px; margin: 18px 0 8px; color: var(--amber); }
.wiring-doc h3 { font-size: 13.5px; margin: 14px 0 6px; color: var(--ink-dim); }
.wiring-doc p { margin: 0 0 10px; }
.wiring-doc table { border-collapse: collapse; margin: 10px 0; font-size: 12.5px; }
.wiring-doc td, .wiring-doc th {
  border: 1px solid var(--line); padding: 5px 9px; text-align: left;
}
.wiring-doc a { color: var(--amber); }
.sys-wiring .nav-count { color: var(--amber); }
.wiring-zoom { display: flex; gap: 6px; }

/* ---- WDS chrome (INPA layout only) ----------------------------------------
   The frame BMW's own tool wore: a grey toolbar of raised buttons, a blue
   title strip, the panes sunken into it, and a footer holding the search and
   the zoom controls. Only the frame is period; the panes inside are the same
   ones the modern layout uses. */
/* WDS filled its window, so the frame ignores .view's padding and takes the
   whole area between the topbar and the F-key bar. Negative margins cancel
   the padding rather than fighting it with viewport maths. */
.wiring-split.wds-frame {
  display: flex; flex-direction: column; gap: 0;
  background: #808080; border: none; max-width: none;
  /* fill .view exactly. It is position:absolute with fixed insets, so its
     own box is already the right size -- viewport maths would have to know
     the topbar and F-key bar heights and got them wrong, which is what let
     the page scroll. box-sizing keeps the negative margins from widening it. */
  /* Break out of .view's padding without growing past it: negative margins
     pull the edges out, and the matching extra width is taken back so the
     box still measures exactly the container. Getting this wrong is what let
     the page scroll right and down. */
  margin: -38px -44px; width: calc(100% + 88px); height: calc(100% + 76px);
  box-sizing: border-box;
}
.wiring-split.wds-frame .wiring-body {
  display: grid; grid-template-columns: 300px 1fr; gap: 0;
  flex: 1; min-height: 0; background: #808080;
}
.wiring-split:not(.wds-frame) .wiring-body {
  display: grid; grid-template-columns: 300px 1fr; gap: 18px;
  flex: 1; min-height: 0;
}
.wds-toolbar {
  display: flex; align-items: center; gap: 10px; padding: 8px 14px;
  background: #808080; flex: none;
}
/* the placeholder is part of the white pane here, not a floating card */
.wds-frame .empty {
  border: none; background: none; margin: 0; border-radius: 0;
}
.wds-nav-pair { display: flex; gap: 6px; margin-left: 26px; }
.wds-help { margin-left: auto; }
/* Win95-era raised button: light top/left, dark bottom/right */
.wds-btn {
  font-family: Arial, Helvetica, sans-serif; font-size: 13px; font-weight: 700;
  color: #000; background: #c0c0c0; cursor: pointer;
  padding: 7px 18px; border: 2px solid;
  border-color: #ffffff #404040 #404040 #ffffff;
  box-shadow: inset 1px 1px 0 #dfdfdf, inset -1px -1px 0 #808080;
}
.wds-btn:active {
  border-color: #404040 #ffffff #ffffff #404040;
  box-shadow: inset 1px 1px 0 #808080;
}
.wds-btn-sq { padding: 7px 12px; min-width: 40px; }
.wds-titlebar {
  display: flex; justify-content: space-between; align-items: center;
  background: #808080; color: #4da6ff; flex: none;
  font-family: Arial, Helvetica, sans-serif; font-size: 17px; font-weight: 700;
  padding: 2px 14px 8px;
}
.wds-version { font-size: 15px; }
/* the panes: white, sunken, separated by the grey frame */
.wds-frame .wiring-nav, .wds-frame .wiring-view {
  background: #fff; border: 2px solid;
  border-color: #404040 #ffffff #ffffff #404040;
  padding: 0; min-height: 0;
}
.wds-frame .wiring-nav { margin-right: 4px; }
.wds-frame .wiring-tree { padding: 6px 4px; }
.wds-frame .wiring-folder, .wds-frame .wiring-leaf {
  color: #000; font-family: Arial, Helvetica, sans-serif; font-size: 12.5px;
}
.wds-frame .wiring-folder { color: #333; }
.wds-frame .wiring-folder:hover, .wds-frame .wiring-leaf:hover { background: #cde0ff; }
.wds-frame .wiring-trail { color: #666; }
.wds-frame .wiring-bar { border-bottom: 1px solid #c0c0c0; background: #f0f0f0; }
.wds-frame .wiring-title { color: #000; }
.wds-frame .wiring-kind { color: #555; }
.wds-frame .wiring-doc { color: #000; }
.wds-frame .wiring-doc h2 { color: #0066cc; }
.wds-frame .wiring-doc h3 { color: #333; }
.wds-frame .empty, .wds-frame .empty div { color: #333; }
.wds-footer {
  display: flex; align-items: center; gap: 10px; padding: 9px 14px;
  background: #808080; flex: none;
}
.wds-searchlabel {
  font-family: Arial, Helvetica, sans-serif; font-size: 13px;
  font-weight: 700; color: #000;
}
.wds-input {
  font-family: Arial, Helvetica, sans-serif; font-size: 13px; color: #000;
  background: #fff; padding: 5px 7px; width: 210px;
  border: 2px solid; border-color: #404040 #ffffff #ffffff #404040;
}
.wds-input:focus { outline: 1px solid #0066cc; }
.wds-zoomgroup { display: flex; gap: 6px; margin-left: auto; }
.wds-zoomgroup .wds-btn { font-size: 15px; line-height: 1; }
.wds-help-doc { max-width: 70ch; }
.wds-help-doc ul { margin: 0 0 12px; padding-left: 22px; }
.wds-help-doc li { margin-bottom: 5px; }
.wds-help-doc .wiring-dot { display: inline-block; margin-right: 3px; }

/* WDS pane buttons: hand the window to the tree, the document, or both.
   A schematic is very wide, so "document only" is the one that earns its
   place; the choice persists across documents and sessions. */
.wds-panegroup { display: flex; gap: 6px; margin-left: 26px; }
.wds-pane { display: inline-flex; align-items: center; justify-content: center; }
.wds-pane.active {
  border-color: #404040 #ffffff #ffffff #404040;
  box-shadow: inset 1px 1px 0 #808080;
  background: #b0b8c8;
}
/* min-width:0 on the panes: a grid item's automatic minimum is its content,
   which on a hidden-sibling layout leaves the surviving pane at its border
   width instead of the track's. */
.wiring-nav, .wiring-view { min-width: 0; }
/* ONE column when a pane is hidden, not a zero-width one: display:none takes
   the hidden pane out of the grid entirely, so the survivor would otherwise
   slide into the collapsed first track and render at its border width. */
.wiring-body[data-pane="doc"] { grid-template-columns: 1fr !important; }
.wiring-body[data-pane="doc"] .wiring-nav { display: none; }
.wiring-body[data-pane="tree"] { grid-template-columns: 1fr !important; }
.wiring-body[data-pane="tree"] .wiring-view { display: none; }
.wiring-body[data-pane="tree"] .wiring-nav { margin-right: 0; }

/* the WDS screen supplies its own footer, so the app's F-key bar steps
   aside and the frame takes the height it leaves */
body.wds-nofkeys .fkeybar { display: none; }
body.wds-nofkeys .view { inset: 56px 0 0 0; }
/* This screen sizes itself to the window, so the page must not scroll: the
   panes scroll their own contents instead. */
.view:has(.wiring-split) { overflow: hidden !important; }
/* .view's inset already grew when the F-key bar went away, so the frame
   needs no separate height here. */

/* ---- print ----------------------------------------------------------------
   On screen this is a tool: toolbar, tree, footer, status bars. On paper the
   document is the only thing wanted, as large as the sheet allows. */
@media print {
  @page { size: landscape; margin: 12mm; }
  html, body {
    background: #fff !important; color: #000 !important;
    height: auto; overflow: visible;
  }
  /* every piece of app chrome */
  .topbar, .fkeybar, .grain, .splash, .modal-overlay,
  .wds-toolbar, .wds-titlebar, .wds-footer, .wiring-nav,
  .screen-head, .crumbs, .breadcrumbs { display: none !important; }

  /* the view stops being a scrolling pane and becomes the page */
  .view {
    position: static !important; inset: auto !important;
    padding: 0 !important; overflow: visible !important;
  }
  .wiring-split, .wiring-split.wds-frame {
    display: block !important; height: auto !important; margin: 0 !important;
    border: none !important; background: #fff !important;
  }
  .wiring-body { display: block !important; }
  .wiring-view {
    display: block !important; border: none !important;
    background: #fff !important; overflow: visible !important;
  }
  /* the diagram fills the sheet; SVG scales, so this is lossless */
  .wiring-stage {
    height: 16cm !important; overflow: visible !important;
    background: #fff !important; border: 1px solid #999;
  }
  .wiring-stage svg { width: 100% !important; height: 100% !important; }
  /* the on-screen title bar is replaced by the print header */
  .wiring-bar { display: none !important; }
  .print-head { display: block !important; margin-bottom: 6mm; }
  .print-title {
    font-family: Arial, Helvetica, sans-serif; font-size: 15pt;
    font-weight: 700; color: #000; margin-bottom: 2mm;
  }
  .print-meta {
    display: flex; gap: 6mm; font-family: Arial, Helvetica, sans-serif;
    font-size: 9pt; color: #444;
    border-bottom: 1px solid #999; padding-bottom: 2mm;
  }
  /* a description prints as a document, not a diagram */
  .wiring-doc {
    max-width: none !important; overflow: visible !important;
    padding: 0 !important; color: #000 !important; font-size: 11pt;
  }
  .wiring-doc h1, .wiring-doc h2, .wiring-doc h3 { color: #000 !important; }
  .wiring-doc h2 { page-break-after: avoid; }
  .wiring-doc table, .wiring-doc tr { page-break-inside: avoid; }
}
/* the header exists only for printing */
.print-head { display: none; }

/* Tooltips that appear at once. The browser's own take about a second and a
   half, which is long enough to give up on; these use the same title text so
   nothing is duplicated and the native one still serves as a fallback. */
[data-tip] { position: relative; }
[data-tip]::after {
  content: attr(data-tip);
  position: absolute; z-index: 60; pointer-events: none;
  bottom: calc(100% + 7px); left: 50%; transform: translateX(-50%);
  white-space: nowrap; font-family: var(--mono); font-size: 11px;
  font-weight: 400; letter-spacing: .01em; line-height: 1.3;
  color: #f2f5f8; background: #1a2129; border: 1px solid #39424d;
  border-radius: 4px; padding: 5px 9px;
  box-shadow: 0 4px 14px rgba(0, 0, 0, .45);
  opacity: 0; transition: opacity .1s .05s;
}
[data-tip]:hover::after, [data-tip]:focus-visible::after { opacity: 1; }
/* a tip that would run off the left or right edge anchors to that edge */
[data-tip].tip-left::after { left: 0; transform: none; }
[data-tip].tip-right::after { left: auto; right: 0; transform: none; }
/* below the control instead, for anything on the top row */
[data-tip].tip-below::after { bottom: auto; top: calc(100% + 7px); }

/* modern-layout wiring toolbar: the same controls the WDS frame carries,
   in this app's own dress rather than 1998's */
.wiring-toolbar {
  display: flex; align-items: center; gap: 8px; flex: none;
  padding: 0 0 12px; margin-bottom: 12px;
  border-bottom: 1px solid var(--line);
}
.wiring-toolbar .wiring-search { width: 260px; margin: 0; flex: none; }
.wiring-tbtn {
  font-size: 12px; padding: 6px 12px; line-height: 1;
  display: inline-flex; align-items: center; justify-content: center;
}
.wiring-tsep { width: 1px; height: 20px; background: var(--line); margin: 0 2px; }
.wiring-tspacer { flex: 1; }
.wiring-panegroup { display: flex; gap: 4px; margin-left: 4px; }
.wiring-panegroup .wiring-tbtn { padding: 6px 9px; }
.wiring-tbtn.wds-pane.active {
  border-color: var(--amber); color: var(--amber);
  background: rgba(255, 158, 44, .12);
}
/* the panes take what the toolbar leaves */
.wiring-split:not(.wds-frame) .wiring-body { min-height: 0; }

/* an inline checkbox beside a setting's control (the offline copy's
   "wiring diagrams" opt-out) */
.setting-check {
  display: inline-flex; align-items: center; gap: 7px; cursor: pointer;
  margin-left: 12px; font-size: 12.5px; color: var(--ink-dim);
  white-space: nowrap;
}
.setting-check input { accent-color: var(--amber); cursor: pointer; margin: 0; }
.setting-check:hover { color: var(--ink); }
.inpa-settings .setting-check { font-family: var(--mono); font-size: 12px; }

/* several controls in one settings cell (the offline copy's picker, its
   wiring checkbox and its button), so a row stays one row */
.setting-controls {
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap;
  justify-content: flex-end;
}
.setting-controls .combo { flex: none; }
.setting-controls .setting-check { margin-left: 0; }
.inpa-settings .setting-controls { justify-content: flex-end; }

/* is the THOR relay up? watched live while Settings is open */
.bridge-state {
  font-family: var(--mono); font-size: 11px; letter-spacing: .04em;
  padding: 5px 10px; border-radius: 4px; border: 1px solid var(--line);
  color: var(--ink-dim); white-space: nowrap;
}
.bridge-state.up { color: var(--green); border-color: var(--green); }
.bridge-state.down { color: var(--ink-faint); }

/* WDS component-location photos: BMW drew them small, so let them be their
   own size rather than stretched, but never wider than the page */
.wiring-doc img { max-width: 100%; height: auto; display: block; margin: 10px 0; }
/* a photograph on its way from the CDN: hold the space, say something is
   coming, and never flash a broken-image box */
.wiring-img-loading {
  min-width: 316px; min-height: 237px; background: rgba(127,127,127,.10);
  border: 1px dashed var(--line);
}

/* waiting for wiring data: the chassis probe on the picker, the archive
   download on a car. Both are seconds on a hosted site. */
.wiring-loading {
  display: flex; align-items: center; gap: 10px; padding: 18px 8px;
  color: var(--ink-dim); font-size: 13px;
}
.wiring-spinner {
  width: 13px; height: 13px; flex: none; border-radius: 50%;
  border: 2px solid var(--line-bright); border-top-color: var(--amber);
  animation: wiring-spin .7s linear infinite;
}
@keyframes wiring-spin { to { transform: rotate(360deg); } }
/* the WDS frame keeps its own palette */
.wds-frame .wiring-loading { color: #333; }
.wds-frame .wiring-spinner { border-color: #b0b0b0; border-top-color: #000080; }
