:root{
  --bg:#0b1220; --panel:#131c2e; --panel2:#1a2438; --line:#25324b;
  --ink:#e8edf6; --muted:#93a1bb; --accent:#4f9cf9; --ok:#31c48d; --warn:#f0a63a; --bad:#f2626b;
  --r:14px;
}
*{box-sizing:border-box}
html,body{margin:0;height:100%}
body{background:var(--bg);color:var(--ink);font:15px/1.45 -apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,sans-serif;-webkit-font-smoothing:antialiased}
#app{max-width:820px;margin:0 auto;padding:0 0 88px}
.boot{padding:40px;text-align:center;color:var(--muted)}

/* header */
.hdr{position:sticky;top:0;z-index:20;background:rgba(11,18,32,.92);backdrop-filter:blur(10px);border-bottom:1px solid var(--line);padding:12px 16px;display:flex;align-items:center;gap:12px}
.hdr h1{font-size:16px;margin:0;font-weight:650;letter-spacing:.2px}
.hdr .sub{font-size:12px;color:var(--muted)}
.spacer{flex:1}
.pill{font-size:11px;padding:3px 9px;border-radius:999px;border:1px solid var(--line);color:var(--muted);white-space:nowrap}
.pill.on{background:rgba(49,196,141,.14);border-color:rgba(49,196,141,.4);color:var(--ok)}
.pill.off{background:rgba(242,98,107,.12);border-color:rgba(242,98,107,.4);color:var(--bad)}
.pill.warn{background:rgba(240,166,58,.12);border-color:rgba(240,166,58,.4);color:var(--warn)}

/* layout */
.wrap{padding:16px}
.card{background:var(--panel);border:1px solid var(--line);border-radius:var(--r);padding:16px;margin-bottom:14px}
.card h2{margin:0 0 4px;font-size:14px;letter-spacing:.3px;text-transform:uppercase;color:var(--muted);font-weight:600}
.row{display:flex;gap:10px;align-items:center}
.grid{display:grid;gap:10px}
.muted{color:var(--muted)}
.small{font-size:12px}
.mono{font-family:ui-monospace,SFMono-Regular,Menlo,monospace;font-size:11px}

