/* Consola de recepție — sistemul vizual ScanExpert.
   ===================================================================
   Valorile stau în tokens.css (copie stampilată a handoff-ului; stampila stă
   o singură dată, în design-kit/EXPORT.json). Aici sunt doar reguli: fiecare
   culoare e un var(--se-…), fiecare mărime de text e din scara tipografică
   (24/20/18/16/14/12), fiecare rază e
   din scara de radius. Ce nu se poate scrie așa e marcat mai jos, o dată, ca să
   fie o listă de întrebat designerul și nu o presărare de excepții.

   Ce s-a schimbat față de consola dinainte: era întunecată (ISA-101,
   `--bg:#0f131a`), argumentată în reception/LAYOUT.md — lint-tokens-ignore: e
   culoarea consolei DE DINAINTE, citată, nu folosită. Decizia userului e
   trecerea pe designul ScanExpert — alb, navy pentru acțiune, roz pentru
   selecție și accent. Ce NU s-a schimbat, fiindcă e politică și nu aspect:
   panourile care costă cereri către centrală rămân oprite implicit, cu
   comutator propriu, vechimea cifrei la vedere și ⟳ care cere o singură dată.
   Un panou care nu mai interoghează trebuie s-o spună; un panou care tace
   despre asta minte.

   Ordinea din fișier: font, bază, cadru, componente, pagini, ferestre, iar la
   final blocurile media și `prefers-reduced-motion` — sunt suprascrieri de
   aceeași specificitate, deci dacă urcă nu se mai aplică deloc. */

/* ---- Fontul, vendorizat ---------------------------------------------------
   Jost (SIL OFL), luat din Google Fonts și servit din binarul nostru. Nu de pe
   fonts.googleapis.com, din același motiv pentru care iconițele nu vin de pe un
   CDN: consola e folosită exact în minutele în care legătura spre exterior e
   problema. `swap` fiindcă un pupitru fără text vreme de o secundă e mai rău
   decât un pupitru cu textul în fontul de sistem pentru o secundă. */
@font-face {
  font-family: "Jost";
  font-style: normal;
  font-weight: 400 600;
  font-display: swap;
  src: url("fonts/jost-latin-ext.woff2?v=f6d14dba158beaef") format("woff2");
  unicode-range:
    U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF,
    U+0304, U+0308, U+030B, U+031B, U+0312, U+0313, U+0326, U+032D,
    U+0331, U+1E00-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113,
    U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: "Jost";
  font-style: normal;
  font-weight: 400 600;
  font-display: swap;
  src: url("fonts/jost-latin.woff2?v=f6d14dba158beaef") format("woff2");
  unicode-range:
    U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA,
    U+02DC, U+0304, U+0308, U+030B, U+0304, U+2000-206F, U+2074,
    U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}

:root {
  /* Umbra flotantă a prototipului. Umbrele nu sunt tokenizate încă (dialect.json:
     `--shadow-float`, canonical null), deci stă aici, o dată. */
  --shadow-float: 0 16px 40px rgba(20, 24, 31, 0.16);
  --shadow-card: 0 1px 2px rgba(20, 24, 31, 0.08);

  /* Cifrele unui pupitru se citesc în coloană — numere de telefon, vechimi,
     contoare, ceas, jurnal — deci literă cu lățime fixă și tabular-nums, ca
     rândul să nu joace sub ochi când se schimbă o cifră. Fontul de text rămâne
     Jost peste tot; ăsta e doar pentru cifre. Stack-ul e deliberat IDENTIC cu
     al back-office-ului (internal/web/assets/app.css) — o componentă partajată
     trebuie să se randeze într-un singur font pe ambele console (PLATFORM-22);
     se schimbă împreună sau deloc. */
  --mono: ui-monospace, "Cascadia Mono", "JetBrains Mono", Menlo, Consolas, monospace;

  --sidebar-w: 240px;
  --sidebar-collapsed-w: 96px;
}

