/* ============================================================================
   Infinity Operator Console — design system
   Drop at: console/assets/console.css   (linked from head.php)

   Replaces the inline <style> block in the old head.php. Tokens first, then
   chrome (sidebar/topbar), then components. Nothing here depends on JS.
   ========================================================================= */

:root{
  /* ground + surfaces */
  --bg:#07090D; --sidebar:#0A0E14; --panel:#0E141E; --panel-hi:#131A26;
  --panel-2:#141A25; --input:#0B0F16; --log:#080B11;
  /* lines */
  --line:#1B2230; --line-2:#1E2634; --line-3:#2C3646; --line-soft:#161D28;
  /* type */
  --tx:#C4CEDB; --tx-2:#8892A4; --tx-3:#6E7A8C; --tx-4:#5C6779; --hd:#EEF3FA;
  /* accents */
  --gold:#E8B96B; --up:#3FD07D; --down:#F0596B; --warn:#EAB63F; --info:#5AA2F0;
  --up-bg:rgba(63,208,125,.12);  --up-bd:rgba(63,208,125,.3);
  --down-bg:rgba(240,89,107,.12); --down-bd:rgba(240,89,107,.3);
  --warn-bg:rgba(234,182,63,.12); --warn-bd:rgba(234,182,63,.3);
  --info-bg:rgba(90,162,240,.12); --info-bd:rgba(90,162,240,.3);
  --gold-bg:rgba(232,185,107,.1); --gold-bd:rgba(232,185,107,.34);
  /* type stacks */
  --sans:Archivo,system-ui,-apple-system,"Segoe UI",sans-serif;
  --mono:"JetBrains Mono",ui-monospace,Consolas,monospace;
  /* geometry */
  --r-sm:7px; --r:9px; --r-md:13px; --r-lg:15px;
  --sh:0 1px 3px rgba(0,0,0,.4); --sh-lg:0 26px 70px rgba(0,0,0,.7);
  --sidebar-w:238px; --topbar-h:62px;
}

*{box-sizing:border-box}
html,body{margin:0;padding:0;background:var(--bg)}
body{color:var(--tx);font-family:var(--sans);font-size:14px;line-height:1.5;
     -webkit-font-smoothing:antialiased}
