/* =====================================================================
   OLT Premium — design-system do módulo OLT (OnNoc)
   Apenas VISUAL. Escopo restrito a .olt-premium para não afetar outras telas.
   Reutiliza tokens globais de design-system.css onde faz sentido.
   ===================================================================== */

.olt-premium {
  /* ---- superfícies / elevação (dark-first, look premium) ---- */
  --oltp-bg:            #0a0e17;
  --oltp-surface-1:     #0e1420;
  --oltp-surface-2:     #131a29;
  --oltp-surface-3:     #18213240;
  --oltp-elevated:      #141c2b;
  --oltp-border:        rgba(148,163,184,0.12);
  --oltp-border-strong: rgba(148,163,184,0.20);
  --oltp-divider:       rgba(148,163,184,0.08);

  /* ---- texto ---- */
  --oltp-fg:            #e8edf5;
  --oltp-fg-soft:       #aab6c8;
  --oltp-fg-muted:      #6b7688;
  --oltp-fg-faint:      #47526440;

  /* ---- acentos ---- */
  --oltp-accent:        #6366f1;
  --oltp-accent-soft:   rgba(99,102,241,0.14);
  --oltp-ok:            #22c55e;
  --oltp-ok-soft:       rgba(34,197,94,0.12);
  --oltp-warn:          #f59e0b;
  --oltp-warn-soft:     rgba(245,158,11,0.12);
  --oltp-danger:        #ef4444;
  --oltp-danger-soft:   rgba(239,68,68,0.12);
  --oltp-info:          #38bdf8;

  /* Cor de TEXTO para números com estado. Não é a mesma do ponto/barra:
     #22c55e sobre branco dá contraste fraco, e #6ee7b7 sobre branco some. */
  --oltp-ok-text:       #6ee7b7;
  --oltp-warn-text:     #fcd34d;
  --oltp-danger-text:   #fca5a5;
  --oltp-info-soft:     rgba(56,189,248,0.12);

  /* ---- forma / movimento ---- */
  --oltp-r-sm: 10px;
  --oltp-r:    14px;
  --oltp-r-lg: 18px;
  --oltp-r-xl: 22px;
  --oltp-gap:  16px;
  --oltp-pad:  18px;
  --oltp-t:    180ms;
  --oltp-e:    cubic-bezier(.2,.8,.2,1);
  --oltp-shadow:    0 1px 2px rgba(0,0,0,.28), 0 8px 24px -12px rgba(0,0,0,.5);
  --oltp-shadow-lg: 0 2px 6px rgba(0,0,0,.35), 0 24px 60px -24px rgba(0,0,0,.65);
  --oltp-glow:      0 0 0 1px var(--oltp-border-strong), 0 0 26px -8px rgba(99,102,241,.35);
}

html[data-theme="light"] .olt-premium {
  --oltp-bg:            #f5f7fb;
  --oltp-surface-1:     #ffffff;
  --oltp-surface-2:     #ffffff;
  --oltp-surface-3:     #f1f4f9;
  --oltp-elevated:      #ffffff;
  --oltp-border:        rgba(15,23,42,0.10);
  --oltp-border-strong: rgba(15,23,42,0.16);
  --oltp-divider:       rgba(15,23,42,0.07);
  --oltp-fg:            #0f172a;
  --oltp-fg-soft:       #475569;
  --oltp-fg-muted:      #94a3b8;
  --oltp-ok-text:       #15803d;
  --oltp-warn-text:     #b45309;
  --oltp-danger-text:   #b91c1c;
  --oltp-shadow:    0 1px 2px rgba(16,24,40,.06), 0 8px 24px -14px rgba(16,24,40,.18);
  --oltp-shadow-lg: 0 2px 6px rgba(16,24,40,.08), 0 24px 60px -24px rgba(16,24,40,.22);
}

/* ============================ superfície base ============================ */
.olt-card {
  background:
    linear-gradient(180deg, color-mix(in srgb, var(--oltp-surface-2) 100%, transparent), var(--oltp-surface-1));
  border: 1px solid var(--oltp-border);
  border-radius: var(--oltp-r-lg);
  box-shadow: var(--oltp-shadow);
  position: relative;
}
.olt-card--pad { padding: var(--oltp-pad); }
.olt-card__title {
  font-family: var(--font-display, 'Outfit'), sans-serif;
  font-weight: 700; font-size: 15px; letter-spacing: .01em;
  color: var(--oltp-fg); display: flex; align-items: center; gap: 8px;
}
.olt-card__sub { font-size: 11.5px; color: var(--oltp-fg-muted); margin-top: 2px; }
.olt-eyebrow {
  font-size: 10px; font-weight: 800; letter-spacing: .12em; text-transform: uppercase;
  color: var(--oltp-fg-muted);
}

/* ============================ HERO ============================ */
.olt-hero {
  border-radius: var(--oltp-r-xl);
  border: 1px solid var(--oltp-border);
  background:
    radial-gradient(120% 140% at 0% 0%, rgba(99,102,241,.10), transparent 42%),
    radial-gradient(120% 160% at 100% 0%, rgba(56,189,248,.08), transparent 46%),
    linear-gradient(180deg, var(--oltp-surface-2), var(--oltp-surface-1));
  box-shadow: var(--oltp-shadow-lg);
  padding: 20px 22px;
  position: relative; overflow: visible;
}
.olt-hero::after {
  content: ""; position: absolute; inset: 0 16px auto 16px; height: 1px;
  background: linear-gradient(90deg, transparent, rgba(148,163,184,.25), transparent);
}
.olt-breadcrumb { display: flex; align-items: center; gap: 8px; font-size: 12px; color: var(--oltp-fg-muted); }
.olt-breadcrumb b { color: var(--oltp-fg-soft); font-weight: 600; }
.olt-breadcrumb .sep { opacity: .5; }

.olt-hero__top { display: flex; align-items: flex-start; justify-content: space-between; gap: 18px; flex-wrap: wrap; }
.olt-hero__id { display: flex; align-items: center; gap: 16px; min-width: 0; }
.olt-hero__glyph {
  width: 56px; height: 56px; border-radius: var(--oltp-r); flex: none;
  display: grid; place-items: center;
  background: linear-gradient(160deg, rgba(99,102,241,.18), rgba(56,189,248,.10));
  border: 1px solid var(--oltp-border-strong);
  color: #c7d2fe;
}
.olt-hero__glyph svg { width: 26px; height: 26px; }
.olt-hero__titles { min-width: 0; }
.olt-hero__name {
  font-family: var(--font-display, 'Outfit'), sans-serif;
  font-weight: 800; font-size: 24px; line-height: 1.05; color: var(--oltp-fg);
  letter-spacing: -.01em; display: flex; align-items: center; gap: 12px; flex-wrap: wrap;
}
.olt-hero__meta { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; margin-top: 7px; font-size: 12px; color: var(--oltp-fg-muted); }
.olt-hero__meta .dot { width: 3px; height: 3px; border-radius: 999px; background: var(--oltp-fg-faint); }
.olt-hero__meta .mono { font-family: var(--font-mono, monospace); color: var(--oltp-fg-soft); }
.olt-hero__vendor { height: 20px; width: auto; max-width: 82px; object-fit: contain; opacity: .95; }