* {
  box-sizing: border-box;
}
html,
body {
  height: 100%;
}
body {
  margin: 0;
  background: var(--se-color-bg-console);
  color: var(--se-color-text-description);
  font-family: var(--se-font-family);
  font-size: var(--se-type-bodyreg-size);
  line-height: var(--se-type-bodyreg-line);
  overflow: hidden;
}
h1,
h2,
h3,
h4,
p,
ul {
  margin: 0;
}
img {
  display: block;
}
button,
input,
select,
textarea {
  font-family: inherit;
  font-size: inherit;
  color: inherit;
}
button {
  cursor: pointer;
}
button:disabled {
  cursor: not-allowed;
}
/* Focusul e navy, nu roz: rozul e culoarea selecției și a accentului, iar un
   contur de focus în aceeași culoare nu se mai citește ca „aici e cursorul de
   tastatură”. Inelul difuz e --se-color-focus-ring; nicio valoare locală de
   rezervă — o culoare scrisă aici ar deveni a doua sursă de adevăr. */
:focus-visible {
  outline: 2px solid var(--se-color-primary-60);
  outline-offset: 2px;
  box-shadow: 0 0 0 4px var(--se-color-focus-ring);
}
.hidden {
  /* biome-ignore lint/complexity/noImportantStyles: a state utility that must beat any component specificity — softening it re-shows gated UI */
  display: none !important;
}
.muted {
  color: var(--se-color-text-muted);
}
.sprite {
  position: absolute;
  width: 0;
  height: 0;
  overflow: hidden;
}

/* Iconițele Phosphor, ca simboluri: iau culoarea textului din jur (fill е
   currentColor în sprite) și mărimea din context. */
.ph {
  width: var(--se-size-icon-functional);
  height: var(--se-size-icon-functional);
  flex: 0 0 auto;
  fill: currentColor;
}

/* Bare de derulare subțiri: pe un pupitru dens bara groasă fură un rând din
   fiecare listă. */
.list,
.lines,
.main,
.sidebar,
.transcript-body,
#log {
  scrollbar-width: thin;
  scrollbar-color: var(--se-color-primary-20) transparent;
}
.list::-webkit-scrollbar,
.lines::-webkit-scrollbar,
.main::-webkit-scrollbar,
.transcript-body::-webkit-scrollbar,
#log::-webkit-scrollbar {
  width: 8px;
  height: 8px;
}
.list::-webkit-scrollbar-thumb,
.lines::-webkit-scrollbar-thumb,
.main::-webkit-scrollbar-thumb,
.transcript-body::-webkit-scrollbar-thumb,
#log::-webkit-scrollbar-thumb {
  background: var(--se-color-primary-20);
  border-radius: var(--se-radius-sm);
}

/* ---- Cadrul ---------------------------------------------------------------
   Poarta trage cortina peste tot: cu `.gated` consola nu se desenează deloc,
   nu doar e acoperită. Un pupitru care se vede pe sub un ecran de autentificare
   e un pupitru din care se citesc numere de telefon fără să fi intrat nimeni. */
.app-shell {
  display: flex;
  height: 100dvh;
  overflow: hidden;
}
body.gated .app-shell {
  display: none;
}
body:not(.gated) .auth-shell {
  display: none;
}

/* Reîncărcarea unui pupitru autentificat. Cookie-ul e httpOnly, deci pagina nu
   știe singură dacă are sesiune — întreabă serverul. Cât ține întrebarea, cine
   avea sesiune data trecută (indiciul din localStorage, vezi SEEN_LS în app.js)
   nu vede poarta: ea nu are voie să-i apară celui autentificat, exact cum
   consola nu are voie să-i apară celui ne-autentificat. Clipa de alb e prețul
   întrebării — vizibilitate, nu display, ca așezarea să nu sară când răspunsul
   e totuși poarta. */
body.checking .auth-shell {
  visibility: hidden;
}

/* Restrângerea navigației. Rail-ul are două lățimi, iar `.collapsed` pe
   `.sidebar` e singurul comutator: fiecare regulă de mai jos atârnă de el, deci
   nu există o a doua stare de ținut în sincron. Ce dispare la restrângere sunt
   ETICHETELE, nu iconițele — un rail îngust din care lipsesc iconițele nu mai e
   navigație, e o coloană goală. */