a{color:#7FB2F2;text-decoration:none}
a:hover{color:#A8CCF8}
h1,h2,h3{margin:0;color:var(--hd);font-weight:650}
::selection{background:rgba(232,185,107,.26)}
.mono{font-family:var(--mono)}
.tnum{font-variant-numeric:tabular-nums}
.muted{color:var(--tx-3);font-size:12px}
.spacer{flex:1}
.nowrap{white-space:nowrap}

::-webkit-scrollbar{width:10px;height:10px}
::-webkit-scrollbar-track{background:var(--input)}
::-webkit-scrollbar-thumb{background:#232C3A;border-radius:6px;border:2px solid var(--input)}
::-webkit-scrollbar-thumb:hover{background:#334054}

@keyframes conPulse{0%,100%{opacity:.45}50%{opacity:1}}
@keyframes conIn{from{opacity:0;transform:translateY(10px)}to{opacity:1;transform:none}}

/* ── shell ─────────────────────────────────────────────────────────────── */
.shell{display:flex;min-height:100vh}
.main{flex:1;min-width:0;display:flex;flex-direction:column}
.page{padding:22px 26px 34px;display:flex;flex-direction:column;gap:18px;max-width:1520px}

/* ── sidebar ───────────────────────────────────────────────────────────── */
.side{flex:none;width:var(--sidebar-w);background:var(--sidebar);border-right:1px solid var(--line);
      display:flex;flex-direction:column;position:sticky;top:0;height:100vh}
.side-hd{padding:20px 18px 18px;border-bottom:1px solid var(--line)}
.brand{display:flex;align-items:center;gap:10px}
.brand .dot{width:9px;height:9px;border-radius:50%;background:var(--gold);
            box-shadow:0 0 12px var(--gold);animation:conPulse 2.8s ease-in-out infinite}
.brand-t{font-size:14.5px;font-weight:700;color:var(--hd);line-height:1.15}
.brand-s{font-size:9.5px;font-weight:600;letter-spacing:.24em;text-transform:uppercase;
         color:var(--gold);margin-top:2px}

/* environment identity: PROD must never read as TEST at a glance */
.env{margin-top:16px;display:flex;align-items:center;gap:7px;padding:7px 10px;border-radius:8px;
     background:var(--info-bg);border:1px solid var(--info-bd);color:var(--info)}
.env b{font-size:11px;font-weight:700;letter-spacing:.16em}
.env .host{flex:1;text-align:right;font-family:var(--mono);font-size:10.5px;color:var(--tx-3)}
.env.prod{background:var(--down-bg);border-color:var(--down-bd);color:var(--down)}

.side-nav{flex:1;overflow-y:auto;padding:12px 10px 18px}
.side-grp{margin-top:14px}
.side-grp>span{display:block;padding:0 11px 7px;font-size:9.5px;font-weight:700;
               letter-spacing:.2em;text-transform:uppercase;color:var(--tx-4)}
.side-nav a{display:flex;align-items:center;gap:10px;padding:7px 11px;border-radius:var(--r-sm);
            font-size:12.5px;font-weight:500;color:var(--tx-2);white-space:nowrap}
.side-nav a i{font-size:15px;opacity:.75;font-style:normal}
.side-nav a:hover{color:var(--hd);background:#151C28}
.side-nav a.active{color:var(--gold);background:var(--gold-bg);font-weight:600}
.side-nav a.top{margin-bottom:4px;padding:9px 11px;font-size:13px;font-weight:600}
.side-nav .n{margin-left:auto;padding:1px 6px;border-radius:5px;font-family:var(--mono);
             font-size:10px;font-weight:700;background:var(--warn-bg);color:var(--warn)}
.side-nav .n.bad{background:var(--down-bg);color:var(--down)}

.side-ft{padding:12px;border-top:1px solid var(--line);display:flex;align-items:center;gap:10px}
.avatar{flex:none;width:32px;height:32px;border-radius:var(--r);display:flex;align-items:center;
        justify-content:center;font-size:12px;font-weight:700;color:var(--gold);
        background:linear-gradient(160deg,#2A3547,#1A2231);border:1px solid var(--line-3)}
.who{flex:1;min-width:0}
.who b{display:block;font-size:12.5px;font-weight:600;color:var(--hd);
       white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.who span{font-size:10.5px;color:var(--tx-3)}
.ibtn{width:28px;height:28px;border-radius:var(--r-sm);border:1px solid #242C3A;display:flex;
      align-items:center;justify-content:center;color:var(--tx-2)}
.ibtn:hover{border-color:#3A5A86;color:var(--hd)}
.ibtn.danger:hover{border-color:var(--down);color:#FFD9DE}

/* ── topbar ────────────────────────────────────────────────────────────── */
.topbar{position:sticky;top:0;z-index:20;height:var(--topbar-h);padding:0 26px;display:flex;
        align-items:center;gap:18px;background:rgba(10,14,20,.9);backdrop-filter:blur(10px);
        border-bottom:1px solid var(--line)}
.topbar h1{font-size:17px;letter-spacing:-.005em}
.topbar .sub{font-size:11.5px;color:var(--tx-3);white-space:nowrap;font-variant-numeric:tabular-nums}

/* ── pills ─────────────────────────────────────────────────────────────── */
.pill{display:inline-flex;align-items:center;gap:7px;padding:6px 12px;border-radius:999px;
      font-size:12px;font-weight:600;white-space:nowrap;border:1px solid var(--line-3);color:var(--tx-2)}
.pill .d{width:7px;height:7px;border-radius:50%;background:currentColor}
.pill.up{background:var(--up-bg);border-color:var(--up-bd);color:var(--up)}
.pill.down{background:var(--down-bg);border-color:var(--down-bd);color:var(--down)}
.pill.warn{background:var(--warn-bg);border-color:var(--warn-bd);color:var(--warn)}
.pill.info{background:var(--info-bg);border-color:var(--info-bd);color:var(--info)}

/* ── panels ────────────────────────────────────────────────────────────── */
.panel{border:1px solid var(--line-2);border-radius:var(--r-md);background:var(--panel)}
.panel.alert{border-color:rgba(240,89,107,.5);
             background:linear-gradient(170deg,rgba(240,89,107,.07),var(--panel) 60%)}
.panel>.hd{padding:13px 18px;border-bottom:1px solid var(--line-2);display:flex;
           align-items:center;gap:10px;flex-wrap:wrap}
.panel>.hd h3{font-size:11.5px;font-weight:700;letter-spacing:.16em;text-transform:uppercase;
              color:var(--tx-2);white-space:nowrap}
.panel>.hd i{font-size:16px;color:var(--gold);font-style:normal}
.panel>.bd{padding:18px}
.split{display:grid;grid-template-columns:1.55fr 1fr;gap:18px;align-items:start}
.col{display:flex;flex-direction:column;gap:18px;min-width:0}
@media(max-width:1180px){.split{grid-template-columns:1fr}}

/* ── stat cards ────────────────────────────────────────────────────────── */
.stats{display:grid;grid-template-columns:repeat(4,minmax(0,1fr));gap:14px}
@media(max-width:1080px){.stats{grid-template-columns:repeat(2,minmax(0,1fr))}}
.stat{border:1px solid var(--line-2);border-radius:var(--r-md);padding:16px 18px;box-shadow:var(--sh);
      background:linear-gradient(170deg,var(--panel-hi),var(--panel))}
.stat .k{display:flex;align-items:center;gap:8px;font-size:10.5px;font-weight:700;
         letter-spacing:.16em;text-transform:uppercase;color:#7C8798;white-space:nowrap}
.stat .k i{font-size:15px;color:var(--tx-3);font-style:normal}
.stat .delta{margin-left:auto;font-family:var(--mono);font-size:11px;font-weight:600;color:var(--tx-4)}
.stat .delta.up{color:var(--up)} .stat .delta.down{color:var(--down)}
.stat .v{display:flex;align-items:flex-end;gap:6px;margin-top:12px}
.stat .v b{font-size:32px;font-weight:700;line-height:1;letter-spacing:-.02em;color:var(--hd);
           font-variant-numeric:tabular-nums}
.stat .v span{font-size:13px;font-weight:600;color:var(--tx-3);padding-bottom:3px}
.stat .sub{margin-top:9px;font-size:11.5px;color:var(--tx-3);font-variant-numeric:tabular-nums}
.bar{margin-top:13px;height:5px;border-radius:3px;background:#1A2130;overflow:hidden}
.bar>i{display:block;height:100%;border-radius:3px;background:var(--info);transition:width .5s ease}
.is-up{color:var(--up)} .is-warn{color:var(--warn)} .is-down{color:var(--down)}

/* ── buttons ───────────────────────────────────────────────────────────── */
.btn{display:inline-flex;align-items:center;gap:9px;padding:11px 16px;border-radius:10px;
     border:1px solid var(--line-3);background:var(--panel-2);color:var(--tx);
     font:600 13px var(--sans);cursor:pointer;transition:.12s}
.btn i{font-size:16px;font-style:normal}
.btn:hover{border-color:#3A5A86;color:var(--hd)}
.btn.sm{padding:9px 14px;font-size:12.5px}
.btn.gold{background:linear-gradient(180deg,var(--gold),#D7A24F);border-color:#CAA15A;
          color:#1A130A;font-weight:700}
.btn.gold:hover{filter:brightness(1.07);color:#1A130A}
.btn.primary{background:linear-gradient(180deg,#243247,#1B2636);border-color:#3A5A86;color:#DBE8FB}
.btn.primary:hover{border-color:var(--info);color:#fff}
.btn.good:hover{border-color:var(--up)}
.btn.danger{background:rgba(240,89,107,.1);border-color:rgba(240,89,107,.4);color:#FFD9DE}
.btn.danger:hover{background:rgba(240,89,107,.18);border-color:var(--down)}
.btn:disabled{opacity:.45;cursor:not-allowed}
.btnrow{display:flex;gap:10px;flex-wrap:wrap}
.btnrow--split{margin-top:18px;padding-top:18px;border-top:1px solid #1A2130;
               display:flex;gap:10px;align-items:flex-end;flex-wrap:wrap}

/* ── fields ────────────────────────────────────────────────────────────── */
label.fld{display:block;min-width:190px;flex:1;max-width:280px}
label.fld>span{display:block;font-size:10.5px;font-weight:700;letter-spacing:.14em;
               text-transform:uppercase;color:#7C8798;margin-bottom:7px}
.inp{width:100%;background:var(--input);border:1px solid var(--line-3);border-radius:var(--r);
     padding:10px 12px;color:var(--hd);font-family:var(--mono);font-size:13px}
.inp:focus{outline:none;border-color:var(--info)}
select.inp{cursor:pointer}

/* ── map grid ──────────────────────────────────────────────────────────── */
/* ONE .mtile rule, not two. The first version of this left an override ABOVE the original, so the
   original won every conflicting property - the tiles stayed square and centre-aligned and the
   labels looked wrong. Merged here so there is nothing to lose an ordering fight with.

   Deliberately compact: 63 tiles share the panel with everything else on the page, and the name is
   a label, not a headline. Clipped rather than wrapped, because a wrapped name changes tile height
   and the grid stops reading as a grid. */
.maps{display:grid;grid-template-columns:repeat(auto-fill,minmax(94px,1fr));gap:4px}
.mtile{border-radius:6px;border:1px solid var(--line-3);background:var(--panel-2);color:var(--tx-3);
       display:flex;flex-direction:column;align-items:flex-start;justify-content:center;gap:0;
       padding:4px 6px;min-height:30px;text-align:left;overflow:hidden;cursor:pointer;
       transition:transform .1s,box-shadow .14s}
.mtile .mn{font:700 10.5px var(--mono);line-height:1.15}
.mtile .ml{font-size:9px;font-weight:600;line-height:1.2;opacity:.75;max-width:100%;
           overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.mtile:hover{transform:translateY(-1px);box-shadow:0 4px 12px rgba(0,0,0,.45)}
.mtile.up{background:rgba(63,208,125,.13);border-color:rgba(63,208,125,.38);color:var(--up)}
.mtile.down{background:rgba(240,89,107,.14);border-color:rgba(240,89,107,.5);color:var(--down)}
.legend{display:inline-flex;align-items:center;gap:6px;font-size:11.5px;color:#7C8798}
.legend .sw{width:9px;height:9px;border-radius:3px;background:var(--up-bg);border:1px solid var(--up-bd)}
.legend .sw.down{background:var(--down-bg);border-color:rgba(240,89,107,.55)}

/* ── rows (db / jobs) ──────────────────────────────────────────────────── */
.rows{padding:6px 18px 14px}
.row{display:flex;align-items:center;gap:12px;padding:11px 0;border-bottom:1px solid var(--line-soft)}
.row:last-child{border-bottom:0}
.row .name{flex:1;min-width:0;font-family:var(--mono);font-size:13px;font-weight:600;color:var(--tx);
           white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.row .meter{width:74px;height:5px;border-radius:3px;background:#1A2130;overflow:hidden;flex:none}
.row .meter>i{display:block;height:100%;background:var(--info)}
.row .val{width:74px;text-align:right;font-family:var(--mono);font-size:12px;color:var(--tx-2);
          font-variant-numeric:tabular-nums}
.row .led{flex:none;width:8px;height:8px;border-radius:50%;background:var(--tx-4)}
.row .state{padding:3px 8px;border-radius:6px;font-size:10.5px;font-weight:700;letter-spacing:.1em}
.state.pending{background:var(--warn-bg);color:var(--warn)}
.state.applied{background:var(--up-bg);color:var(--up)}
.state.refused{background:var(--down-bg);color:var(--down)}

/* ── watchdog log ──────────────────────────────────────────────────────── */
.logwrap{background:var(--log);max-height:262px;overflow-y:auto;
         border-bottom-left-radius:var(--r-md);border-bottom-right-radius:var(--r-md)}
.logline{display:grid;grid-template-columns:62px 54px 1fr;gap:10px;padding:8px 16px;
         border-bottom:1px solid #10151E;font-family:var(--mono);font-size:11.5px;line-height:1.45}
.logline .t{color:var(--tx-4);font-variant-numeric:tabular-nums}
.logline .l{font-weight:700}
.logline .m{color:var(--tx-2);word-break:break-word}
.l.OK{color:var(--up)} .l.WARN{color:var(--warn)} .l.ERR{color:var(--down)} .l.INFO{color:var(--info)}
.stale{color:var(--warn)}

/* ── confirm sheet ─────────────────────────────────────────────────────── */
.sheet{position:fixed;inset:0;z-index:80;display:flex;align-items:center;justify-content:center;
       padding:24px;background:rgba(4,6,10,.72);backdrop-filter:blur(4px)}
.sheet[hidden]{display:none}
.sheet-box{width:100%;max-width:462px;border:1px solid var(--line-3);border-radius:var(--r-lg);
           background:#101724;box-shadow:var(--sh-lg);animation:conIn .16s ease;overflow:hidden}
.sheet-hd{padding:20px 22px 0;display:flex;gap:14px}
.sheet-ic{flex:none;width:38px;height:38px;border-radius:11px;display:flex;align-items:center;
          justify-content:center;font-size:20px;background:var(--info-bg);color:var(--info)}
.sheet-ic.gold{background:var(--gold-bg);color:var(--gold)}
.sheet-ic.bad{background:var(--down-bg);color:var(--down)}
.sheet-ic.good{background:var(--up-bg);color:var(--up)}
.sheet-hd h3{font-size:16.5px}
.sheet-hd p{margin:6px 0 0;font-size:13.5px;line-height:1.6;color:var(--tx-2);text-wrap:pretty}
.sheet-impact{margin:16px 22px 0;padding:11px 14px;border-radius:10px;display:flex;align-items:center;
              gap:9px;background:rgba(240,89,107,.09);border:1px solid rgba(240,89,107,.28);
              font-size:12.5px;color:#FFD9DE}
.sheet-phrase{margin:16px 22px 0}
.sheet-phrase label{display:block;font-size:11px;font-weight:700;letter-spacing:.12em;
                    text-transform:uppercase;color:#7C8798;margin-bottom:7px}
.sheet-phrase label b{color:var(--gold);font-family:var(--mono);letter-spacing:0}
.sheet-ft{margin-top:20px;padding:14px 22px;border-top:1px solid var(--line-2);background:#0C121C;
          display:flex;gap:10px;justify-content:flex-end}
.sheet-ft .btn{padding:10px 18px;font-size:12.5px}

/* ── toasts ────────────────────────────────────────────────────────────── */
.toasts{position:fixed;right:22px;bottom:22px;z-index:90;display:flex;flex-direction:column;
        gap:9px;pointer-events:none}
.toast{min-width:260px;max-width:360px;padding:11px 15px;border-radius:10px;background:#161E2B;
       border:1px solid var(--line-3);border-left:3px solid var(--info);
       box-shadow:0 12px 34px rgba(0,0,0,.55);animation:conIn .18s ease}
.toast.ok{border-left-color:var(--up)}
.toast.err{border-left-color:var(--down)}
.toast.warn{border-left-color:var(--warn)}
.toast b{display:block;font-size:12.5px;font-weight:650;color:var(--hd)}
.toast span{font-size:11.5px;color:var(--tx-2);font-family:var(--mono)}

/* ── pager (unchanged contract with conPager) ──────────────────────────── */
.pager{display:flex;align-items:center;gap:10px;justify-content:center;padding:10px 6px 2px;flex-wrap:wrap}
.pager .btn{padding:4px 11px;font-size:12px}
.pager .pinfo{color:var(--tx-3);font-size:12px;font-variant-numeric:tabular-nums}
.pager .cap{color:var(--warn);font-size:11px}

/* ── legacy shims: old markup keeps working while pages migrate ────────── */
/* width:100% is load-bearing: .main is a COLUMN flex container, so the auto margins below
   are CROSS-axis margins, which override align-items:stretch and shrink-wrap the page to
   its content. Pages that want to be narrower set their own inline max-width. */
.wrap{width:100%;max-width:1520px;margin:0 auto;padding:22px 26px}
.grid{display:grid;gap:16px}
.cols{grid-template-columns:repeat(auto-fit,minmax(230px,1fr))}
.badge{display:inline-block;padding:2px 9px;border-radius:6px;font-size:11px;font-weight:700}
.badge.ok{background:var(--up-bg);color:var(--up)}
.badge.bad{background:var(--down-bg);color:var(--down)}
.badge.warn{background:var(--warn-bg);color:var(--warn)}
.badge.info{background:var(--info-bg);color:var(--info)}
.alert{padding:11px 14px;border-radius:var(--r);font-size:13px;margin-bottom:14px}
.alert.err{background:var(--down-bg);border:1px solid rgba(240,89,107,.35);color:#FFD0D6}
.alert.warn{background:var(--warn-bg);border:1px solid rgba(234,182,63,.35);color:#F6E3B0}
.logtbl{width:100%;border-collapse:collapse;font-size:12px;font-family:var(--mono)}
.logtbl td,.logtbl th{padding:5px 8px;border-bottom:1px solid var(--line-2);text-align:left}
.logtbl th{color:var(--tx-3);font-weight:600;text-transform:uppercase;font-size:10px;letter-spacing:.05em}
.kv{display:flex;justify-content:space-between;gap:12px;padding:7px 0;border-bottom:1px solid var(--line-2)}
.kv:last-child{border:0}
.kv .k{color:var(--tx-3);font-size:12px;text-transform:uppercase;letter-spacing:.05em}
.kv .v{color:var(--tx);font-weight:600}

/* ============================================================================================
   COMPATIBILITY - classes the old head.php <style> defined and this file did not.

   Replacing that inline stylesheet orphaned 16 selectors. Three were already dead (big, dbrow,
   lbl) and the nav/navgrp/navmenu set belonged to the retired top nav, but the rest are still
   used by live pages and lost their styling silently: gm.php's result rows had no box, no hover
   and no selected state at all.

   Re-expressed against THIS file's tokens. The old rules referenced --panel2, --border, --border2
   and --tx2, none of which exist here - restoring them verbatim would have resolved to nothing.
   ========================================================================================== */

/* gm.php account/character results. Each entry is its own separated card now, rather than a
   transparent row that ran into its neighbour. */
.res{display:block;padding:10px 12px;margin-bottom:8px;border-radius:var(--r);cursor:pointer;
     background:var(--panel);border:1px solid var(--line-2);
     transition:background .12s,border-color .12s}
.res:last-child{margin-bottom:0}
.res:hover{background:var(--panel-hi);border-color:var(--line-3)}
.res.sel{background:var(--panel-hi);border-color:var(--info);box-shadow:inset 0 0 0 1px var(--info-bd)}
.res .rn{font-weight:650;color:var(--hd);font-size:13.5px;line-height:1.35}
.res .rv{font-size:11.5px;color:var(--tx-2);margin-top:3px}

/* gm.php character cards */
.charcard{background:var(--panel-2);border:1px solid var(--line-2);border-radius:var(--r-md);
          padding:12px 14px;cursor:pointer;transition:border-color .12s}
.charcard:hover{border-color:var(--info)}
.charcard .cn{font-weight:700;color:var(--hd);font-size:15px}
.charcard .cm{color:var(--tx-2);font-size:12px;margin-top:2px}

/* muted pill state - used across 15 pages */
.pill.mut{color:var(--tx-2);background:rgba(136,146,164,.10);border-color:var(--line-3)}

/* preformatted log block - used by gm, logs, index and others */
.log{font-family:var(--mono);font-size:12px;color:var(--tx-2);background:var(--log);
     border:1px solid var(--line-2);border-radius:var(--r);padding:12px;max-height:150px;
     overflow:auto;white-space:pre-wrap;line-height:1.6}

/* ============================================================================================
   BACK-COMPAT TOKEN ALIASES

   Pages carry inline styles written against the OLD head.php palette. This file renames every
   one of those tokens, so `var(--tx2)` and friends resolved to nothing the moment the chrome was
   swapped - 64 references across 15 pages silently lost their colour.

   Aliased here rather than rewritten in 64 places: one block, reversible, and it keeps working if
   a page is edited later without knowing about the rename.

   The second group (--bd, --bg2, --ok, --ok-bg, --bad, --wn) was NEVER defined, not even by the
   old head.php - those references have always resolved to nothing. Given correct values here.
   ========================================================================================== */
:root{
  --tx2:var(--tx-2);
  --panel2:var(--panel-hi);
  --border:var(--line-2);
  --border2:var(--line-3);

  --bd:var(--line-2);
  --bg2:var(--panel-2);
  --ok:var(--up);
  --ok-bg:var(--up-bg);
  --bad:var(--down);
  --wn:var(--warn);
}

/* ============================================================================================
   Scheduled Tasks - centred topbar menu.
   .topbar is position:sticky with z-index:20 and no overflow clipping, so an absolutely
   positioned panel inside it paints over the page below without needing an override.
   ========================================================================================== */
.taskmenu{position:relative;outline:none;cursor:default;user-select:none}
.tm-label{display:inline-flex;align-items:center;gap:7px;padding:5px 11px;border-radius:999px;
  border:1px solid var(--line-2);background:var(--panel);color:var(--tx-2);
  font-size:11.5px;font-weight:700;letter-spacing:.05em;text-transform:uppercase;white-space:nowrap;
  transition:border-color .12s,color .12s}
.taskmenu:hover .tm-label,.taskmenu:focus-within .tm-label{border-color:var(--line-3);color:var(--hd)}
.tm-label i{color:var(--gold);font-style:normal}
.tm-count{min-width:17px;padding:0 5px;border-radius:999px;background:var(--gold-bg);
  color:var(--gold);font-size:10.5px;text-align:center}
.tm-drop{position:absolute;top:calc(100% + 8px);left:50%;transform:translateX(-50%) translateY(-5px);
  width:340px;max-height:60vh;overflow:auto;z-index:60;
  opacity:0;visibility:hidden;transition:opacity .12s ease,transform .12s ease,visibility .12s;
  background:var(--panel-2);border:1px solid var(--line-3);border-radius:var(--r-md);
  box-shadow:var(--sh-lg);padding:8px 10px;text-transform:none;letter-spacing:normal}
.taskmenu:hover .tm-drop,.taskmenu:focus-within .tm-drop{opacity:1;visibility:visible;transform:translateX(-50%) translateY(0)}
.tm-head{font-size:11px;color:var(--tx-2);padding:0 2px 7px;border-bottom:1px solid var(--line-2);
  margin-bottom:6px;font-weight:600}

/* ── skeleton: hold the footprint of content that has not been chosen yet ──
   gm.php's #detail is empty until an account is picked. Rather than an empty
   column, it draws the loaded layout's panels with inert placeholders, so
   choosing an account swaps text in instead of building the page. */
.skel .panel>.bd{opacity:.55;pointer-events:none;user-select:none}
.skel .bar{height:34px;border-radius:var(--r-sm);background:var(--line-2)}
.skel .bar.tall{height:86px}
.skel .row{display:flex;gap:10px;flex-wrap:wrap}

/* ── prose measure ──────────────────────────────────────────
   Help text and banners were running the full column - 56 runs over 90
   characters on one line, worst 392, against a comfortable 45-75.
   The cap goes on the TEXT, not on .wrap: the tables and editors sitting
   beside this help text still want the whole width.
   🛑 Scoped to <p> and .alert deliberately. .muted is also used INLINE -
   in table cells, flex rows and control labels - and a max-width there
   squeezes a chip or a row summary out of shape. Name the tag, never
   bare .muted. A page whose prose still reads long wants a page-level
   max-width (see passkey.php), not a change to this number. */
p.muted,.alert{max-width:66ch}
