/* ==========================================================================
   Backed Up Loads Visualizer · Cape Fear Energy Systems
   Tokens and values transcribed from the Claude Design doc
   "Backed Up Loads Visualizer.dc.html".
   ========================================================================== */

/* --- tokens --------------------------------------------------------------- */

:root {
  /* neutrals */
  --bg:            #f2f1ec;
  --surface:       #fbfaf7;
  --card:          #ffffff;
  --field:         #fdfdfc;
  --field-soft:    #f8f7f4;
  --track:         #eceae4;
  --ink:           #2b2b2b;
  --ink-2:         #666666;
  --ink-3:         #8b8b85;
  --ink-4:         #9a9a93;
  --ink-5:         #a3a39c;

  /* identity green */
  --green:         #71A62B;
  --green-hover:   #66992a;
  --green-link:    #5d8c22;
  --green-deep:    #3f6b16;
  --green-mid:     #7f9c5c;
  --green-soft:    #8fae65;
  --green-light:   #9ec471;
  --green-field:   #fcfdf9;

  /* advisory ramp, never red, per the design's "over limit is advisory" note */
  --yellow:        #FFDB05;
  --orange:        #F49C20;
  --orange-ink:    #a06a12;
  --warn-ink:      #8a5b12;

  /* lines */
  --line:          rgba(0, 0, 0, .07);
  --line-soft:     rgba(0, 0, 0, .05);
  --line-mid:      rgba(0, 0, 0, .09);
  --line-strong:   rgba(0, 0, 0, .12);
  --line-green:    rgba(113, 166, 43, .3);
  --line-green-2:  rgba(113, 166, 43, .28);
  --line-green-3:  rgba(113, 166, 43, .25);

  /* enclosure faces */
  --face-main:     linear-gradient(180deg, #fdfdfb, #f5f4f0);
  --face-backup:   linear-gradient(180deg, #fbfdf7, #f1f6e8);

  /* the design doc exposed this as a `panelTilt` control (0 to 8 deg, default 3.5) */
  --tilt:          3.5deg;

  /* One typeface across the whole app. --mono is kept as a token because it is
     woven through the `font:` shorthands; it now names the same family, and the
     figure alignment the monospace used to give comes from tabular-nums below. */
  --font:          'Montserrat', system-ui, -apple-system, sans-serif;
  --mono:          'Montserrat', system-ui, -apple-system, sans-serif;
}

/* --- base ----------------------------------------------------------------- */

* { box-sizing: border-box; }

/* The `hidden` attribute must win over any element that sets its own display.
   Without this, .scan (display: flex) stays laid out as a full-viewport overlay
   and swallows every click on the page underneath it. */
[hidden] { display: none !important; }

body {
  margin: 0;
  background: var(--bg);
  color: var(--ink);
  font-family: var(--font);
  font-variant-numeric: tabular-nums;
  -webkit-font-smoothing: antialiased;
  text-wrap: pretty;
}

a { color: var(--green-link); text-decoration: none; }
a:hover { color: var(--green); text-decoration: underline; }

h1, h2, h3 { margin: 0; font-weight: 600; }

button { font-family: inherit; }

:focus-visible {
  outline: 2px solid var(--green);
  outline-offset: 2px;
}

.sr-only {
  position: absolute; width: 1px; height: 1px;
  padding: 0; margin: -1px; overflow: hidden;
  clip: rect(0 0 0 0); white-space: nowrap; border: 0;
}

/* --- topbar --------------------------------------------------------------- */

.topbar {
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
  gap: 20px;
  padding: 14px 24px;
  background: var(--card);
  border-bottom: 1px solid var(--line);
}

/* The outer columns are equal, so whatever sits in the middle is centred on
   the bar rather than on whatever is left over after the sides. */
.topbar__left  { justify-self: start; }
.topbar__right { justify-self: end; grid-column: 3; }

.topbar__left,
.topbar__right { display: flex; align-items: center; gap: 14px; min-width: 0; }

.topbar .steps { justify-self: center; grid-column: 2; }

.topbar__job   { font: 600 13.5px/1.2 var(--font); color: var(--ink); }
.topbar__addr  { font: 500 12px/1.2 var(--mono); color: var(--ink-4); }
.topbar__user  { font: 500 11.5px/1 var(--font); color: var(--ink-4); }

.topbar__back {
  border: none; background: none; padding: 0;
  cursor: pointer;
  font: 600 12.5px/1 var(--font);
  color: var(--ink-4);
  transition: color .15s;
}
.topbar__back:hover { color: var(--green-link); }

.steps {
  display: flex;
  gap: 5px;
  padding: 3px;
  background: #f4f4f1;
  border-radius: 9px;
}
.steps button {
  padding: 6px 11px;
  border: none;
  border-radius: 7px;
  background: none;
  cursor: pointer;
  font: 500 11.5px/1 var(--font);
  color: var(--ink-4);
  transition: color .18s ease;
}
.steps button:hover { color: var(--ink-2); }
.steps button[aria-current="step"] {
  background: #fff;
  box-shadow: 0 1px 2px rgba(0, 0, 0, .1);
  font-weight: 600;
  color: var(--ink);
}

/* homeowner chrome: surface 1a's own header */
.topbar--homeowner { padding: 20px 30px 18px; }
.topbar__center { grid-column: 2; justify-self: center; min-width: 0; }
.topbar--homeowner .topbar__title { font: 700 17px/1.2 var(--font); color: var(--ink); }

.linkbtn {
  border: none; background: none; padding: 0;
  cursor: pointer;
  font: 600 11.5px/1 var(--font);
  color: var(--green-link);
}
.linkbtn:hover { color: var(--green); text-decoration: underline; }

/* --- layout --------------------------------------------------------------- */

.view { padding: 22px 24px 48px; }
.view > * { animation: viewIn .32s cubic-bezier(.2, .9, .3, 1); }

/* Grows with the window instead of sitting in a 1180px column with a third of
   a wide screen empty on either side. The cap keeps a line of text from running
   the full width of an ultrawide, and the circuits table, which needs 830px of
   its own, stops having to scroll its last column out of sight. */
.sheet {
  width: 100%;
  max-width: 1760px;
  margin: 0 auto;
  background: var(--surface);
  border: 1px solid rgba(0, 0, 0, .08);
  border-radius: 16px;
  box-shadow: 0 1px 3px rgba(0, 0, 0, .06);
  overflow: hidden;
}
.sheet__body {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 340px;
  gap: 24px;
  padding: 22px 24px 26px;
}
.sheet__main { min-width: 0; display: flex; flex-direction: column; gap: 18px; }
.sheet__side {
  display: flex; flex-direction: column; gap: 14px;
  position: sticky; top: 20px; align-self: start;
}

.block {
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: 14px;
  padding: 16px 18px;
}
.block__title {
  font: 600 11px/1 var(--font);
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ink-5);
  margin-bottom: 14px;
}

/* --- controls ------------------------------------------------------------- */

.field { display: flex; flex-direction: column; gap: 6px; min-width: 0; }
.field__label {
  font: 500 10.5px/1 var(--font);
  letter-spacing: .05em;
  text-transform: uppercase;
  color: var(--ink-5);
}
.field--backup .field__label { color: var(--green-soft); }

.input,
.select {
  font: 500 13px/1 var(--font);
  color: var(--ink);
  padding: 10px 11px;
  border: 1px solid var(--line-strong);
  border-radius: 9px;
  background: var(--field);
  width: 100%;
  min-width: 0;
}
.select { cursor: pointer; }
.input--num { font-family: var(--mono); text-align: right; }
.input:focus, .select:focus { outline: none; border-color: var(--green); background: #fff; }
.field--backup .input { border-color: rgba(113, 166, 43, .35); background: var(--green-field); }

.btn {
  cursor: pointer;
  padding: 13px 18px;
  border-radius: 11px;
  border: 1px solid transparent;
  font: 600 13.5px/1 var(--font);
  transition: background .18s ease, border-color .18s ease, transform .18s ease, box-shadow .18s ease;
}
.btn--primary {
  border: none;
  background: var(--green);
  color: #fff;
  box-shadow: 0 5px 14px -6px rgba(64, 96, 20, .7);
}
.btn--primary:hover { background: var(--green-hover); }
.btn--ghost {
  background: #fff;
  color: var(--ink-2);
  border-color: rgba(0, 0, 0, .14);
}
.btn--ghost:hover { border-color: rgba(0, 0, 0, .3); }
.btn--block { width: 100%; }
.btn[disabled] { opacity: .55; cursor: default; }
.btn:active:not([disabled]) { transform: translateY(1px); }

.btn--submit {
  padding: 15px 30px;
  border-radius: 13px;
  font-size: 15px;
}
.btn--submit:hover:not([disabled]) {
  transform: translateY(-1px);
  box-shadow: 0 10px 22px -8px rgba(64, 96, 20, .75);
}
.btn--submit:active:not([disabled]) { transform: translateY(1px); }

/* --- meters --------------------------------------------------------------- */

.meter { position: relative; }
.meter__track {
  position: relative;
  height: 20px;
  border-radius: 999px;
  background: var(--track);
  box-shadow: inset 0 2px 4px rgba(0, 0, 0, .13), inset 0 -1px 0 rgba(255, 255, 255, .7);
  overflow: hidden;
}
.meter__fill {
  position: absolute; inset: 0;
  border-radius: 999px;
  background: linear-gradient(90deg, var(--green) 0%, var(--green) 62%, var(--yellow) 84%, var(--orange) 100%);
  transition: clip-path .45s cubic-bezier(.22, .9, .28, 1);
}
.meter__shed {
  position: absolute; inset: 0;
  border-radius: 999px;
  background: repeating-linear-gradient(
    135deg,
    rgba(154, 154, 147, .55) 0 5px,
    rgba(154, 154, 147, .22) 5px 10px
  );
  transition: clip-path .45s cubic-bezier(.22, .9, .28, 1);
}
.meter__gloss {
  position: absolute; inset: 0;
  border-radius: 999px;
  pointer-events: none;
  background: linear-gradient(180deg, rgba(255, 255, 255, .4), rgba(255, 255, 255, 0) 52%, rgba(0, 0, 0, .06));
}
.meter__note {
  margin: 10px 0 0;
  font: 500 12.5px/1.5 var(--font);
  color: var(--warn-ink);
  animation: warnIn .3s ease-out;
}
.meter__note--soft { color: var(--ink-4); font-weight: 400; }

/* the installer meters run the track out to 1.4× the limit so the fill can
   visibly cross into the advisory band instead of pinning at full */
.meter--demand .meter__track { height: 12px; box-shadow: inset 0 1px 3px rgba(0, 0, 0, .13); }
.meter--demand .meter__fill {
  background: linear-gradient(90deg, var(--green) 0%, var(--green) 48%, var(--yellow) 70%, var(--orange) 84%, var(--orange) 100%);
}
.meter--demand-lg .meter__track { height: 14px; box-shadow: inset 0 2px 4px rgba(0, 0, 0, .13); }

.bar { margin-bottom: 12px; }
.bar__head {
  display: flex; justify-content: space-between;
  font: 500 11px/1 var(--mono);
  color: var(--ink-4);
  margin-bottom: 5px;
}
.bar__track {
  height: 10px;
  border-radius: 5px;
  background: var(--track);
  box-shadow: inset 0 1px 2px rgba(0, 0, 0, .12);
  overflow: hidden;
}
.bar__fill {
  height: 100%;
  background: linear-gradient(180deg, #9c9c95, var(--ink-2));
  transition: width .5s cubic-bezier(.2, .85, .25, 1);
}
.bar--backup .bar__head { color: var(--green-mid); }
.bar--backup .bar__fill { background: linear-gradient(180deg, var(--green-light), var(--green)); }
.bar--over .bar__fill { background: linear-gradient(180deg, var(--yellow), var(--orange)); }

.bars3d { perspective: 900px; display: flex; flex-direction: column; }
.bars3d .bar { transform-style: preserve-3d; }
.bars3d .bar:first-child { transform: rotateY(4deg); }
.bars3d .bar--backup { transform: rotateY(-4deg); }

.note {
  margin: 10px 0 0;
  font: 400 11.5px/1.45 var(--font);
  color: var(--ink-4);
}
.note--warn { color: var(--warn-ink); font-weight: 500; }
/* Most notes stay silent until they have something to say. */
.note:empty { display: none; }

/* --- step 1: job setup ---------------------------------------------------- */

.jobspecs {
  display: grid;
  grid-template-columns: 110px minmax(0, 1fr) 170px;
  gap: 10px;
}
.jobspecs .field--wide { grid-column: 1 / -1; }

.panelspecs { display: flex; flex-direction: column; gap: 16px; }
.panelspecs__col { display: flex; flex-direction: column; gap: 10px; }
.panelspecs__col--sub { padding-left: 14px; border-left: 2px solid var(--line); }
.panelspecs__legend {
  display: flex; align-items: center; gap: 8px;
  font: 600 12.5px/1 var(--font); color: var(--ink-2);
}
.panelspecs__legend--backup { color: var(--green-deep); }
.panelspecs__legend .rowdel { opacity: 0; margin-left: auto; }
.panelspecs__col:hover .rowdel,
.panelspecs__legend .rowdel:focus-visible { opacity: 1; }
.panelspecs__row { display: grid; grid-template-columns: minmax(0, 1fr) 76px 76px; gap: 8px; align-items: end; }
.panelspecs__row--sub { grid-template-columns: minmax(0, 1fr) 70px 70px 132px 74px; }

.tiles { display: grid; grid-template-columns: repeat(2, 1fr); gap: 10px; margin-top: 12px; }
.tile { padding: 11px 12px; border-radius: 10px; background: #f6f5f2; }
.tile__label {
  font: 500 10.5px/1 var(--font);
  letter-spacing: .05em;
  text-transform: uppercase;
  color: var(--ink-5);
}
.tile__value { margin-top: 6px; font: 500 17px/1 var(--mono); color: var(--ink); }

.tablehead {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: 12px; margin-bottom: 12px;
}
.tablehead h3 { font: 600 13.5px/1 var(--font); color: var(--ink); }
.tablehead span { font: 500 11.5px/1 var(--mono); color: var(--ink-4); }

.batteryrow { display: grid; grid-template-columns: minmax(0, 1fr) 116px; gap: 10px; }

.tablewrap { overflow-x: auto; }
.circuits { min-width: 830px; }
.circuits__head,
.circuits__row {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 80px 64px 78px 86px 132px 74px 28px;
  gap: 10px;
  align-items: center;
}
.circuits__head {
  padding: 0 4px 8px;
  border-bottom: 1px solid rgba(0, 0, 0, .08);
  font: 600 10.5px/1 var(--font);
  letter-spacing: .05em;
  text-transform: uppercase;
  color: var(--ink-5);
}
.circuits__head .num { text-align: right; }
.circuits__row {
  padding: 7px 4px;
  border-bottom: 1px solid var(--line-soft);
}
.circuits .input,
.circuits .select { padding: 8px 9px; font-size: 13px; }
.circuits__row .input {
  border-color: transparent;
  background: var(--field-soft);
}
.circuits__row .select {
  font: 500 12.5px/1 var(--mono);
  border-color: transparent;
  background: var(--field-soft);
  padding: 8px 6px;
}
.circuits__row .select--panel {
  font-family: var(--font);
  border-color: rgba(0, 0, 0, .1);
  background: #fff;
  padding: 8px;
}
.circuits__row .input:disabled {
  background: transparent;
  color: var(--ink-5);
  cursor: default;
}

.switch {
  justify-self: start;
  width: 36px; height: 20px;
  padding: 2px;
  border: none;
  border-radius: 999px;
  background: #dedcd5;
  cursor: pointer;
  display: flex; align-items: center;
  transition: background .22s ease;
}
.switch::after {
  content: "";
  width: 16px; height: 16px;
  border-radius: 50%;
  background: #fff;
  box-shadow: 0 1px 2px rgba(0, 0, 0, .28);
  transition: transform .22s cubic-bezier(.3, 1.1, .35, 1);
}
.switch[aria-pressed="true"] { background: var(--orange); }
.switch[aria-pressed="true"]::after { transform: translateX(16px); }

.rowdel {
  border: none; background: none;
  cursor: pointer;
  padding: 4px;
  border-radius: 6px;
  font: 500 15px/1 var(--font);
  color: var(--ink-5);
  opacity: 0;
  transition: opacity .15s ease, color .15s ease;
}
.circuits__row:hover .rowdel,
.rowdel:focus-visible { opacity: 1; }
.rowdel:hover { color: var(--orange-ink); }

.addrow {
  margin-top: 12px;
  padding: 9px 14px;
  border: 1px dashed rgba(0, 0, 0, .2);
  border-radius: 9px;
  background: none;
  cursor: pointer;
  font: 600 12.5px/1 var(--font);
  color: var(--ink-2);
  transition: border-color .2s ease, color .2s ease;
}
.addrow:hover { border-color: var(--green); color: var(--green-deep); }

.sidelabel {
  display: flex; justify-content: space-between; align-items: baseline;
  font: 500 12px/1 var(--font); color: var(--ink-2);
}

.linkout {
  display: flex; align-items: center; gap: 8px;
  padding: 10px 11px;
  border: 1px solid var(--line-green);
  border-radius: 10px;
  background: var(--green-field);
  animation: warnIn .3s ease-out;
}
.linkout code {
  flex: 1; min-width: 0;
  font: 500 11px/1.3 var(--mono);
  color: var(--green-deep);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}

/* --- step 2: homeowner picks ---------------------------------------------- */

.picks { padding: 26px 30px 4px; }
.picks__meter {
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: 18px;
  padding: 20px 22px 18px;
  box-shadow: 0 1px 2px rgba(0, 0, 0, .04);
}
.picks__meter h2 {
  font: 600 12px/1 var(--font);
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--ink-4);
  margin-bottom: 16px;
}

.stage {
  perspective: 1900px;
  perspective-origin: 50% 40%;
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 30px;
  align-items: start;
  padding: 24px 30px 30px;
}

.panel { position: relative; transform-style: preserve-3d; z-index: 1; }
.panel--backup { z-index: 2; }
.panel.is-source { z-index: 5; }

/* The enclosure keeps its tilt for the whole drag. Moving it in Z on hover
   shifted every row underneath the pointer, which made the drop target jump. */
.panel__face {
  transform: rotateY(var(--tilt));
  transform-style: preserve-3d;
  background: var(--face-main);
  border: 1px solid var(--line-mid);
  border-radius: 22px;
  padding: 18px 18px 14px;
  box-shadow: 0 2px 3px rgba(0, 0, 0, .04), 0 30px 55px -34px rgba(0, 0, 0, .5);
  min-height: 640px;
  display: flex; flex-direction: column;
  transition: box-shadow .35s ease, border-color .35s ease;
}
.panel--backup .panel__face {
  transform: rotateY(calc(-1 * var(--tilt)));
  background: var(--face-backup);
  border-color: var(--line-green);
  box-shadow: 0 2px 3px rgba(0, 0, 0, .04), 0 30px 55px -34px rgba(64, 96, 20, .55);
}
.panel.is-over .panel__face {
  box-shadow: 0 2px 3px rgba(0, 0, 0, .04), 0 38px 66px -34px rgba(0, 0, 0, .55);
}
.panel--backup.is-over .panel__face {
  box-shadow: 0 2px 3px rgba(0, 0, 0, .04), 0 38px 66px -34px rgba(64, 96, 20, .6);
}

.panel__head {
  padding: 4px 4px 14px;
  border-bottom: 1px solid var(--line);
  text-align: center;
}
.panel__head h3 { font: 600 15.5px/1.3 var(--font); color: var(--ink-2); }
.panel--backup .panel__head { border-color: var(--line-green-3); }
.panel--backup .panel__head h3 { color: var(--green-deep); }

.panel__list {
  display: flex; flex-direction: column; gap: 10px;
  flex: 1; margin-top: 12px;
}

.panel__ring {
  position: absolute; inset: -7px;
  border: 2px solid rgba(102, 102, 102, .4);
  border-radius: 27px;
  pointer-events: none;
  animation: ringIn .2s ease-out;
  display: none;
}
.panel--backup .panel__ring {
  border-color: rgba(113, 166, 43, .65);
  box-shadow: 0 0 0 6px rgba(113, 166, 43, .09);
}
.panel.is-over .panel__ring { display: block; }

/* The row, not the card inside it, is the grab handle and the focus target:
   inside the tilted enclosure the browser hit-tests the row reliably and the
   card only about half the time. */
.slot {
  position: relative;
  touch-action: none;
  cursor: grab;
  border-radius: 14px;
}
.slot:active { cursor: grabbing; }
.slot:focus { outline: none; }
.slot:focus-visible { outline: 2px solid var(--green); outline-offset: 3px; }

/* Placeholder left behind while its card is in flight. */
.slot.is-source {
  border: 1.5px dashed rgba(102, 102, 102, .4);
  background: rgba(102, 102, 102, .045);
  cursor: grabbing;
}
.slot.is-source--backup {
  border-color: rgba(113, 166, 43, .75);
  background: rgba(113, 166, 43, .09);
}

.card {
  position: relative;
  display: flex; align-items: center; gap: 12px;
  height: 60px;
  padding: 0 17px;
  border-radius: 14px;
  background: #fff;
  border: 1px solid rgba(0, 0, 0, .08);
  box-shadow: 0 1px 2px rgba(0, 0, 0, .05);
  transform-style: preserve-3d;
  transition: border-color .2s ease, box-shadow .2s ease;
}
.slot:hover .card,
.slot:focus-visible .card {
  border-color: rgba(0, 0, 0, .16);
  box-shadow: 0 8px 18px -12px rgba(0, 0, 0, .4);
}
.slot.is-source .card { display: none; }

.panel--backup .card { border-color: var(--line-green-2); box-shadow: 0 1px 2px rgba(64, 96, 20, .07); }
.panel--backup .slot:hover .card,
.panel--backup .slot:focus-visible .card {
  border-color: rgba(113, 166, 43, .55);
  box-shadow: 0 8px 18px -12px rgba(64, 96, 20, .45);
}

/* Lifted: re-parented to <body> so it is measured against the viewport and
   tracks the pointer exactly, outside the enclosure's perspective. */
.card.is-dragging {
  position: fixed;
  margin: 0;
  z-index: 1000;
  pointer-events: none;
  transition: box-shadow .2s ease;
  box-shadow: 0 20px 44px -14px rgba(0, 0, 0, .38), 0 2px 8px rgba(0, 0, 0, .1);
  will-change: transform;
}
.card.is-settling { z-index: 20; will-change: transform; }

.card__body { flex: 1; min-width: 0; }
.card__name { display: block; font: 600 15px/1.25 var(--font); color: var(--ink); }
.card__meta { display: flex; align-items: center; gap: 8px; margin-top: 4px; }
.card__meta:empty { display: none; }

.heavy {
  display: inline-flex; align-items: center; gap: 4px;
  padding: 3px 7px 3px 5px;
  border-radius: 6px;
  background: rgba(244, 156, 32, .13);
  font: 600 10.5px/1 var(--font);
  letter-spacing: .03em;
  color: var(--orange-ink);
}

.empty {
  display: flex; align-items: center; justify-content: center;
  height: 150px;
  padding: 0 24px;
  border-radius: 16px;
  border: 1.5px dashed rgba(113, 166, 43, .5);
  background: rgba(113, 166, 43, .05);
  font: 500 13px/1.5 var(--font);
  color: var(--green-mid);
  text-align: center;
  animation: fadeIn .3s ease-out;
}
.stage.is-dragging .empty { display: none; }

.picks__foot {
  display: flex; align-items: center; justify-content: space-between;
  gap: 24px; flex-wrap: wrap;
  padding: 20px 30px 26px;
  border-top: 1px solid var(--line);
  background: #fff;
}

.save { font: 500 12px/1 var(--font); color: var(--ink-4); }
.save.is-saving { animation: breathe 1.1s ease-in-out infinite; }

/* phone layout: the same surface, drag replaced by tap */
.mobile { padding: 18px 16px 4px; display: flex; flex-direction: column; gap: 14px; }

.tabs {
  position: relative;
  display: grid; grid-template-columns: 1fr 1fr;
  padding: 3px;
  border-radius: 11px;
  background: #f1f0ec;
}
.tabs__pill {
  position: absolute; top: 3px; bottom: 3px; left: 3px;
  width: calc(50% - 3px);
  border-radius: 9px;
  background: #fff;
  box-shadow: 0 1px 3px rgba(0, 0, 0, .12);
  transition: transform .34s cubic-bezier(.3, 1.1, .35, 1);
}
.tabs button {
  position: relative;
  border: none; background: none;
  cursor: pointer;
  padding: 9px 0;
  font: 600 13px/1 var(--font);
  color: var(--ink-4);
  transition: color .2s ease;
}
.tabs button[aria-selected="true"] { color: var(--ink); }
.tabs button[aria-selected="true"][data-tab="backup"] { color: var(--green-deep); }

.mlist { display: flex; flex-direction: column; gap: 9px; }
.mcard {
  display: flex; align-items: center; gap: 11px;
  padding: 12px 12px 12px 14px;
  border-radius: 14px;
  background: #fff;
  border: 1px solid rgba(0, 0, 0, .08);
  box-shadow: 0 1px 2px rgba(0, 0, 0, .04);
}
.mcard--backup { border-color: var(--line-green); }
.mcard__body { flex: 1; min-width: 0; }
.mcard__name { font: 600 14.5px/1.25 var(--font); color: var(--ink); }
.mcard__meta { display: flex; align-items: center; gap: 7px; margin-top: 3px; }
.mcard__meta:empty { display: none; }
.mcard__btn {
  flex: none;
  min-width: 88px; min-height: 44px;
  padding: 0 14px;
  border-radius: 11px;
  border: 1px solid var(--green);
  background: var(--green);
  color: #fff;
  cursor: pointer;
  font: 600 12.5px/1 var(--font);
  transition: transform .16s ease;
}
.mcard__btn:active { transform: scale(.96); }
.mcard--backup .mcard__btn {
  border-color: rgba(0, 0, 0, .08);
  background: #f4f4f1;
  color: var(--ink-2);
}
.mcard.is-leaving {
  opacity: 0;
  transform: scale(.97);
  transition: opacity .16s ease, transform .16s ease;
  pointer-events: none;
}

/* --- step 3: review & approve --------------------------------------------- */

.status { font: 600 12px/1 var(--font); color: #5c5c57; }
.status--approved { color: var(--green-deep); }
.status--sentback { color: var(--orange-ink); }

.summary { display: flex; align-items: flex-end; justify-content: space-between; gap: 18px; flex-wrap: wrap; }
.summary__label {
  font: 600 11px/1 var(--font);
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--ink-5);
}
.summary__value { display: flex; align-items: baseline; gap: 6px; margin-top: 7px; }
.summary__value b { font: 500 26px/1 var(--mono); color: var(--ink); }
.summary__value span { font: 500 13px/1 var(--mono); color: var(--ink-4); }
.summary__stats {
  display: flex; gap: 22px;
  font: 500 11.5px/1.5 var(--mono);
  color: var(--ink-4);
  text-align: right;
}
.summary__stats b { display: block; font-size: 14px; font-weight: 500; color: var(--ink); }
.summary__stats b.green { color: var(--green-deep); }

.review {
  perspective: 1700px;
  perspective-origin: 50% 40%;
  display: grid; grid-template-columns: 1fr 1fr; gap: 24px;
  align-items: start;
}
.rpanel {
  transform: rotateY(3deg);
  transform-style: preserve-3d;
  background: var(--face-main);
  border: 1px solid var(--line-mid);
  border-radius: 18px;
  padding: 14px 14px 12px;
  box-shadow: 0 2px 3px rgba(0, 0, 0, .04), 0 24px 44px -30px rgba(0, 0, 0, .45);
}
/* Inside its parent, not another card in the grid. No 3D of its own: it
   inherits the parent's tilt, so a nested panel that rotated again would fight
   it. Inset and tinted so the containment is the first thing read. */
.rpanel--sub {
  transform: none;
  margin: 12px 0 2px;
  padding: 11px 11px 9px;
  border-radius: 13px;
  background: rgba(255, 255, 255, .55);
  border: 1px solid var(--line-mid);
  box-shadow: none;
}
.rpanel--sub.rpanel--backup {
  transform: none;
  background: rgba(255, 255, 255, .5);
  border-color: var(--line-green);
  box-shadow: none;
}
.rpanel--sub .rpanel__head h3 { font-size: 11.5px; }
.rpanel--sub .rlist__empty { padding: 6px 3px; }

.rpanel--backup {
  transform: rotateY(-3deg);
  background: var(--face-backup);
  border-color: var(--line-green);
  box-shadow: 0 2px 3px rgba(0, 0, 0, .04), 0 24px 44px -30px rgba(64, 96, 20, .5);
}
.rpanel__head {
  display: flex; justify-content: space-between; align-items: baseline;
  padding: 0 3px 10px;
  border-bottom: 1px solid var(--line);
}
.rpanel__head h3 {
  font: 600 10.5px/1 var(--font);
  letter-spacing: .09em;
  text-transform: uppercase;
  color: var(--ink-5);
}
.rpanel__head span { font: 500 11px/1 var(--mono); color: var(--ink-4); }
.rpanel--backup .rpanel__head { border-color: var(--line-green-3); }
.rpanel--backup .rpanel__head h3 { color: var(--green); }
.rpanel--backup .rpanel__head span { color: var(--green-mid); }

.rlist { display: flex; flex-direction: column; gap: 6px; margin-top: 10px; }
.rrow {
  display: grid; grid-template-columns: minmax(0, 1fr) auto;
  gap: 10px; align-items: center;
  padding: 9px 10px;
  border-radius: 10px;
  background: #fff;
  border: 1px solid var(--line);
}
.rpanel--backup .rrow { border-color: var(--line-green-2); }
.rrow__top { display: flex; align-items: center; gap: 7px; }
.rrow__name { font: 600 13px/1.2 var(--font); color: var(--ink); }
.rrow__spec { margin-top: 3px; font: 500 10.5px/1 var(--mono); color: var(--ink-5); }
.rpanel--backup .rrow__spec { color: var(--green-mid); }
.rrow__kw { font: 500 12px/1 var(--mono); color: var(--ink-2); }
.rpanel--backup .rrow__kw { color: var(--green-deep); }
.rlist__empty { padding: 10px 4px; font: 400 12px/1.5 var(--font); color: var(--ink-4); }

.badge {
  padding: 2px 6px;
  border-radius: 5px;
  font: 600 9.5px/1.4 var(--font);
  letter-spacing: .04em;
}
.badge--added    { background: rgba(113, 166, 43, .14); color: var(--green-deep); }
.badge--dropped  { background: rgba(102, 102, 102, .12); color: #6f6f69; }
.badge--edited   { background: rgba(244, 156, 32, .14); color: var(--orange-ink); }
.badge--approved { background: rgba(113, 166, 43, .14); color: var(--green-deep); }
.badge--sentback { background: rgba(244, 156, 32, .14); color: var(--orange-ink); }
.badge--awaiting { background: rgba(102, 102, 102, .12); color: #6f6f69; }

/* --- jobs index ----------------------------------------------------------- */

.jobsbody { padding: 22px 24px 26px; }

.joblist { display: flex; flex-direction: column; gap: 8px; }

/* The row is a container so the delete control is its own button rather than
   a button nested inside the one that opens the job. */
.jobrow {
  display: flex;
  align-items: stretch;
  gap: 6px;
  background: var(--field);
  border: 1px solid var(--line);
  border-radius: 11px;
  padding-right: 8px;
  transition: border-color .15s, background .15s;
}
.jobrow:hover { border-color: var(--green); background: var(--card); }
.jobrow--live { border-left: 3px solid var(--green); }

.jobrow__open {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  align-items: center;
  gap: 3px 14px;
  flex: 1;
  min-width: 0;
  text-align: left;
  padding: 12px 4px 12px 15px;
  background: none;
  border: 0;
  border-radius: 11px;
  cursor: pointer;
  font: inherit;
  color: inherit;
}

/* Same hover reveal as the circuit table: present when you are on the row,
   out of the way otherwise, and always reachable by keyboard. */
.jobrow .rowdel { align-self: center; }
.jobrow:hover .rowdel,
.jobrow .rowdel:focus-visible { opacity: 1; }

.jobsfoot { display: flex; align-items: center; gap: 14px; margin-top: 16px; }

.jobrow__top { grid-column: 1; display: flex; align-items: baseline; gap: 9px; min-width: 0; }
.jobrow__num  { font: 600 13.5px/1.2 var(--font); color: var(--ink); flex: none; }
.jobrow__cust { font: 500 12.5px/1.2 var(--font); color: var(--ink-2);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }

.jobrow .badge { grid-column: 2; justify-self: end; align-self: center; white-space: nowrap; }

.jobrow__meta { grid-column: 1; font: 500 11.5px/1.4 var(--mono); color: var(--ink-4);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.jobrow__updated { grid-column: 2; justify-self: end;
  font: 500 11px/1 var(--mono); color: var(--ink-4); white-space: nowrap; }

.diffs { display: flex; flex-direction: column; gap: 10px; }
.diff { display: flex; gap: 10px; align-items: flex-start; animation: warnIn .3s ease-out; }
.diff__dot { width: 7px; height: 7px; margin-top: 5px; border-radius: 50%; flex: none; }
.diff__name { font: 600 12.5px/1.3 var(--font); color: var(--ink); }
.diff__detail { margin-top: 2px; font: 400 11.5px/1.35 var(--font); color: var(--ink-3); }
.diff__detail span { font-family: var(--mono); }
.diffs__none { font: 400 12px/1.5 var(--font); color: var(--ink-4); }

.approved {
  display: flex; align-items: center; gap: 10px;
  padding: 13px 15px;
  border-radius: 11px;
  background: rgba(113, 166, 43, .1);
  animation: warnIn .3s ease-out;
}
.approved span { flex: 1; font: 600 12.5px/1.3 var(--font); color: var(--green-deep); }

.notefield {
  width: 100%;
  min-height: 74px;
  resize: vertical;
  padding: 11px 12px;
  border: 1px solid rgba(244, 156, 32, .5);
  border-radius: 10px;
  background: #fffdf8;
  font: 400 12.5px/1.5 var(--font);
  color: var(--ink);
  animation: warnIn .3s ease-out;
}
.notefield:focus { outline: none; border-color: var(--orange); }

.exportrow {
  display: flex; align-items: center; justify-content: space-between;
  gap: 10px;
  padding-top: 5px;
  margin-top: 3px;
  border-top: 1px solid var(--line);
}
.exportbtn {
  border: none; background: none;
  cursor: pointer;
  padding: 6px 0;
  font: 600 12.5px/1 var(--font);
  color: var(--green-deep);
  display: flex; align-items: center; gap: 7px;
}
.exportbtn:hover { color: var(--green); }
.exportname {
  font: 500 11.5px/1 var(--mono);
  color: var(--ink-4);
  animation: warnIn .3s ease-out;
}

/* --- panel photo scan ----------------------------------------------------- */

.rowactions { display: flex; gap: 8px; flex-wrap: wrap; }

.scan__backdrop {
  position: fixed; inset: 0;
  background: rgba(43, 43, 43, .38);
  animation: fadeIn .18s ease-out;
}
/* Centred with flex, not transform: the entry animation owns `transform`, and
   sharing it left the sheet parked at the 50% offset with no translate back. */
.scan {
  position: fixed; inset: 0; z-index: 900;
  display: flex; align-items: center; justify-content: center;
  padding: 16px;
}
.scan__sheet {
  position: relative; z-index: 1;
  width: min(680px, 100%);
  max-height: min(80vh, 720px);
  display: flex; flex-direction: column;
  background: var(--card);
  border: 1px solid var(--line);
  border-radius: 16px;
  box-shadow: 0 30px 70px -24px rgba(0, 0, 0, .45);
  animation: viewIn .24s cubic-bezier(.2, .9, .3, 1);
}
.scan__body { padding: 20px 22px; overflow-y: auto; }
.scan__foot {
  display: flex; justify-content: flex-end; gap: 9px;
  padding: 14px 22px;
  border-top: 1px solid var(--line);
}

.scan__status { margin: 0; font: 500 13.5px/1.5 var(--font); color: var(--ink-2); }
.scan__status--warn { color: var(--warn-ink); }

.scanhead,
.scanrow {
  display: grid;
  grid-template-columns: 20px 46px minmax(0, 1fr) 58px 62px 40px 62px;
  gap: 10px;
  align-items: center;
}
.scanhead {
  grid-template-columns: 66px minmax(0, 1fr) 58px 62px 40px 62px;
  padding: 0 4px 8px;
  border-bottom: 1px solid var(--line);
  font: 600 10.5px/1 var(--font);
  letter-spacing: .05em;
  text-transform: uppercase;
  color: var(--ink-5);
}
.scanhead span:last-child,
.scanrow .conf { text-align: right; }

.scanlist { display: flex; flex-direction: column; }
.scanrow {
  padding: 7px 4px;
  border-bottom: 1px solid var(--line-soft);
  cursor: pointer;
}
.scanrow input[type="checkbox"] { accent-color: var(--green); width: 15px; height: 15px; }
.scanrow__slot { font: 500 12px/1 var(--mono); color: var(--ink-4); }
.scanrow .input,
.scanrow .select { border-color: transparent; background: var(--field-soft); padding: 8px 9px; }
.scanrow .select { font-size: 12.5px; }

/* A number the photo did not actually show, sitting at the default. Quiet
   rather than alarming: it is a starting point, not an error. */
.scanrow__amps[data-guess] { color: var(--ink-5); font-style: italic; }

.conf { font: 600 10px/1 var(--font); letter-spacing: .04em; text-transform: uppercase; }
.conf--high { color: var(--green-mid); }
.conf--medium { color: var(--orange-ink); }
.conf--low { color: var(--warn-ink); }

/* On a phone the label is the thing being corrected, so it gets the full
   width and the slot and confidence drop to a second line. */
@media (max-width: 560px) {
  .scan { padding: 10px; }
  .scan__body { padding: 16px; }
  .scan__foot { padding: 12px 16px; }
  .scanhead { display: none; }
  .scanrow {
    grid-template-columns: 20px minmax(0, 1fr) 58px 62px 40px;
    grid-template-areas:
      "check label label label heavy"
      "meta  amps  poles .     conf";
    row-gap: 8px;
    padding: 10px 4px;
  }
  .scanrow input[type="checkbox"] { grid-area: check; }
  .scanrow input.scanrow__amps { grid-area: amps; }
  .scanrow .scanrow__poles { grid-area: poles; }
  .scanrow input.input:not(.scanrow__amps) { grid-area: label; }
  .scanrow .switch { grid-area: heavy; }
  .scanrow__slot { grid-area: meta; justify-self: start; }
  .scanrow .conf { grid-area: conf; justify-self: end; }
}

/* --- toast ---------------------------------------------------------------- */

.toast {
  position: fixed;
  left: 50%; bottom: 26px;
  transform: translateX(-50%);
  z-index: 999;
  padding: 11px 16px;
  border-radius: 11px;
  background: var(--ink);
  color: #fff;
  font: 600 12.5px/1 var(--font);
  box-shadow: 0 12px 30px -12px rgba(0, 0, 0, .55);
  animation: warnIn .25s ease-out;
}

/* --- figures -------------------------------------------------------------- */

/* Every `font:` shorthand above resets font-variant-numeric, so the readouts
   that used to be monospaced ask for even-width digits again by name. Keeps
   columns from shuffling as values change. */
.input--num,
.topbar__addr,
.bar__head,
.tile__value,
.summary__value b,
.summary__value span,
.summary__stats,
.summary__stats b,
.rrow__spec,
.rrow__kw,
.diff__detail span,
.exportname,
.linkout code,
.circuits .input,
.circuits .select,
.circuits__row .select {
  font-variant-numeric: tabular-nums;
}

/* --- wide screens ----------------------------------------------------------
   The sheet grows with the window, so the extra width has to go somewhere
   deliberate. The circuits table earns it: eight columns that otherwise scroll
   the last one out of sight. A single address field does not, so the rows that
   would just stretch are either given another column to fill or held to a
   width a form still reads at.
   -------------------------------------------------------------------------- */

@media (min-width: 1400px) {
  /* Address moves up onto the same row rather than spanning underneath. */
  .jobspecs { grid-template-columns: 120px minmax(0, 1fr) 190px minmax(0, 1.6fr); }
  .jobspecs .field--wide { grid-column: auto; }

  .panelspecs__row,
  .batteryrow,
  .tiles { max-width: 820px; }
}

/* --- print export --------------------------------------------------------- */

.cutsheet { display: none; }

@media print {
  .app, .toast { display: none !important; }
  .cutsheet { display: block; padding: 0; color: #000; font-family: var(--font); }
  .cutsheet h1 { font-size: 17pt; margin: 0 0 2mm; }
  .cutsheet .sub { font-size: 9pt; color: #444; margin: 0 0 8mm; font-family: var(--mono); }
  .cutsheet h2 {
    font-size: 12pt; margin: 0 0 2mm;
    padding-bottom: 1.5mm; border-bottom: 1.5pt solid #000;
    break-after: avoid;
  }
  .cutsheet section { margin-bottom: 10mm; break-inside: avoid; }
  .cutsheet table { width: 100%; border-collapse: collapse; font-size: 10pt; }
  .cutsheet th {
    text-align: left; font-size: 8pt; letter-spacing: .06em; text-transform: uppercase;
    color: #444; padding: 2mm 0; border-bottom: .5pt solid #999;
  }
  .cutsheet td { padding: 2mm 0; border-bottom: .5pt solid #ddd; }
  .cutsheet td.num, .cutsheet th.num { text-align: right; width: 22mm; font-family: var(--mono); }
  @page { margin: 16mm; }
}

/* --- responsive ----------------------------------------------------------- */

@media (max-width: 1080px) {
  .sheet__body { grid-template-columns: minmax(0, 1fr); }
  .sheet__side { position: static; }
  .review { grid-template-columns: minmax(0, 1fr); perspective: none; }
  .rpanel, .rpanel--backup { transform: none; }
}

@media (max-width: 900px) {
  .view { padding: 14px 12px 40px; }
  .sheet { border-radius: 14px; }
  .sheet__body { padding: 16px 14px 20px; }
  .jobspecs { grid-template-columns: 1fr; }
  .panelspecs { grid-template-columns: 1fr; }
  .tiles { grid-template-columns: 1fr; }
  .batteryrow { grid-template-columns: 1fr; }
  .picks { padding: 16px 14px 0; }
  .picks__foot { padding: 14px 16px 18px; }
  .topbar {
    display: flex;
    flex-wrap: wrap;
    justify-content: space-between;
    padding: 12px 14px;
    gap: 12px;
  }
  .topbar .steps { justify-self: auto; }
  .topbar__addr { display: none; }
}

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: .001ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: .001ms !important;
  }
}

/* --- keyframes ------------------------------------------------------------ */

@keyframes ringIn { from { opacity: 0; transform: scale(.985) } to { opacity: 1; transform: scale(1) } }
@keyframes warnIn { from { opacity: 0; transform: translateY(-4px) } to { opacity: 1; transform: translateY(0) } }
@keyframes fadeIn { from { opacity: 0 } to { opacity: 1 } }
@keyframes viewIn { from { opacity: 0; transform: translateY(6px) } to { opacity: 1; transform: none } }
@keyframes breathe { 0%, 100% { opacity: .55 } 50% { opacity: 1 } }

/* --- subpanels and PCS load shed ------------------------------------------ */

/* Backed up, but the PCS drops it under overload, so it is held out of the
   carried total. Muted rather than alarming: it is a designed behaviour. */
.shedtag {
  display: inline-flex; align-items: center;
  padding: 3px 7px;
  border-radius: 6px;
  background: rgba(154, 154, 147, .16);
  font: 600 10.5px/1 var(--font);
  letter-spacing: .03em;
  color: var(--ink-2);
}

.switch--shed[aria-pressed="true"] { background: var(--ink-4); }
.switch--shed:disabled { opacity: .3; cursor: default; }

.rrow__kw--shed { color: var(--ink-4); }

/* A subpanel reads as one movable thing, so its card is tinted and its meta
   line carries the group rather than a single circuit's badges. */
.grouptag {
  font: 500 11px/1 var(--font);
  color: var(--ink-4);
}
.panel--backup .grouptag { color: var(--green-mid); }

.slot[data-slot^="p:"] .card {
  background: linear-gradient(180deg, #fbfbf9, #f4f3ef);
  border-style: dashed;
}
.panel--backup .slot[data-slot^="p:"] .card {
  background: linear-gradient(180deg, #f8fbf3, #eef4e4);
}

.mcard--group { background: var(--field-soft); border-style: dashed; }

@media (max-width: 900px) {
  .panelspecs__row,
  .panelspecs__row--sub { grid-template-columns: 1fr; }
  .panelspecs__col--sub { padding-left: 10px; }
}

/* --- sign in, and the dead homeowner link ---------------------------------- */

.signin {
  max-width: 380px;
  margin: 0 auto;
  padding: 40px 24px 44px;
  display: flex;
  flex-direction: column;
  gap: 14px;
  text-align: center;
}
.signin h2 { font: 600 17px/1.35 var(--font); color: var(--ink); }
.signin p  { font: 500 13px/1.5 var(--font); color: var(--ink-3); }

.signin__form { display: flex; flex-direction: column; gap: 12px; text-align: left; }
.signin__form .btn { justify-content: center; }

.signin__error { font: 500 12.5px/1.4 var(--font); color: var(--warn-ink); }

/* The shared code sits under the Zoho button as the quieter way in. */
.signin__or {
  display: flex; align-items: center; gap: 10px;
  font: 500 11.5px/1 var(--font); text-transform: uppercase; letter-spacing: .05em;
  color: var(--ink-5);
  margin-top: 6px;
}
.signin__or::before, .signin__or::after {
  content: ''; flex: 1; height: 1px; background: var(--line-mid);
}

.topbar__who { font: 500 11.5px/1 var(--mono); color: var(--ink-4); }

/* Sign in and the dead link have only a title, centred. */
.topbar--plain { grid-template-columns: 1fr auto 1fr; }

/* --- homeowner notices ----------------------------------------------------
   Sent back, or approved and locked. Above the meter because it is the first
   thing that changed since they last looked.
   -------------------------------------------------------------------------- */

/* Full width of the surface, matching the meter and the panels below it, so it
   reads as a bar across the top of the page rather than a card floating over
   one. 30px sides is what .picks and .stage use. */
.notice {
  margin: 26px 30px 0;
  padding: 15px 18px;
  border-radius: 12px;
  border: 1px solid var(--line-mid);
  background: var(--card);
  display: flex;
  flex-direction: column;
  gap: 6px;
}
/* The installer's version is a status line with its way out beside it, so it
   lays out across rather than down. */
.notice--locked { flex-direction: row; align-items: center; justify-content: space-between; gap: 16px; }
.notice--inset { margin: 22px 24px 0; }
.btn--tight { padding: 7px 14px; font-size: 12.5px; }

.notice h3 { font: 600 14px/1.35 var(--font); color: var(--ink); }
.notice p  { font: 500 13px/1.5 var(--font); color: var(--ink-3); white-space: pre-wrap; }

/* No colour sliver: the heading already says which of the two this is, and a
   stripe down one edge reads as decoration rather than information. */

@media (max-width: 900px) {
  .notice { margin: 16px 14px 0; }
}

/* Approved and locked. The cards stay legible, so the homeowner can still read
   what was agreed, but nothing about them offers to move. */
.slot--locked,
.slot--locked .card,
.slot--locked:active { cursor: default; }
.slot--locked .card:hover { transform: none; box-shadow: none; }

/* --- the scan wait ---------------------------------------------------------
   Ten to twenty seconds with nothing to report. The bar is indeterminate
   because there is no progress to show, and a moving bar is the honest way to
   say the machine is still working.
   -------------------------------------------------------------------------- */

.scanwait { display: flex; flex-direction: column; gap: 14px; padding: 18px 0 6px; }

.scanwait__bar {
  height: 4px;
  border-radius: 999px;
  background: var(--track);
  overflow: hidden;
}
.scanwait__fill {
  height: 100%;
  width: 38%;
  border-radius: 999px;
  background: linear-gradient(90deg, var(--green-light), var(--green), var(--green-light));
  animation: scanSweep 1.5s cubic-bezier(.5, 0, .5, 1) infinite;
}

@keyframes scanSweep {
  0%   { transform: translateX(-100%); }
  100% { transform: translateX(363%); }
}

.scanwait .scan__status { text-align: center; margin: 0; transition: opacity .2s; }

/* Reduced motion already kills the animation globally, so leave a bar that
   simply sits there filled rather than an empty track that looks broken. */
@media (prefers-reduced-motion: reduce) {
  .scanwait__fill { width: 100%; }
}