.sidebar {
  width: var(--sidebar-w);
  flex: 0 0 auto;
  background: var(--se-color-bg-console);
  display: flex;
  flex-direction: column;
  height: 100%;
  overflow-y: auto;
  transition: width 0.15s ease;
}
.sidebar.collapsed {
  width: var(--sidebar-collapsed-w);
}

.sidebar-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--se-space-8);
  padding: 18px 20px 18px 28px;
}
.sidebar.collapsed .sidebar-header {
  flex-direction: column;
  justify-content: flex-start;
  padding: 0;
  gap: 0;
}

/* Sigla duce la Panou principal: în prototip e un buton, nu o imagine, fiindcă e
   primul lucru pe care se apasă din reflex când operatorul s-a rătăcit. */
.sidebar-logo {
  display: block;
  border: none;
  background: none;
  padding: 0;
  line-height: 0;
}
.sidebar-logo img {
  height: 32px;
  width: auto;
  display: block;
}
.sidebar-logo .logo-mark {
  display: none;
}
.sidebar.collapsed .sidebar-logo {
  width: var(--sidebar-collapsed-w);
  height: 68px;
  display: flex;
  align-items: center;
  justify-content: center;
}
.sidebar.collapsed .sidebar-logo .logo-full {
  display: none;
}
.sidebar.collapsed .sidebar-logo .logo-mark {
  display: block;
}

.sidebar-collapse-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 28px;
  height: 28px;
  flex-shrink: 0;
  padding: 0;
  border: none;
  background: none;
  border-radius: var(--se-radius-md);
  color: var(--se-color-text-title);
}
/* Perechea de navigație: roz 10 la hover, roz 20 la apăsare, pastilă. Griul
   --se-color-fill-hover a fost scos anume — stătea la trei trepte de fundalul
   sidebarului, deci starea exista în cod și nu se vedea pe ecran. */
.sidebar-collapse-btn:hover {
  background: var(--se-color-secondary-10);
  border-radius: var(--se-radius-pill);
}
.sidebar-collapse-btn:active {
  background: var(--se-color-secondary-20);
  border-radius: var(--se-radius-pill);
}
.sidebar.collapsed .sidebar-collapse-btn {
  width: 40px;
  height: 40px;
  margin: var(--se-space-8) 0 var(--se-space-24);
}

.sidebar-nav {
  padding: var(--se-space-12);
  display: flex;
  flex-direction: column;
  gap: var(--se-space-8);
}
.sidebar.collapsed .sidebar-nav {
  padding: 0 var(--se-space-28);
  align-items: center;
}
.nav-item {
  display: flex;
  align-items: center;
  gap: var(--se-space-8);
  padding: var(--se-space-8) var(--se-space-16);
  border-radius: var(--se-radius-md);
  color: var(--se-color-text-title);
  background: none;
  border: none;
  width: 100%;
  text-align: left;
  font-size: var(--se-type-bodyreg-size);
  line-height: var(--se-type-bodyreg-line);
}
.sidebar.collapsed .nav-item {
  justify-content: center;
  padding: 10px;
  gap: 0;
}
.sidebar.collapsed .nav-label {
  display: none;
}
.nav-item:hover {
  background: var(--se-color-secondary-10);
  color: var(--se-color-text-title);
  border-radius: var(--se-radius-pill);
}
.nav-item:active {
  background: var(--se-color-secondary-20);
  color: var(--se-color-text-title);
  border-radius: var(--se-radius-pill);
}
.nav-item.active {
  background: var(--se-color-secondary-20);
  border-radius: var(--se-radius-pill);
}
/* Pagina curentă nu se întoarce pe roz 10 sub cursor: ar părea mai puțin
   selectată decât e. Selectorii poartă și starea (0,3,0) ca să bată
   `.nav-item:hover` / `.nav-item:active` (0,2,0) pe SPECIFICITATE — la
   egalitate ar decide ordinea din fișier, iar o rearanjare ar întoarce pe
   tăcute pastila la roz 10. */
.nav-item.active:hover,
.nav-item.active:active {
  background: var(--se-color-secondary-20);
  color: var(--se-color-text-title);
}
/* Focusul se declară DUPĂ starea curentă și o bate pe specificitate, ca inelul
   să se vadă tocmai pe elementul la care ajungi cu Tab. */