/* status online chip */
.olt-live {
  display: inline-flex; align-items: center; gap: 6px; padding: 3px 10px; border-radius: 999px;
  font-size: 10.5px; font-weight: 800; letter-spacing: .06em; text-transform: uppercase;
  border: 1px solid var(--oltp-ok-soft); color: #6ee7b7; background: var(--oltp-ok-soft);
}
.olt-live .pulse { width: 7px; height: 7px; border-radius: 999px; background: var(--oltp-ok); box-shadow: 0 0 0 0 rgba(34,197,94,.6); animation: oltPulse 2s infinite; }
.olt-live--danger { border-color: var(--oltp-danger-soft); color: #fca5a5; background: var(--oltp-danger-soft); }
.olt-live--danger .pulse { background: var(--oltp-danger); animation: none; }
@keyframes oltPulse { 0%{box-shadow:0 0 0 0 rgba(34,197,94,.55)} 70%{box-shadow:0 0 0 7px rgba(34,197,94,0)} 100%{box-shadow:0 0 0 0 rgba(34,197,94,0)} }

/* health ring */
.olt-health { display: flex; align-items: center; gap: 14px; }
.olt-ring { --v: 0; width: 78px; height: 78px; flex: none; position: relative; display: grid; place-items: center; }
.olt-ring svg { transform: rotate(-90deg); width: 100%; height: 100%; }
.olt-ring__bg { fill: none; stroke: var(--oltp-border); stroke-width: 7; }
.olt-ring__fg { fill: none; stroke: var(--oltp-ok); stroke-width: 7; stroke-linecap: round; transition: stroke-dashoffset .8s var(--oltp-e), stroke .4s; }
.olt-ring__val { position: absolute; text-align: center; }
.olt-ring__num { font-family: var(--font-display,'Outfit'); font-weight: 800; font-size: 20px; color: var(--oltp-fg); line-height: 1; }
.olt-ring__pct { font-size: 9px; color: var(--oltp-fg-muted); }
.olt-health__label .k { font-size: 11px; color: var(--oltp-fg-muted); }
.olt-health__label .v { font-family: var(--font-display,'Outfit'); font-weight: 700; font-size: 14px; color: var(--oltp-fg); }

/* inline KPIs do hero */
.olt-hero__kpis {
  margin-top: 18px; display: grid; gap: 1px; grid-template-columns: repeat(6, 1fr);
  background: var(--oltp-divider); border: 1px solid var(--oltp-border); border-radius: var(--oltp-r);
  overflow: hidden;
}
.olt-hero__kpi { background: var(--oltp-surface-1); padding: 13px 16px; }
.olt-hero__kpi .k { font-size: 10.5px; color: var(--oltp-fg-muted); font-weight: 600; }
.olt-hero__kpi .v { font-family: var(--font-display,'Outfit'); font-weight: 800; font-size: 19px; color: var(--oltp-fg); margin-top: 3px; line-height: 1; }
.olt-hero__kpi .v small { font-size: 11px; color: var(--oltp-fg-muted); font-weight: 600; }
.olt-hero__kpi .v.ok { color: #6ee7b7; } .olt-hero__kpi .v.danger { color: #fca5a5; } .olt-hero__kpi .v.warn { color: #fcd34d; }
@media (max-width: 1100px){ .olt-hero__kpis { grid-template-columns: repeat(3,1fr); } }
@media (max-width: 560px){ .olt-hero__kpis { grid-template-columns: repeat(2,1fr); } }

/* seletor de OLT */
.olt-switcher { position: relative; }
.olt-switch-btn {
  display: inline-flex; align-items: center; gap: 9px; padding: 8px 12px; cursor: pointer;
  border-radius: var(--oltp-r-sm); border: 1px solid var(--oltp-border-strong);
  background: var(--oltp-surface-3); color: var(--oltp-fg-soft); font-size: 12.5px; font-weight: 600;
  transition: border-color var(--oltp-t) var(--oltp-e), background var(--oltp-t);
}
.olt-switch-btn:hover { border-color: var(--oltp-accent); background: var(--oltp-accent-soft); color: var(--oltp-fg); }
.olt-switch-btn svg { width: 15px; height: 15px; opacity: .7; }
.olt-switch-menu {
  position: absolute; z-index: 40; top: calc(100% + 6px); right: 0; min-width: 288px;
  background: var(--oltp-elevated); border: 1px solid var(--oltp-border-strong);
  border-radius: var(--oltp-r); box-shadow: var(--oltp-shadow-lg); padding: 4px;
  max-height: calc(100vh - 260px); overflow-y: auto; overscroll-behavior: contain;
  opacity: 0; transform: translateY(-6px) scale(.98); pointer-events: none;
  transition: opacity var(--oltp-t) var(--oltp-e), transform var(--oltp-t) var(--oltp-e);
}
.olt-switch-menu::-webkit-scrollbar { width: 8px; }
.olt-switch-menu::-webkit-scrollbar-thumb { background: var(--oltp-border-strong); border-radius: 999px; }
.olt-switch-menu::-webkit-scrollbar-track { background: transparent; }
.olt-switcher.is-open .olt-switch-menu { opacity: 1; transform: none; pointer-events: auto; }
.olt-switch-item {
  display: flex; align-items: center; gap: 10px; width: 100%; text-align: left; cursor: pointer;
  padding: 6px 10px; border-radius: var(--oltp-r-sm); border: 0; background: transparent; color: var(--oltp-fg-soft);
  transition: background var(--oltp-t);
}
.olt-switch-item:hover { background: var(--oltp-surface-3); }
.olt-switch-item--active { background: var(--oltp-accent-soft); }
.olt-switch-item__dot { width: 8px; height: 8px; border-radius: 999px; flex: none; }
.olt-switch-item__main { min-width: 0; flex: 1; }
.olt-switch-item__name { font-size: 12.5px; font-weight: 600; line-height: 1.2; color: var(--oltp-fg); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.olt-switch-item__sub { font-size: 9.5px; line-height: 1.15; color: var(--oltp-fg-muted); font-family: var(--font-mono,monospace); }
.olt-switch-item__pct { font-family: var(--font-display,'Outfit'); font-weight: 800; font-size: 13px; }

/* ============================ KPI row (por OLT) ============================ */
.olt-kpi-row { display: grid; gap: var(--oltp-gap); grid-template-columns: repeat(6, 1fr); }
@media (max-width: 1200px){ .olt-kpi-row { grid-template-columns: repeat(3,1fr); } }
@media (max-width: 640px){ .olt-kpi-row { grid-template-columns: repeat(2,1fr); } }
.olt-kpi {
  background: linear-gradient(180deg, var(--oltp-surface-2), var(--oltp-surface-1));
  border: 1px solid var(--oltp-border); border-radius: var(--oltp-r); padding: 15px 16px 11px;
  position: relative; overflow: hidden; box-shadow: var(--oltp-shadow);
  transition: border-color var(--oltp-t) var(--oltp-e), transform var(--oltp-t) var(--oltp-e), box-shadow var(--oltp-t);
}
.olt-kpi:hover { border-color: var(--oltp-border-strong); transform: translateY(-2px); box-shadow: var(--oltp-shadow-lg); }
.olt-kpi__top { display: flex; align-items: center; justify-content: space-between; min-height: 22px; }
.olt-kpi__ico { width: 32px; height: 32px; border-radius: 9px; display: grid; place-items: center; background: var(--oltp-surface-3); color: var(--oltp-fg-soft); }
.olt-kpi__ico svg { width: 16px; height: 16px; }
.olt-kpi__ico--info { background: var(--oltp-info-soft); color: #7dd3fc; }
.olt-kpi__ico--ok { background: var(--oltp-ok-soft); color: #6ee7b7; }
.olt-kpi__ico--warn { background: var(--oltp-warn-soft); color: #fcd34d; }
.olt-kpi__ico--danger { background: var(--oltp-danger-soft); color: #fca5a5; }
.olt-kpi__ico--accent { background: var(--oltp-accent-soft); color: #c7d2fe; }
.olt-kpi__label { font-size: 11px; color: var(--oltp-fg-muted); font-weight: 600; margin-top: 11px; letter-spacing: .01em; }
.olt-kpi__value { font-family: var(--font-display,'Outfit'); font-weight: 800; font-size: 23px; color: var(--oltp-fg); line-height: 1.05; margin-top: 2px; font-variant-numeric: tabular-nums; }
.olt-kpi__value small { font-size: 12px; font-weight: 600; color: var(--oltp-fg-muted); }
.olt-kpi__sub { font-size: 10.5px; color: var(--oltp-fg-muted); margin-top: 3px; min-height: 13px; }
.olt-kpi__spark { margin-top: 8px; height: 34px; }
.olt-kpi__spark--sev { display: flex; align-items: flex-end; gap: 5px; height: 34px; }
.olt-kpi__sevbar { flex: 1; border-radius: 4px 4px 0 0; min-height: 3px; opacity: .9; }

/* ============================ botões premium ============================ */
.olt-btn {
  display: inline-flex; align-items: center; gap: 7px; padding: 8px 13px; cursor: pointer;
  border-radius: var(--oltp-r-sm); font-size: 12.5px; font-weight: 600; line-height: 1;
  border: 1px solid var(--oltp-border-strong); background: var(--oltp-surface-3); color: var(--oltp-fg-soft);
  transition: transform var(--oltp-t) var(--oltp-e), border-color var(--oltp-t), background var(--oltp-t), color var(--oltp-t);
}
.olt-btn svg { width: 15px; height: 15px; }
.olt-btn:hover { border-color: var(--oltp-border-strong); background: var(--oltp-surface-2); color: var(--oltp-fg); transform: translateY(-1px); }
.olt-btn:active { transform: translateY(0); }
.olt-btn--primary {
  border-color: transparent; color: #fff;
  background: linear-gradient(180deg, #6d6ff5, var(--oltp-accent));
  box-shadow: 0 6px 18px -8px rgba(99,102,241,.7);
}
.olt-btn--primary:hover { background: linear-gradient(180deg, #7a7cf7, #5a5df0); }
.olt-btn--ghost { background: transparent; }
.olt-btn--icon { padding: 8px; }
.olt-btn:disabled { opacity: .5; cursor: not-allowed; transform: none; }

/* ============================ badges ============================ */
.olt-tag {
  display: inline-flex; align-items: center; gap: 6px; padding: 3px 9px; border-radius: 999px;
  font-size: 10.5px; font-weight: 800; letter-spacing: .03em; line-height: 1.4;
  border: 1px solid var(--oltp-border); color: var(--oltp-fg-soft); background: var(--oltp-surface-3);
}
.olt-tag--ok     { color:#6ee7b7; border-color:var(--oltp-ok-soft); background:var(--oltp-ok-soft); }
.olt-tag--warn   { color:#fcd34d; border-color:var(--oltp-warn-soft); background:var(--oltp-warn-soft); }
.olt-tag--danger { color:#fca5a5; border-color:var(--oltp-danger-soft); background:var(--oltp-danger-soft); }
/* LOS (perda de sinal óptico): roxo, para não se confundir com o vermelho de offline. */
.olt-tag--los    { color:#c4b5fd; border-color:rgba(139,92,246,.38); background:rgba(139,92,246,.16); }
/* Porta PON da placa que ainda não tem ONU nenhuma: é onde se planeja cliente novo. */
.olt-sinal-lbl { font-size:11px; color:var(--oltp-fg-muted); letter-spacing:.04em; text-transform:uppercase; }
#oltSinalBox .olt-mgmtvlan__in { width:96px; }
.olt-porta-livre { margin-left:6px; padding:1px 6px; border-radius:999px; font-size:11px; letter-spacing:.02em;
                   color:#7dd3fc; background:rgba(56,189,248,.14); border:1px solid rgba(56,189,248,.3); }
.olt-tag--info   { color:#7dd3fc; border-color:var(--oltp-info-soft); background:var(--oltp-info-soft); }
.olt-tag__dot { width:6px; height:6px; border-radius:999px; background: currentColor; }

/* ============================ Portas PON (cards) ============================ */
#ponGrid.olt-pon-grid { grid-template-columns: repeat(auto-fill, minmax(196px, 1fr)); gap: var(--oltp-gap); }
.olt-pon {
  text-align: left; cursor: pointer; border-radius: var(--oltp-r); padding: 13px 15px;
  border: 1px solid var(--oltp-border);
  background: linear-gradient(180deg, var(--oltp-surface-2), var(--oltp-surface-1));
  position: relative; overflow: hidden;
  transition: transform var(--oltp-t) var(--oltp-e), border-color var(--oltp-t), box-shadow var(--oltp-t);
}
.olt-pon::before {
  content: ""; position: absolute; left: 0; top: 0; bottom: 0; width: 3px;
  background: var(--_accent, transparent); opacity: .85;
}
.olt-pon:hover { transform: translateY(-2px); border-color: var(--oltp-border-strong); box-shadow: var(--oltp-shadow-lg); }
.olt-pon--active { border-color: var(--oltp-accent); box-shadow: var(--oltp-glow); }
.olt-pon--down { border-color: rgba(239,68,68,.32); }
.olt-pon--alert { border-color: rgba(245,158,11,.34); }
.olt-pon__head { display: flex; align-items: center; justify-content: space-between; gap: 6px; }
.olt-pon__label { font-family: var(--font-mono,monospace); font-weight: 800; font-size: 13px; color: var(--oltp-fg); letter-spacing: .02em; }
.olt-pon__count { display: flex; align-items: baseline; gap: 5px; margin-top: 12px; }
.olt-pon__count b { font-family: var(--font-display,'Outfit'); font-weight: 800; font-size: 22px; color: var(--oltp-fg); line-height: 1; font-variant-numeric: tabular-nums; }
.olt-pon__count span { font-size: 11px; color: var(--oltp-fg-muted); }
.olt-pon__pct { margin-left: auto; font-family: var(--font-display,'Outfit'); font-weight: 800; font-size: 14px; }
.olt-pon__bar { height: 6px; border-radius: 999px; background: var(--oltp-surface-3); overflow: hidden; margin-top: 10px; }
.olt-pon__fill { height: 100%; border-radius: 999px; transition: width .5s var(--oltp-e); }
.olt-pon__foot { display: flex; justify-content: space-between; align-items: center; margin-top: 10px; font-size: 10px; color: var(--oltp-fg-muted); }
.olt-pon__rx { font-family: var(--font-mono,monospace); color: var(--oltp-fg-soft); }
.olt-pon__badge { font-size: 9px; font-weight: 800; padding: 1px 6px; border-radius: 999px; }

/* faceplate (slots) — leve refino */
#ponFace.olt-faceplate { gap: 7px; }

/* ============================ Mapa de saúde das ONUs ============================ */
#onuGrid.olt-onu-grid { gap: 4px; margin-top: 12px; }
.olt-onu-cell {
  width: 16px; height: 16px; border-radius: 4px; cursor: pointer; border: 0; padding: 0;
  transition: transform var(--oltp-t) var(--oltp-e), box-shadow var(--oltp-t);
}
.olt-onu-cell:hover { transform: scale(1.35); box-shadow: 0 0 0 2px var(--oltp-bg), 0 0 12px -2px rgba(99,102,241,.7); position: relative; z-index: 2; }
.olt-onu-cell--ok { background: #22c55e; }
.olt-onu-cell--down { background: #ef4444; }
.olt-onu-cell--warn { background: #f59e0b; }
.olt-onu-cell--los  { background: #8b5cf6; }
.olt-onu-cell--idle { background: #334155; }
.olt-onu-cell--bad { outline: 2px solid #fbbf24; outline-offset: -2px; }

.olt-onu-legend { display: flex; flex-wrap: wrap; gap: 16px; margin-top: 13px; font-size: 11px; color: var(--oltp-fg-muted); }
.olt-onu-legend .it { display: inline-flex; align-items: center; gap: 7px; }
.olt-onu-legend .sw { width: 11px; height: 11px; border-radius: 3px; flex: none; }
.olt-onu-legend .sw--bad { background: transparent; outline: 2px solid #fbbf24; outline-offset: -2px; }

.olt-onu-tip {
  /* Fica em document.body, fora de .olt-premium: precisa dos tokens aqui, senão
     `var(--oltp-elevated)` não resolve e o balão perde o fundo. Escuro fixo nos dois
     temas, como o modal da ONU. */
  --oltp-elevated: #141c2b; --oltp-border-strong: rgba(148,163,184,0.20);
  --oltp-divider: rgba(148,163,184,0.08);
  --oltp-fg: #e8edf5; --oltp-fg-soft: #aab6c8; --oltp-fg-muted: #6b7688;
  --oltp-ok-text: #6ee7b7; --oltp-warn-text: #fcd34d; --oltp-danger-text: #fca5a5;
  position: fixed; z-index: 200; pointer-events: none; min-width: 196px; max-width: 264px;
  background: var(--oltp-elevated); border: 1px solid var(--oltp-border-strong);
  border-radius: var(--oltp-r); box-shadow: var(--oltp-shadow-lg); padding: 11px 12px;
  opacity: 0; transform: translateY(4px); transition: opacity .12s var(--oltp-e), transform .12s var(--oltp-e);
}
.olt-onu-tip.is-on { opacity: 1; transform: none; }
.olt-onu-tip__h { display: flex; align-items: center; justify-content: space-between; gap: 8px; }
.olt-onu-tip__name { font-weight: 700; font-size: 13px; color: var(--oltp-fg); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.olt-onu-tip__grid { display: grid; grid-template-columns: auto 1fr; gap: 4px 12px; margin-top: 9px; font-size: 11px; align-items: baseline; }
.olt-onu-tip__k { color: var(--oltp-fg-muted); }
.olt-onu-tip__v { color: var(--oltp-fg-soft); font-family: var(--font-mono,monospace); text-align: right; overflow: hidden; text-overflow: ellipsis; }

/* ============================ sparkline ============================ */
.olt-spark { display:block; width:100%; height:34px; }
.olt-spark path.line { fill:none; stroke-width:2; stroke-linecap:round; stroke-linejoin:round; }
.olt-spark path.area { stroke:none; opacity:.16; }

/* tendência */
.olt-trend { display:inline-flex; align-items:center; gap:3px; font-size:11px; font-weight:700; }
.olt-trend svg { width:13px; height:13px; }
.olt-trend--up { color:#6ee7b7; } .olt-trend--down { color:#fca5a5; } .olt-trend--flat { color:var(--oltp-fg-muted); }

/* ============================ Layout conteúdo + sidebar ============================ */
.olt-layout { display: grid; grid-template-columns: minmax(0, 1fr) 340px; gap: var(--oltp-gap); align-items: start; }
.olt-layout__main { min-width: 0; display: flex; flex-direction: column; gap: var(--oltp-gap); }
@media (max-width: 1180px) { .olt-layout { grid-template-columns: 1fr; } }

/* ============================ Painel lateral ============================ */
.olt-side { display: flex; flex-direction: column; gap: var(--oltp-gap); position: sticky; top: 12px; }
@media (max-width: 1180px) { .olt-side { position: static; } }
.olt-side-kv { display: grid; grid-template-columns: auto 1fr; gap: 10px 12px; margin-top: 14px; font-size: 12px; align-items: center; }
.olt-side-kv .k { color: var(--oltp-fg-muted); }
.olt-side-kv .v { color: var(--oltp-fg); font-weight: 600; text-align: right; overflow: hidden; text-overflow: ellipsis; }
.olt-side-kv .v.mono { font-family: var(--font-mono,monospace); font-weight: 500; color: var(--oltp-fg-soft); }
.olt-side-kv .v .vlogo { display: inline-flex; vertical-align: middle; }
.olt-side-stat { display: flex; align-items: center; justify-content: space-between; padding: 11px 0; border-bottom: 1px solid var(--oltp-divider); }
.olt-side-stat:last-child { border-bottom: 0; padding-bottom: 0; }
.olt-side-stat__l { display: flex; align-items: center; gap: 10px; font-size: 12px; color: var(--oltp-fg-soft); }
.olt-side-stat__ico { width: 28px; height: 28px; border-radius: 8px; display: grid; place-items: center; background: var(--oltp-surface-3); color: var(--oltp-fg-soft); }
.olt-side-stat__ico svg { width: 14px; height: 14px; }
.olt-side-stat__v { font-family: var(--font-display,'Outfit'); font-weight: 800; font-size: 15px; color: var(--oltp-fg); font-variant-numeric: tabular-nums; }
.olt-side-events { margin-top: 12px; }
.olt-side-event { display: flex; gap: 10px; padding: 9px 0; border-top: 1px solid var(--oltp-divider); }
.olt-side-event:first-child { border-top: 0; }
.olt-side-event__dot { width: 7px; height: 7px; border-radius: 999px; margin-top: 5px; flex: none; }
.olt-side-event__msg { font-size: 12px; color: var(--oltp-fg-soft); line-height: 1.35; }
.olt-side-event__meta { font-size: 10px; color: var(--oltp-fg-muted); margin-top: 2px; text-transform: uppercase; letter-spacing: .04em; }

/* ============================ inputs / filtros ============================ */
.olt-input, .olt-select {
  background: var(--oltp-surface-3); border: 1px solid var(--oltp-border-strong); color: var(--oltp-fg);
  border-radius: var(--oltp-r-sm); padding: 8px 12px; font-size: 12.5px; outline: none;
  transition: border-color var(--oltp-t), box-shadow var(--oltp-t);
}
.olt-input::placeholder { color: var(--oltp-fg-muted); }
.olt-input:focus, .olt-select:focus { border-color: var(--oltp-accent); box-shadow: 0 0 0 3px var(--oltp-accent-soft); }
.olt-check { display: inline-flex; align-items: center; gap: 7px; font-size: 12px; color: var(--oltp-fg-soft); cursor: pointer; }
.olt-check input { accent-color: var(--oltp-accent); width: 14px; height: 14px; }

/* ============================ tabela ONU ============================ */
.olt-table-wrap { overflow: auto; max-height: 440px; margin-top: 14px; border-radius: var(--oltp-r); border: 1px solid var(--oltp-border); }
table.olt-table { width: 100%; border-collapse: collapse; font-size: 12.5px; }
.olt-table thead th {
  position: sticky; top: 0; z-index: 1; text-align: left; padding: 11px 14px; white-space: nowrap;
  font-size: 10px; font-weight: 800; letter-spacing: .06em; text-transform: uppercase; color: var(--oltp-fg-muted);
  background: var(--oltp-surface-2); border-bottom: 1px solid var(--oltp-border);
}
.olt-table tbody td { padding: 9px 14px; border-bottom: 1px solid var(--oltp-divider); color: var(--oltp-fg-soft); vertical-align: middle; white-space: nowrap; }
.olt-table tbody tr { cursor: pointer; transition: background var(--oltp-t); }
.olt-table tbody tr:hover { background: var(--oltp-accent-soft); }
.olt-table tbody tr:last-child td { border-bottom: 0; }
.olt-table .mono { font-family: var(--font-mono,monospace); }
.olt-table__name { color: var(--oltp-fg); font-weight: 600; }
.olt-table__model { display: inline-flex; align-items: center; gap: 7px; }
.olt-table__act { width: 30px; height: 30px; border-radius: 8px; border: 1px solid var(--oltp-border); background: var(--oltp-surface-3); color: var(--oltp-fg-muted); display: inline-grid; place-items: center; cursor: pointer; transition: color var(--oltp-t), border-color var(--oltp-t); }
tr:hover .olt-table__act { color: var(--oltp-fg-soft); border-color: var(--oltp-border-strong); }
.olt-t-right { text-align: right; } .olt-t-center { text-align: center; }

/* paginação */
.olt-pager { display: flex; align-items: center; justify-content: space-between; gap: 12px; margin-top: 14px; flex-wrap: wrap; }
.olt-pager__info { font-size: 12px; color: var(--oltp-fg-muted); }
.olt-pager__ctrl { display: flex; align-items: center; gap: 4px; }
.olt-page-btn {
  min-width: 30px; height: 30px; padding: 0 8px; border-radius: 8px; border: 1px solid var(--oltp-border);
  background: var(--oltp-surface-3); color: var(--oltp-fg-soft); font-size: 12px; font-weight: 600; cursor: pointer;
  display: inline-grid; place-items: center; transition: border-color var(--oltp-t), background var(--oltp-t), color var(--oltp-t);
}
.olt-page-btn svg { width: 15px; height: 15px; }
.olt-page-btn:hover:not(:disabled) { border-color: var(--oltp-accent); color: var(--oltp-fg); }
.olt-page-btn--active { background: var(--oltp-accent); border-color: var(--oltp-accent); color: #fff; }
.olt-page-btn:disabled { opacity: .4; cursor: not-allowed; }
.olt-page-ellipsis { color: var(--oltp-fg-muted); padding: 0 3px; }

/* ============================ skeleton / estados ============================ */
.olt-skel { position: relative; overflow: hidden; background: var(--oltp-surface-3); border-radius: var(--oltp-r-sm); }
.olt-skel::after {
  content:""; position:absolute; inset:0;
  background: linear-gradient(90deg, transparent, rgba(148,163,184,.12), transparent);
  transform: translateX(-100%); animation: oltShimmer 1.3s infinite;
}
@keyframes oltShimmer { 100% { transform: translateX(100%); } }

/* barra de carregamento (topo) */
.olt-loadbar { position: fixed; top: 0; left: 0; right: 0; height: 2px; z-index: 300; overflow: hidden; opacity: 0; transition: opacity .2s var(--oltp-e); pointer-events: none; }
.olt-loadbar.is-on { opacity: 1; }
.olt-loadbar::before { content: ""; position: absolute; top: 0; left: -40%; width: 40%; height: 100%; background: linear-gradient(90deg, transparent, var(--oltp-accent), #7dd3fc, transparent); animation: oltBar 1.1s var(--oltp-e) infinite; }
@keyframes oltBar { 0% { left: -40%; } 100% { left: 100%; } }
.olt-spin svg { animation: oltSpin .8s linear infinite; }
@keyframes oltSpin { to { transform: rotate(360deg); } }

.olt-empty { text-align:center; padding: 28px 16px; color: var(--oltp-fg-muted); }
.olt-empty__icon { width:44px; height:44px; border-radius:12px; margin:0 auto 10px; display:grid; place-items:center; background:var(--oltp-surface-3); border:1px solid var(--oltp-border); color:var(--oltp-fg-soft); }
.olt-empty__title { font-weight:700; color:var(--oltp-fg-soft); font-size:14px; }
.olt-empty__text { font-size:12px; margin-top:4px; }

/* animação de atualização (aplicada e removida via JS) */
@keyframes oltFlash { 0%{ box-shadow: 0 0 0 0 rgba(99,102,241,.0);} 30%{ box-shadow: inset 0 0 0 1px rgba(99,102,241,.5), 0 0 20px -6px rgba(99,102,241,.5);} 100%{ box-shadow: 0 0 0 0 rgba(99,102,241,0);} }
.olt-flash { animation: oltFlash .9s var(--oltp-e); }

@keyframes oltFadeUp { from { opacity:0; transform: translateY(6px);} to { opacity:1; transform:none; } }
.olt-fade-up { animation: oltFadeUp .28s var(--oltp-e) both; }
@media (prefers-reduced-motion: reduce) {
  .olt-live .pulse, .olt-skel::after, .olt-flash, .olt-fade-up { animation: none !important; }
  .olt-ring__fg { transition: none; }
}

/* =====================================================================
   MODAL DA ONU — densidade e hierarquia
   O grid anterior dava o MESMO peso visual a tudo: potência, distância,
   provisionamento e fase ocupavam cards idênticos. Quem abre a ONU está
   atrás do sinal; o resto é contexto. Aqui o sinal vira o herói e o
   contexto vira lista densa.
   Escopo próprio (.olt-onu-modal) porque o modal fica FORA do <main>
   que carrega .olt-premium.
   ===================================================================== */
.olt-onu-modal {
  --oltp-surface-1: #0e1420; --oltp-surface-2: #131a29; --oltp-elevated: #141c2b;
  --oltp-border: rgba(148,163,184,0.12); --oltp-border-strong: rgba(148,163,184,0.20);
  --oltp-divider: rgba(148,163,184,0.08);
  --oltp-fg: #e8edf5; --oltp-fg-soft: #aab6c8; --oltp-fg-muted: #6b7688;
  --oltp-ok: #22c55e; --oltp-warn: #f59e0b; --oltp-danger: #ef4444; --oltp-info: #38bdf8;
  --oltp-accent: #6366f1;
}

/* ---- herói: as duas potências ----
   Prefixo .olt-rxc (rx card) e NÃO .olt-sig: esse último já existe no <style> do
   olt.html para a célula de sinal da TABELA, como `display:inline-flex; font-size:11px`.
   Como a tag <style> vem depois do <link>, ela vencia por ordem e achatava o herói
   numa linha só — foi o que o usuário viu na tela. */
.olt-onu-hero {
  display: grid; grid-template-columns: 1fr 1fr minmax(120px, auto); gap: 22px; align-items: stretch;
  background: linear-gradient(180deg, rgba(56,189,248,0.05), transparent 70%), var(--oltp-surface-1);
  border: 1px solid var(--oltp-border-strong); border-radius: 16px; padding: 18px 20px;
}
@media (max-width: 720px) { .olt-onu-hero { grid-template-columns: 1fr; } }

.olt-rxc { min-width: 0; }
.olt-rxc__lbl {
  font-size: 10px; letter-spacing: .1em; text-transform: uppercase;
  color: var(--oltp-fg-muted); font-weight: 600;
}
.olt-rxc__val {
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  font-size: 32px; font-weight: 600; letter-spacing: -.02em; line-height: 1.1;
  font-variant-numeric: tabular-nums; margin-top: 2px; color: var(--oltp-fg);
}
.olt-rxc__val small { font-size: 14px; font-weight: 500; color: var(--oltp-fg-muted); margin-left: 4px; }
.olt-rxc__val--ok { color: var(--oltp-ok); }
.olt-rxc__val--warn { color: var(--oltp-warn); }
.olt-rxc__val--bad { color: var(--oltp-danger); }
.olt-rxc__val--none { color: var(--oltp-fg-muted); font-size: 22px; }
.olt-rxc__hint { font-size: 11px; color: var(--oltp-fg-muted); margin-top: 3px; }

/* Régua com as faixas reais: crítico / atenção / normal / ótimo.
   O marcador mostra ONDE o valor cai, não só o número. */
.olt-gauge { margin-top: 10px; position: relative; height: 6px; border-radius: 999px; overflow: visible;
  background: linear-gradient(90deg,
    var(--oltp-danger) 0%, var(--oltp-danger) 11.5%,
    var(--oltp-warn) 11.5%, var(--oltp-warn) 26.9%,
    var(--oltp-ok) 26.9%, var(--oltp-ok) 100%);
  opacity: .55; }
.olt-gauge__pin { position: absolute; top: -4px; width: 3px; height: 14px; border-radius: 2px;
  background: var(--oltp-fg); box-shadow: 0 0 0 2px var(--oltp-surface-1); transform: translateX(-1.5px); }
.olt-gauge__scale { display: flex; justify-content: space-between; font-size: 9px;
  color: var(--oltp-fg-muted); font-family: ui-monospace, monospace; margin-top: 7px; }

.olt-hero-side { display: flex; flex-direction: column; gap: 10px; justify-content: center;
  padding-left: 18px; border-left: 1px solid var(--oltp-divider); min-width: 132px; }
@media (max-width: 720px) { .olt-hero-side { border-left: 0; padding-left: 0; border-top: 1px solid var(--oltp-divider); padding-top: 12px; } }
.olt-hero-side__lbl { font-size: 10px; letter-spacing: .08em; text-transform: uppercase; color: var(--oltp-fg-muted); }
.olt-hero-side__val { font-family: ui-monospace, monospace; font-size: 16px; color: var(--oltp-fg); font-variant-numeric: tabular-nums; }

/* ---- faixa de identidade: denso, sem card por campo ---- */
.olt-ident { display: flex; flex-wrap: wrap; gap: 0; margin-top: 14px;
  border: 1px solid var(--oltp-border); border-radius: 12px; overflow: hidden; background: var(--oltp-surface-2); }
.olt-ident__item { flex: 1 1 150px; min-width: 0; padding: 10px 14px; border-right: 1px solid var(--oltp-divider); }
.olt-ident__item:last-child { border-right: 0; }
.olt-ident__lbl { font-size: 9.5px; letter-spacing: .09em; text-transform: uppercase; color: var(--oltp-fg-muted); font-weight: 600; }
.olt-ident__val { font-size: 13px; color: var(--oltp-fg); margin-top: 2px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.olt-ident__val--mono { font-family: ui-monospace, monospace; font-size: 12px; }

/* ---- painéis ---- */
.olt-cols { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; margin-top: 12px; }
@media (max-width: 720px) { .olt-cols { grid-template-columns: 1fr; } }
.olt-panel { border: 1px solid var(--oltp-border); border-radius: 12px; background: var(--oltp-surface-2); padding: 14px 16px; }
.olt-panel__title { font-size: 10px; letter-spacing: .1em; text-transform: uppercase; color: var(--oltp-fg-muted);
  font-weight: 600; display: flex; align-items: center; justify-content: space-between; gap: 8px; }
.olt-kv { display: flex; align-items: baseline; justify-content: space-between; gap: 12px;
  padding: 7px 0; border-bottom: 1px solid var(--oltp-divider); }
.olt-kv:last-child { border-bottom: 0; }
.olt-kv__k { font-size: 11.5px; color: var(--oltp-fg-muted); }
.olt-kv__v { font-size: 12.5px; color: var(--oltp-fg); text-align: right; font-variant-numeric: tabular-nums; }
.olt-kv__v--mono { font-family: ui-monospace, monospace; font-size: 12px; }
.olt-kv__v--none { color: var(--oltp-fg-muted); }
.olt-empty { font-size: 11.5px; color: var(--oltp-fg-muted); padding: 10px 0; line-height: 1.5; }

/* ---- tabela de portas do cliente ---- */
.olt-ptable { width: 100%; border-collapse: collapse; font-size: 12px; margin-top: 6px; }
.olt-ptable th { text-align: left; font-size: 9.5px; letter-spacing: .09em; text-transform: uppercase;
  color: var(--oltp-fg-muted); font-weight: 600; padding: 6px 8px; border-bottom: 1px solid var(--oltp-border); }
.olt-ptable td { padding: 7px 8px; border-bottom: 1px solid var(--oltp-divider); color: var(--oltp-fg); }
.olt-ptable tr:last-child td { border-bottom: 0; }
.olt-ptable .up { color: var(--oltp-ok); }
.olt-ptable .down { color: var(--oltp-fg-muted); }
.olt-ptable .alert { color: var(--oltp-danger); font-weight: 600; }

/* Ficha da ONU: pares rótulo/valor em colunas, densa como o "ONU details" da CLI. */
.olt-ficha { display: grid; grid-template-columns: repeat(auto-fill, minmax(190px, 1fr)); gap: 0 18px; margin-top: 4px; }
.olt-ficha .olt-kv { padding: 6px 0; }
/* Histórico: o motivo é a coluna que importa, então ganha cor por tipo. */
.olt-ptable .motivo-energia { color: var(--oltp-warn); }
.olt-ptable .motivo-optico { color: var(--oltp-danger); }
.olt-ptable .motivo-outro { color: var(--oltp-fg-soft); }
.olt-ptable .agora { color: var(--oltp-ok); font-weight: 600; }

/* Barra de ações do modal — consultas ao equipamento, sob demanda. */
.olt-actions { display: flex; flex-wrap: wrap; gap: 8px; align-items: center; margin-bottom: 14px; }
.olt-act { display: inline-flex; align-items: center; gap: 6px; font-size: 12px; font-weight: 600;
  padding: 7px 13px; border-radius: 9px; cursor: pointer; white-space: nowrap;
  background: var(--oltp-surface-2); color: var(--oltp-fg-soft);
  border: 1px solid var(--oltp-border-strong); transition: background .15s, color .15s, border-color .15s; }
.olt-act:hover:not(:disabled) { background: var(--oltp-surface-3); color: var(--oltp-fg); border-color: var(--oltp-accent); }
.olt-act--primary { background: var(--oltp-accent); border-color: var(--oltp-accent); color: #fff; }
.olt-act--primary:hover:not(:disabled) { filter: brightness(1.12); color: #fff; }
.olt-act:disabled { opacity: .5; cursor: default; }
.olt-act[aria-pressed="true"] { border-color: var(--oltp-accent); color: var(--oltp-fg); }
.olt-actions__at { font-size: 10.5px; color: var(--oltp-fg-muted); margin-left: auto; font-family: ui-monospace, monospace; }

/* Transcrição crua: é a fonte, então monoespaçada e rolável, sem reinterpretação. */
.olt-raw { font-family: ui-monospace, SFMono-Regular, Menlo, monospace; font-size: 11.5px; line-height: 1.5;
  color: var(--oltp-fg-soft); background: var(--oltp-bg, #0a0e17); border: 1px solid var(--oltp-divider);
  border-radius: 8px; padding: 12px 14px; margin-top: 8px; max-height: 380px; overflow: auto; white-space: pre; }
.olt-raw b { color: var(--oltp-info); font-weight: 600; }

/* =====================================================================
   Layout "ficha" — mesma estrutura do SmartOLT (rótulo à direita, valor à
   esquerda, duas colunas), na identidade do OnNoc. O que o técnico
   reconhece é a ORDEM e o NOME dos campos, não a paleta.
   ===================================================================== */
.olt-ficha2 { display: grid; grid-template-columns: 1fr 1fr; gap: 0 28px; }
@media (max-width: 800px) { .olt-ficha2 { grid-template-columns: 1fr; } }
.olt-fr { display: grid; grid-template-columns: minmax(96px, 34%) 1fr; gap: 12px;
  align-items: baseline; padding: 4px 0; }
.olt-fr__k { font-size: 11.5px; color: var(--oltp-fg-muted); text-align: right; line-height: 1.4; }
.olt-fr__v { font-size: 12.5px; color: var(--oltp-fg); min-width: 0; overflow-wrap: anywhere; }
.olt-fr__v--mono { font-family: ui-monospace, monospace; font-size: 12px; }
.olt-fr__v--link { color: var(--oltp-info); }
.olt-fr__v--none { color: var(--oltp-fg-muted); font-style: italic; }
.olt-fr__v--ok { color: var(--oltp-ok); }
.olt-fr__v strong { font-weight: 600; }

/* Cabeçalho da ficha: duas colunas + espaço do aparelho à direita. */
.olt-ficha-top { display: grid; grid-template-columns: 1fr auto; gap: 18px; align-items: start;
  border: 1px solid var(--oltp-border); border-radius: 14px; background: var(--oltp-surface-2);
  padding: 16px 18px; }
@media (max-width: 900px) { .olt-ficha-top { grid-template-columns: 1fr; } }
.olt-dev { width: 132px; text-align: center; color: var(--oltp-fg-muted); }
.olt-dev__ico { width: 100%; height: 62px; border-radius: 10px; border: 1px dashed var(--oltp-border-strong);
  display: flex; align-items: center; justify-content: center; background: var(--oltp-surface-3); }
.olt-dev__cap { font-size: 10px; margin-top: 6px; font-family: ui-monospace, monospace; }

/* Linha de seção no estilo do print: rótulo à esquerda, conteúdo à direita. */
/* Rótulo ACIMA do conteúdo, não ao lado.
   No SmartOLT o rótulo fica à esquerda porque a página dele passa de 1500px. Aqui o
   painel tem 1000px, e reservar 150px + gap por seção empurrava tudo para a direita e
   espremia justamente o que precisa de largura — o gráfico de sinal e as tabelas.
   A ordem e os nomes das seções continuam os mesmos; só o rótulo mudou de lugar.
   NÃO usar @media aqui: media query mede a JANELA, e a janela é larga enquanto o
   painel é fixo em 1000px — a primeira tentativa reativou a coluna e o conteúdo
   continuou empurrado para a direita. O painel tem largura fixa, então a regra
   também é fixa. */
.olt-sec { display: grid; grid-template-columns: 1fr; gap: 8px;
  align-items: start; padding: 14px 0; border-top: 1px solid var(--oltp-divider); }
.olt-sec__k { font-size: 10px; letter-spacing: .1em; text-transform: uppercase; font-weight: 600;
  color: var(--oltp-fg-muted); text-align: left; padding-top: 0; }
.olt-sec__v { min-width: 0; }

/* Tráfego e histórico de sinal LADO A LADO, como no SmartOLT. */
.olt-graficos { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; margin-top: 10px; }
@media (max-width: 760px) { .olt-graficos { grid-template-columns: 1fr; } }
.olt-graficos > .olt-panel { min-width: 0; }
.olt-sec--vazia .olt-sec__v { font-size: 11.5px; color: var(--oltp-fg-muted); font-style: italic; }

/* Tráfego instantâneo: dois números grandes, download primeiro (é o que o cliente sente). */
.olt-traf { display: grid; grid-template-columns: 1fr 1fr; gap: 18px; margin-top: 8px; }
.olt-traf__item { min-width: 0; }
.olt-traf__lbl { font-size: 10px; letter-spacing: .09em; text-transform: uppercase; color: var(--oltp-fg-muted); font-weight: 600; }
.olt-traf__val { font-family: ui-monospace, monospace; font-size: 22px; font-weight: 600;
  font-variant-numeric: tabular-nums; color: var(--oltp-fg); margin-top: 2px; letter-spacing: -.02em; }
.olt-traf__val small { font-size: 12px; color: var(--oltp-fg-muted); margin-left: 4px; font-weight: 500; }
.olt-traf__sub { font-size: 10.5px; color: var(--oltp-fg-muted); margin-top: 2px; }
.olt-traf__down .olt-traf__val { color: var(--oltp-info); }
.olt-traf__up .olt-traf__val { color: var(--oltp-accent); }
.olt-traf__nota { font-size: 10.5px; color: var(--oltp-fg-muted); margin-top: 14px; line-height: 1.5; }

/* ============================================================================
   Configurar serviço da ONU (PPPoE + Wi-Fi)
   Nomes com prefixo próprio (.olt-cfg-*) de propósito: a olt.html tem um <style>
   inline que vem DEPOIS deste arquivo e vence em especificidade igual — já
   perdemos o herói de sinal para um `.olt-sig` que existia lá dentro.
   ========================================================================== */
/* Lista de linhas chave/valor do estado atual — .olt-kv já traz a linha divisória. */
.olt-kv-list { border: 1px solid var(--oltp-line); border-radius: 10px; padding: 2px 12px; }

.olt-cfg-grid {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 10px 12px;
}
.olt-cfg-lbl {
    display: block;
    font-size: 10px;
    text-transform: uppercase;
    letter-spacing: .06em;
    font-weight: 600;
    color: var(--oltp-fg-muted);
    margin-bottom: 4px;
}
.olt-cfg-in { width: 100%; font-size: 13px; padding: 8px 10px; }
.olt-cfg-nota {
    font-size: 11px;
    line-height: 1.5;
    color: var(--oltp-fg-muted);
    margin-top: 8px;
}
.olt-cfg-aviso {
    font-size: 12px;
    line-height: 1.5;
    border-radius: 10px;
    padding: 10px 12px;
    border: 1px solid var(--oltp-line);
    background: var(--oltp-surface-2, rgba(255, 255, 255, .03));
    color: var(--oltp-fg);
}
.olt-cfg-aviso--erro { border-color: rgba(248, 113, 113, .35); background: rgba(248, 113, 113, .07); }
.olt-cfg-aviso--ok { border-color: rgba(52, 211, 153, .35); background: rgba(52, 211, 153, .07); }
.olt-cfg-aviso--atencao { border-color: rgba(251, 191, 36, .35); background: rgba(251, 191, 36, .07); }

/* Um cartão por rádio Wi-Fi. Quantos aparecem depende do que a ONU reporta. */
.olt-cfg-radio {
    border: 1px solid var(--oltp-line);
    border-radius: 10px;
    padding: 10px 12px;
    margin-bottom: 8px;
}
.olt-cfg-radio__t {
    font-size: 11px;
    font-weight: 600;
    letter-spacing: .04em;
    color: var(--oltp-fg);
    margin-bottom: 8px;
    font-family: var(--oltp-mono, ui-monospace, monospace);
}

.olt-cfg-rodape {
    display: flex;
    align-items: center;
    justify-content: flex-end;
    gap: 8px;
    padding-top: 12px;
    margin-top: 4px;
    border-top: 1px solid var(--oltp-line);
}
.olt-cfg-status { flex: 1; font-size: 11px; color: var(--oltp-fg-muted); min-width: 0; }

@media (max-width: 640px) {
    .olt-cfg-grid { grid-template-columns: 1fr; }
}

/* Confirmação do OnNoc. Precisa vencer o modal de configuração, que a olt.html
   declara inline em z-index 120 — uma confirmação que aparece ATRÁS do que ela
   confirma é pior do que não existir. Nome próprio, sem colisão com o <style> inline. */
.olt-confirm { z-index: 160; }
.olt-confirm .noc-modal__content { padding-top: 14px; }
.olt-confirm__frase { font-size: 13px; line-height: 1.6; color: var(--oltp-fg); }
.olt-confirm__lista { margin-top: 12px; border: 1px solid var(--oltp-line); border-radius: 10px; padding: 2px 12px; }
.olt-confirm__cmds {
    margin-top: 12px; max-height: 168px; overflow: auto;
    font-family: ui-monospace, monospace; font-size: 11.5px; line-height: 1.6;
    background: var(--oltp-surface-2, rgba(255, 255, 255, .03));
    border: 1px solid var(--oltp-line); border-radius: 10px; padding: 10px 12px;
    color: var(--oltp-fg); white-space: pre-wrap; word-break: break-word;
}

/* O sistema não tinha um botão de ação destrutiva; a confirmação precisa de um
   para que "Aplicar" e "Excluir" não pareçam o mesmo clique. */
.noc-btn--danger {
    background: rgba(248, 113, 113, .14);
    border-color: rgba(248, 113, 113, .42);
    color: #fca5a5;
}
.noc-btn--danger:hover { background: rgba(248, 113, 113, .22); border-color: rgba(248, 113, 113, .6); }

/* Wi-Fi pelo ACS (TR-069) — mesma família .olt-cfg-*; prefixo .olt-tr-* sem colisão com o
   <style> inline da olt.html. */
.olt-tr-acoes { display: flex; align-items: center; justify-content: flex-end; gap: 8px; margin-top: 12px; }
.olt-tr-acoes .olt-cfg-status { flex: 1; }
.olt-tr-banda { margin-top: 10px; }
.olt-tr-banda__t {
    font-size: 10px; text-transform: uppercase; letter-spacing: .06em; font-weight: 600;
    color: var(--oltp-fg-muted); margin-bottom: 4px;
}
.olt-tr-rede { display: flex; align-items: center; gap: 10px; padding: 6px 0; border-bottom: 1px solid var(--oltp-line); font-size: 12.5px; }
.olt-tr-rede:last-child { border-bottom: 0; }
.olt-tr-rede__i { width: 22px; color: var(--oltp-fg-muted); font-variant-numeric: tabular-nums; font-size: 11px; }
.olt-tr-rede__s { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; color: var(--oltp-fg); }
.olt-tr-rede--off .olt-tr-rede__s { color: var(--oltp-fg-muted); }
.olt-tr-badge { font-size: 10px; font-weight: 600; letter-spacing: .04em; padding: 2px 7px; border-radius: 999px; border: 1px solid var(--oltp-line); color: var(--oltp-fg-muted); }
.olt-tr-badge--ar { color: #6ee7b7; border-color: rgba(52, 211, 153, .4); background: rgba(52, 211, 153, .08); }
.olt-tr-badge--principal { color: var(--oltp-fg); }
.olt-tr-verif { margin-top: 10px; }

/* Ação destrutiva na barra da ONU: separada das outras e em vermelho, para não ser o
   clique "do lado" de Obter status. */
.olt-act.olt-act--danger { margin-left: auto; color: #fca5a5; border-color: rgba(248, 113, 113, .35); }
.olt-act.olt-act--danger:hover { background: rgba(248, 113, 113, .10); border-color: rgba(248, 113, 113, .55); }

/* Reiniciar: interrompe o cliente mas não apaga nada — âmbar, não vermelho. Abre o grupo
   da direita da barra; o Desautorizar logo depois não precisa mais empurrar. */
.olt-act.olt-act--aviso { margin-left: auto; color: #fcd34d; border-color: rgba(251, 191, 36, .35); }
.olt-act.olt-act--aviso:hover { background: rgba(251, 191, 36, .10); border-color: rgba(251, 191, 36, .55); }
.olt-act--aviso:not(.hidden) + .olt-act--danger { margin-left: 0; }

/* ===== Configuração da OLT (portas PON, uplink, VLANs) ===== */
.olt-cfgtabs { display: flex; align-items: center; gap: 2px; margin-top: 14px; border-bottom: 1px solid var(--oltp-border); }
.olt-cfgtab { padding: 9px 14px; margin-bottom: -1px; background: none; border: 0; border-bottom: 2px solid transparent; color: var(--oltp-fg-muted); font-size: 12.5px; font-weight: 700; letter-spacing: .02em; cursor: pointer; transition: color var(--oltp-t), border-color var(--oltp-t); }
.olt-cfgtab:hover { color: var(--oltp-fg-soft); }
.olt-cfgtab.is-on { color: var(--oltp-accent, #38bdf8); border-bottom-color: currentColor; }
.olt-cfgtab:focus-visible { outline: 2px solid var(--oltp-accent, #38bdf8); outline-offset: 2px; border-radius: 6px; }
.olt-cfgtabs__acao { margin-left: auto; margin-bottom: 6px; }
/* O utilitário .hidden precisa vencer o layout desta seção: as regras acima (display:flex/grid) vêm
   DEPOIS do utilitário na ordem das folhas, então esconder as abas internas não surtia efeito e a tela
   oferecia "Ler da OLT" numa OLT cujo driver não lê configuração (V-SOL, 14/09). */
#oltCfgSection .hidden { display: none !important; }
#oltCfgSection .olt-empty { margin-top: 14px; }
#oltCfgTabela tbody td { white-space: normal; }
.olt-st { display: inline-flex; align-items: center; gap: 6px; font-weight: 700; font-size: 12px; white-space: nowrap; }
.olt-st::before { content: ''; width: 7px; height: 7px; border-radius: 50%; background: currentColor; }
.olt-st--up { color: var(--oltp-ok, #34d399); }
.olt-st--down { color: var(--red, #f87171); }
.olt-st--off { color: var(--oltp-fg-muted); }
.olt-vchips { display: flex; flex-wrap: wrap; gap: 4px; }
.olt-vchip { display: inline-flex; align-items: center; gap: 4px; padding: 1px 8px; border-radius: 999px; border: 1px solid var(--oltp-border); font-family: var(--font-mono, monospace); font-size: 11px; color: var(--oltp-fg-soft); font-variant-numeric: tabular-nums; }
.olt-vchip--untag { border-style: dashed; }
.olt-vchip button { border: 0; background: none; color: var(--oltp-fg-muted); cursor: pointer; padding: 0 0 0 2px; font-size: 13px; line-height: 1; }
.olt-vchip button:hover { color: var(--red, #f87171); }
.olt-vchip.is-rm { opacity: .5; text-decoration: line-through; }
.olt-vchip.is-add { border-color: var(--oltp-accent, #38bdf8); color: var(--oltp-accent, #38bdf8); }
.olt-cfg-grade { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; }
.olt-cfg-grade > .is-cheia { grid-column: 1 / -1; }
.olt-cfg-seg { display: inline-flex; border: 1px solid var(--oltp-border); border-radius: 10px; overflow: hidden; }
.olt-cfg-seg label { display: inline-flex; align-items: center; gap: 6px; padding: 7px 12px; cursor: pointer; font-size: 12.5px; color: var(--oltp-fg-soft); }
.olt-cfg-seg input { accent-color: var(--oltp-accent, #38bdf8); }
.olt-cfg-seg label + label { border-left: 1px solid var(--oltp-border); }
.olt-cfg-mud { margin: 0; padding-left: 18px; display: grid; gap: 4px; color: var(--oltp-fg-soft); }
.olt-cfg-cmds { margin: 8px 0 0; padding: 10px 12px; border-radius: 10px; background: var(--oltp-surface-3); border: 1px solid var(--oltp-border); font-family: var(--font-mono, monospace); font-size: 11.5px; line-height: 1.55; color: var(--oltp-fg-soft); white-space: pre-wrap; overflow-x: auto; }
.olt-cfg-alto { margin-top: 10px; padding: 10px 12px; border-radius: 10px; border: 1px solid rgba(248, 113, 113, .45); background: rgba(248, 113, 113, .08); color: var(--oltp-fg); }
.olt-cfg-alto strong { color: var(--red, #f87171); }
@media (max-width: 520px) { .olt-cfg-grade { grid-template-columns: 1fr; } }

/* O painel base do noc_modal tem altura fixa (860 px, feita para o modal grande do host):
   os modais pequenos da OLT ficavam com um vazio enorme embaixo. Altura do conteúdo, com
   rolagem interna quando passa da tela. */
#oltPortaModal .noc-modal__panel,
.olt-confirm .noc-modal__panel { height: auto; max-height: min(90vh, 820px); }
#oltPortaModal .noc-modal__content,
.olt-confirm .noc-modal__content { overflow-y: auto; min-height: 0; }
/* Botão desativado precisa PARECER desativado: antes o "Aplicar" desativado era igual ao
   ativo e o clique simplesmente não fazia nada. */
.olt-onu-modal .noc-btn:disabled,
#oltCfgSection .noc-btn:disabled { opacity: .45; cursor: not-allowed; transform: none; box-shadow: none; }
/* X de fechar dos modais pequenos da OLT: tamanho explícito (a página não carrega o CSS
   que dimensiona .modal-close-icon, e o ícone saía como um ponto). */
#oltPortaModal .modal-close-icon, .olt-confirm .modal-close-icon { width: 36px; height: 36px; padding: 0; color: var(--oltp-fg-soft); }
#oltPortaModal .modal-close-icon svg, .olt-confirm .modal-close-icon svg { width: 20px; height: 20px; }

/* ===== Card "Sinal ruim" (clicável: lista as ONUs abaixo do limite) ===== */
/* 7 cards na fileira: 4 + 3 na faixa média em vez de 3 + 3 + 1 órfão. */
.olt-kpi-row { grid-template-columns: repeat(7, minmax(0, 1fr)); }
@media (max-width: 1280px) { .olt-kpi-row { grid-template-columns: repeat(4, minmax(0, 1fr)); } }
@media (max-width: 640px) { .olt-kpi-row { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
button.olt-kpi { font: inherit; color: inherit; text-align: left; width: 100%; cursor: pointer; }
.olt-kpi--acao:focus-visible { outline: 2px solid var(--oltp-accent, #38bdf8); outline-offset: 2px; }
.olt-kpi__ver { display: inline-flex; align-items: center; gap: 3px; font-size: 10.5px; font-weight: 700; color: var(--oltp-fg-muted); transition: color var(--oltp-t); }
.olt-kpi__ver svg { width: 12px; height: 12px; }
.olt-kpi--acao:hover .olt-kpi__ver, .olt-kpi--acao:focus-visible .olt-kpi__ver { color: var(--oltp-accent, #38bdf8); }
.olt-kpi--ruim .olt-kpi__value { color: var(--oltp-warn, #f59e0b); }
.olt-kpi--limpo .olt-kpi__value { color: var(--oltp-ok, #34d399); }
.olt-kpi--acao.is-filtrando { border-color: var(--oltp-warn, #f59e0b); }

/* Card "Sem sinal (LOS)": cliente sem luz na fibra é vermelho, não âmbar como o sinal ruim. */
#kpiLosCard.olt-kpi--ruim .olt-kpi__value { color: var(--oltp-danger, #ef4444); }
#kpiLosCard.is-filtrando { border-color: var(--oltp-danger, #ef4444); }
/* Proporção entre as ONUs COM leitura de RX: abaixo do limite × dentro. */
.olt-kpi__prop { display: flex; height: 6px; margin-top: 20px; border-radius: 999px; overflow: hidden; background: var(--oltp-surface-3); }
.olt-kpi__prop span { display: block; height: 100%; }
.olt-kpi__prop .is-ruim { background: var(--oltp-warn, #f59e0b); }
.olt-kpi__prop .is-bom { background: var(--oltp-ok, #34d399); opacity: .5; }

/* Filtro de status da lista de ONUs: combobox do OnNoc (searchable-select) no lugar do
   select nativo, cuja lista aberta saía clara no tema escuro. */
.olt-ss-status { width: 170px; }
.olt-ss-status .ss-input { width: 100%; cursor: pointer; }
/* Temperatura: uma barra por placa (lida da CLI); a mais quente em destaque. */
.olt-kpi__tbar { background: #f59e0b; opacity: .35; }
.olt-kpi__tbar.is-max { opacity: .95; }

/* ===== Lista de ONUs: cabeçalho com busca, status em abas com contagem, tabela ===== */
.olt-onu-head { display: flex; align-items: flex-end; justify-content: space-between; gap: 16px; flex-wrap: wrap; }
.olt-search { position: relative; width: min(360px, 100%); }
.olt-search svg { position: absolute; left: 12px; top: 50%; transform: translateY(-50%); width: 15px; height: 15px; color: var(--oltp-fg-muted); pointer-events: none; }
.olt-search .olt-input { width: 100%; padding: 9px 12px 9px 36px; }
.olt-onu-bar { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; margin-top: 14px; }
.olt-seg { display: inline-flex; flex-wrap: wrap; gap: 2px; padding: 3px; border-radius: 11px; background: var(--oltp-surface-3); border: 1px solid var(--oltp-border); }
.olt-seg button { display: inline-flex; align-items: center; gap: 7px; padding: 6px 12px; border: 0; border-radius: 8px; background: transparent; color: var(--oltp-fg-muted); font-size: 12px; font-weight: 700; cursor: pointer; transition: color var(--oltp-t), background var(--oltp-t); }
.olt-seg button:hover { color: var(--oltp-fg-soft); }
.olt-seg button.is-on { background: var(--oltp-surface-2); color: var(--oltp-fg); box-shadow: 0 1px 0 rgba(255,255,255,.04), 0 2px 10px rgba(0,0,0,.25); }
.olt-seg button:focus-visible { outline: 2px solid var(--oltp-accent, #38bdf8); outline-offset: 1px; }
.olt-seg .d { width: 7px; height: 7px; border-radius: 50%; flex: none; }
.olt-seg .n { font-family: var(--font-mono, monospace); font-size: 11px; padding: 0 6px; border-radius: 999px; background: rgba(148,163,184,.14); color: var(--oltp-fg-soft); font-variant-numeric: tabular-nums; }
.olt-seg button.is-on .n { background: var(--oltp-accent-soft); color: var(--oltp-fg); }
.olt-pon-chip { display: inline-flex; align-items: center; gap: 4px; padding: 4px 4px 4px 11px; border-radius: 999px; border: 1px solid var(--oltp-accent, #38bdf8); background: var(--oltp-accent-soft); color: var(--oltp-fg); font-size: 12px; font-weight: 700; }
.olt-pon-chip button { width: 22px; height: 22px; border: 0; border-radius: 50%; background: transparent; color: var(--oltp-fg-soft); cursor: pointer; font-size: 15px; line-height: 1; display: grid; place-items: center; }
.olt-pon-chip button:hover { background: rgba(255,255,255,.1); color: var(--oltp-fg); }
.olt-pon-chip button:focus-visible { outline: 2px solid var(--oltp-accent, #38bdf8); }
#onuSection .olt-onu-legend { margin-top: 10px; }
#onuSection .olt-table-wrap { max-height: 580px; margin-top: 16px; }
.olt-table--onu tbody td { padding: 10px 14px; }
/* Faixa de status na borda esquerda da linha. */
.olt-table--onu tbody td:first-child { box-shadow: inset 3px 0 0 var(--_st, transparent); }
.olt-table--onu tr.st-online { --_st: #22c55e; }
.olt-table--onu tr.st-offline { --_st: #ef4444; }
.olt-table--onu tr.st-poweroff { --_st: #f59e0b; }
.olt-table--onu tr.st-los { --_st: #8b5cf6; }
.olt-table--onu tr.st-unknown { --_st: #334155; }
.olt-table--onu tr.is-ruim { background: rgba(245, 158, 11, .06); }
.olt-table--onu tr.is-ruim:hover { background: rgba(245, 158, 11, .11); }
.olt-onu-nome { display: flex; flex-direction: column; gap: 3px; min-width: 0; max-width: 360px; }
.olt-onu-nome b { color: var(--oltp-fg); font-weight: 650; font-size: 13px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.olt-onu-nome small { font-family: var(--font-mono, monospace); font-size: 11px; color: var(--oltp-fg-muted); letter-spacing: .02em; }
.olt-onu-nome__aviso { color: #fcd34d; font-family: inherit; }
.olt-porta { display: inline-block; padding: 2px 8px; border-radius: 6px; border: 1px solid var(--oltp-border); background: var(--oltp-surface-3); color: var(--oltp-fg-soft); font-family: var(--font-mono, monospace); font-size: 11.5px; font-variant-numeric: tabular-nums; }
.olt-st2 { display: inline-flex; flex-direction: column; align-items: flex-start; gap: 3px; }
.olt-st2 small { font-size: 10.5px; color: var(--oltp-fg-muted); padding-left: 2px; }
.sr-only { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; }

/* Menu de troca de OLT ficava ATRÁS dos cards: sem a faixa de KPIs (11/09) ele passa da borda do
   topo e cai sobre a fileira de cards, que vem depois na página (e se move no hover/animação).
   O topo ganha camada própria acima das seções seguintes. */
/* 5 e não mais: basta ficar acima dos cards (que não têm camada) e ABAIXO do cabeçalho do OnNoc
   (menu.css, z-index 35) — senão o topo cobriria o painel do sino quando ele abre por cima. */
.olt-hero { position: relative; z-index: 5; }

/* Linha de baixo do topo: tempo de atividade e sincronização. Menor que a linha do IP/SNMP, e com
   o separador só entre itens preenchidos — a primeira linha fica do mesmo tamanho em todas as OLTs,
   e o círculo de saúde e os botões continuam ao lado do nome. */
.olt-hero__meta--sub { margin-top: 3px; gap: 0; font-size: 11.5px; }
.olt-hero__meta--sub > span:not(:empty) ~ span:not(:empty)::before {
  content: ""; display: inline-block; width: 3px; height: 3px; margin: 0 9px 2px; border-radius: 999px;
  background: var(--oltp-fg-faint); vertical-align: middle;
}
.olt-hero__meta--sub:not(:has(span:not(:empty))) { display: none; }

/* ===== Abas da página da OLT: Visão geral / ONUs / Configuração ===== */
.olt-abas { display: flex; gap: 2px; border-bottom: 1px solid var(--oltp-border); }
.olt-aba { display: inline-flex; align-items: center; gap: 8px; padding: 10px 16px; margin-bottom: -1px; border: 0; border-bottom: 2px solid transparent; background: none; color: var(--oltp-fg-muted); font-size: 13.5px; font-weight: 700; cursor: pointer; transition: color var(--oltp-t), border-color var(--oltp-t); }
.olt-aba svg { width: 16px; height: 16px; }
.olt-aba:hover { color: var(--oltp-fg-soft); }
.olt-aba.is-on { color: var(--oltp-fg); border-bottom-color: var(--oltp-accent, #38bdf8); }
.olt-aba:focus-visible { outline: 2px solid var(--oltp-accent, #38bdf8); outline-offset: 2px; border-radius: 6px; }
.olt-premium[data-aba-atual="geral"] [data-olt-aba]:not([data-olt-aba="geral"]),
.olt-premium[data-aba-atual="onus"] [data-olt-aba]:not([data-olt-aba="onus"]),
.olt-premium[data-aba-atual="config"] [data-olt-aba]:not([data-olt-aba="config"]) { display: none !important; }
/* Fora da Visão geral a coluna lateral (resumo) some: o conteúdo ocupa a largura toda. */
.olt-premium:not([data-aba-atual="geral"]) .olt-layout { grid-template-columns: minmax(0, 1fr); }

/* ===== Alarmes e eventos (Visão geral, no lugar da Tendência PON) ===== */
.olt-al-lista { display: flex; flex-direction: column; margin-top: 12px; max-height: 440px; overflow-y: auto; }
.olt-al { display: grid; grid-template-columns: 4px minmax(0, 1fr) auto; gap: 12px; align-items: center; width: 100%; padding: 10px 8px; margin: 0; border: 0; border-bottom: 1px solid var(--oltp-divider); border-radius: 0; background: none; color: inherit; font: inherit; text-align: left; }
.olt-al:last-child { border-bottom: 0; }
button.olt-al { cursor: pointer; transition: background var(--oltp-t); }
button.olt-al:hover { background: var(--oltp-accent-soft); }
button.olt-al:focus-visible { outline: 2px solid var(--oltp-accent, #38bdf8); outline-offset: -2px; }
.olt-al__faixa { align-self: stretch; min-height: 30px; border-radius: 2px; }
.olt-al__faixa--crit { background: var(--oltp-danger, #ef4444); }
.olt-al__faixa--aviso { background: var(--oltp-warn, #f59e0b); }
.olt-al.is-resolvido .olt-al__faixa { opacity: .35; }
.olt-al__txt { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.olt-al__msg { color: var(--oltp-fg); font-size: 13px; font-weight: 600; }
.olt-al.is-resolvido .olt-al__msg { color: var(--oltp-fg-soft); font-weight: 500; }
.olt-al__quando { font-size: 11px; color: var(--oltp-fg-muted); }
.olt-al .olt-tag { white-space: nowrap; }
.olt-al-vazio { padding: 22px 8px; font-size: 13px; color: var(--oltp-fg-muted); }
.olt-al-link { display: inline-flex; align-items: center; gap: 6px; margin-top: 12px; font-size: 12px; font-weight: 700; color: var(--oltp-accent, #38bdf8); }
.olt-al-link svg { width: 14px; height: 14px; }

/* ===== Gerência em lote (modal da aba ONUs) ===== */
#btnGerLote { margin-left: auto; }
.olt-lote-escopo { display: flex; align-items: flex-end; gap: 10px; flex-wrap: wrap; }
.olt-lote-escopo > div { flex: 1; min-width: 220px; }
.olt-lote-nums { display: flex; flex-wrap: wrap; gap: 8px; margin: 12px 0; }
.olt-lote-num { display: flex; flex-direction: column; gap: 2px; min-width: 92px; padding: 8px 12px; border: 1px solid var(--oltp-line); border-radius: 10px; background: var(--oltp-surface-2, rgba(255, 255, 255, .03)); }
.olt-lote-num b { font-size: 18px; font-weight: 800; font-variant-numeric: tabular-nums; color: var(--oltp-fg); }
.olt-lote-num span { font-size: 10.5px; font-weight: 700; color: var(--oltp-fg-muted); text-transform: uppercase; letter-spacing: .05em; }
.olt-lote-num--ok b { color: var(--oltp-ok, #34d399); }
.olt-lote-num--falha b { color: var(--red, #f87171); }
.olt-lote-num--aviso b { color: var(--oltp-warn, #f59e0b); }
.olt-lote-num--acs b { color: var(--oltp-accent, #38bdf8); }
.olt-lote-lista { max-height: 320px; overflow: auto; border: 1px solid var(--oltp-line); border-radius: 10px; }
.olt-lote-tab { width: 100%; border-collapse: collapse; font-size: 12px; }
.olt-lote-tab th { position: sticky; top: 0; z-index: 1; background: var(--oltp-surface-3); text-align: left; font-size: 10.5px; font-weight: 700; color: var(--oltp-fg-muted); padding: 7px 10px; text-transform: uppercase; letter-spacing: .05em; }
.olt-lote-tab td { padding: 7px 10px; border-top: 1px solid var(--oltp-line); color: var(--oltp-fg-soft); vertical-align: top; }
.olt-lote-tab td.mono { font-family: ui-monospace, monospace; font-size: 11.5px; white-space: nowrap; font-variant-numeric: tabular-nums; }
.olt-lote-tab td.nome { color: var(--oltp-fg); font-weight: 600; }
.olt-lote-tab tr.is-rodando td { background: rgba(56, 189, 248, .07); }
.olt-lote-msg { font-size: 11px; color: var(--oltp-fg-muted); margin-top: 2px; line-height: 1.45; }
.olt-lote-st { display: inline-flex; align-items: center; gap: 5px; padding: 2px 8px; border-radius: 999px; font-size: 11px; font-weight: 700; white-space: nowrap; border: 1px solid var(--oltp-line); color: var(--oltp-fg-muted); }
.olt-lote-st--ok { color: #34d399; border-color: rgba(52, 211, 153, .35); }
.olt-lote-st--ja_ativa, .olt-lote-st--acs { color: #7dd3fc; border-color: rgba(125, 211, 252, .35); }
.olt-lote-st--pulada { color: #fcd34d; border-color: rgba(251, 191, 36, .35); }
.olt-lote-st--falhou { color: #fca5a5; border-color: rgba(248, 113, 113, .4); }
.olt-lote-st--rodando { color: var(--oltp-accent, #38bdf8); border-color: var(--oltp-accent, #38bdf8); }
.olt-lote-barra { height: 6px; border-radius: 999px; background: var(--oltp-surface-3); overflow: hidden; margin-top: 12px; }
.olt-lote-barra span { display: block; height: 100%; background: var(--oltp-accent, #38bdf8); transition: width .4s ease; }
.olt-lote-aviso { margin: 10px 0; padding: 10px 12px; border-radius: 10px; font-size: 12.5px; line-height: 1.5; border: 1px solid rgba(251, 191, 36, .35); background: rgba(251, 191, 36, .07); color: var(--oltp-fg); }
.olt-lote-fora { margin-top: 12px; }
.olt-lote-fora summary { cursor: pointer; font-size: 12px; font-weight: 700; color: var(--oltp-fg-muted); margin-bottom: 8px; }
.olt-lote-vazio { padding: 18px 12px; font-size: 13px; color: var(--oltp-fg-muted); }
@media (prefers-reduced-motion: reduce) { .olt-lote-barra span { transition: none; } }

/* ===== VLAN de gerência desta OLT (topo da aba Configuração) ===== */
.olt-mgmtvlan { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; margin-top: 14px; padding: 10px 12px; border: 1px solid var(--oltp-line); border-radius: 12px; background: var(--oltp-surface-2, rgba(255, 255, 255, .03)); }
.olt-mgmtvlan__txt { flex: 1; min-width: 220px; }
.olt-mgmtvlan__tit { font-size: 13px; font-weight: 700; color: var(--oltp-fg); }
.olt-mgmtvlan__sub { font-size: 11px; line-height: 1.5; color: var(--oltp-fg-muted); margin-top: 2px; }
.olt-mgmtvlan__in { width: 120px; font-variant-numeric: tabular-nums; }
.olt-mgmtvlan__msg { font-size: 11px; color: var(--oltp-fg-muted); min-width: 0; }

/* ── Celular: topo da OLT (16/09/2026) ─────────────────────────────────────
   As duas linhas de botões não quebravam: "Atualizar" e "ONUs" saíam da tela e o seletor
   de OLT era espremido até virar uma coluna de 3 linhas. No celular o bloco ocupa a
   largura toda, o seletor ganha linha própria e os botões dividem o espaço. */
@media (max-width: 720px) {
    .olt-hero__top { flex-direction: column; align-items: stretch; gap: 14px; }
    .olt-hero__lado { width: 100%; }
    .olt-hero__acoes { width: 100%; align-items: stretch !important; }
    .olt-hero__acoes-linha { flex-wrap: wrap; }
    .olt-hero__acoes-linha > * { flex: 1 1 auto; justify-content: center; }
    .olt-hero__acoes-linha > .olt-btn--icon { flex: 0 0 auto; }
    .olt-hero__acoes .olt-switcher { flex: 1 1 100%; }
    .olt-hero__acoes .olt-switch-btn { width: 100%; justify-content: flex-start; }
    .olt-hero__acoes .olt-switch-btn span { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; min-width: 0; }
    .olt-hero__acoes .olt-switch-menu { left: 0; right: 0; min-width: 0; }
}