/* controls */
button{font:inherit;cursor:pointer;border-radius:10px;border:1px solid var(--line);background:var(--panel2);color:var(--ink);padding:11px 14px;transition:.12s}
button:active{transform:scale(.985)}
button:disabled{opacity:.45;cursor:not-allowed}
button.primary{background:var(--accent);border-color:var(--accent);color:#04162e;font-weight:650}
button.ok{background:var(--ok);border-color:var(--ok);color:#04261a;font-weight:650}
button.bad{background:transparent;border-color:rgba(242,98,107,.5);color:var(--bad)}
button.wide{width:100%}
button.sm{padding:7px 11px;font-size:13px}
input,select,textarea{font:inherit;width:100%;padding:11px 12px;border-radius:10px;border:1px solid var(--line);background:#0e1626;color:var(--ink)}
textarea{min-height:74px;resize:vertical}
label{display:block;font-size:12px;color:var(--muted);margin:0 0 5px}
.field{margin-bottom:12px}

/* tabs */
.tabs{position:fixed;bottom:0;left:0;right:0;z-index:30;display:flex;background:rgba(13,20,35,.97);backdrop-filter:blur(12px);border-top:1px solid var(--line);padding:8px max(8px,env(safe-area-inset-left)) max(8px,env(safe-area-inset-bottom))}
.tabs button{flex:1;background:none;border:none;color:var(--muted);font-size:12px;padding:10px 2px;letter-spacing:.2px}
.tabs button.sel{color:var(--accent)}

/* stops */
.stop{display:flex;gap:12px;padding:12px;border:1px solid var(--line);border-radius:12px;background:var(--panel2);margin-bottom:10px}
.stop.done{opacity:.62;border-color:rgba(49,196,141,.35)}
.stop.next{border-color:var(--accent);box-shadow:0 0 0 1px rgba(79,156,249,.25)}
.seq{width:26px;height:26px;flex:none;border-radius:50%;display:grid;place-items:center;font-size:12px;font-weight:700;background:var(--line);color:var(--ink)}
.stop.done .seq{background:var(--ok);color:#04261a}
.stop.next .seq{background:var(--accent);color:#04162e}
.addr{font-weight:600}
.svc{font-size:12px;color:var(--muted)}

/* map
   The slot is what a screen renders; the map element itself is owned by map.js and
   moved into the slot after each repaint, so the Google map is built once and keeps
   the zoom the crew set. Both carry the height, or the card collapses in the moment
   between the repaint and the re-parent. */
.mapslot{width:100%;height:260px;border-radius:12px;overflow:hidden;background:#0a1120;border:1px solid var(--line)}
.map{width:100%;height:260px;border-radius:12px;background:#0a1120;display:block;position:relative}
.offlineMapTag{position:absolute;right:8px;bottom:8px;font-size:10px;color:var(--muted);background:rgba(4,22,46,.75);padding:2px 7px;border-radius:6px}
.legend{display:flex;gap:14px;flex-wrap:wrap;font-size:11px;color:var(--muted);margin-top:8px}
.dot{display:inline-block;width:9px;height:9px;border-radius:50%;margin-right:5px;vertical-align:middle}

/* table */
table{width:100%;border-collapse:collapse;font-size:12.5px}
th,td{text-align:left;padding:7px 6px;border-bottom:1px solid var(--line);vertical-align:top}
th{color:var(--muted);font-weight:600;font-size:11px;text-transform:uppercase;letter-spacing:.3px}
.scroll{overflow-x:auto}

/* misc */
.thumb{width:74px;height:74px;object-fit:cover;border-radius:9px;border:1px solid var(--line)}
.thumbs{display:flex;gap:8px;flex-wrap:wrap}
#toast{position:fixed;left:50%;bottom:88px;transform:translateX(-50%);z-index:60;display:flex;flex-direction:column;gap:8px;align-items:center;pointer-events:none}
.toast{background:#1f2b44;border:1px solid var(--line);padding:10px 16px;border-radius:999px;font-size:13px;box-shadow:0 8px 24px rgba(0,0,0,.45)}
.toast.bad{border-color:rgba(242,98,107,.55);color:#ffd7da}
.toast.ok{border-color:rgba(49,196,141,.55);color:#c9f5e4}
.banner{background:rgba(240,166,58,.12);border:1px solid rgba(240,166,58,.4);color:#ffdca6;padding:9px 13px;border-radius:10px;font-size:12.5px;margin-bottom:14px}
.login{max-width:390px;margin:0 auto;padding:44px 20px}
.brand{text-align:center;margin-bottom:26px}
.brand h1{margin:8px 0 2px;font-size:21px}
.acct{display:flex;justify-content:space-between;gap:8px;padding:9px 11px;border:1px solid var(--line);border-radius:10px;background:var(--panel2);margin-bottom:7px;cursor:pointer;font-size:13px}
.acct:hover{border-color:var(--accent)}
.chain{font-family:ui-monospace,Menlo,monospace;font-size:10px;color:#5f7590}

/* ---- time on the job + parts used ----
   Both sit inside the stop card, on the working side of the Complete button. A crew
   records these while they are doing the job, not while filling in a form afterwards.
   Indented off the card's left edge so they read as detail about the stop above them
   rather than as two more stops. */
.jobBlk{margin-top:10px;padding:10px 11px;border:1px solid var(--line);border-radius:10px;background:rgba(255,255,255,.02)}
.jobBlkHd{display:flex;align-items:baseline;justify-content:space-between;gap:8px;font-size:12px;color:var(--muted);margin-bottom:8px}
.jobBlkHd strong{color:var(--ink);font-size:13px}
.partList{display:flex;flex-direction:column;gap:7px}
.partRow{display:flex;align-items:center;gap:9px;padding:8px 9px;border:1px solid var(--line);border-radius:9px;background:var(--panel2)}
.partName{font-size:13px;font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.qty{font-size:13px;font-weight:700;color:var(--accent);white-space:nowrap}
/* Wide enough for three digits, no wider — a quantity box that fills the row pushes
   the Add button off a phone screen. */
.qtyIn{width:64px;flex:0 0 auto;padding:8px 9px;text-align:center}
button.warn{border-color:rgba(240,166,58,.45);color:var(--warn)}
.outcomeList{display:flex;flex-direction:column;gap:6px}
.outcomeRow{display:flex;align-items:center;gap:9px;padding:9px 10px;border:1px solid var(--line);border-radius:9px;background:var(--panel2);margin:0;color:var(--ink);font-size:13px;cursor:pointer}
.outcomeRow input{width:auto;flex:0 0 auto}