.nav-item:focus-visible,
.nav-item.active:focus-visible {
  outline: 2px solid var(--se-color-primary-60);
  outline-offset: -2px;
  box-shadow: 0 0 0 4px var(--se-color-focus-ring);
}
.tour-relaunch {
  color: var(--se-color-text-description);
  font-size: var(--se-type-captionreg-size);
  line-height: var(--se-type-captionreg-line);
  margin: 0 var(--se-space-12) var(--se-space-4);
  width: auto;
}
.tour-relaunch .ph {
  width: var(--se-size-icon-functional);
  height: var(--se-size-icon-functional);
}
.tour-relaunch:hover {
  color: var(--se-color-text-title);
}
.sidebar-spacer {
  flex: 1;
}
.sidebar-divider {
  height: 1px;
  background: var(--se-color-border-default);
  margin: var(--se-space-4) var(--se-space-8);
}
.sidebar-profile {
  padding: var(--se-space-12);
  position: relative;
}
.profile-row {
  display: flex;
  align-items: center;
  gap: var(--se-space-12);
  padding: var(--se-space-12) var(--se-space-8);
  border: none;
  background: none;
  width: 100%;
  text-align: left;
  border-radius: var(--se-radius-md);
}
/* Sidebarul E --se-color-bg-console, deci hover-ul de dinainte repicta fundalul
   cu exact culoarea de sub el: 1.00:1, adică nimic. Rândul ia perechea de
   navigație. */
.profile-row:hover {
  background: var(--se-color-secondary-10);
}
/* Restrâns rămâne doar avatarul: numele și pastila de stare ar fi tăiate la 96px,
   iar un nume tăiat pe rândul de profil se citește ca alt operator. */
.sidebar.collapsed .profile-row {
  justify-content: center;
  padding: var(--se-space-12) var(--se-space-4);
}
.sidebar.collapsed .profile-name,
.sidebar.collapsed .badge-green {
  display: none;
}
.profile-who {
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  gap: 2px;
  min-width: 0;
}
.avatar-pink {
  width: 40px;
  height: 40px;
  border-radius: 50%;
  background: var(--se-color-secondary-60);
  color: var(--se-color-text-on-dark);
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: var(--se-type-bodylgmed-size);
  font-weight: var(--se-type-bodylgmed-weight);
  flex: 0 0 auto;
}
/* Numele se RUPE pe al doilea rând, nu se taie: pe rândul de profil un nume tăiat
   se citește ca alt operator, iar aici textul e identitatea cu care s-a intrat în
   tură. Plafonul de 150px a plecat odată cu el — rail-ul are 240px și își impune
   singur lățimea, iar `profile-who` are deja `min-width: 0`. `anywhere` fiindcă
   partea dinainte de „@" n-are spații pe care să se rupă („dorobat_mihai99"). */
.profile-name {
  font-size: var(--se-type-bodyreg-size);
  color: var(--se-color-text-title);
  overflow-wrap: anywhere;
}
.badge-green {
  display: inline-flex;
  background: var(--se-color-badge-green-100);
  color: var(--se-color-badge-green-600);
  font-size: var(--se-type-micromed-size);
  line-height: var(--se-type-micromed-line);
  font-weight: var(--se-type-micromed-weight);
  padding: 0 10px;
  border-radius: var(--se-radius-pill);
}
/* Neînregistrat nu e „disponibil”: aceeași pastilă, altă culoare, fiindcă
   diferența dintre „primesc apeluri” și „nu primesc apeluri” e tot ce contează
   pe rândul ăsta. */
.badge-green.off {
  background: var(--se-color-badge-gray-100);
  color: var(--se-color-badge-gray-600);
}
.profile-dropdown {
  position: absolute;
  left: var(--se-space-12);
  right: var(--se-space-12);
  bottom: calc(100% + var(--se-space-4));
  background: var(--se-color-bg-surface);
  border: 1px solid var(--se-color-border-default);
  border-radius: var(--se-radius-lg);
  box-shadow: var(--shadow-float);
  padding: var(--se-space-8);
  z-index: 20;
}
/* Restrâns, meniul nu se mai poate întinde între marginile rail-ului — ar fi lat
   de 96px. Se ancorează la stânga și își ia lățimea proprie, ca „Delogare” să
   rămână pe un rând. */
.sidebar.collapsed .profile-dropdown {
  left: var(--se-space-8);
  right: auto;
  width: 220px;
}
/* Adresa întreagă, deasupra „Delogare": text, nu buton — nu face nimic la apăsare,
   se citește și se selectează. */
.profile-dropdown-who {
  padding: var(--se-space-4) var(--se-space-12) var(--se-space-8);
  color: var(--se-color-text-description);
  font-size: var(--se-type-captionreg-size);
  line-height: var(--se-type-captionreg-line);
  overflow-wrap: anywhere;
}
.profile-dropdown-who:empty {
  display: none;
}
.profile-dropdown-item {
  width: 100%;
  display: flex;
  align-items: center;
  gap: var(--se-space-8);
  border: none;
  background: none;
  padding: 10px var(--se-space-12);
  border-radius: var(--se-radius-md);
  color: var(--se-color-text-title);
  font-size: var(--se-type-bodyreg-size);
}
.profile-dropdown-item:hover {
  background: var(--se-color-bg-console);
}
.profile-dropdown-item .ph {
  color: var(--se-color-primary-60);
}

.main {
  flex: 1;
  min-width: 0;
  height: 100%;
  display: flex;
  flex-direction: column;
  padding: var(--se-space-8) var(--se-space-8) var(--se-space-8) 0;
  background: var(--se-color-bg-canvas);
  overflow: hidden;
}

/* ---- Bannerul de înregistrare (index.html #sipBanner, softphone.js) --------
   Singura bandă din antetul consolei: primul copil al .main, deasupra oricărei
   pagini, fiindcă ce spune — centrala refuză apelurile — nu așteaptă ca cineva
   să deschidă Setările. Roșu de STARE, perechea alert-red a insignelor `missed`
   și a .patient-alert: e exact rândul care oprește ceva (LAYOUT.md §3). Clasa
   pune `display: flex`, deci atributul `hidden` are nevoie de regula lui, ca la
   .card-outer[hidden]. Marginea stângă e cea a paginilor (.main are padding 0
   pe stânga, spre rail). */
.sip-banner {
  display: flex;
  align-items: center;
  gap: var(--se-space-12);
  flex: 0 0 auto;
  margin: 0 0 var(--se-space-8) var(--se-space-8);
  padding: var(--se-space-8) var(--se-space-16);
  border: 1px solid var(--se-color-alert-red-600);
  border-radius: var(--se-radius-md);
  background: var(--se-color-alert-red-100);
  color: var(--se-color-alert-red-600);
  font-size: var(--se-type-bodymed-size);
  line-height: var(--se-type-bodymed-line);
  font-weight: var(--se-type-bodymed-weight);
}
.sip-banner[hidden] {
  display: none;
}
.sip-banner .ph {
  width: var(--se-size-icon-functional);
  height: var(--se-size-icon-functional);
  flex: 0 0 auto;
}
.sip-banner-text {
  flex: 1 1 auto;
  min-width: 0;
}
.sip-banner-btn {
  flex: 0 0 auto;
}

/* ---- Banda de stare -------------------------------------------------------
   Nu mai e o bandă în antetul consolei: din 2026-08-31 stă în Setări, în
   acordeonul „Starea centralei". Regulile de aici desenează cuprinsul ei —
   ceasul, cele două lămpi SIP, comutatorul general și pastilele — oriunde ar fi
   pus, fiindcă niciuna nu mai depinde de antet. */
.clock {
  font-family: var(--mono);
  font-variant-numeric: tabular-nums;
  font-size: var(--se-type-captionmed-size);
  line-height: var(--se-type-captionmed-line);
  color: var(--se-color-text-muted);
  letter-spacing: 0.04em;
  white-space: nowrap;
}
.clock:empty {
  display: none;
}
.status-strip {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: var(--se-space-12);
}
.dot {
  width: 10px;
  height: 10px;
  border-radius: 50%;
  flex: 0 0 auto;
  background: var(--se-color-text-disabled);
  transition: background 0.2s;
}
.dot.on {
  background: var(--se-color-status-success);
}
.dot.warn {
  background: var(--se-color-badge-yellow-600);
}
.dot.busy {
  background: var(--se-color-accent-pink);
}

/* ---- Insigne --------------------------------------------------------------- */
.badge {
  font-size: var(--se-type-micromed-size);
  line-height: var(--se-type-micromed-line);
  font-weight: var(--se-type-micromed-weight);
  padding: 2px 10px;
  border-radius: var(--se-radius-pill);
  background: var(--se-color-badge-gray-100);
  color: var(--se-color-badge-gray-600);
  white-space: nowrap;
  font-variant-numeric: tabular-nums;
}
.badge.ok,
.badge.answered {
  background: var(--se-color-badge-green-100);
  color: var(--se-color-badge-green-600);
}
.badge.err,
.badge.missed {
  background: var(--se-color-badge-red-100);
  color: var(--se-color-badge-red-600);
}
.badge.warn,
.badge.noanswer {
  background: var(--se-color-badge-yellow-100);
  color: var(--se-color-badge-yellow-600);
}
.badge.neutral {
  background: var(--se-color-badge-gray-100);
  color: var(--se-color-badge-gray-600);
}
.badge[hidden] {
  display: none;
}

/* ---- Comutatoarele panourilor care costă cereri ---------------------------
   Oprit e starea de repaus și arată ca atare. Pornit e deliberat: șină navy,
   ca orice acțiune din sistemul ScanExpert. */
.switch {
  display: inline-flex;
  align-items: center;
  gap: var(--se-space-8);
  background: none;
  border: 0;
  padding: 0;
  color: var(--se-color-text-muted);
  font-size: var(--se-type-micromed-size);
  line-height: var(--se-type-micromed-line);
}
.switch-text {
  text-transform: uppercase;
  letter-spacing: 0.06em;
  font-weight: var(--se-type-micromed-weight);
}
.switch .track {
  position: relative;
  display: block;
  width: 34px;
  height: 20px;
  border-radius: var(--se-radius-pill);
  background: var(--se-color-fill-neutral);
  border: 1px solid var(--se-color-border-card);
  transition:
    background 0.18s,
    border-color 0.18s;
}
.switch .knob {
  position: absolute;
  top: 50%;
  left: 2px;
  transform: translateY(-50%);
  width: 14px;
  height: 14px;
  border-radius: 50%;
  background: var(--se-color-text-muted);
  transition:
    left 0.18s,
    background 0.18s;
}
.switch.on .track {
  background: var(--se-color-primary-60);
  border-color: var(--se-color-primary-60);
}
.switch.on .knob {
  left: 17px;
  background: var(--se-color-text-on-dark);
}
.switch.on {
  color: var(--se-color-primary-60);
}
.switch.partial .track {
  background: var(--se-color-badge-yellow-100);
  border-color: var(--se-color-badge-yellow-600);
}
.switch.partial .knob {
  left: 9px;
  background: var(--se-color-badge-yellow-600);
}
.switch.partial {
  color: var(--se-color-badge-yellow-600);
}
.switch:disabled {
  opacity: 0.5;
}
.switch.small .track {
  width: 30px;
  height: 18px;
}
.switch.small .knob {
  width: 12px;
  height: 12px;
}
.switch.small.on .knob {
  left: 15px;
}

/* ---- Vechimea cifrei ------------------------------------------------------
   Panourile live nu interoghează centrala când nu se uită nimeni la ele, deci
   asta e ce ține un panou pauzat cinstit. Stă în antetul cardului, la vedere. */
.age {
  font-family: var(--mono);
  font-variant-numeric: tabular-nums;
  font-size: var(--se-type-microreg-size);
  line-height: var(--se-type-microreg-line);
  color: var(--se-color-text-muted);
  white-space: nowrap;
}
.age.stale {
  opacity: 0.55;
  font-style: italic;
}
.age:empty {
  display: none;
}
