/* ============================================================================
   DANACO CONSOLE — BIBLIOTEKA KOMPONENTÓW · v2.0
   ----------------------------------------------------------------------------
   Barwy, odstępy i pismo wyłącznie z żetonów semantycznych (zasoby/zetony/zetony.css).
   Geometria jednorazowa komponentu (reguła nazewnicza 8) stoi lokalnie, nie w żetonie.
   Każdy komponent interaktywny ma stany: spoczynek · najechanie · naciśnięcie ·
   fokus · wybrany · ładowanie · błąd. Zasada zero blokad: żaden wariant nie odbiera
   klikalności — niegotowość komunikuje się opisem albo komunikatem.
   Stan nigdy samym kolorem — komponent stanu niesie ikonę albo etykietę.
   ============================================================================ */

/* Panel menu rozwijanego jest osobnym komponentem: bryła, szerokość i
   przewijanie w `menu.css`. Wpięty tutaj, bo każdy widok korzystający
   z biblioteki komponentów korzysta z menu. */
@import url('../menu.css');

/* ==========================================================================
   PRZYCISK
   ========================================================================== */
.dn-btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: var(--dn-od-2);
  min-height: var(--dn-wym-kontrolka);
  padding: 0 var(--dn-od-4);
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-sm);
  background: var(--dn-powierzchnia);
  color: var(--dn-tekst);
  font-family: var(--dn-ff-bazowa);
  font-size: var(--dn-fs-base);
  font-weight: var(--dn-fw-srednia);
  line-height: var(--dn-lh-ciasny);
  text-decoration: none;
  cursor: pointer;
  user-select: none;
  transition:
    background-color var(--dn-czas-2) var(--dn-ease),
    border-color var(--dn-czas-2) var(--dn-ease),
    color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-1) var(--dn-ease);
}
.dn-btn:hover { background: var(--dn-hover); }
.dn-btn:active { transform: translateY(1px); }
/* Ikona w przycisku z napisem: wymiar niesie przycisk, nie znacznik. Bez tej
   reguły wstawiony `svg` bierze wymiar z pojemnika i rośnie do jego wysokości. */
/* Przycisk ikonowy: wymiar znaku należy do przycisku. Bez tej reguły `svg`
   bez klasy rozciąga się do wysokości pojemnika, a reguły miejsc (pas narzędzi,
   pasmo kart, panel) łapią tylko wybrane zagnieżdżenia. */
.dn-btn-ikona > svg { flex: none; width: var(--dn-wym-ikona); height: var(--dn-wym-ikona); }
.dn-btn-ikona--sm > svg { width: var(--dn-wym-ikona-sm); height: var(--dn-wym-ikona-sm); }

.dn-btn > svg { flex: none; width: var(--dn-wym-ikona); height: var(--dn-wym-ikona); }
.dn-btn--sm > svg { width: var(--dn-wym-ikona-sm); height: var(--dn-wym-ikona-sm); }

.dn-btn:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: var(--dn-wym-fokus-odsuniecie);
}

/* Wybrany trwale — sygnał wskazuje (obrys + tło, zmiana kształtu przez obrys) */
.dn-btn[aria-pressed='true'],
.dn-btn.dn-btn--wybrany {
  background: var(--dn-sygnal-tlo);
  border-color: var(--dn-sygnal-obrys);
  color: var(--dn-sygnal);
}

/* Ładowanie — wskaźnik obok treści; przycisk pozostaje klikalny (zero blokad) */
.dn-btn[aria-busy='true'] { cursor: progress; }
.dn-btn[aria-busy='true']::after {
  content: '';
  width: var(--dn-wym-spinner);
  height: var(--dn-wym-spinner);
  flex: none;
  border: 2px solid currentColor;
  border-top-color: transparent;
  border-radius: var(--dn-r-pill);
  opacity: 0.7;
  animation: dn-obrot 0.8s linear infinite;
}

/* Błąd — obrys + barwa; treść przycisku niesie ikonę albo etykietę błędu */
.dn-btn[aria-invalid='true'] {
  border-color: var(--dn-blad-obrys);
  color: var(--dn-blad-tekst);
}

/* GŁÓWNY — inwersja atramentu: czerń na jasnym, biel na ciemnym */
.dn-btn--atrament {
  background: var(--dn-atrament);
  border-color: var(--dn-atrament);
  color: var(--dn-atrament-tekst);
}
/* Czynność główna odpowiada na wskazanie barwą sygnałową. Przejście
   `szary-900 → szary-1000` było niewidoczne i przycisk czytał się jak martwy.
   Biel na wypełnieniu sygnałowym to konwencja domu — patrz `.dn-btn--sygnal`. */
.dn-btn--atrament:hover {
  background: var(--dn-sygnal-wypelnienie);
  border-color: var(--dn-sygnal-wypelnienie);
  color: var(--dn-szary-0);
}

/* SYGNAŁOWY — wyłącznie działanie systemowe „uruchom / zatwierdź plan";
   jeden na widok. Nie zastępuje atramentu jako domyślnego głównego. */
.dn-btn--sygnal {
  background: var(--dn-sygnal-wypelnienie);
  border-color: var(--dn-sygnal-wypelnienie);
  color: var(--dn-szary-0);
}
.dn-btn--sygnal:hover {
  background: var(--dn-sygnal-wypelnienie-hover);
  border-color: var(--dn-sygnal-wypelnienie-hover);
}

/* ZARYS — akcje drugorzędne równorzędne */
.dn-btn--zarys { background: transparent; }

/* DUCH — akcje trzeciorzędne, paski narzędzi */
.dn-btn--duch {
  background: transparent;
  border-color: transparent;
  color: var(--dn-tekst-2);
}
.dn-btn--duch:hover { background: var(--dn-hover); color: var(--dn-tekst); }

/* NIEBEZPIECZNY — czynności nieodwracalne; sygnalizuje wagę, nie blokuje */
.dn-btn--niebezpieczny {
  background: transparent;
  border-color: var(--dn-blad-obrys);
  color: var(--dn-blad-tekst);
}
.dn-btn--niebezpieczny:hover { background: var(--dn-blad-tlo); }

/* Rozmiary — pochodne kontrolki, bez wartości spoza skali */
.dn-btn--sm {
  min-height: calc(var(--dn-wym-kontrolka) - var(--dn-od-1));
  padding: 0 var(--dn-od-3);
  font-size: var(--dn-fs-sm);
}
.dn-btn--lg {
  min-height: calc(var(--dn-wym-kontrolka) + var(--dn-od-2));
  padding: 0 var(--dn-od-5);
  font-size: var(--dn-fs-md);
}

/* Przycisk ikonowy */
.dn-btn-ikona {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: var(--dn-wym-ikonowy);
  height: var(--dn-wym-ikonowy);
  flex: none;
  padding: 0;
  border: 1px solid transparent;
  border-radius: var(--dn-r-sm);
  background: transparent;
  color: var(--dn-tekst-2);
  cursor: pointer;
  transition:
    background-color var(--dn-czas-2) var(--dn-ease),
    color var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-1) var(--dn-ease);
}
.dn-btn-ikona:hover { background: var(--dn-hover); color: var(--dn-tekst); }

/* Pole dotyku — WCAG 2.5.8 wymaga 24×24 px, a przycisk ikonowy bywa mniejszy
   tam, gdzie wiersz jest zwarty (np. `.dn-obszar-pozycja-menu` bierze wymiar
   ze skali ikon, nie kontrolek). Nakładka powiększa pole trafienia, nie
   zmieniając rysunku; przy przycisku 24 px i większym `max()` jest bezczynne.
   Nakładka idzie przez `::before`, bo `::after` przycisku nosi już dymek
   etykietki (`rama.css`) — dwie nakładki na jednym pseudoelemencie znosiłyby
   się nawzajem. */
.dn-btn-ikona { position: relative; }
.dn-btn-ikona::before {
  content: '';
  position: absolute;
  top: 50%;
  left: 50%;
  width: max(100%, var(--dn-wym-pole-dotyku));
  height: max(100%, var(--dn-wym-pole-dotyku));
  transform: translate(-50%, -50%);
}
.dn-btn-ikona:active { transform: translateY(1px); }
.dn-btn-ikona[aria-pressed='true'] {
  background: var(--dn-sygnal-tlo);
  color: var(--dn-sygnal);
}
.dn-btn-ikona:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: var(--dn-wym-fokus-odsuniecie);
}

/* Wariant na ramie (pasek górny — zawsze atramentowy) */
.dn-btn-ikona--na-ramie { color: var(--dn-rama-tekst-2); }
.dn-btn-ikona--na-ramie:hover { background: var(--dn-rama-hover); color: var(--dn-rama-tekst); }
.dn-btn-ikona--na-ramie[aria-pressed='true'] {
  background: var(--dn-rama-hover);
  color: var(--dn-sygnal-300);
}

/* ==========================================================================
   POLE FORMULARZA
   ========================================================================== */
.dn-pole { display: flex; flex-direction: column; gap: var(--dn-od-1); }
/* Pole, którego kontrolka bierze całą wolną wysokość — dokument do przeczytania,
   wykaz do przejrzenia. Bez tego pole kurczy się do treści i osadzona kontrolka
   nie ma do czego urosnąć, choć sama o wzrost prosi. */
.dn-pole--rosnace { flex: 1 1 auto; min-height: 0; }

.dn-pole-etykieta {
  font-size: var(--dn-fs-sm);
  font-weight: var(--dn-fw-srednia);
  color: var(--dn-tekst-2);
}

.dn-pole-kontrolka {
  min-height: var(--dn-wym-kontrolka);
  padding: 0 var(--dn-od-3);
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-sm);
  background: var(--dn-powierzchnia);
  color: var(--dn-tekst);
  font-size: var(--dn-fs-base);
  transition:
    border-color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-2) var(--dn-ease),
    background-color var(--dn-czas-2) var(--dn-ease);
}
textarea.dn-pole-kontrolka {
  min-height: calc(var(--dn-wym-kontrolka) * 2);
  padding: var(--dn-od-2) var(--dn-od-3);
  resize: vertical;
}
.dn-pole-kontrolka::placeholder { color: var(--dn-tekst-3); }
.dn-pole-kontrolka:hover { border-color: var(--dn-tekst-3); }
.dn-pole-kontrolka:focus {
  outline: none;
  border-color: var(--dn-fokus);
  box-shadow: var(--dn-cien-sygnal);
}
.dn-pole-kontrolka[aria-invalid='true'] { border-color: var(--dn-blad-tekst); }
.dn-pole-kontrolka[readonly] {
  background: var(--dn-powierzchnia-2);
  color: var(--dn-tekst-2);
}

/* Drugi stopień: opis pola bywa jedyną informacją o wymaganiach wobec wartości,
   a przy 13 px trzeci stopień daje 3,85:1 wobec panelu. */
.dn-pole-opis {
  font-size: var(--dn-fs-sm);
  color: var(--dn-tekst-2);
}

/* ── Klasy formularzowe używane w oknach nakładkowych i w Ustawieniach ──────
   Były w markupie prototypów bez deklaracji; opis stawia je w jednym miejscu. */
.dn-pole-etyk {
  display: block;
  margin-bottom: var(--dn-od-1);
  color: var(--dn-tekst-2);
  font-size: var(--dn-fs-sm);
  font-weight: var(--dn-fw-polgruba);
}
.dn-pole-grupa {
  display: flex;
  flex-direction: column;
  gap: var(--dn-od-2);
  margin: var(--dn-od-3) 0;
}
/* Komórka tabeli z ikoną przed nazwą — ikona jest elementem blokowym, więc
   bez tego opakowania nazwa spadała do drugiego wiersza. */
.dn-tabela-ikona-tekst {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
}
.dn-check-etyk {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
  color: var(--dn-tekst);
  font-size: var(--dn-fs-sm);
  cursor: pointer;
}
.dn-pole-blad {
  display: inline-flex;
  align-items: flex-start;
  gap: var(--dn-od-1);
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-bazowy);
  color: var(--dn-blad-tekst);
}
/* Znak przy komunikacie — bez wymiaru `svg` bez atrybutów rozpycha się do
   rozmiaru zastępczego elementu zastępowanego (300 × 150 px). */
.dn-pole-blad > svg {
  width: var(--dn-wym-ikona-xs);
  height: var(--dn-wym-ikona-xs);
  flex: none;
  margin-top: calc((var(--dn-fs-sm) * var(--dn-lh-bazowy) - var(--dn-wym-ikona-xs)) / 2);
}

/* Pole wyszukiwania z ikoną */
.dn-szukaj { position: relative; display: flex; align-items: center; }
.dn-szukaj > svg {
  position: absolute;
  left: var(--dn-od-3);
  width: var(--dn-wym-ikona);
  height: var(--dn-wym-ikona);
  color: var(--dn-tekst-3);
  pointer-events: none;
}
.dn-szukaj > .dn-pole-kontrolka { width: 100%; padding-left: var(--dn-od-8); }
/* Pole wpisane bezpośrednio, bez klasy kontrolki, dziedziczy jej wygląd —
   inaczej ikona wyszukiwania nachodzi na tekst zastępczy. */
.dn-szukaj > input {
  width: 100%;
  min-height: var(--dn-wym-kontrolka);
  padding: 0 var(--dn-od-3) 0 var(--dn-od-8);
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-sm);
  background: var(--dn-panel);
  color: var(--dn-tekst);
  font-family: var(--dn-ff-bazowa);
  font-size: var(--dn-fs-base);
  transition:
    border-color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-2) var(--dn-ease),
    background-color var(--dn-czas-2) var(--dn-ease);
}

/* Wybór rozwijany */
select.dn-pole-kontrolka { padding-right: var(--dn-od-6); cursor: pointer; }

/* ==========================================================================
   WYBÓR: POLE WYBORU · PRZEŁĄCZNIK · RADIO
   ========================================================================== */
.dn-wybor {
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-2);
  min-height: var(--dn-wym-kontrolka);
  cursor: pointer;
  font-size: var(--dn-fs-base);
}

/* Wybór blokowy — kontrolka u góry, obok niej kolumna: nazwa, opis, nota.
   Postać dla wariantów instalacji i innych wyborów wymagających wyjaśnienia. */
.dn-wybor--blokowy {
  display: flex;
  align-items: flex-start;
  width: 100%;
}
.dn-wybor-nazwa {
  display: block;
  font-size: var(--dn-fs-md);
  font-weight: var(--dn-fw-polgruba);
  color: var(--dn-tekst);
}
.dn-wybor-opis {
  display: block;
  margin-top: var(--dn-od-2);
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-bazowy);
  color: var(--dn-tekst-2);
}
/* Zero blokad: wybór niegotowy nie odbiera klikalności, tylko niesie stan. */
.dn-wybor:has([aria-invalid='true']) { color: var(--dn-blad-tekst); }
.dn-wybor [aria-invalid='true'] {
  border-color: var(--dn-blad-obrys);
  box-shadow: 0 0 0 1px var(--dn-blad-obrys);
}

.dn-check {
  appearance: none;
  width: var(--dn-wym-check);
  height: var(--dn-wym-check);
  flex: none;
  margin: 0;
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-xs);
  background: var(--dn-powierzchnia);
  cursor: pointer;
  display: grid;
  place-content: center;
  transition: background-color var(--dn-czas-1) var(--dn-ease), border-color var(--dn-czas-1) var(--dn-ease);
}
.dn-check::before {
  content: '';
  width: 10px; height: 10px;
  transform: scale(0);
  transition: transform var(--dn-czas-1) var(--dn-ease);
  clip-path: polygon(14% 44%, 0 62%, 40% 100%, 100% 18%, 84% 4%, 38% 68%);
  background: var(--dn-atrament-tekst);
}
.dn-check:checked { background: var(--dn-atrament); border-color: var(--dn-atrament); }
.dn-check:checked::before { transform: scale(1); }

.dn-radio { border-radius: var(--dn-r-pill); }
.dn-radio::before { clip-path: none; border-radius: var(--dn-r-pill); width: 8px; height: 8px; }

/* Przełącznik — tor + suwak; wybrany = sygnał (wskazanie stanu, nie akcja) */
.dn-przelacznik {
  appearance: none;
  width: var(--dn-wym-przelacznik-szer);
  height: var(--dn-wym-przelacznik-wys);
  flex: none;
  margin: 0;
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-pill);
  background: var(--dn-powierzchnia-2);
  position: relative;
  cursor: pointer;
  transition: background-color var(--dn-czas-2) var(--dn-ease), border-color var(--dn-czas-2) var(--dn-ease);
}
.dn-przelacznik::before {
  content: '';
  position: absolute;
  top: 50%;
  left: 2px;
  translate: 0 -50%;
  width: calc(var(--dn-wym-przelacznik-wys) - 6px);
  height: calc(var(--dn-wym-przelacznik-wys) - 6px);
  border-radius: var(--dn-r-pill);
  background: var(--dn-tekst-2);
  transition: left var(--dn-czas-2) var(--dn-ease), background-color var(--dn-czas-2) var(--dn-ease);
}
.dn-przelacznik:checked,
/* Przełącznik bywa w prototypach przyciskiem z role="switch" — bez tej reguły
   stan włączony nie był widoczny w żadnym oknie. */
.dn-przelacznik[aria-checked='true'],
.dn-przelacznik[aria-pressed='true'] {
  background: var(--dn-sygnal-wypelnienie);
  border-color: var(--dn-sygnal-wypelnienie);
}
.dn-przelacznik:checked::before,
.dn-przelacznik[aria-checked='true']::before,
.dn-przelacznik[aria-pressed='true']::before {
  left: calc(100% - var(--dn-wym-przelacznik-wys) + 4px);
  background: var(--dn-szary-0);
}

/* Suwak — nakład rozumowania (szybciej ↔ mądrzej) */
.dn-suwak {
  appearance: none;
  width: 100%;
  height: 4px;
  border-radius: var(--dn-r-pill);
  background: linear-gradient(to right, var(--dn-sygnal-wypelnienie) var(--dn-suwak-pozycja, 50%), var(--dn-powierzchnia-2) var(--dn-suwak-pozycja, 50%));
  outline-offset: var(--dn-od-1);
  cursor: pointer;
}
.dn-suwak::-webkit-slider-thumb {
  appearance: none;
  width: 16px; height: 16px;
  border: 2px solid var(--dn-sygnal-wypelnienie);
  border-radius: var(--dn-r-pill);
  background: var(--dn-powierzchnia);
  box-shadow: var(--dn-cien-1);
}
.dn-suwak::-moz-range-thumb {
  width: 12px; height: 12px;
  border: 2px solid var(--dn-sygnal-wypelnienie);
  border-radius: var(--dn-r-pill);
  background: var(--dn-powierzchnia);
}

/* ==========================================================================
   KROPKA SYGNAŁU — element sygnaturowy (praca w tle; rozstrzygnięcie projektowe)
   ========================================================================== */
.dn-kropka {
  display: inline-block;
  width: var(--dn-wym-kropka);
  height: var(--dn-wym-kropka);
  flex: none;
  border-radius: var(--dn-r-pill);
  background: var(--dn-kropka);
}
/* Tętno — jedyny ruch ciągły interfejsu (2,4 s) */
.dn-kropka--tetno { animation: dn-tetno var(--dn-czas-tetno) var(--dn-ease) infinite; }
/* Przy ograniczonym ruchu tętno zamiera — kropkę wzmacnia pierścień statyczny */
@media (prefers-reduced-motion: reduce) {
  .dn-kropka--tetno { box-shadow: 0 0 0 2px var(--dn-fokus-cien); }
}
/* Warianty stanu (zawsze obok etykiety albo ikony — nigdy same) */
.dn-kropka--sukces { background: var(--dn-sukces-tekst); }
.dn-kropka--ostrzezenie { background: var(--dn-ostrzezenie-tekst); }
.dn-kropka--blad { background: var(--dn-blad-tekst); }
.dn-kropka--neutralna { background: var(--dn-tekst-3); }

/* ==========================================================================
   PLAKIETKA — stany i role
   ========================================================================== */
.dn-plakietka {
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-1);
  padding: 1px var(--dn-od-2) 2px;
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-pill);
  background: var(--dn-powierzchnia-2);
  color: var(--dn-tekst-2);
  font-size: var(--dn-fs-xs);
  font-weight: var(--dn-fw-srednia);
  line-height: var(--dn-lh-bazowy);
  white-space: nowrap;
}
.dn-plakietka > svg { width: 12px; height: 12px; }
.dn-plakietka--sukces { background: var(--dn-sukces-tlo); border-color: var(--dn-sukces-obrys); color: var(--dn-sukces-tekst); }
.dn-plakietka--ostrzezenie { background: var(--dn-ostrzezenie-tlo); border-color: var(--dn-ostrzezenie-obrys); color: var(--dn-ostrzezenie-tekst); }
.dn-plakietka--blad { background: var(--dn-blad-tlo); border-color: var(--dn-blad-obrys); color: var(--dn-blad-tekst); }
.dn-plakietka--informacja { background: var(--dn-informacja-tlo); border-color: var(--dn-informacja-obrys); color: var(--dn-informacja-tekst); }
.dn-plakietka--sygnal { background: var(--dn-sygnal-tlo); border-color: var(--dn-sygnal-obrys); color: var(--dn-sygnal); }

/* Plakietka roli okna — mono wersaliki (koordynator / wykonawca / walidator) */
.dn-plakietka--rola {
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  letter-spacing: var(--dn-ls-mono-wersaliki);
  text-transform: uppercase;
  border-radius: var(--dn-r-xs);
}

/* ==========================================================================
   KARTA
   ========================================================================== */
.dn-karta {
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-lg);
  background: var(--dn-powierzchnia);
  box-shadow: var(--dn-cien-1);
}
.dn-karta-cialo { padding: var(--dn-odstep-panel) var(--dn-od-4); }
.dn-karta-naglowek {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
  padding: var(--dn-od-3) var(--dn-od-4);
  border-bottom: 1px solid var(--dn-obrys-subtelny);
}
.dn-karta-tytul {
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-lg);
  font-weight: var(--dn-fw-polgruba);
  letter-spacing: var(--dn-ls-naglowek);
}

/* Karta interaktywna */
.dn-karta--klikalna {
  cursor: pointer;
  transition:
    border-color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-2) var(--dn-ease),
    background-color var(--dn-czas-2) var(--dn-ease);
}
.dn-karta--klikalna:hover {
  border-color: var(--dn-obrys-mocny);
  box-shadow: var(--dn-cien-2);
  transform: translateY(-1px);
}
.dn-karta--klikalna:active { transform: translateY(0); }
.dn-karta--wybrana { border-color: var(--dn-sygnal-obrys); background: var(--dn-sygnal-tlo); }

/* KARTA ŚRODOWISKA (Centrum dowodzenia, strefa 1) — wejście do środowiska.
   Spoczynek bez sygnału; najechanie/aktywność: wstęga górna 2 px. */
.dn-karta-srodowiska {
  position: relative;
  overflow: hidden;
  padding: var(--dn-od-6);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-xl);
  /* Wypełnienie o stopień jaśniejsze od powierzchni: w motywie ciemnym karta na
     tacy panelu (--dn-wstazka) była za głucha. Nadal ciemniejsza od panelu,
     więc hierarchia „taca → karta" zostaje (rozstrzygnięcie Właściciela). */
  background: var(--dn-panel);
  cursor: pointer;
  transition:
    border-color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-2) var(--dn-ease);
}
.dn-karta-srodowiska::before {
  content: '';
  position: absolute;
  inset: 0 0 auto 0;
  height: var(--dn-wym-wstega);
  background: var(--dn-kropka);
  opacity: 0;
  transition: opacity var(--dn-czas-2) var(--dn-ease);
}
.dn-karta-srodowiska:hover,
.dn-karta-srodowiska[aria-current='true'] {
  border-color: var(--dn-obrys-mocny);
  box-shadow: var(--dn-cien-2);
  transform: translateY(-2px);
}
.dn-karta-srodowiska:hover::before,
.dn-karta-srodowiska[aria-current='true']::before { opacity: 1; }
.dn-karta-srodowiska-godlo {
  /* Element liniowy nie przyjmuje szerokości — bez tej deklaracji godło
     rozciągało się na całą kartę. */
  display: grid;
  place-content: center;
  /* Emblemat jest znakiem marki, nie ikoną interfejsu, więc nie bierze skali
     ikon. Wymiar stoi w żetonie --dn-wym-godlo-karty i tylko tam. */
  width: var(--dn-wym-godlo-karty);
  height: var(--dn-wym-godlo-karty);
  margin-bottom: var(--dn-od-4);
  color: var(--dn-tekst);
}
.dn-karta-srodowiska-tytul {
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-3xl);
  font-weight: var(--dn-fw-polgruba);
  letter-spacing: var(--dn-ls-naglowek);
  line-height: var(--dn-lh-ciasny);
}
.dn-karta-srodowiska-motto {
  margin-top: var(--dn-od-1);
  font-family: var(--dn-ff-mono);
  /* Miara i opis o stopień wyżej — razem z miarą sesji w stopce. */
  font-size: var(--dn-fs-md);
  color: var(--dn-tekst-3);
}
.dn-karta-srodowiska-opis {
  margin-top: var(--dn-od-3);
  font-size: var(--dn-fs-md);
  color: var(--dn-tekst-2);
  max-width: 44ch;
}

/* Karta wiodąca — środowisko podane akcentem: tytuł o stopień większy, bez
   wstęgi sygnału u góry, bo akcent niesie już sama skala. Rozmieszczenie
   kolumnowe zostaje w oknie, bo to siatka. Godła wariant nie rusza: wymiar
   emblematu jest jeden dla wszystkich kart. */
.dn-karta-srodowiska--akcent::before { content: none; }
.dn-karta-srodowiska--akcent .dn-karta-srodowiska-tytul { font-size: var(--dn-fs-4xl); }

/* Warstwa tła karty — pole na znak przestrzenny przy prawej krawędzi. Karta
   trzyma tylko krycie i przejście; CO w tej warstwie stoi, wskazuje okno.
   W spoczynku znak jest tłem (11%), przy wskazaniu wychodzi na wierzch (50%) —
   nadal pod pismem, bo `pointer-events` i warstwa go tam trzymają. */
.dn-karta-tlo {
  position: absolute;
  inset: 0 0 0 auto;
  display: grid;
  place-items: center;
  z-index: 0;
  opacity: 0.11;
  pointer-events: none;
  container-type: inline-size;
  transition: opacity var(--dn-czas-2) var(--dn-ease);
}
.dn-karta-srodowiska:hover > .dn-karta-tlo,
.dn-karta-srodowiska:focus-within > .dn-karta-tlo { opacity: 0.5; }
/* Treść karty stoi nad warstwą tła. */
.dn-karta-srodowiska > :not(.dn-karta-tlo) { position: relative; z-index: 1; }

/* Najechanie na kartę podnosi jej własny opis i motto do pełnej barwy pisma:
   karta wskazana czyta się w całości, nie tylko tytułem. Reguła stała
   w arkuszu Centrum dowodzenia — należy do rodziny, nie do okna. */
.dn-karta-srodowiska-opis,
.dn-karta-srodowiska-motto {
  transition: color var(--dn-czas-2) var(--dn-ease);
}
.dn-karta-srodowiska:hover .dn-karta-srodowiska-opis,
.dn-karta-srodowiska:hover .dn-karta-srodowiska-motto,
.dn-karta-srodowiska:focus-within .dn-karta-srodowiska-opis,
.dn-karta-srodowiska:focus-within .dn-karta-srodowiska-motto { color: var(--dn-tekst); }

/* Stopka karty — nota maszynowa nad dolną krawędzią. Rozdziela ją ODSTĘP,
   nie kreska: kreska przecinała kartę w poprzek i czytała się jak koniec
   treści, a nie jak zmiana rejestru z opisu na miarę. */
.dn-karta-stopka {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
  /* Stopka podciągnięta do treści: odstęp 16 + 12 px zostawiał w karcie pas
     pustego pola nad miarą. Wyściółki karty nie ruszamy, więc odstęp grotu
     od dolnej i od prawej krawędzi zostaje równy. */
  margin-top: var(--dn-od-2);
  padding-top: 0;
  font-family: var(--dn-ff-mono);
  /* Miara sesji o dwa stopnie wyżej: na 12 px ginęła pod nazwą na 36 px. */
  font-size: var(--dn-fs-base);
  /* Stopień 12 px na panelu nie przechodzi 4,5 : 1 na `--dn-tekst-3`. */
  color: var(--dn-tekst-2);
}

/* KAFEL KOMPONENTU WŁASNEGO (Centrum dowodzenia, strefa 2) — budowanie, krój bazowy */
.dn-kafel {
  display: flex;
  align-items: center;
  gap: var(--dn-od-3);
  padding: var(--dn-od-4);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-lg);
  background: var(--dn-panel);
  color: var(--dn-tekst);
  font-family: var(--dn-ff-bazowa);
  font-size: var(--dn-fs-base);
  line-height: var(--dn-lh-bazowy);
  text-align: left;
  cursor: pointer;
  transition: border-color var(--dn-czas-2) var(--dn-ease), background-color var(--dn-czas-2) var(--dn-ease);
}
.dn-kafel:hover { border-color: var(--dn-obrys-mocny); background: var(--dn-powierzchnia); }
.dn-kafel-ikona {
  display: grid;
  place-content: center;
  width: var(--dn-wym-awatar-lg);
  height: var(--dn-wym-awatar-lg);
  flex: none;
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia);
  color: var(--dn-tekst-2);
}
.dn-kafel-etykieta { font-weight: var(--dn-fw-polgruba); font-size: var(--dn-fs-base); }
.dn-kafel-opis { font-size: var(--dn-fs-sm); color: var(--dn-tekst-3); }

/* Znak bez ramki — kafel modułu podaje ikonę wprost na tle kafla. Medalion
   z obrysem zostaje tam, gdzie znak zastępuje godło (karta środowiska). */
/* Znak bez pola — kafel modułu podaje ikonę wprost na tle kafla: bez obrysu,
   bez wypełnienia i bez podświetlenia pola, także pod wskaźnikiem. Medalion
   z obrysem zostaje tam, gdzie znak zastępuje godło (karta środowiska). */
.dn-kafel-ikona--bez-ramki {
  border: 0;
  background: none;
  color: var(--dn-tekst);
}
/* Znak kafla modułu jest emblematem, nie ikoną interfejsu ze skali
   14/16/20/24, więc ma własny żeton. O stopień mniejszy od emblematu karty
   środowiska (40 wobec 54 px) — po oględzinach Właściciela z 27.08.2026
   równy wymiar rozpychał kafel. Skala `svg` idzie za pojemnikiem. */
.dn-kafel-ikona--godlowa,
.dn-kafel-ikona--godlowa > svg {
  width: var(--dn-wym-znak-modulu);
  height: var(--dn-wym-znak-modulu);
}

/* Kafel modułu — nazwa czytana jak nagłówek, nie jak etykieta: stopień wyżej
   i grubość normalna. Opis o stopień jaśniejszy od pisma, ale nad progiem. */
/* Nazwa modułu bierze krój, grubość i barwę nazwy środowiska, ale nie jej
   stopień — stopień wiąże szerokość kafla. Kafel 289 px w układzie poziomym
   oddaje nazwie 121 px po odjęciu wyściółki 48, znaku 40, grotu 38 i luk 42.
   „Automations" zajmuje 103 px na stopniu 17, 128 px na 21 i 218 px na 36:
   mieści się dopiero na 17, z zapasem 18 px. Powiększenie znaku i grotu
   (oględziny Właściciela z 27.08.2026) odebrało nazwie te 23 px. */
.dn-kafel--modul .dn-kafel-etykieta {
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-2xl);
  font-weight: var(--dn-fw-polgruba);
  letter-spacing: var(--dn-ls-naglowek);
  line-height: var(--dn-lh-ciasny);
  color: var(--dn-tekst);
}
/* Opis w kaflu modułu o stopień wyżej niż w kaflu bazowym: nazwa stoi tu
   na 24 px, więc opis na 13 px czytał się jak przypis. */
.dn-kafel--modul .dn-kafel-opis { font-size: var(--dn-fs-base); color: var(--dn-tekst-2); }
/* Wysokość najmniejsza żetonem, nie z sumy treści: opisy czterech kafli mają
   różną liczbę wierszy, a rząd ma stać równo niezależnie od redakcji.
   Kompozycja zostaje pozioma — znak, treść, czynność w jednym rzędzie
   (rozstrzygnięcie Właściciela z 27.08.2026). Szerokość, jakiej wymaga nazwa
   na stopniu 36 px, zapewnia siatka okna, nie zmiana układu kafla. */
.dn-kafel--modul { min-height: var(--dn-wym-kafel-modulu); }

/* Wiersz — kafel zwarty do wykazu: jedna linia nazwy, druga rodzaju. Ta sama
   bryła i te same stany co kafel, mniejsza wyściółka i promień. */
.dn-kafel--wiersz {
  gap: var(--dn-od-3);
  padding: var(--dn-od-2) var(--dn-od-3);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia);
  font-size: var(--dn-fs-sm);
  transition:
    background-color var(--dn-czas-1) var(--dn-ease),
    border-color var(--dn-czas-1) var(--dn-ease);
}
.dn-kafel--wiersz:hover { border-color: var(--dn-obrys-mocny); background: var(--dn-panel); }
.dn-kafel--wiersz:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: calc(-1 * var(--dn-wym-fokus));
}
.dn-kafel-nazwa { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.dn-kafel-rodzaj { font-size: var(--dn-fs-xs); color: var(--dn-tekst-opis); }
/* Znak wiersza — ikona przy nazwie, bez medalionu. Ustępuje pismu o stopień,
   bo nazywa rodzaj pozycji, a nie ją samą. */
.dn-kafel-znak {
  display: grid;
  place-content: center;
  flex: none;
  color: var(--dn-tekst-2);
}
.dn-kafel-znak > svg { width: var(--dn-wym-ikona); height: var(--dn-wym-ikona); }

/* Wybór — kafel do wskazania jednej z kilku dróg: znak nad nazwą, nazwa nad
   stanem, wszystko w osi. Rodzina stała w arkuszu okna wejściowego jako
   `.au-metoda`; różniła się od kafla tylko układem kolumnowym i zwarciem
   wyściółki, więc weszła tu jako odmiana, a nie jako druga rodzina.

   Barwa nazwy zostaje z kafla (`--dn-tekst`). Arkusz okna gasił ją do
   `--dn-tekst-2` razem ze stanem, przez co nazwa drogi i przypis o jej
   dostępności ważyły tyle samo; stan ustępuje teraz nazwie o stopień. */
.dn-kafel--wybor {
  flex-direction: column;
  align-items: center;
  gap: var(--dn-od-1);
  padding: var(--dn-od-3) var(--dn-od-2);
  border-radius: var(--dn-r-md);
  font-size: var(--dn-fs-xs);
  text-align: center;
}
.dn-kafel--wybor > svg {
  width: var(--dn-wym-ikona);
  height: var(--dn-wym-ikona);
  flex: none;
  color: var(--dn-tekst-2);
  transition: color var(--dn-czas-2) var(--dn-ease), transform var(--dn-czas-uwyd) var(--dn-ease);
}
.dn-kafel--wybor:hover > svg, .dn-kafel--wybor:focus-visible > svg {
  color: var(--dn-sygnal);
  transform: scale(var(--dn-skala-ikony));
}
/* Stan drogi — przypis pod nazwą. Krój maszynowy, bo to wartość odczytana,
   a nie zdanie: „aktywna" / „nieaktywna" stoją zawsze w tym samym miejscu. */
.dn-kafel-stan {
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  color: var(--dn-tekst-2);
}

/* ==========================================================================
   GROT WEJŚCIA — znak marki jako czynność „wejdź"
   --------------------------------------------------------------------------
   Rodzina stała w arkuszu Centrum dowodzenia jako `.cd-wejdz--grot`
   i `.cd-grot-marki`, w dwóch skalach i z ośmioma regułami stanów. Grot nie
   jest ikoną interfejsu — jest znakiem marki, więc nie podlega skali ikon;
   wysokość bierze żeton `--dn-wym-grot`.

   Ruch: grot przesuwa się o jeden stopień siatki w stronę, w którą prowadzi,
   a kropka marki zapala się sygnałem. Reakcja idzie zarówno z najechania na
   sam grot, jak i z najechania na kartę albo kafel, w którym stoi — dlatego
   stany są wypisane dla rodzica z biblioteki, nie dla klasy okna.
   ========================================================================== */

.dn-wejdz-grot {
  position: relative;
  display: grid;
  place-items: center;
  padding: 0;
  border: 0;
  background: none;
  color: var(--dn-tekst-2);
  cursor: pointer;
}
/* Cel kliknięcia rośnie NA ZEWNĄTRZ znaku. Gdy przycisk sam miał wymiar celu,
   znak siedział w nim wyśrodkowany i do krawędzi karty zostawało 31,6 px
   z prawej, a 43 px z dołu — bo znak jest szerszy niż wyższy. Pole przycisku
   równa się znakowi, więc odstęp od dołu RÓWNA SIĘ odstępowi od prawej. */
.dn-wejdz-grot::before {
  content: '';
  position: absolute;
  left: 50%;
  top: 50%;
  translate: -50% -50%;
  width: var(--dn-wym-grot);
  height: var(--dn-wym-grot);
}
.dn-wejdz-grot:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: var(--dn-wym-fokus-odsuniecie);
  border-radius: var(--dn-r-sm);
}

.dn-grot-marki {
  width: auto;
  height: var(--dn-wym-grot-znak);
  flex: none;
  transition:
    color var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-2) var(--dn-ease);
}
.dn-grot-marki--sm { height: var(--dn-wym-grot-sm); color: var(--dn-tekst-2); }
/* Kropka marki: na karcie zostaje sygnałem (atrybut `fill` w znaczniku),
   w grocie zwartym idzie barwą pisma, bo grot jest tam znacznikiem czynności,
   nie znakiem marki. Reguła ogólna gasiła kropkę na kartach — CSS wygrywa
   z atrybutem prezentacji. */
.dn-grot-marki { transition:
    color var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-2) var(--dn-ease); }
.dn-grot-marki--sm .kropka { fill: currentColor; transition: fill var(--dn-czas-2) var(--dn-ease); }

/* Zapalenie grotu — z najechania na całą kartę albo cały kafel. Znak wychodzi
   w stronę, w którą prowadzi: trzy stopnie siatki. */
.dn-karta-srodowiska:hover .dn-grot-marki,
.dn-karta-srodowiska:focus-within .dn-grot-marki,
.dn-kafel:hover .dn-grot-marki,
.dn-kafel:focus-visible .dn-grot-marki {
  color: var(--dn-tekst);
  transform: translateX(var(--dn-od-3));
}

/* Ruch WŁASNY grotu — gdy wskaźnik stoi na nim samym, a nie tylko na karcie
   pod nim. Wychodzi wtedy dalej, o pięć stopni siatki: wskazanie karty mówi
   „ta karta", wskazanie grotu mówi „ta czynność". Reguła stoi PO regule wyżej,
   więc przy równej swoistości wygrywa. Dotyczy obu skal — podwójnego grotu
   na karcie środowiska i pojedynczego w kaflu modułu. */
.dn-wejdz-grot:hover .dn-grot-marki,
.dn-wejdz-grot:focus-visible .dn-grot-marki,
.dn-karta-srodowiska .dn-grot-marki:hover,
.dn-kafel .dn-grot-marki:hover {
  color: var(--dn-tekst);
  transform: translateX(var(--dn-od-5));
}
.dn-kafel:hover .dn-grot-marki--sm .kropka,
.dn-kafel:focus-visible .dn-grot-marki--sm .kropka { fill: var(--dn-sygnal); }

/* Miniatura — kafel nieinteraktywny w siatce podglądu. Ta sama bryła co kafel
   wiodący, tylko zwarta i ułożona w kolumnę: znak, nazwa, nota. Nie jest
   przyciskiem, więc zdejmuje wskaźnik i przejście stanu najechania. */
.dn-kafel--miniatura {
  flex-direction: column;
  align-items: flex-start;
  gap: var(--dn-od-1);
  padding: var(--dn-od-2);
  border-color: var(--dn-obrys-subtelny);
  border-radius: var(--dn-r-sm);
  font-size: var(--dn-fs-xs);
  cursor: default;
  transition: none;
}
.dn-kafel--miniatura:hover { border-color: var(--dn-obrys-subtelny); background: var(--dn-panel); }
.dn-kafel--miniatura > svg {
  width: var(--dn-wym-ikona-xl);
  height: var(--dn-wym-ikona-xl);
  flex: none;
  color: var(--dn-tekst-3);
}

/* ==========================================================================
   TABELA — zwarta, robocza
   ========================================================================== */
.dn-tabela {
  width: 100%;
  border-collapse: collapse;
  font-size: var(--dn-fs-base);
}
.dn-tabela th {
  position: sticky;
  top: 0;
  z-index: var(--dn-z-przybornik);
  padding: 0 var(--dn-od-3);
  height: calc(var(--dn-wym-wiersz) - var(--dn-od-1));
  border-bottom: 1px solid var(--dn-obrys);
  background: var(--dn-panel);
  text-align: left;
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  font-weight: var(--dn-fw-srednia);
  letter-spacing: var(--dn-ls-mono-wersaliki);
  text-transform: uppercase;
  color: var(--dn-tekst-3);
  white-space: nowrap;
}
.dn-tabela td {
  height: var(--dn-wym-wiersz);
  padding: 0 var(--dn-od-3);
  border-bottom: 1px solid var(--dn-obrys-subtelny);
  vertical-align: middle;
}
.dn-tabela tbody tr { transition: background-color var(--dn-czas-1) var(--dn-ease); }
.dn-tabela tbody tr:hover { background: var(--dn-hover); }
.dn-tabela tbody tr[aria-selected='true'] { background: var(--dn-sygnal-tlo); }
.dn-tabela td.dn-dane { font-size: var(--dn-fs-sm); color: var(--dn-tekst-2); }

/* Wariant treściowy — tabela w dokumencie, nie siatka danych. Trzy różnice
   wynikają z jednej: komórka niesie zdanie, nie wartość. Wysokość wiersza
   przestaje być stała (zdanie łamie się na kilka linii), tekst równa się do
   góry (inaczej pierwsza linia komórki jednolinijkowej wisi w połowie sąsiedniej
   wielolinijkowej), a głowa nie przykleja się do krawędzi, bo dokument przewija
   się w całości i przyklejony nagłówek zasłaniałby treść rozdziału. */
.dn-tabela--tresc { font-size: var(--dn-fs-sm); }
.dn-tabela--tresc th {
  position: static;
  height: auto;
  padding: var(--dn-od-1) var(--dn-od-3);
  background: none;
  font-weight: var(--dn-fw-normalna);
}
.dn-tabela--tresc td {
  height: auto;
  padding: var(--dn-od-2) var(--dn-od-3);
  color: var(--dn-tekst-2);
  vertical-align: top;
}
.dn-tabela--tresc tbody tr:last-child td { border-bottom: 0; }
/* Kolumna liczbowa — wyrównanie do prawej i pismo maszynowe, żeby rzędy
   wielkości stały w jednej pionowej linii. Dotąd okna robiły to atrybutem
   `style` na każdej komórce osobno, a pismo brały z rusztowania `.pt-mono`. */
.dn-tabela-liczba { text-align: right; font-family: var(--dn-ff-mono); font-variant-numeric: tabular-nums; }
th.dn-tabela-liczba { text-align: right; }
/* Podpis tabeli czyta się jak nadtytuł rozdziału, nie jak wiersz danych. */
.dn-tabela caption {
  padding-bottom: var(--dn-od-2);
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  letter-spacing: var(--dn-ls-mono-wersaliki);
  text-transform: uppercase;
  color: var(--dn-tekst-3);
  text-align: left;
}

/* ==========================================================================
   ZAKŁADKI · KARTY SESJI
   ========================================================================== */
.dn-zakladki {
  display: flex;
  gap: var(--dn-od-1);
  border-bottom: 1px solid var(--dn-obrys);
}
.dn-zakladka {
  position: relative;
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-2);
  min-height: var(--dn-wym-kontrolka);
  padding: 0 var(--dn-od-3);
  border: none;
  background: transparent;
  color: var(--dn-tekst-2);
  font-size: var(--dn-fs-base);
  font-weight: var(--dn-fw-srednia);
  cursor: pointer;
  transition: color var(--dn-czas-2) var(--dn-ease), background-color var(--dn-czas-2) var(--dn-ease);
}
.dn-zakladka:hover { color: var(--dn-tekst); background: var(--dn-hover); }
.dn-zakladka[aria-selected='true'] { color: var(--dn-tekst); }
.dn-zakladka[aria-selected='true']::after {
  content: '';
  position: absolute;
  inset: auto 0 -1px 0;
  height: 2px;
  background: var(--dn-kropka);
}

/* ── Wariant pigułkowy ──────────────────────────────────────────────────────
   Przełącznik dwóch równorzędnych stanów (np. logowanie albo rejestracja).
   Nie ma dolnej kreski zakładek: wybór niesie wypełniona pigułka. Stan wybrany
   dostaje barwę sygnałową i kontrę — sam kształt bez koloru czytałby się jako
   pole nieaktywne, a to jest kontrolka wyboru, nie etykieta. */
.dn-zakladki--pigulki {
  display: inline-flex;
  /* Pigułki mają szerokość własnej treści także wtedy, gdy stoją w kolumnie
     rozciągającej dzieci — inaczej przełącznik dwóch dróg rozpiera się na całą
     kolumnę i przestaje czytać się jako kontrolka wyboru. */
  align-self: flex-start;
  gap: 2px;
  padding: 3px;
  border: 0;
  border-radius: var(--dn-r-pill);
  background: var(--dn-powierzchnia-2);
}
.dn-zakladki--pigulki .dn-zakladka {
  border-radius: var(--dn-r-pill);
  padding: 0 var(--dn-od-4);
  font-size: var(--dn-fs-sm);
}
.dn-zakladki--pigulki .dn-zakladka::after { content: none; }

.dn-zakladki--pigulki .dn-zakladka:hover { background: var(--dn-hover); }
.dn-zakladki--pigulki .dn-zakladka[aria-selected='true'] {
  background: var(--dn-sygnal-wypelnienie);
  /* Biel, nie `--dn-tekst-inv`: w motywie ciemnym odwrotność tekstu jest niemal
     czarna i na wypełnieniu sygnałowym daje 4,14:1. Konwencja domu dla pisma na
     wypełnieniu sygnałowym stoi w `.dn-btn--sygnal`. */
  color: var(--dn-szary-0);
  font-weight: var(--dn-fw-polgruba);
}
.dn-zakladki--pigulki .dn-zakladka[aria-selected='true']:hover {
  background: var(--dn-sygnal-wypelnienie);
}
.dn-zakladki--pigulki .dn-zakladka:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: var(--dn-wym-fokus-odsuniecie);
}

/* Pigułki wyboru — wariant dla dwóch dróg RÓWNORZĘDNYCH. Stan wybrany niesie
   podświetlenie i obwódkę, nie pełne wypełnienie: pigułka w pełnym błękicie
   czyta się jak przycisk działania, a to kontrolka wskazująca, gdzie stoisz,
   nie co wykonasz. Wariant stał wcześniej w arkuszu okna wejścia i po cichu
   przemalowywał składnik biblioteki. */
.dn-zakladki--wybor {
  gap: var(--dn-od-1);
  border: 1px solid var(--dn-obrys);
}
.dn-zakladki--wybor .dn-zakladka {
  border: 0;
  min-height: calc(var(--dn-wym-kontrolka) - var(--dn-od-2));
  color: var(--dn-tekst-2);
}
.dn-zakladki--wybor .dn-zakladka[aria-selected='true'],
.dn-zakladki--wybor .dn-zakladka[aria-checked='true'] {
  background: var(--dn-sygnal-tlo);
  border: 1px solid var(--dn-sygnal-obrys);
  color: var(--dn-sygnal);
  font-weight: var(--dn-fw-polgruba);
}
.dn-zakladki--wybor .dn-zakladka[aria-selected='true']:hover,
.dn-zakladki--wybor .dn-zakladka[aria-checked='true']:hover {
  background: var(--dn-sygnal-wypelnienie);
  /* Biel, nie --dn-tekst-inv: w motywie ciemnym odwrotność tekstu jest niemal
     czarna i na wypełnieniu sygnałowym daje 4,14:1. Konwencja domu stoi
     przy .dn-btn--sygnal. */
  color: var(--dn-szary-0);
}
.dn-zakladki--wybor .dn-zakladka svg { width: var(--dn-wym-ikona-sm); height: var(--dn-wym-ikona-sm); flex: none; }

/* Pas kart sesji powłoki środowiska — mechanika zakładek + wskaźnik pracy w tle */
.dn-karty-sesji {
  display: flex;
  align-items: stretch;
  gap: var(--dn-od-1);
  height: var(--dn-wym-pas-kart);
  padding: 0 var(--dn-od-2);
  background: var(--dn-powierzchnia-2);
  border-bottom: 1px solid var(--dn-obrys);
  overflow-x: auto;
  scrollbar-width: none;
}

/* Same zakładki, bez czynności pasa. Roli `tablist` nie wolno nałożyć na cały pas:
   lista zakładek może zawierać wyłącznie zakładki, a w pasie stoi jeszcze przycisk
   nowej karty i pole przywracania. Czytnik ekranu dostawał wtedy widżet zakładek
   z dwoma elementami, które zakładkami nie są, i gubił liczbę kart. */
.dn-karty-sesji-tory {
  display: flex;
  align-items: stretch;
  gap: var(--dn-od-1);
  min-width: 0;
}
.dn-karta-sesji {
  position: relative;
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-2);
  margin-top: var(--dn-od-1);
  padding: 0 var(--dn-od-2) 0 var(--dn-od-3);
  border: 1px solid transparent;
  border-bottom: none;
  border-radius: var(--dn-r-sm) var(--dn-r-sm) 0 0;
  background: transparent;
  color: var(--dn-tekst-2);
  font-size: var(--dn-fs-sm);
  white-space: nowrap;
  cursor: pointer;
  transition: background-color var(--dn-czas-2) var(--dn-ease), color var(--dn-czas-2) var(--dn-ease);
}
.dn-karta-sesji:hover { background: var(--dn-hover); color: var(--dn-tekst); }
.dn-karta-sesji[aria-selected='true'] {
  background: var(--dn-powierzchnia);
  border-color: var(--dn-obrys);
  color: var(--dn-tekst);
}
/* wstęga aktywnej karty — sygnał */
.dn-karta-sesji[aria-selected='true']::before {
  content: '';
  position: absolute;
  inset: -1px -1px auto -1px;
  height: var(--dn-wym-wstega);
  border-radius: var(--dn-r-sm) var(--dn-r-sm) 0 0;
  background: var(--dn-kropka);
}

/* ==========================================================================
   RAMA KOKPITU — pasek górny (zawsze atramentowy) + listwa ustawień
   ========================================================================== */
.dn-pasek {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
  height: var(--dn-wym-pasek);
  padding: 0 var(--dn-od-3);
  background: var(--dn-rama);
  color: var(--dn-rama-tekst);
  border-bottom: 1px solid var(--dn-rama-obrys);
}
.dn-pasek-godlo {
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-2);
  color: var(--dn-rama-tekst);
  text-decoration: none;
}
.dn-pasek-godlo:hover { color: var(--dn-rama-tekst); text-decoration: none; }
.dn-pasek-logotyp {
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-md);
  font-weight: var(--dn-fw-gruba);
  letter-spacing: 0.02em;
}
.dn-pasek-logotyp small {
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  font-weight: var(--dn-fw-srednia);
  letter-spacing: var(--dn-ls-mono-wersaliki);
  color: var(--dn-rama-tekst-2);
  text-transform: uppercase;
  margin-left: var(--dn-od-1);
}
.dn-pasek-szukaj {
  flex: 1;
  max-width: 420px;
  min-height: 30px;
  padding: 0 var(--dn-od-3);
  border: 1px solid var(--dn-rama-obrys);
  border-radius: var(--dn-r-sm);
  background: var(--dn-rama-pole);
  color: var(--dn-rama-tekst);
  font-size: var(--dn-fs-sm);
}
.dn-pasek-szukaj::placeholder { color: var(--dn-rama-tekst-2); }
.dn-pasek-szukaj:focus {
  outline: none;
  border-color: var(--dn-fokus);
  box-shadow: var(--dn-cien-sygnal);
}
/* Wariant opakowany — <label class="dn-pasek-szukaj"> z ikoną i polem w środku.
   Ramka i tło należą do opakowania; pole wewnątrz jest przezroczyste. */
label.dn-pasek-szukaj {
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-2);
}
label.dn-pasek-szukaj > input {
  flex: 1;
  min-width: 0;
  padding: 0;
  border: 0;
  background: transparent;
  color: inherit;
  font: inherit;
  outline: none;
}
label.dn-pasek-szukaj:focus-within {
  border-color: var(--dn-fokus);
  box-shadow: var(--dn-cien-sygnal);
}

.dn-pasek-prawa { margin-left: auto; display: flex; align-items: center; gap: var(--dn-od-1); }

/* Listwa ustawień (Centrum dowodzenia, strefa 3) — najniższa masa */
.dn-listwa {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
  padding: var(--dn-od-2) var(--dn-od-3);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-lg);
  background: var(--dn-powierzchnia-2);
}
.dn-listwa-pozycja {
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-2);
  min-height: calc(var(--dn-wym-kontrolka) - var(--dn-od-1));
  padding: 0 var(--dn-od-3);
  border: none;
  border-radius: var(--dn-r-sm);
  background: transparent;
  color: var(--dn-tekst-2);
  font-size: var(--dn-fs-sm);
  cursor: pointer;
  transition: background-color var(--dn-czas-2) var(--dn-ease), color var(--dn-czas-2) var(--dn-ease);
}
.dn-listwa-pozycja:hover { background: var(--dn-hover); color: var(--dn-tekst); }

/* Wariant pulpitowy — listwa Centrum dowodzenia. Pozycja nie jest tu drobnym
   ustawieniem w pasku, tylko wejściem w tryb pracy, więc odpowiada na wskazanie
   mocniej: podnosi się, dostaje obrys i powiększa znak. Stan wciśnięty niesie
   `aria-pressed`, bo to przełącznik widoku, nie czynność jednorazowa.
   Wariant stał wcześniej w arkuszu okna jako osobny składnik `.cd-listwa-poz`
   i powielał całą listwę, żeby dodać jej podniesienie. */
.dn-listwa-pozycja--pulpit {
  /* Większa kontrolka: pozycja stoi samotnie na płótnie, bez tacy pod sobą,
     więc musi mieć własną masę. Wyściółka o stopień wyżej w obu osiach. */
  padding: var(--dn-od-3) var(--dn-od-4);
  font-size: var(--dn-fs-md);
  /* Ramka widoczna w SPOCZYNKU. Obrys mocny dawał na powierzchni panelu
     tylko 7,4 stopnia L* i kreska ginęła; kreska wyrazna daje 14,4 w ciemnym
     i 37 w jasnym. */
  border: 1px solid var(--dn-obrys-wyrazny);
  border-radius: var(--dn-r-md);
  color: var(--dn-tekst);
  transition:
    background-color var(--dn-czas-1) var(--dn-ease),
    border-color var(--dn-czas-1) var(--dn-ease),
    color var(--dn-czas-1) var(--dn-ease),
    transform var(--dn-czas-1) var(--dn-ease);
}
.dn-listwa-pozycja--pulpit:hover {
  background: var(--dn-panel);
  border-color: var(--dn-sygnal-obrys);
  transform: translateY(var(--dn-podniesienie-sm));
}
.dn-listwa-pozycja--pulpit:active { transform: translateY(0) scale(var(--dn-skala-nacisk)); }
.dn-listwa-pozycja--pulpit:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: calc(-1 * var(--dn-wym-fokus));
}
.dn-listwa-pozycja--pulpit[aria-pressed='true'] {
  border-color: var(--dn-obrys-mocny);
  background: var(--dn-panel);
}
.dn-listwa-pozycja--pulpit > svg {
  transition: transform var(--dn-czas-uwyd) var(--dn-ease), color var(--dn-czas-2) var(--dn-ease);
}
.dn-listwa-pozycja--pulpit:hover > svg {
  transform: scale(var(--dn-skala-ikony));
  color: var(--dn-sygnal);
}

/* ==========================================================================
   BOCZNA NAWIGACJA MODUŁÓW
   ========================================================================== */
.dn-boczna {
  width: var(--dn-wym-boczna);
  flex: none;
  display: flex;
  flex-direction: column;
  gap: var(--dn-od-1);
  padding: var(--dn-od-3) var(--dn-od-2);
  background: var(--dn-panel);
  border-right: 1px solid var(--dn-obrys);
  overflow-y: auto;
}
.dn-boczna-naglowek {
  padding: var(--dn-od-2) var(--dn-od-3);
}
.dn-boczna-pozycja {
  position: relative;
  display: flex;
  align-items: center;
  gap: var(--dn-od-3);
  min-height: var(--dn-wym-kontrolka);
  padding: 0 var(--dn-od-3);
  border: none;
  border-radius: var(--dn-r-sm);
  background: transparent;
  color: var(--dn-tekst-2);
  font-size: var(--dn-fs-base);
  font-weight: var(--dn-fw-srednia);
  text-align: left;
  cursor: pointer;
  transition: background-color var(--dn-czas-2) var(--dn-ease), color var(--dn-czas-2) var(--dn-ease);
}
.dn-boczna-pozycja:hover { background: var(--dn-hover); color: var(--dn-tekst); }
.dn-boczna-pozycja[aria-current='page'] {
  background: var(--dn-sygnal-tlo);
  color: var(--dn-tekst);
}
/* znacznik aktywności — krótka kreska sygnału zamiast pełnej wstęgi */
.dn-boczna-pozycja[aria-current='page']::before {
  content: '';
  position: absolute;
  left: 0;
  top: 50%;
  translate: 0 -50%;
  width: var(--dn-wym-wstega);
  height: 16px;
  border-radius: var(--dn-r-pill);
  background: var(--dn-kropka);
}
.dn-boczna-pozycja > svg { width: var(--dn-wym-ikona); height: var(--dn-wym-ikona); flex: none; }
/* Zwarta — ta sama pozycja w stopce panelu, gdzie wiersz nie jest nawigacją
   główną: niższa, o stopień mniejsze pismo, bez znacznika bieżącości. */
.dn-boczna-pozycja--zwarta {
  min-height: 0;
  padding: var(--dn-od-2) var(--dn-od-3);
  font-size: var(--dn-fs-sm);
  font-weight: var(--dn-fw-normalna);
  text-decoration: none;
}
.dn-boczna-pozycja--zwarta::before { content: none; }
.dn-boczna-pozycja--zwarta:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: calc(var(--dn-wym-fokus-odsuniecie) * -1);
}

/* ==========================================================================
   WPIS OKNA KOMUNIKACJI — dziewięciu nadawców (rozstrzygnięcie projektowe)
   --------------------------------------------------------------------------
   Zasada: wspólne tło powierzchni; rozróżnienie niesie ZAWSZE komplet:
   ikona w medalionie + etykieta nadawcy + klasa semantyczna krawędzi.
   Trzy klasy semantyczne (nie dziewięć barw):
     --czlowiek      atrament   (użytkownik)
     --inteligencja  sygnał     (model · agent · Coordinator · Executor · Validator)
     --system        neutralna  (Automation · Always On Display · wynik narzędzia)
   Rola w obrębie klasy różnicuje się ikoną i plakietką roli, nie kolorem.
   ========================================================================== */
.dn-wpis {
  position: relative;
  display: grid;
  grid-template-columns: var(--dn-wym-awatar-sm) 1fr;
  gap: var(--dn-od-2) var(--dn-od-3);
  max-width: 860px;
  padding: var(--dn-od-3) var(--dn-od-4);
  border: 1px solid var(--dn-obrys-subtelny);
  border-left: 2px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia);
}
.dn-wpis-medalion {
  display: grid;
  place-content: center;
  width: var(--dn-wym-awatar-sm);
  height: var(--dn-wym-awatar-sm);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-sm);
  background: var(--dn-powierzchnia-2);
  color: var(--dn-tekst-2);
}
.dn-wpis-medalion > svg { width: var(--dn-wym-ikona-sm); height: var(--dn-wym-ikona-sm); }
.dn-wpis-tozsamosc {
  display: flex;
  align-items: baseline;
  flex-wrap: wrap;
  gap: var(--dn-od-2);
}
.dn-wpis-nadawca {
  font-size: var(--dn-fs-xs);
  font-weight: var(--dn-fw-polgruba);
  letter-spacing: var(--dn-ls-wersaliki);
  text-transform: uppercase;
  color: var(--dn-tekst-2);
}
.dn-wpis-godzina {
  margin-left: auto;
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  color: var(--dn-tekst-3);
}
.dn-wpis-tresc {
  grid-column: 2;
  font-size: var(--dn-fs-md);
  line-height: var(--dn-lh-luzny);
  white-space: pre-wrap;
  word-break: break-word;
}

/* klasa: człowiek — atrament */
.dn-wpis--czlowiek { border-left-color: var(--dn-atrament); }
.dn-wpis--czlowiek .dn-wpis-medalion {
  background: var(--dn-atrament);
  border-color: var(--dn-atrament);
  color: var(--dn-atrament-tekst);
}
/* klasa: inteligencja — sygnał */
.dn-wpis--inteligencja { border-left-color: var(--dn-sygnal-wypelnienie); }
.dn-wpis--inteligencja .dn-wpis-medalion {
  background: var(--dn-sygnal-tlo);
  border-color: var(--dn-sygnal-obrys);
  color: var(--dn-sygnal);
}
/* klasa: system — neutralna, tło wycofane */
.dn-wpis--system { background: transparent; border-left-color: var(--dn-obrys-mocny); }

/* wpis pracujący — kropka tętna przy nadawcy */
.dn-wpis--pracuje .dn-wpis-nadawca::after {
  content: '';
  display: inline-block;
  width: var(--dn-wym-kropka);
  height: var(--dn-wym-kropka);
  margin-left: var(--dn-od-1);
  border-radius: var(--dn-r-pill);
  background: var(--dn-kropka);
  animation: dn-tetno var(--dn-czas-tetno) var(--dn-ease) infinite;
  vertical-align: 1px;
}

/* ==========================================================================
   MONITOR WYKONANIA · KOLEJKA KROKÓW
   ========================================================================== */
.dn-postep {
  display: flex;
  align-items: center;
  gap: var(--dn-od-3);
}
.dn-postep-tor {
  flex: 1;
  height: 4px;
  border-radius: var(--dn-r-pill);
  background: var(--dn-powierzchnia-2);
  overflow: hidden;
}
/* Zakładki bez kreski pod spodem — gdy pasek zakładek stoi w oprawie, która
   sama niesie granicę, druga kreska daje podwójną linię. Zawijanie na wypadek
   paska szerszego niż kolumna. */
.dn-zakladki--bez-kreski { border-bottom: 0; }
.dn-zakladki--zawijane { flex-wrap: wrap; }

/* Miara postępu bierze się z danej na znaczniku, nie z wyglądu wpisanego
   w atrybut `style` — wartość ustawia mechanika okna. */
.dn-postep-wartosc { width: 0; }

.dn-postep-wartosc {
  height: 100%;
  border-radius: var(--dn-r-pill);
  background: var(--dn-sygnal-wypelnienie);
  transition: width var(--dn-czas-3) var(--dn-ease);
}
.dn-postep-etykieta {
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  color: var(--dn-tekst-2);
  white-space: nowrap;
}

/* ==========================================================================
   BRYŁA WARSTW PLATFORMY
   --------------------------------------------------------------------------
   Cztery powłoki produktu — rdzeń, środowiska, moduły, stanowisko — osadzane
   jedna na drugiej wraz z postępem. Bryła nie jest ozdobą: pokazuje, ile
   z programu już stoi.

   Scenę rysuje `zasoby/bryla.js` w płótnie, biorąc barwy wyłącznie z żetonów
   `--dn-*`; okno wstawia puste pole i nadaje mu miejsce w układzie. Płótno jest
   powtórzeniem tego, co niesie `aria-label` pola, więc nie wchodzi w drzewo
   dostępności. Ruch gaśnie przy `prefers-reduced-motion` po stronie skryptu —
   stan bryły czyta się z osadzonych powłok, nie z ruchu.
   ========================================================================== */
/* Bryła nie ma własnego tła. Stoi wprost na powierzchni, na której leży okno —
   scena z własnym podłożem czyta się jako okno w oknie, niezależnie od tego,
   jak starannie wygaszy się jej krawędzie. Brzegi rysunku rozpuszcza samo
   płótno, więc pole nie potrzebuje ani ramki, ani przycięcia. */
.dn-bryla { position: relative; display: block; min-width: 0; min-height: 0; }
.dn-bryla > canvas { display: block; width: 100%; height: 100%; }

/* Ekran startowy — pole dla znaku kreślonego światłem. Bez własnego tła:
   kładzie się na tym, co pod spodem. Płótno zakłada składnik. */
.dn-ekran-startowy { position: relative; display: block; width: 100%; height: 100%; }
.dn-ekran-startowy > canvas { display: block; width: 100%; height: 100%; }

/* Powłoki platformy — pole dla animacji składania. Bez własnego tła, jak bryła
   i ekran startowy: rysunek kładzie się na powierzchni okna. */
.dn-powloki { position: relative; display: block; width: 100%; height: 100%; }
.dn-powloki > canvas { display: block; width: 100%; height: 100%; }

/* Kolejka kroków — trzy wyjścia weryfikacji (rozstrzygnięcie projektowe):
   poprawny → zieleń · błędy + licznik obiegów → bursztyn · zdarzenie
   nieoczekiwane → czerwień + wstrzymanie kolejki. Zawsze ikona + etykieta. */
.dn-kolejka {
  display: flex;
  flex-direction: column;
  /* Kolejka bywa listą porządkową — wcięcie i znaczniki listy należą do niej,
     nie do okna, które ją wstawia. */
  list-style: none;
  margin: 0;
  padding: 0;
}
.dn-krok {
  display: grid;
  grid-template-columns: 20px 1fr auto;
  align-items: center;
  gap: var(--dn-od-3);
  min-height: var(--dn-wym-wiersz);
  padding: 0 var(--dn-od-3);
  border-left: 2px solid var(--dn-obrys);
  font-size: var(--dn-fs-base);
}
.dn-krok-znak {
  display: grid;
  place-content: center;
  width: 20px; height: 20px;
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-pill);
  background: var(--dn-powierzchnia);
  color: var(--dn-tekst-3);
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
}
.dn-krok-znak > svg { width: 12px; height: 12px; }

/* ==========================================================================
   SAMOUCZEK — numerowany wykaz kroków w panelu
   --------------------------------------------------------------------------
   Różny od `.dn-kolejka` z `.dn-krok`: kolejka pokazuje, co maszyna ROBI teraz,
   samouczek mówi, co ma zrobić człowiek. Stąd numer w medalionie sygnału
   zamiast znaku stanu i dwa wiersze treści zamiast jednego z miarą.
   Rodzina stała w arkuszu Centrum dowodzenia jako `.cd-nauka-*`.
   ========================================================================== */

.dn-nauka {
  display: flex;
  flex-direction: column;
  gap: var(--dn-od-4);
  padding: var(--dn-od-4);
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-luzny);
}
.dn-nauka-wstep { margin: 0; color: var(--dn-tekst-2); }
.dn-nauka-kroki {
  display: flex;
  flex-direction: column;
  gap: var(--dn-od-3);
  margin: 0;
  padding: 0;
  list-style: none;
}
.dn-nauka-kroki > li {
  display: grid;
  grid-template-columns: var(--dn-wym-awatar-sm) minmax(0, 1fr);
  gap: var(--dn-od-1) var(--dn-od-3);
  align-items: start;
}
.dn-nauka-kroki > li > b { color: var(--dn-tekst); }
.dn-nauka-kroki > li > span:last-child { grid-column: 2; color: var(--dn-tekst-2); }
.dn-nauka-numer {
  grid-row: 1 / span 2;
  display: grid;
  place-content: center;
  width: var(--dn-wym-awatar-sm);
  height: var(--dn-wym-awatar-sm);
  border: 1px solid var(--dn-sygnal-obrys);
  border-radius: var(--dn-r-pill);
  background: var(--dn-sygnal-tlo);
  color: var(--dn-sygnal);
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
}
.dn-nauka-nota {
  display: flex;
  align-items: flex-start;
  gap: var(--dn-od-2);
  margin: 0;
  padding-top: var(--dn-od-3);
  border-top: 1px solid var(--dn-obrys-subtelny);
  /* Stopień 12 px nie przechodzi progu na `--dn-tekst-3`. */
  color: var(--dn-tekst-2);
  font-size: var(--dn-fs-xs);
}
.dn-nauka-nota > svg { flex: none; }

/* Uchwyt zmiany szerokości panelu — pasek chwytu między panelami. Barwę
   przyjmuje dopiero pod wskaźnikiem i w trakcie ciągnięcia; w spoczynku jest
   niewidoczny, bo obszar chwytu ma być większy od tego, co widać. */
.dn-uchwyt {
  flex: none;
  position: relative;
  z-index: 3;
  width: 6px;
  margin: 0 calc(var(--dn-od-1) * -1);
  border-radius: var(--dn-r-pill);
  background: transparent;
  cursor: col-resize;
  transition: background-color var(--dn-czas-1) var(--dn-ease);
}
.dn-uchwyt:hover,
.dn-uchwyt[data-ciagniety='tak'] { background: var(--dn-sygnal-500); }
.dn-uchwyt:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: 1px;
}
/* Opis pod pozycją kolejki — mówi, co dzieje się z komputerem na tym etapie.
   Wchodzi w drugi wiersz pozycji, pod nazwą; znak i stan zostają w pierwszym,
   więc kolumna znaków i kolumna stanów biegną nieprzerwanie przez cały wykaz. */
.dn-krok:has(> .dn-krok-opis) {
  align-items: start;
  padding-block: var(--dn-od-2);
}
.dn-krok-opis {
  grid-column: 2 / -1;
  margin-top: var(--dn-od-1);
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-bazowy);
  color: var(--dn-tekst-2);
}
/* Nota maszynowa — metryka pod tytułem, miara przy pozycji, nota na dnie kolumny.
   Rola ogólna: jeden przepis pisma dla całej aplikacji.
   Barwa to DRUGI stopień, nie trzeci: `--dn-tekst-3` (#7C7C7C) wolno stosować
   wyłącznie do tekstu ≥ 18,66 px półgrubego — przy 12 px daje 3,85:1 wobec panelu
   i nie przechodzi WCAG 1.4.3. Nota jest drobna z definicji, więc bierze drugi. */
.dn-meta,
.dn-krok-meta {
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  color: var(--dn-tekst-2);
}
.dn-meta { font-variant-numeric: tabular-nums; }
.dn-meta b,
.dn-meta strong { color: var(--dn-tekst); font-weight: var(--dn-fw-srednia); }
.dn-meta--mocna { color: var(--dn-tekst); }
.dn-meta--na-ramie { color: var(--dn-rama-tekst-2); }
.dn-meta--przygaszona { color: var(--dn-tekst-3); font-size: var(--dn-fs-base); }
.dn-meta--w-wierszu,
.dn-krok-meta {
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-2);
}

/* Etykieta w mono-wersalikach — nadtytuł, nazwa modułu, głowa kolumny, zapowiedź
   grupy kontrolek. Rola ogólna; dotąd istniała wyłącznie wewnątrz rodziny AOD. */
.dn-etyk-mono {
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  letter-spacing: var(--dn-ls-mono-wersaliki);
  text-transform: uppercase;
  /* Drugi stopień z tego samego powodu co przy `.dn-meta`. */
  color: var(--dn-tekst-2);
}
.dn-etyk-mono--mocna { color: var(--dn-tekst); }
.dn-etyk-mono--na-ramie { color: var(--dn-rama-tekst-2); }
/* Wiodąca — etykieta, która nazywa to, na co się patrzy, nie opisuje pod
   spodem: stopień wyżej i pełna barwa pisma. Stąd nazwa modułu w głowie karty. */
.dn-etyk-mono--wiodaca { font-size: var(--dn-fs-sm); color: var(--dn-tekst); }
/* Etykieta w rzędzie z czynnością po prawej stronie. */
.dn-etyk-mono--z-czynnoscia {
  display: flex;
  align-items: center;
  justify-content: space-between;
}
/* Słowo stanu w kolejce kroków. Osobne od `.dn-krok-meta`, bo stan nie jest
   miarą: „Gotowe" to tekst interfejsu i idzie pismem bezszeryfowym, podczas gdy
   nota maszynowa niesie liczbę. Barwy nie bierze — stan rozróżnia znak kroku,
   więc słowo nie musi go powtarzać kolorem. */
.dn-krok-stan {
  font-size: var(--dn-fs-sm);
  color: var(--dn-tekst-2);
  white-space: nowrap;
}
.dn-krok--pracuje { border-left-color: var(--dn-sygnal-wypelnienie); }
/* Wypełnienie znaku: stan pracujący był jedynym z czterech bez tła, przez co
   w kolejce czterech kroków rzucał się w oczy słabiej niż zakończone. */
.dn-krok--pracuje .dn-krok-znak {
  border-color: var(--dn-sygnal-obrys);
  background: var(--dn-sygnal-tlo);
  color: var(--dn-sygnal);
}
.dn-krok--poprawny { border-left-color: var(--dn-sukces-obrys); }
.dn-krok--poprawny .dn-krok-znak {
  background: var(--dn-sukces-tlo);
  border-color: var(--dn-sukces-obrys);
  color: var(--dn-sukces-tekst);
}
.dn-krok--bledy { border-left-color: var(--dn-ostrzezenie-obrys); }
.dn-krok--bledy .dn-krok-znak {
  background: var(--dn-ostrzezenie-tlo);
  border-color: var(--dn-ostrzezenie-obrys);
  color: var(--dn-ostrzezenie-tekst);
}
.dn-krok--wstrzymany { border-left-color: var(--dn-blad-obrys); }
.dn-krok--wstrzymany .dn-krok-znak {
  background: var(--dn-blad-tlo);
  border-color: var(--dn-blad-obrys);
  color: var(--dn-blad-tekst);
}

/* Pole — krok rysowany bryłą zamiast szyną. Szyna prowadzi wzrok w dół listy
   i nadaje się tam, gdzie kroki czyta się po kolei; bryła zamyka krok w polu
   i nadaje się tam, gdzie ważny jest ten JEDEN, który trwa teraz — bo tylko
   on dostaje wypełnienie, a pozostałe stoją na przezroczystym tle.

   Rodzina stała w arkuszu okna wejściowego jako `.we-krok` i różniła się od
   kroku wyłącznie tym rysunkiem; stany brała te same, tyle że przez
   `data-stan` zamiast przez odmiany. */
.dn-kolejka--pola { gap: var(--dn-od-1); }
.dn-krok--pole {
  padding: var(--dn-od-2) var(--dn-od-3);
  border: 1px solid transparent;
  border-radius: var(--dn-r-md);
  font-size: var(--dn-fs-sm);
  color: var(--dn-tekst-2);
}
/* Bryła nie ma szyny, więc stany malują pole, a nie jego krawędź lewą. */
.dn-krok--pole.dn-krok--pracuje {
  border-color: var(--dn-obrys-subtelny);
  background: var(--dn-powierzchnia-2);
  color: var(--dn-tekst);
}

/* ==========================================================================
   MODAL (dialog) · NAKŁADKA
   ========================================================================== */
.dn-modal {
  /* Reset zeruje marginesy wszystkim elementom — dialog modalny musi odzyskać
     margin:auto, inaczej okno staje przy lewej górnej krawędzi ekranu. */
  margin: auto;
  width: min(var(--dn-wym-modal), calc(100vw - var(--dn-od-8)));
  max-height: min(80dvh, 720px);
  padding: 0;
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-lg);
  background: var(--dn-panel);
  color: var(--dn-tekst);
  box-shadow: var(--dn-cien-lg);
}
.dn-modal--szeroki { width: min(1080px, calc(100vw - var(--dn-od-8))); max-height: min(86dvh, 780px); }
.dn-modal-zamknij { margin-left: auto; }
.dn-modal::backdrop { background: var(--dn-nakladka); backdrop-filter: blur(2px); }
.dn-modal[open] { animation: dn-wejscie var(--dn-czas-3) var(--dn-ease); }
.dn-modal-naglowek {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
  padding: var(--dn-od-4) var(--dn-od-5);
  border-bottom: 1px solid var(--dn-obrys-subtelny);
}
.dn-modal-tytul {
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-xl);
  font-weight: var(--dn-fw-polgruba);
  letter-spacing: var(--dn-ls-naglowek);
}
.dn-modal-cialo { padding: var(--dn-od-5); overflow-y: auto; }
/* Akapit wprowadzający w oknie nakładkowym — jedno zdanie o tym, co okno robi. */
/* Zdanie wprowadzające — stoi pod tytułem i tłumaczy, czego dotyczy widok.
   Rola ogólna; dotąd istniała wyłącznie wewnątrz rodziny modalu. */
.dn-lid,
.dn-modal-lid {
  margin: 0 0 var(--dn-od-4);
  max-width: 72ch;
  color: var(--dn-tekst-2);
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-luzny);
}
.dn-lid b,
.dn-lid strong { color: var(--dn-tekst); font-weight: var(--dn-fw-srednia); }
/* Zdanie wprowadzające pod tytułem okna: odsuwa się od niego, bo tytuł ma
   `margin: 0`, i stoi o dwa stopnie wyżej niż zdanie w panelu — to pierwszy
   tekst okna, czytany przed wszystkim innym. Stopień 15 px poszerza pole
   do 665 px przy tej samej mierze 72 znaków, bo `ch` rośnie z krojem. */
.dn-tytul-okna + .dn-lid {
  margin-top: var(--dn-od-4);
  /* Bez zera dolny margines zdania dokładał się do luki płótna i odstęp pod
     opisem wynosił 40 px, przy 24 px w pozostałych przejściach sekcji. */
  margin-bottom: 0;
  font-size: var(--dn-fs-md);
  /* Miara wiersza o trzy znaki dłuższa od zdania w panelu — pole sięga wtedy
     675 px, czyli linii wskazanej przez Właściciela. */
  max-width: 75ch;
}
.dn-lid--bez-odstepu { margin-bottom: 0; }
.dn-lid--na-ramie { color: var(--dn-rama-tekst-2); }

/* ==========================================================================
   TYTUŁ SEKCJI — nagłówek strefy w płótnie, ze znacznikiem wagi
   --------------------------------------------------------------------------
   Rola stała dotąd w arkuszu Centrum dowodzenia jako `.cd-sekcja-tytul`.
   Waga strefy nie jest osobnym składnikiem — idzie atrybutem `data-waga`
   na przodku, więc jedna sekcja może zmienić rangę bez zmiany klas.
   Znacznik jest powtórzeniem kolejności, którą niesie układ, dlatego gaśnie
   krycie, a nie barwę: przy pierwszym stopniu pozostaje pełny sygnał.
   ========================================================================== */
.dn-sekcja-tytul {
  font-size: var(--dn-fs-lg);
  font-weight: var(--dn-fw-polgruba);
  color: var(--dn-tekst);
}
.dn-sekcja-tytul::before {
  content: '';
  display: inline-block;
  width: var(--dn-wym-sila);
  height: 0.9em;
  margin-right: var(--dn-od-2);
  border-radius: var(--dn-r-pill);
  background: var(--dn-sygnal-500);
  vertical-align: -1px;
}
[data-waga='2'] .dn-sekcja-tytul::before { opacity: 0.62; }
[data-waga='3'] .dn-sekcja-tytul::before { opacity: 0.38; }

.dn-modal-stopka {
  display: flex;
  justify-content: flex-end;
  gap: var(--dn-od-2);
  padding: var(--dn-od-4) var(--dn-od-5);
  border-top: 1px solid var(--dn-obrys-subtelny);
  background: var(--dn-powierzchnia-2);
  border-radius: 0 0 var(--dn-r-lg) var(--dn-r-lg);
}

/* ==========================================================================
   POWIADOMIENIE (toast)
   ========================================================================== */
.dn-toasty {
  position: fixed;
  inset: auto var(--dn-od-4) var(--dn-od-4) auto;
  z-index: var(--dn-z-powiadomienie);
  display: flex;
  flex-direction: column;
  gap: var(--dn-od-2);
}
.dn-toast {
  display: grid;
  grid-template-columns: auto 1fr auto;
  align-items: start;
  gap: var(--dn-od-3);
  min-width: var(--dn-wym-toast-min);
  max-width: var(--dn-wym-toast-max);
  padding: var(--dn-od-3) var(--dn-od-4);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-md);
  background: var(--dn-panel);
  box-shadow: var(--dn-cien-3);
  animation: dn-wejscie var(--dn-czas-3) var(--dn-ease);
}
.dn-toast > svg { width: var(--dn-wym-ikona); height: var(--dn-wym-ikona); margin-top: 1px; }
.dn-toast-tytul { font-weight: var(--dn-fw-polgruba); font-size: var(--dn-fs-base); }
.dn-toast-tresc { font-size: var(--dn-fs-sm); color: var(--dn-tekst-2); }
.dn-toast--sukces { border-left: 2px solid var(--dn-sukces-tekst); }
.dn-toast--sukces > svg { color: var(--dn-sukces-tekst); }
.dn-toast--ostrzezenie { border-left: 2px solid var(--dn-ostrzezenie-tekst); }
.dn-toast--ostrzezenie > svg { color: var(--dn-ostrzezenie-tekst); }
.dn-toast--blad { border-left: 2px solid var(--dn-blad-tekst); }
.dn-toast--blad > svg { color: var(--dn-blad-tekst); }
.dn-toast--informacja { border-left: 2px solid var(--dn-informacja-tekst); }
.dn-toast--informacja > svg { color: var(--dn-informacja-tekst); }

/* ==========================================================================
   DYMEK OBJAŚNIENIA (tooltip)
   ========================================================================== */
.dn-tooltip { position: relative; display: inline-flex; }
.dn-tooltip-tresc {
  position: absolute;
  bottom: calc(100% + var(--dn-od-2));
  left: 50%;
  z-index: var(--dn-z-tooltip);
  max-width: 260px;
  padding: var(--dn-od-2) var(--dn-od-3);
  border-radius: var(--dn-r-sm);
  background: var(--dn-rama);
  color: var(--dn-rama-tekst);
  box-shadow: var(--dn-cien-3);
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-bazowy);
  white-space: normal;
  opacity: 0;
  visibility: hidden;
  transform: translate(-50%, var(--dn-od-1));
  transition:
    opacity var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-2) var(--dn-ease),
    visibility var(--dn-czas-2) var(--dn-ease);
  pointer-events: none;
}
.dn-tooltip:hover .dn-tooltip-tresc,
.dn-tooltip:focus-within .dn-tooltip-tresc {
  opacity: 1;
  visibility: visible;
  transform: translate(-50%, 0);
}

/* ==========================================================================
   AWATAR · SPINNER · PUSTY STAN
   ========================================================================== */
.dn-awatar {
  position: relative;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: var(--dn-wym-awatar);
  height: var(--dn-wym-awatar);
  flex: none;
  border-radius: var(--dn-r-pill);
  background: var(--dn-grad-atrament);
  color: var(--dn-szary-100);
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-sm);
  font-weight: var(--dn-fw-polgruba);
  overflow: hidden;
}
.dn-awatar--sm { width: var(--dn-wym-awatar-sm); height: var(--dn-wym-awatar-sm); font-size: var(--dn-fs-xs); }
.dn-awatar--lg { width: var(--dn-wym-awatar-lg); height: var(--dn-wym-awatar-lg); font-size: var(--dn-fs-md); }
.dn-awatar--kwadrat { border-radius: var(--dn-r-sm); }
/* jednostka inteligencji (agent/model) — rdzeń sygnałowy */
.dn-awatar--inteligencja { background: var(--dn-grad-sygnal); color: var(--dn-szary-0); }
.dn-awatar-stan {
  position: absolute;
  right: -1px; bottom: -1px;
  width: 8px; height: 8px;
  border-radius: var(--dn-r-pill);
  background: var(--dn-sukces-tekst);
  box-shadow: 0 0 0 2px var(--dn-powierzchnia);
}

.dn-spinner {
  display: inline-block;
  width: var(--dn-wym-spinner);
  height: var(--dn-wym-spinner);
  flex: none;
  border: 2px solid var(--dn-obrys-mocny);
  border-top-color: var(--dn-sygnal-wypelnienie);
  border-radius: var(--dn-r-pill);
  animation: dn-obrot 0.8s linear infinite;
}
.dn-pusty-stan {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: var(--dn-od-2);
  padding: var(--dn-od-10) var(--dn-od-5);
  text-align: center;
  color: var(--dn-tekst-3);
}
.dn-pusty-stan > svg { width: 28px; height: 28px; }
/* Zwarty — stan pusty wewnątrz siatki, nie na całym płótnie: znak mniejszy,
   opis o stopień mocniejszy, bo stoi bliżej treści. */
.dn-pusty-stan--zwarty > svg {
  width: var(--dn-wym-ikona-xl);
  height: var(--dn-wym-ikona-xl);
  color: var(--dn-tekst-2);
}
.dn-pusty-stan--zwarty .dn-pusty-stan-opis { color: var(--dn-tekst-2); }
.dn-pusty-stan-tytul {
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-lg);
  font-weight: var(--dn-fw-polgruba);
  color: var(--dn-tekst-2);
}
.dn-pusty-stan-opis { max-width: 40ch; font-size: var(--dn-fs-sm); }

/* ==========================================================================
   POLE WPISYWANIA PROMPTU — grot ❯ jako sygnatura wejścia
   ========================================================================== */
.dn-prompt {
  display: grid;
  grid-template-columns: auto 1fr auto;
  align-items: end;
  gap: var(--dn-od-2);
  padding: var(--dn-od-2);
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia);
  transition: border-color var(--dn-czas-2) var(--dn-ease), box-shadow var(--dn-czas-2) var(--dn-ease);
}
.dn-prompt:focus-within {
  border-color: var(--dn-fokus);
  box-shadow: var(--dn-cien-sygnal);
}
.dn-prompt-grot {
  align-self: start;
  padding: var(--dn-od-2) 0 0 var(--dn-od-2);
  font-family: var(--dn-ff-mono);
  font-weight: var(--dn-fw-polgruba);
  /* Pismo, nie kropka — próg kontrastu 4,5:1, nie 3:1. */
  color: var(--dn-sygnal);
  user-select: none;
}
.dn-prompt-obszar {
  min-height: 40px;
  max-height: 160px;
  padding: var(--dn-od-2) 0;
  border: none;
  background: transparent;
  color: var(--dn-tekst);
  font-size: var(--dn-fs-md);
  line-height: var(--dn-lh-bazowy);
  resize: none;
}
.dn-prompt-obszar:focus { outline: none; }
.dn-prompt-obszar::placeholder { color: var(--dn-tekst-3); }

/* Przybornik promptu — załączniki, biblioteka, agent, model… */
.dn-przybornik {
  display: flex;
  align-items: center;
  gap: var(--dn-od-1);
  flex-wrap: wrap;
}

/* ==========================================================================
   ALWAYS ON DISPLAY — pływający awatar
   ========================================================================== */
.dn-aod {
  /* Awatar unosi się nad paskiem stanu i nad uchwytem prototypu — żaden pas
     ramy nie może zniknąć pod warstwą pływającą. */
  position: fixed;
  right: var(--dn-od-5);
  bottom: calc(var(--dn-wym-stan) + var(--dn-wym-kontrolka) + var(--dn-od-4));
  z-index: var(--dn-z-aod);
  display: flex;
  align-items: center;
  gap: var(--dn-od-3);
  padding: var(--dn-od-2) var(--dn-od-4) var(--dn-od-2) var(--dn-od-2);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-pill);
  background: var(--dn-panel);
  box-shadow: var(--dn-cien-3);
}
.dn-aod-rdzen {
  position: relative;
  display: grid;
  place-content: center;
  width: var(--dn-wym-awatar-lg);
  height: var(--dn-wym-awatar-lg);
  border-radius: var(--dn-r-pill);
  background: var(--dn-grad-sygnal);
  color: var(--dn-szary-0);
}
.dn-aod-rdzen::after {
  content: '';
  position: absolute;
  inset: -3px;
  border-radius: inherit;
  border: 1px solid var(--dn-sygnal-obrys);
  animation: dn-tetno var(--dn-czas-tetno) var(--dn-ease) infinite;
}
.dn-aod-tresc { font-size: var(--dn-fs-sm); color: var(--dn-tekst-2); max-width: 36ch; }
.dn-aod-tresc strong { color: var(--dn-tekst); font-weight: var(--dn-fw-polgruba); }

/* ==========================================================================
   MENU ROZWIJANE — pasek narzędzi, belki okien, kontrolki kontekstowe
   ========================================================================== */
/* Bryła i położenie panelu menu: `menu.css` + `menu.js`. Tutaj zostaje
   anatomia wnętrza: wiersz, nagłówek, separator, skrót, znacznik. */
.sta-menu-poz { display:flex; align-items:center; gap:var(--dn-od-2); width:100%; padding:var(--dn-od-1) var(--dn-od-2);
  border:none; background:none; border-radius:var(--dn-r-sm); color:var(--dn-tekst); font-size:var(--dn-fs-sm);
  text-align:left; cursor:pointer;
  /* Wiersz menu jest nazwą, więc nie łamie się nigdy: przy ciasnym panelu
     skraca się wartość obok, nie etykieta. */
  white-space:nowrap; }
.sta-menu-poz:hover { background:var(--dn-hover); }
.sta-menu-poz .skrot { order:2; margin-left:auto; min-width:0; overflow:hidden; text-overflow:ellipsis;
  white-space:nowrap; font-family:var(--dn-ff-mono); font-size:var(--dn-fs-xs); color:var(--dn-tekst-3); }
/* Znacznik włączonej opcji stoi po PRAWEJ — tam, gdzie w menu systemowych
   oznacza się stan włączony. Ikony wszystkich wierszy zaczynają się od lewej,
   bez rezerwowanej kolumny z przodu (rozstrzygnięcie Właściciela 2026-08-20).
   Kolejność w wierszu: ikona · etykieta · skrót · znacznik. */
/* Znacznik wyboru niesie barwę sygnału niezależnie od pojemnika: ta sama rola
   w menu, w popoverze i w wykazie. Reguły niżej dokładają wyłącznie rozmieszczenie
   właściwe dla menu. */
.ptaszek { color: var(--dn-sygnal); }
.sta-menu-poz .ptaszek {
  order: 3;
  flex: none;
  width: var(--dn-wym-ikona-sm);
  text-align: right;
}
/* Wiersz bez skrótu: znacznik sam dosuwa się do prawej krawędzi. */
.sta-menu-poz:not(:has(.skrot)) .ptaszek { margin-left: auto; }
/* Wyłączona opcja zachowuje miejsce znacznika, żeby prawa kolumna nie drgała. */
.sta-menu-poz[aria-checked="false"] .ptaszek { visibility:hidden; }
/* Rozmiar ikony wstawianej poza komponentem, który sam ją wymiaruje. Trzy
   stopnie skali ikon systemu; poza tymi klasami ikona bierze rozmiar z reguły
   swojego komponentu. */
.dn-ik { width: var(--dn-wym-ikona); height: var(--dn-wym-ikona); flex: none; }
.dn-ik--sm { width: var(--dn-wym-ikona-sm); height: var(--dn-wym-ikona-sm); flex: none; }
.dn-ik--lg { width: var(--dn-wym-ikona-lg); height: var(--dn-wym-ikona-lg); flex: none; }
/* Znak w barwie sygnalu — podpowiedz, wskazanie, znacznik pierwszego wejscia. */
.dn-ik--sygnal { color: var(--dn-sygnal); }
/* Przygaszona — znak towarzyszący, nie nazywający: odsyłacz zewnętrzny, strzałka. */
.dn-ik--przygaszona { color: var(--dn-tekst-2); }
/* Cichy — przycisk ikonowy, który czeka: widoczny, ale ustępujący, dopóki
   nie najedzie się na jego kartę albo na niego samego. Okna malowały to
   własnymi regułami po jednej na każde miejsce użycia. */
.dn-btn-ikona--cichy { color: var(--dn-tekst-2); }
.dn-btn-ikona--cichy:hover,
.dn-btn-ikona--cichy:focus-visible { color: var(--dn-tekst); }

/* Czynność ujawniana najechaniem — stoi w dokumencie zawsze, widoczna staje się
   przy najechaniu na swój wiersz albo przy wejściu w niego klawiaturą. Wzorzec
   powtarzał się w oknach po jednej regule na każde miejsce użycia. */
.dn-na-najechanie { opacity: 0; transition: opacity var(--dn-czas-1) var(--dn-ease); }
:hover > .dn-na-najechanie,
:focus-within > .dn-na-najechanie,
.dn-na-najechanie:focus-within { opacity: 1; }
:hover > .dn-btn-ikona--cichy,
:focus-within > .dn-btn-ikona--cichy { color: var(--dn-tekst); }

/* Wiersz menu z czynnością dodatkową: pozycja i jej zamknięcie stoją obok
   siebie jako rodzeństwo — przycisk w przycisku jest niepoprawnym dokumentem. */
.sta-menu-wiersz { display: flex; align-items: center; gap: var(--dn-od-1); }
.sta-menu-wiersz > .sta-menu-poz { flex: 1 1 auto; min-width: 0; }
.sta-menu-wiersz > .dn-btn-ikona { flex: none; opacity: 0; transition: opacity var(--dn-czas-1) var(--dn-ease); }
.sta-menu-wiersz:hover > .dn-btn-ikona,
.sta-menu-wiersz:focus-within > .dn-btn-ikona { opacity: 1; }

.sta-menu-sep { height:1px; background:var(--dn-obrys-subtelny); margin:var(--dn-od-1) 0; }

/* ── Menu aplikacji z podmenu rozwijanym w bok ─────────────────────────────
   Menu aplikacji nie jest jednym długim blokiem od góry do dołu ekranu: górna
   lista jest wąska (same tytuły sekcji), a szczegóły wysuwają się w prawo jako
   podmenu. Mechanika stoi na :hover i :focus-within — bez skryptu, żeby nie
   ingerować w prototyp.js. */
#menu-aplikacji { min-width:220px; }
.sta-podmenu { position:relative; }
.sta-podmenu-wyzw { justify-content:flex-start; }
.sta-podmenu-grot { margin-left:auto; color:var(--dn-tekst-3); font-size:var(--dn-fs-md); }
.sta-podmenu-tresc {
  position:absolute; top:calc(-1 * var(--dn-od-1)); left:100%; z-index:1;
  min-width:260px; margin-left:var(--dn-od-1);
  padding:var(--dn-od-1); border:1px solid var(--dn-obrys); border-radius:var(--dn-r-md);
  background:var(--dn-powierzchnia); box-shadow:var(--dn-cien-3);
  opacity:0; visibility:hidden; transform:translateX(-4px);
  transition:opacity var(--dn-czas-1) var(--dn-ease), transform var(--dn-czas-1) var(--dn-ease), visibility var(--dn-czas-1);
}
.sta-podmenu:hover > .sta-podmenu-tresc,
.sta-podmenu:focus-within > .sta-podmenu-tresc {
  opacity:1; visibility:visible; transform:translateX(0);
}
.sta-podmenu:hover > .sta-podmenu-wyzw,
.sta-podmenu:focus-within > .sta-podmenu-wyzw { background:var(--dn-hover); }
.sta-podmenu:hover > .sta-podmenu-wyzw .sta-podmenu-grot,
.sta-podmenu:focus-within > .sta-podmenu-wyzw .sta-podmenu-grot { color:var(--dn-tekst); }
/* Podmenu przy prawej krawędzi okna otwiera się w lewo. */
.sta-podmenu-tresc--w-lewo { left:auto; right:100%; margin-left:0; margin-right:var(--dn-od-1); transform:translateX(4px); }
.sta-podmenu--w-lewo:hover > .sta-podmenu-tresc--w-lewo,
.sta-podmenu--w-lewo:focus-within > .sta-podmenu-tresc--w-lewo { transform:translateX(0); }
@media (prefers-reduced-motion: reduce) { .sta-podmenu-tresc { transition:none; } }

/* ══════════════════════════════════════════════════════════════════════════
   KOMPONENTY BRAKUJĄCE W ARKUSZU

   Poniższe klasy były używane w prototypach, lecz nie miały deklaracji —
   elementy renderowały się bez żadnego stylu. Nazwy zachowane, ponieważ
   należą do istniejących rodzin (.dn-modal, .dn-kropka, .dn-btn-ikona,
   .dn-karta-sesji, .dn-dost-barwa, .sta-chip, .sta-wpis). Wyłącznie żetony.
   ══════════════════════════════════════════════════════════════════════════ */

/* Tło okna nakładkowego budowanego bez znacznika dialog. */
.dn-modal-tlo {
  position: fixed;
  inset: 0;
  z-index: var(--dn-z-nakladka);
  display: grid;
  place-items: center;
  padding: var(--dn-od-4);
  background: var(--dn-nakladka);
}

/* Nazwa barwy przy próbce w widoku dostępności. */
.dn-dost-barwa-nazwa { white-space: nowrap; }

/* Kropka w barwie sygnałowej — rodzina miała sukces, błąd, ostrzeżenie
   i barwę neutralną, brakowało odpowiednika dla barwy wiodącej. */
.dn-kropka--sygnal { background: var(--dn-sygnal-500); }

/* Drobniejszy przycisk ikonowy — wymiar wyprowadzony z żetonu podstawowego,
   żeby nadążał za jego przesterowaniem w innych zakresach. */
.dn-btn-ikona--sm {
  width: calc(var(--dn-wym-ikonowy) - var(--dn-od-1));
  height: calc(var(--dn-wym-ikonowy) - var(--dn-od-1));
}
.dn-btn-ikona--sm svg { width: var(--dn-wym-ikona-sm); height: var(--dn-wym-ikona-sm); }

/* Zamknięcie karty sesji — znak wewnątrz karty, nie osobny przycisk. */
.dn-karta-sesji-zamknij {
  display: inline-grid;
  place-content: center;
  width: var(--dn-wym-ikona);
  height: var(--dn-wym-ikona);
  flex: none;
  border-radius: var(--dn-r-xs);
  color: var(--dn-tekst-3);
}
.dn-karta-sesji-zamknij svg { width: var(--dn-wym-ikona-sm); height: var(--dn-wym-ikona-sm); }
.dn-karta-sesji:hover .dn-karta-sesji-zamknij { color: var(--dn-tekst-2); }

/* Adnotacja w toku treści — krótka uwaga przy wpisie albo pozycji listy. */
.dn-alert {
  display: block;
  padding: var(--dn-od-2) var(--dn-od-3);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia-2);
  font-size: var(--dn-fs-sm);
  color: var(--dn-tekst-2);
}
.dn-alert--info {
  border-color: var(--dn-informacja-obrys);
  background: var(--dn-informacja-tlo);
  color: var(--dn-informacja-tekst);
}
.dn-alert--ostrzezenie {
  border-color: var(--dn-ostrzezenie-obrys);
  background: var(--dn-ostrzezenie-tlo);
  color: var(--dn-ostrzezenie-tekst);
}

/* Rząd znaczników pod wpisem rozmowy. */
.sta-chip-rzad { display: flex; flex-wrap: wrap; gap: var(--dn-od-1); }

/* Czynności przypisane do wpisu rozmowy. */
.sta-wpis-akcje { display: flex; gap: var(--dn-od-1); margin-top: var(--dn-od-2); }

/* ============================================================================
   WARSTWA RUCHU, AKCJI I UWYDATNIENIA
   ----------------------------------------------------------------------------
   Reakcja na wskazanie, naciśnięcie i wybór dla komponentów biblioteki.
   Granice: jedna krzywa `--dn-ease`, czasy z żetonów, animowane wyłącznie
   `transform`, `opacity`, `box-shadow` i barwy, jedno tętno na widok,
   `prefers-reduced-motion` gasi ruch żetonem — informację przejmuje kształt.
   ============================================================================ */

/* Biblioteka nie zna nazw okien. Wcześniej ta reguła wyliczała `.cd-siatka-*`
   z Centrum dowodzenia — biblioteka zależała wtedy od okna i przeniesienie okna
   zabierało zachowanie razem z nim. Siatka, która ma przygaszać rodzeństwo,
   deklaruje to sama, klasą `.dn-uwydatnij` w znaczniku. */
:where(.dn-uwydatnij, .dn-karty-sesji, .dn-przybornik) > * {
  transition: opacity var(--dn-czas-uwyd) var(--dn-ease);
}
:where(.dn-uwydatnij):hover > *:not(:hover) {
  opacity: var(--dn-przygasz-rodzenstwa);
}

.dn-karta-srodowiska {
  transition:
    border-color var(--dn-czas-2) var(--dn-ease),
    background-color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-uwyd) var(--dn-ease),
    transform var(--dn-czas-uwyd) var(--dn-ease);
}
.dn-karta-srodowiska::before {
  transform: scaleX(0);
  transform-origin: left center;
  background: var(--dn-sygnal-wypelnienie);
  opacity: 1;
  transition: transform var(--dn-czas-uwyd) var(--dn-ease);
}

.dn-karta-srodowiska::after {
  content: '';
  position: absolute;
  inset: 0;
  pointer-events: none;
  background: radial-gradient(120% 90% at 0% 0%, var(--dn-sygnal-tlo) 0%, transparent 60%);
  opacity: 0;
  transition: opacity var(--dn-czas-uwyd) var(--dn-ease);
}
.dn-karta-srodowiska:hover,
.dn-karta-srodowiska:focus-visible,
.dn-karta-srodowiska[aria-current='true'] {
  border-color: var(--dn-sygnal);
  box-shadow: var(--dn-cien-uniesienie);
  transform: translateY(var(--dn-podniesienie-lg));
}
.dn-karta-srodowiska:hover::before,
.dn-karta-srodowiska:focus-visible::before,
.dn-karta-srodowiska[aria-current='true']::before { transform: scaleX(1); }
.dn-karta-srodowiska:hover::after,
.dn-karta-srodowiska[aria-current='true']::after { opacity: 1; }
.dn-karta-srodowiska:active {
  transform: translateY(0) scale(var(--dn-skala-nacisk));
  box-shadow: var(--dn-cien-1);
}
.dn-karta-srodowiska:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: var(--dn-wym-fokus-odsuniecie);
}
.dn-karta-srodowiska-godlo {
  transition: transform var(--dn-czas-uwyd) var(--dn-ease), color var(--dn-czas-2) var(--dn-ease);
}
.dn-karta-srodowiska:hover .dn-karta-srodowiska-godlo {
  transform: scale(var(--dn-skala-godla));
  color: var(--dn-sygnal);
}

.dn-karta-srodowiska:hover .dn-btn {
  border-color: var(--dn-sygnal-wypelnienie);
  background: var(--dn-sygnal-wypelnienie);
  /* Biel, nie --dn-tekst-inv: w motywie ciemnym odwrotność tekstu jest niemal
     czarna i na wypełnieniu sygnałowym daje 4,14:1. Konwencja domu stoi
     przy .dn-btn--sygnal. */
  color: var(--dn-szary-0);
  box-shadow: var(--dn-poswiata-sygnal);
}

.dn-karta--klikalna {
  transition:
    border-color var(--dn-czas-2) var(--dn-ease),
    background-color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-uwyd) var(--dn-ease),
    transform var(--dn-czas-uwyd) var(--dn-ease);
}
.dn-karta--klikalna:hover {
  border-color: var(--dn-obrys-mocny);
  box-shadow: var(--dn-cien-uniesienie);
  transform: translateY(var(--dn-podniesienie-md));
}
.dn-karta--klikalna:active { transform: translateY(0) scale(var(--dn-skala-nacisk)); }

.dn-kafel {
  position: relative;
  overflow: hidden;
  transition:
    border-color var(--dn-czas-2) var(--dn-ease),
    background-color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-uwyd) var(--dn-ease),
    transform var(--dn-czas-uwyd) var(--dn-ease);
}

.dn-kafel::before {
  content: '';
  position: absolute;
  inset: 0 auto 0 0;
  width: var(--dn-wym-wstega);
  background: var(--dn-sygnal-wypelnienie);
  transform: scaleY(0);
  transform-origin: center top;
  transition: transform var(--dn-czas-uwyd) var(--dn-ease);
}
.dn-kafel:hover, .dn-kafel:focus-visible {
  border-color: var(--dn-sygnal-obrys);
  box-shadow: var(--dn-cien-uniesienie);
  transform: translateY(var(--dn-podniesienie-md));
}
.dn-kafel:hover::before, .dn-kafel:focus-visible::before { transform: scaleY(1); }
.dn-kafel:active { transform: translateY(0) scale(var(--dn-skala-nacisk)); }
.dn-kafel-ikona {
  transition:
    background-color var(--dn-czas-2) var(--dn-ease),
    color var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-uwyd) var(--dn-ease);
}
.dn-kafel:hover .dn-kafel-ikona {
  background: var(--dn-sygnal-tlo);
  color: var(--dn-sygnal);
  transform: scale(var(--dn-skala-ikony));
}
/* Znak bez ramki nie ma pola, więc nie ma czego podświetlić ani czym ruszyć:
   pod wskaźnikiem zmienia się wyłącznie barwa samego znaku. Reguła wyżej ma
   swoistość (0,2,0) i wygrywała z wariantem (0,1,0) — dlatego znosi się ją
   tutaj, na tej samej swoistości i później w arkuszu. */
.dn-kafel:hover .dn-kafel-ikona--bez-ramki {
  background: none;
  transform: none;
}

.dn-btn {
  transition:
    background-color var(--dn-czas-1) var(--dn-ease),
    border-color var(--dn-czas-1) var(--dn-ease),
    color var(--dn-czas-1) var(--dn-ease),
    box-shadow var(--dn-czas-2) var(--dn-ease),
    transform var(--dn-czas-1) var(--dn-ease);
}
.dn-btn:hover { transform: translateY(var(--dn-podniesienie-sm)); }
.dn-btn:active { transform: translateY(0) scale(var(--dn-skala-nacisk)); box-shadow: none; }
.dn-btn--sygnal:hover { box-shadow: var(--dn-poswiata-sygnal); }
.dn-btn--atrament:hover, .dn-btn--niebezpieczny:hover { box-shadow: var(--dn-cien-2); }
/* Stan nieczynny. `aria-disabled` zamiast `disabled`: przycisk zostaje osiągalny
   klawiaturą i czytnikiem, więc operator dowie się, dlaczego nie działa, zamiast
   trafiać na kontrolkę, której nie da się dosięgnąć. */
.dn-btn[aria-disabled='true'] {
  transform: none;
  box-shadow: none;
  opacity: .45;
  cursor: default;
}

.dn-btn-ikona {
  transition:
    background-color var(--dn-czas-1) var(--dn-ease),
    border-color var(--dn-czas-1) var(--dn-ease),
    color var(--dn-czas-1) var(--dn-ease),
    transform var(--dn-czas-1) var(--dn-ease);
}

.dn-btn-ikona > svg { transition: transform var(--dn-czas-uwyd) var(--dn-ease); }
.dn-btn-ikona:not(.dn-btn-ikona--na-ramie):hover > svg { transform: scale(var(--dn-skala-ikony)); }
.dn-btn-ikona--na-ramie:hover { transform: translateY(var(--dn-podniesienie-sm)); }
.dn-btn-ikona:active { transform: scale(var(--dn-skala-nacisk)); }

.dn-boczna-pozycja::before {
  content: '';
  position: absolute;
  left: 0;
  top: 50%;
  translate: 0 -50%;
  width: var(--dn-wym-wstega);
  height: 16px;
  border-radius: var(--dn-r-pill);
  background: var(--dn-kropka);
  transform: scaleY(0);
  transition: transform var(--dn-czas-2) var(--dn-ease);
}
.dn-boczna-pozycja:hover::before { transform: scaleY(0.6); }
.dn-boczna-pozycja[aria-current='page']::before { transform: scaleY(1); }

.sta-menu-poz {
  transition:
    background-color var(--dn-czas-1) var(--dn-ease),
    color var(--dn-czas-1) var(--dn-ease);
}

.sta-menu-poz > svg,
.sta-menu-poz > .dn-menu-poz-ikona { transition: transform var(--dn-czas-1) var(--dn-ease), color var(--dn-czas-1) var(--dn-ease); }
.sta-menu-poz:hover > svg,
.sta-menu-poz:hover > .dn-menu-poz-ikona { transform: translateX(2px); color: var(--dn-sygnal); }

.dn-tabela tbody tr { transition: background-color var(--dn-czas-1) var(--dn-ease); }

.dn-zakladka::after {
  content: '';
  position: absolute;
  inset: auto 0 -1px 0;
  height: var(--dn-wym-wstega);
  background: var(--dn-kropka);
  transform: scaleX(0);
  transform-origin: center;
  transition: transform var(--dn-czas-2) var(--dn-ease);
}
.dn-zakladka:hover::after { transform: scaleX(0.4); }
.dn-zakladka[aria-selected='true']::after { transform: scaleX(1); }

.dn-check, .dn-radio, .dn-przelacznik { transition: background-color var(--dn-czas-1) var(--dn-ease), border-color var(--dn-czas-1) var(--dn-ease), box-shadow var(--dn-czas-2) var(--dn-ease); }
.dn-check:active, .dn-radio:active, .dn-przelacznik:active { transform: scale(var(--dn-skala-nacisk)); }
.dn-check:checked, .dn-radio:checked { box-shadow: var(--dn-cien-sygnal); }
.dn-pole-kontrolka:focus, .dn-pole-kontrolka:focus-visible { box-shadow: var(--dn-cien-sygnal); }

.dn-wejscie-kaskada > * {
  animation: dn-wejscie-strefa var(--dn-czas-3) var(--dn-ease) both;
}
.dn-wejscie-kaskada > *:nth-child(1) { animation-delay: calc(0 * var(--dn-krok-kaskady)); }
.dn-wejscie-kaskada > *:nth-child(2) { animation-delay: calc(1 * var(--dn-krok-kaskady)); }
.dn-wejscie-kaskada > *:nth-child(3) { animation-delay: calc(2 * var(--dn-krok-kaskady)); }
.dn-wejscie-kaskada > *:nth-child(4) { animation-delay: calc(3 * var(--dn-krok-kaskady)); }
.dn-wejscie-kaskada > *:nth-child(5) { animation-delay: calc(4 * var(--dn-krok-kaskady)); }
/* Ogon zamiast szostej pozycji: wykaz dluzszy niz szesc pozycji nie wchodzil
   dotad z zadnym opoznieniem od siodmej w gore — kaskada gubila rytm. */
.dn-wejscie-kaskada > *:nth-child(n + 6) { animation-delay: calc(5 * var(--dn-krok-kaskady)); }
.dn-wejscie-kaskada > *:nth-child(n + 7) { animation-delay: calc(6 * var(--dn-krok-kaskady)); }

@media (prefers-reduced-motion: reduce) {
  
  .dn-karta-srodowiska:hover::before,
  .dn-karta-srodowiska[aria-current='true']::before,
  .dn-kafel:hover::before,
  .dn-zakladka[aria-selected='true']::after,
  .dn-boczna-pozycja[aria-current='page']::before { transition: none; }
  .dn-wejscie-kaskada > * { animation: none; }
}

.dn-karta-srodowiska { overflow: visible; }
.dn-karta-srodowiska::before { border-radius: var(--dn-r-xl) var(--dn-r-xl) 0 0; }
.dn-karta-srodowiska::after { border-radius: inherit; }

.dn-karta-srodowiska:hover,
.dn-karta-srodowiska:focus-within,
.dn-karta-srodowiska:has(.sta-menu-tresc[data-otwarte='tak']) { z-index: 3; }

/* ==========================================================================
   OKNO SPRZED UWIERZYTELNIENIA
   --------------------------------------------------------------------------
   Instalator, okno startowe, rejestracja i logowanie oraz przygotowanie
   środowiska stoją poza ramą aplikacji: nie mają szyny nawigacji, wstążki
   ani paska stanu. Mają wspólną bryłę — jedną dla całej rodziny, żeby
   wszystkie okna drogi wejścia czytały się jako to samo okno w kolejnych
   odsłonach, a nie jako cztery różne programy.
   ========================================================================== */

/* Scena — podłoże, na którym stoi bryła okna. */
.dn-scena {
  display: flex;
  align-items: center;
  justify-content: center;
  /* Scena bierze całą szerokość, jaką ma. Bez tego kurczy się do treści,
     a okno o szerokości `min(…, 100%)` zmienia wymiar razem z długością
     tekstu w kroku — okno kreatora ma stać nieruchomo. */
  width: 100%;
  min-height: 100%;
  padding: var(--dn-od-8) var(--dn-od-6);
  background: var(--dn-tlo);
}
.dn-scena--gora { align-items: flex-start; }

/* Bryła okna. Wymiar stały: okno wejściowe nie skaluje się z przeglądarką,
   bo w produkcie jest oknem systemowym o zadanej wielkości. */
.dn-okno-wejsciowe {
  --dn-okw-szerokosc: var(--dn-wym-okno-wejsciowe-szer);
  --dn-okw-wysokosc: var(--dn-wym-okno-wejsciowe-wys);
  --dn-okw-kolumna: var(--dn-wym-okno-wejsciowe-kolumna);
  --dn-okw-wciecie-x: var(--dn-od-6);
  --dn-okw-wciecie-y: var(--dn-od-6);
  --dn-okw-pas-dzialan: calc(var(--dn-wym-kontrolka) + var(--dn-od-8));
  --dn-okw-rytm: var(--dn-od-4);          /* odstęp między blokami kolumny */

  width: min(var(--dn-okw-szerokosc), 100%);
  height: var(--dn-okw-wysokosc);
  flex: none;
  display: grid;
  grid-template-columns: var(--dn-okw-kolumna) minmax(0, 1fr);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-xl);
  /* Strefa 3 z 3 — płótno. Trzy strefy okna przedaplikacyjnego stoją
     w NORMA-OKNA.md i sprawdza je strefy-okna.mjs; okno ich nie ustala. */
  background: var(--dn-okno-plotno);
  box-shadow: var(--dn-cien-3);
  overflow: hidden;
}
/* Wariant z belką okna systemowego: pierwszy wiersz siatki zajmuje belka,
   drugi — kolumna tożsamości i kolumna stanu. */
.dn-okno-wejsciowe--z-belka { grid-template-rows: var(--dn-wym-belka) minmax(0, 1fr); }
.dn-okno-wejsciowe--jednokolumnowe { grid-template-columns: minmax(0, 1fr); }

/* Belka okna systemowego — znak, tytuł, uchwyt przeciągania, zamknięcie.
   Rozciąga się na obie kolumny bryły. */
.dn-okno-wejsciowe-belka {
  grid-column: 1 / -1;
  display: flex;
  align-items: center;
  gap: var(--dn-od-3);
  height: var(--dn-wym-belka);
  /* Sterowanie okna stoi na przyciskach ikonowych biblioteki, a te mają własny
     narożnik — stąd odstęp od prawej krawędzi, którego belka ramy nie ma. */
  padding: 0 var(--dn-od-2) 0 var(--dn-od-3);
  /* Strefa 1 z 3 — najciemniejsza. Nie --dn-rama: rama należy do powłoki
     aplikacji, a to okno stoi przed nią. */
  background: var(--dn-okno-belka);
  color: var(--dn-rama-tekst);
}
/* Uchwyt przeciągania rozpiera belkę: tytuł zostaje przy znaku, sterowanie
   okna odchodzi do prawej krawędzi. */
.dn-okno-wejsciowe-belka-uchwyt { flex: 1 1 auto; }

/* Części belki przedaplikacyjnej. Rodzina jest osobna od `.dn-belka-*` z ramy
   i musi być samodzielna: okno przed uwierzytelnieniem nie wczytuje `rama.css`
   — powłoka dochodzi dopiero po wydaniu dostępu. Bez tych części belka nie
   miałaby czym się złożyć i okno dopisywałoby własne klasy. */
.dn-okno-wejsciowe-belka-znak {
  width: var(--dn-wym-ikona-sm);
  height: var(--dn-wym-ikona-sm);
  flex: none;
  color: var(--dn-rama-tekst);
}
.dn-okno-wejsciowe-belka-znak .kropka { fill: var(--dn-rama-sygnal); }
.dn-okno-wejsciowe-belka-tytul {
  margin: 0;
  font-size: var(--dn-fs-sm);
  font-weight: var(--dn-fw-srednia);
}
/* Sterowanie oknem: szerokość wg konwencji podpisu Windows, wysokość pełna,
   żeby cel kliknięcia sięgał krawędzi belki. */
.dn-okno-wejsciowe-belka-btn {
  display: grid;
  place-content: center;
  width: var(--dn-wym-belka-btn);
  height: 100%;
  flex: none;
  padding: 0;
  margin: 0;
  border: 0;
  background: transparent;
  color: var(--dn-rama-tekst-2);
  cursor: pointer;
  transition: background-color var(--dn-czas-1) var(--dn-ease), color var(--dn-czas-1) var(--dn-ease);
}
.dn-okno-wejsciowe-belka-btn > svg {
  width: var(--dn-wym-ikona-sm);
  height: var(--dn-wym-ikona-sm);
}
.dn-okno-wejsciowe-belka-btn:hover {
  background: var(--dn-rama-hover);
  color: var(--dn-rama-tekst);
}
.dn-okno-wejsciowe-belka-btn:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: calc(-1 * var(--dn-wym-fokus));
}
.dn-okno-wejsciowe-belka-btn--zamknij:hover {
  background: var(--dn-blad-tekst);
  color: var(--dn-tekst-inv);
}

/* Kolumna stanu albo formularza — jasna powierzchnia, własny rytm bloków. */
.dn-okno-wejsciowe-panel {
  display: flex;
  flex-direction: column;
  gap: var(--dn-okw-rytm);
  min-width: 0;
  min-height: 0;
  padding: var(--dn-okw-wciecie-y) var(--dn-okw-wciecie-x);
  overflow-y: auto;
  /* Strefa 3 z 3 — płótno kroku. Rozdzielenie stref idzie samą powierzchnią,
     bez kreski; żetony stref niosą zmierzone stopnie rozdzielenia. */
  background: var(--dn-okno-plotno);
}
.dn-okno-wejsciowe-panel--scentrowany { justify-content: center; }

/* ── Czynności okna wejściowego ─────────────────────────────────────────── */

/* Czynność główna i drogi poboczne — kolumna przycisków pełnej szerokości. */
.dn-akcje { display: flex; flex-direction: column; gap: var(--dn-od-2); }
.dn-akcje .dn-btn { justify-content: center; white-space: nowrap; }
.dn-akcje .dn-btn > svg { width: var(--dn-wym-ikona-sm); height: var(--dn-wym-ikona-sm); flex: none; }

/* Czynności poboczne — rząd przycisków przy lewej krawędzi, nie na całą szerokość. */
.dn-akcje--poboczne {
  flex-direction: row;
  align-items: center;
  align-self: flex-start;
  flex-wrap: wrap;
}
.dn-akcje--poboczne .dn-btn { width: auto; }

/* Pas działań na dnie kolumny. Odcina się powierzchnią, nie kreską, i sięga
   krawędzi kolumny — stąd ujemne marginesy równe wcięciom panelu. */
.dn-pas-dzialan {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: var(--dn-od-3);
  margin: auto calc(-1 * var(--dn-okw-wciecie-x)) calc(-1 * var(--dn-okw-wciecie-y));
  min-height: var(--dn-okw-pas-dzialan);
  padding: var(--dn-od-3) var(--dn-okw-wciecie-x);
  /* Strefa 2 z 3 — obrzeże. Norma obejmuje nim kolumnę lewą ORAZ pas działań
     na dole, więc oba biorą ten sam żeton. */
  background: var(--dn-okno-obrzeze);
  font-size: var(--dn-fs-sm);
  color: var(--dn-tekst-2);
}
.dn-pas-dzialan--ciag { justify-content: flex-end; }
/* Dwa marginesy `auto` w jednej kolumnie dzielą wolne miejsce na dwa pola
   zamiast jednego. Tam, gdzie nadmiar zbiera czynność główna, pas go nie dobiera. */
.dn-okno-wejsciowe-panel > .dn-akcje { margin-top: auto; }
.dn-okno-wejsciowe-panel:has(> .dn-akcje) > .dn-pas-dzialan { margin-top: 0; }

/* ── Kolumna tożsamości ─────────────────────────────────────────────────── */

/* Atramentowa kolumna okna wejściowego: godło, nazwa, motto, wykaz cech
   i nota na dnie. Atrament jest stały w obu motywach — kolumna tożsamości
   niesie markę, a marka nie zmienia barwy razem z motywem systemu. */
.dn-tozsamosc {
  display: flex;
  flex-direction: column;
  gap: var(--dn-od-6);
  padding: var(--dn-okw-wciecie-y) var(--dn-okw-wciecie-x);
  /* Strefa 2 z 3 — obrzeże, wspólne z pasem działań. */
  background: var(--dn-okno-obrzeze);
  color: var(--dn-rama-tekst);
}

/* Pozycja wykazu cech: ikona, wytłuszczony lead w osobnym wierszu, zdanie opisu. */
.dn-tozsamosc-poz {
  display: flex;
  gap: var(--dn-od-3);
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-bazowy);
  color: var(--dn-rama-tekst-2);
}
.dn-tozsamosc-poz > svg {
  width: var(--dn-wym-ikona);
  height: var(--dn-wym-ikona);
  flex: none;
  color: var(--dn-rama-tekst);
}
.dn-tozsamosc-poz b { display: block; color: var(--dn-rama-tekst); font-weight: var(--dn-fw-srednia); }

/* Stopka kolumny odcina się odstępem i stopniem pisma, nie kreską. */
.dn-tozsamosc-stopka {
  margin-top: auto;
  padding-top: var(--dn-od-5);
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
  line-height: var(--dn-lh-ciasny);
  color: var(--dn-rama-tekst-2);
}

/* ── Godło ──────────────────────────────────────────────────────────────── */

/* Samodzielny znak marki albo modułu — nieinteraktywny, w jednej ze skal
   księgi znaku, w barwie z żetonu. Interaktywny znak w pasku aplikacji
   pozostaje osobnym komponentem `.dn-pasek-godlo`, bo jest odsyłaczem. */
.dn-godlo {
  width: var(--dn-wym-godlo);
  height: var(--dn-wym-godlo);
  flex: none;
  color: var(--dn-rama-tekst);
}
.dn-godlo--lg { --dn-wym-godlo: var(--dn-wym-godlo-lg); }
.dn-godlo--ikonowy { --dn-wym-godlo: var(--dn-wym-godlo-ikonowy); }
.dn-godlo--lockup { width: var(--dn-wym-godlo-lockup); height: auto; }
.dn-godlo--na-plotnie { color: var(--dn-tekst); }
.dn-godlo--sygnal { color: var(--dn-sygnal); }
.dn-godlo .kropka { fill: var(--dn-sygnal-500); }
/* Tętno kropki godła — jeden wspólny puls sygnału platformy, jedna kropka.
   Dotąd stały tu DWIE reguły o sprzecznych zakresach: jedna wyłączała
   `.kropka--konsola` z przebiegu `dn-tetno-kropki`, druga nakładała przebieg
   `dn-tetno` na wszystkie kropki godła. Kropka biła więc dwoma przebiegami
   naraz. Zostaje jeden przebieg i jeden zakres: kropka sygnetu. */
.dn-godlo--tetno .kropka:not(.kropka--konsola),
.dn-belka-marka .kropka {
  transform-box: fill-box;
  transform-origin: center;
  animation: dn-tetno var(--dn-czas-tetno) var(--dn-ease) infinite;
}
@media (prefers-reduced-motion: reduce) {
  .dn-godlo--tetno .kropka,
  .dn-belka-marka .kropka { animation: none; }
}

/* ==========================================================================
   TYTUŁ OKNA · ODSYŁACZ
   ========================================================================== */

/* Tytuł okna w stopniu ekspozycyjnym — najwyższy poziom nagłówka na płótnie
   treści. Nad nim stoi zwykle `.dn-etyk-mono` jako nadtytuł, pod nim `.dn-lid`. */
.dn-tytul-okna {
  margin: 0;
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-display);
  font-weight: var(--dn-fw-polgruba);
  letter-spacing: var(--dn-ls-naglowek);
  line-height: var(--dn-lh-ciasny);
  color: var(--dn-tekst);
}
/* Tytuł ze znakiem wyniku w wierszu — zakończenie kreatora, wynik operacji.
   Znak stoi przed tekstem, nie pod nim: `svg` jest w tym pakiecie blokowy,
   więc rząd musi zbudować rodzina, a nie okno własną regułą. Znak jest
   powtórzeniem tego, co mówi tytuł — dlatego bierze `aria-hidden`. */
.dn-tytul-ze-znakiem { display: flex; align-items: center; gap: var(--dn-od-3); }
.dn-tytul-znak {
  flex: none;
  width: var(--dn-wym-ikona-lg);
  height: var(--dn-wym-ikona-lg);
  color: var(--dn-tekst-2);
}
.dn-tytul-znak--sukces { color: var(--dn-sukces-tekst); }
.dn-tytul-znak--ostrzezenie { color: var(--dn-ostrzezenie-tekst); }
.dn-tytul-okna--sm { font-size: var(--dn-fs-3xl); }
.dn-tytul-okna--na-ramie { color: var(--dn-rama-tekst); }

/* Odsyłacz w treści. Podkreślenie niesie rolę — barwa sama nie wystarcza,
   bo stan nigdy nie może stać wyłącznie na kolorze. */
.dn-link {
  color: var(--dn-sygnal);
  text-decoration: underline;
  text-underline-offset: var(--dn-wym-fokus-odsuniecie);
  border-radius: var(--dn-r-sm);
  transition: color var(--dn-czas-2) var(--dn-ease);
}
/* Najechanie idzie żetonem mocnego sygnału, nie prymitywem: prymityw 600 jest
   wartością motywu jasnego i w ciemnym dawał 2,52–3,00:1, czyli po najechaniu
   odnośnik czytał się gorzej niż przed nim. */
.dn-link:hover { color: var(--dn-sygnal-mocny); }
.dn-link:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: var(--dn-wym-fokus-odsuniecie);
}
/* Odsyłacz bywa czynnością w oknie, a nie adresem — niesie go wtedy `<button>`,
   bo klawiatura i czytnik mają dostać przycisk. Bryłę przycisku zdejmuje
   rodzina, żeby okno nie musiało tego robić własną regułą. */
button.dn-link {
  padding: 0;
  border: 0;
  background: none;
  text-align: left;
  cursor: pointer;
}
/* Odsyłacz stojący samodzielnie — poza tokiem zdania — nie musi nieść
   podkreślenia w spoczynku: nie ma tekstu, od którego miałby się odróżnić
   inaczej niż barwą, a WCAG 1.4.1 mówi o odsyłaczu wewnątrz akapitu.
   Podkreślenie wraca przy najechaniu i przy fokusie. Wewnątrz zdania ten
   wariant jest niedozwolony. */
.dn-link--cichy { text-decoration: none; }
.dn-link--cichy:hover,
.dn-link--cichy:focus-visible { text-decoration: underline; }
.dn-link--drugorzedny { color: var(--dn-tekst-2); }
.dn-link--drugorzedny:hover { color: var(--dn-tekst); }
.dn-link--na-ramie { color: var(--dn-rama-tekst); }

/* ==========================================================================
   POLE PRZEWIJANE
   --------------------------------------------------------------------------
   Obszar dłuższy niż miejsce, jakie na niego przypada: warunki licencji,
   wykaz składników, długa treść panelu. Niesie własną szynę i suwak, bo pasek
   systemowy w oknie o stałym wymiarze rysuje się drugi raz obok istniejącego.
   Gaśnięcie u góry i u dołu mówi, że treść biegnie dalej.
   ========================================================================== */

.dn-przewijane {
  --dn-przew-gasniecie: var(--dn-od-6);
  --dn-przew-tlo: var(--dn-powierzchnia-2);
  position: relative;
  display: flex;
  flex: 1 1 auto;
  min-height: 0;
}
.dn-przewijane::before,
.dn-przewijane::after {
  content: '';
  position: absolute;
  left: 0;
  right: var(--dn-od-5);
  height: var(--dn-od-10);
  pointer-events: none;
  transition: opacity var(--dn-czas-2) var(--dn-ease);
}
.dn-przewijane::before {
  top: 0;
  border-radius: var(--dn-r-md) var(--dn-r-md) 0 0;
  background: linear-gradient(to bottom, var(--dn-przew-tlo) var(--dn-przew-gasniecie), transparent);
}
.dn-przewijane::after {
  bottom: 0;
  border-radius: 0 0 var(--dn-r-md) var(--dn-r-md);
  background: linear-gradient(to top, var(--dn-przew-tlo) var(--dn-przew-gasniecie), transparent);
}
/* Skrajne położenia gaszą znacznik od tej strony, w którą już nie ma dokąd iść. */
.dn-przewijane[data-gora='tak']::before,
.dn-przewijane[data-dol='tak']::after { opacity: 0; }

.dn-przewijane-szyna {
  position: absolute;
  top: var(--dn-od-3);
  right: var(--dn-od-3);
  bottom: var(--dn-od-3);
  width: var(--dn-od-1);
  border-radius: var(--dn-r-pill);
  background: var(--dn-obrys-mocny);
}
.dn-przewijane-suwak {
  position: absolute;
  left: 0;
  right: 0;
  border-radius: var(--dn-r-pill);
  background: var(--dn-tekst-2);
}
/* Szyna własna ZASTĘPUJE pasek systemowy. Bez tego przewijające się wnętrze
   dostaje własny pasek z `fundament.css` i obok szyny rysuje się drugi. */
.dn-przewijane > * { scrollbar-width: none; }
.dn-przewijane > *::-webkit-scrollbar { width: 0; height: 0; }

/* ==========================================================================
   TEKST CIĄGŁY
   --------------------------------------------------------------------------
   Płótno treści czytanej, nie przeglądanej: warunki licencji, nota prawna,
   samouczek. Miara wiersza i interlinia są jego jedynym zadaniem.
   ========================================================================== */

.dn-tekst-ciagly {
  max-width: 72ch;
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-luzny);
  color: var(--dn-tekst-2);
}
.dn-tekst-ciagly > p { margin: 0 0 var(--dn-od-4); }
.dn-tekst-ciagly > p:last-child { margin-bottom: 0; }
.dn-tekst-ciagly b,
.dn-tekst-ciagly strong { color: var(--dn-tekst); font-weight: var(--dn-fw-polgruba); }

/* Osadzony — własna powierzchnia i przewijanie. Postać dla warunków licencji
   wewnątrz kroku kreatora. Ogniskowalny klawiaturą, bo sam się przewija. */
.dn-tekst-ciagly--osadzony {
  flex: 1 1 auto;
  min-height: 0;
  max-width: none;
  overflow-y: auto;
  padding: var(--dn-od-4) var(--dn-od-6) var(--dn-od-4) var(--dn-od-4);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia-2);
}
.dn-tekst-ciagly--osadzony:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: var(--dn-wym-fokus-odsuniecie);
}
.dn-tekst-ciagly--dokument { max-width: 78ch; font-size: var(--dn-fs-base); }
/* Wyróżnienie fragmentu — `mark` był w znaczniku bez deklaracji, więc brał
   żółte tło przeglądarki, jedyną barwę w produkcie spoza palety. Tło idzie ROLĄ
   `--dn-sygnal-tlo`, nie szczeblem `--dn-sygnal-100`: szczebel ma jedną wartość
   na oba motywy i w ciemnym kładł biel pod jasne pismo. Barwa pisma dziedziczona
   — wyróżnienie wskazuje miejsce, nie zmienia stopnia czytelności. */
.dn-tekst-ciagly mark {
  padding: 0 2px;
  border-radius: var(--dn-r-xs);
  background: var(--dn-sygnal-tlo);
  color: inherit;
}
.dn-tekst-ciagly--drobny { font-size: var(--dn-fs-xs); }

/* ==========================================================================
   POZIOMY TOR KROKÓW
   --------------------------------------------------------------------------
   Wskazanie miejsca w przepływie, czytane w jednym wierszu nad treścią.
   Różny od `.dn-kolejka` z `.dn-krok`, która jest pionowym wykazem czynności.
   ========================================================================== */

.dn-tor-krokow {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
  font-size: var(--dn-fs-xs);
  color: var(--dn-tekst-2);
}
.dn-tor-krokow-poz {
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-1);
}
.dn-tor-krokow-nr {
  display: grid;
  place-content: center;
  width: var(--dn-wym-krok-nr);
  height: var(--dn-wym-krok-nr);
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-pill);
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-xs);
}
.dn-tor-krokow-strzalka { color: var(--dn-tekst-2); }
/* Krok bieżący niesie wypełnienie i pismo, nie samą barwę. */
.dn-tor-krokow-poz[aria-current='step'] { color: var(--dn-tekst); font-weight: var(--dn-fw-srednia); }
.dn-tor-krokow-poz[aria-current='step'] .dn-tor-krokow-nr {
  border-color: var(--dn-sygnal-obrys);
  background: var(--dn-sygnal-tlo);
  color: var(--dn-sygnal);
}
.dn-tor-krokow-poz[data-zrobiony='tak'] .dn-tor-krokow-nr {
  border-color: var(--dn-sukces-obrys);
  background: var(--dn-sukces-tlo);
  color: var(--dn-sukces-tekst);
}

/* ==========================================================================
   SIŁA HASŁA I KRYTERIA
   ========================================================================== */

.dn-sila { display: flex; flex-direction: column; gap: var(--dn-od-2); }
.dn-sila-tor { display: grid; grid-template-columns: repeat(4, 1fr); gap: var(--dn-wym-sila); }
.dn-sila-odcinek {
  height: var(--dn-wym-sila);
  border-radius: var(--dn-r-pill);
  background: var(--dn-obrys);
}
.dn-sila[data-stopien='1'] .dn-sila-odcinek:nth-child(-n+1),
.dn-sila[data-stopien='2'] .dn-sila-odcinek:nth-child(-n+2) { background: var(--dn-ostrzezenie-tekst); }
.dn-sila[data-stopien='3'] .dn-sila-odcinek:nth-child(-n+3),
.dn-sila[data-stopien='4'] .dn-sila-odcinek { background: var(--dn-sukces-tekst); }
.dn-sila-opis { font-size: var(--dn-fs-xs); color: var(--dn-tekst-2); }

/* Wykaz warunków, jakie hasło ma spełnić. Stan niesie znak, nie sama barwa. */
.dn-kryteria {
  display: flex;
  flex-wrap: wrap;
  gap: var(--dn-od-1) var(--dn-od-3);
  font-size: var(--dn-fs-xs);
  color: var(--dn-tekst-2);
}
.dn-kryterium { display: inline-flex; align-items: center; gap: var(--dn-od-1); }
.dn-kryterium > svg { width: var(--dn-wym-ikona-xs); height: var(--dn-wym-ikona-xs); flex: none; }
.dn-kryterium[data-spelniony='tak'] { color: var(--dn-sukces-tekst); }

/* ==========================================================================
   KOD POTWIERDZENIA
   ========================================================================== */

/* Nazwa `.dn-kod` należy do bloku kodu w `fundament.css` — ta rodzina nosi
   nazwę roli, nie treści: wprowadzenie kodu potwierdzenia. */
.dn-potwierdzenie { display: flex; gap: var(--dn-od-2); }
.dn-potwierdzenie-pole {
  width: var(--dn-wym-kod-szer);
  height: var(--dn-wym-kod-wys);
  flex: none;
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia);
  color: var(--dn-tekst);
  font-family: var(--dn-ff-mono);
  font-size: var(--dn-fs-2xl);
  text-align: center;
  transition:
    border-color var(--dn-czas-1) var(--dn-ease),
    box-shadow var(--dn-czas-1) var(--dn-ease);
}
.dn-potwierdzenie-pole:focus {
  outline: none;
  border-color: var(--dn-fokus);
  box-shadow: var(--dn-cien-sygnal);
}
.dn-potwierdzenie-pole[aria-invalid='true'] { border-color: var(--dn-blad-obrys); }
.dn-potwierdzenie-stopka {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: var(--dn-od-4);
  font-size: var(--dn-fs-sm);
}

/* ==========================================================================
   ZESTAWIENIE
   --------------------------------------------------------------------------
   Wiersz „nazwa — wartość" domykający wybór: zajętość, suma, rachunek miejsca.
   ========================================================================== */

.dn-zestawienie {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--dn-od-3);
  padding: var(--dn-od-3) var(--dn-od-4);
  border-radius: var(--dn-r-md);
  /* Ta sama miara rozdzielenia stref, którą niesie pas działań. */
  background: var(--dn-powierzchnia-2);
  font-size: var(--dn-fs-sm);
  color: var(--dn-tekst);
}
.dn-zestawienie b { font-family: var(--dn-ff-mono); font-weight: var(--dn-fw-srednia); }

/* Wykaz cichy — dane bez własnej bryły. Wiersze rozdziela włos, nie ramka:
   cztery zestawienia w pudełkach czytają się jak cztery osobne rzeczy,
   a to jest jedna tabliczka znamionowa. */
.dn-zestawienie--cichy {
  /* Wiersz tabliczki jest wierszem wykazu, nie sekcją — 8 px u góry i u dołu
     dawało 16 px między danymi i wykaz rozpadał się na osobne pasy. */
  padding: var(--dn-od-1) 0;
  border-radius: 0;
  background: none;
  border-bottom: 1px solid var(--dn-obrys-subtelny);
}
.dn-zestawienie--cichy:last-child { border-bottom: 0; }
/* Nazwa i odczyt to jeden wiersz jednej tabliczki, więc idą TYM SAMYM pismem:
   ten sam krój, stopień i waga. Pismo maszynowe po prawej przy bezszeryfowym
   po lewej robiło z jednego wiersza dwie różne rzeczy. Rozdziela je wyłącznie
   kontrast — nazwa przygaszona, odczyt pełny. */
/* Nazwa i odczyt to jeden wiersz jednej tabliczki — idą TYM SAMYM pismem
   i w TEJ SAMEJ barwie. Rozdziela je wyłącznie położenie: nazwa przy lewej
   krawędzi, odczyt przy prawej. Każda różnica pisma albo kontrastu rozbijała
   wiersz na dwie różne rzeczy i podnosiła kolumnę danych do rangi, która jej
   nie przysługuje. */
.dn-zestawienie--cichy > span,
.dn-zestawienie--cichy > b {
  font-family: var(--dn-ff-bazowa);
  font-size: var(--dn-fs-sm);
  font-weight: var(--dn-fw-normalna);
  color: var(--dn-tekst-2);
}
.dn-wykaz-cichy { display: flex; flex-direction: column; }

/* ==========================================================================
   ADNOTACJA — brakujące części i warianty
   ========================================================================== */

.dn-alert--sukces {
  border-left: var(--dn-wym-wstega) solid var(--dn-sukces-obrys);
  background: var(--dn-sukces-tlo);
  color: var(--dn-sukces-tekst);
}
.dn-alert--blad {
  border-left: var(--dn-wym-wstega) solid var(--dn-blad-obrys);
  background: var(--dn-blad-tlo);
  color: var(--dn-blad-tekst);
}
/* Adnotacja ze znakiem: gniazdo ikony i gniazdo treści w jednym wierszu. */
/* Znak stoi w osi komunikatu, nie przy jego pierwszym wierszu. */
.dn-alert:has(> .dn-alert-znak) { display: flex; align-items: center; gap: var(--dn-od-3); }
.dn-alert-znak {
  display: grid;
  place-content: center;
  flex: none;
  width: var(--dn-wym-ikona-lg);
  height: var(--dn-wym-ikona-lg);
  color: currentColor;
}
.dn-alert-znak > svg { width: var(--dn-wym-ikona); height: var(--dn-wym-ikona); }
.dn-alert-tresc { flex: 1 1 auto; min-width: 0; line-height: var(--dn-lh-bazowy); }
/* Głowa komunikatu — nazywa rzecz, treść pod nią ją uzasadnia. Bez tego rozdziału
   komunikat i uzasadnienie czytają się jako jeden ciąg zdania. Wyróżnia waga
   i osobny wiersz, nie barwa: barwa należy do rodzaju komunikatu, nie do jego
   głowy, i przełączenie jej rozbijałoby alert na dwa różne stany. */
.dn-alert-tresc b.dn-alert-tytul {
  display: block;
  margin-bottom: var(--dn-od-1);
  /* Głowa niesie komunikat, treść pod nią tylko go uzasadnia — musi więc być
     wyeksponowana stopniem, nie samą wagą. Przy równym stopniu i równej barwie
     półgruba waga sama nie wystarczała, żeby oko rozdzieliło te dwie rangi. */
  font-size: var(--dn-fs-base);
  font-weight: var(--dn-fw-polgruba);
  line-height: var(--dn-lh-ciasny);
  /* Głowa odcina się od uzasadnienia także barwą: pełny kontrast tekstu wobec
     przygaszonej barwy komunikatu. Sam stopień i waga za mało ją eksponowały. */
  color: var(--dn-tekst);
}
.dn-alert-tresc b,
.dn-alert-tresc strong { color: var(--dn-tekst); font-weight: var(--dn-fw-polgruba); }

/* Alert ze wstęgą — komunikat, który stoi w treści okna, a nie nad nią.
   Barwa stanu obejmuje ZNAK I GŁOWĘ, nie całe pismo: treść pozostaje w barwie
   tekstu drugiego stopnia, więc czyta się tak samo dobrze jak reszta okna.
   Wstęga przy lewej krawędzi niesie stan kształtem, nie samą barwą tła.
   Wariant stał wcześniej w arkuszu okna wejścia jako `.we-alarm`. */
.dn-alert--wstega {
  display: flex;
  gap: var(--dn-od-3);
  padding: var(--dn-od-3);
  border-left-width: 2px;
  line-height: var(--dn-lh-bazowy);
  color: var(--dn-tekst-2);
}
/* Znak stoi przy GŁOWIE, nie w połowie wysokości: komunikat ze wstęgą ma głowę
   i treść, więc znak należy do pierwszego wiersza. Wyśrodkowanie z reguły
   `.dn-alert:has(> .dn-alert-znak)` dotyczy komunikatów jednozdaniowych i ma
   równą siłę, więc odwrócenie wymaga selektora tej samej budowy. */
.dn-alert--wstega:has(> .dn-alert-znak) { align-items: flex-start; }
/* Gniazdo znaku dorównuje samemu znakowi: komunikat stojący w treści nie ma
   nad sobą pola nagłówkowego, więc większe gniazdo odsuwałoby pismo od wstęgi
   bez powodu. */
.dn-alert--wstega > .dn-alert-znak {
  width: var(--dn-wym-ikona);
  height: var(--dn-wym-ikona);
  color: var(--dn-tekst-2);
}
.dn-alert--wstega > .dn-alert-tresc > b { display: block; color: var(--dn-tekst); font-weight: var(--dn-fw-polgruba); }

.dn-alert--wstega.dn-alert--sukces { color: var(--dn-tekst-2); }
.dn-alert--wstega.dn-alert--sukces > .dn-alert-znak,
.dn-alert--wstega.dn-alert--sukces > .dn-alert-tresc > b { color: var(--dn-sukces-tekst); }
.dn-alert--wstega.dn-alert--ostrzezenie { color: var(--dn-tekst-2); }
.dn-alert--wstega.dn-alert--ostrzezenie > .dn-alert-znak,
.dn-alert--wstega.dn-alert--ostrzezenie > .dn-alert-tresc > b { color: var(--dn-ostrzezenie-tekst); }
.dn-alert--wstega.dn-alert--info { color: var(--dn-tekst-2); }
.dn-alert--wstega.dn-alert--info > .dn-alert-znak,
.dn-alert--wstega.dn-alert--info > .dn-alert-tresc > b { color: var(--dn-informacja-tekst); }
.dn-alert--wstega.dn-alert--blad { color: var(--dn-tekst-2); }
.dn-alert--wstega.dn-alert--blad > .dn-alert-znak,
.dn-alert--wstega.dn-alert--blad > .dn-alert-tresc > b { color: var(--dn-blad-tekst); }

/* ==========================================================================
   POSTĘP — brakująca głowa · CZYNNOŚCI — tekst w pasie
   ========================================================================== */

/* Głowa paska postępu: nazwa czynności z lewej, miara z prawej, nad torem. */
.dn-postep-glowa {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--dn-od-3);
  font-size: var(--dn-fs-sm);
  color: var(--dn-tekst);
}

/* Objaśnienie albo odsyłacz stojący w pasie działań obok przycisków. */
.dn-akcje-tekst {
  flex: 1 1 auto;
  min-width: 0;
  font-size: var(--dn-fs-sm);
  line-height: var(--dn-lh-bazowy);
  color: var(--dn-tekst-2);
}
.dn-akcje-tekst--blad { color: var(--dn-blad-tekst); }

/* ==========================================================================
   TOR KROKÓW — odsłona pionowa i odsłona na ramie
   --------------------------------------------------------------------------
   Kreator instalacji prowadzi sześć kroków. Poziomo sześć nazw nie mieści się
   w kolumnie, więc ten sam tor dostaje odsłonę pionową; stoi w atramentowej
   kolumnie tożsamości, stąd druga odsłona — barwy z rodziny ramy. Rama nie
   zmienia się z motywem, więc stany biorą prymitywy, tak samo jak
   `.dn-btn-ikona--na-ramie` — z tą różnicą, że barwy stanu na ramie mają
   własne żetony `--dn-rama-*`, a nie prymitywy wprost.
   ========================================================================== */

/* Krok zrobiony niesie znak, nie samą barwę — znak wchodzi w miejsce numeru. */
.dn-tor-krokow-nr > svg { width: var(--dn-wym-ikona-xs); height: var(--dn-wym-ikona-xs); }

.dn-tor-krokow--pionowy {
  flex-direction: column;
  align-items: stretch;
  gap: var(--dn-od-3);
  font-size: var(--dn-fs-sm);
}
.dn-tor-krokow--pionowy .dn-tor-krokow-poz { gap: var(--dn-od-3); }
.dn-tor-krokow--pionowy .dn-tor-krokow-strzalka { display: none; }

/* Drugi stopień jasności ramy, nie trzeci: kroki przyszłe przy 13 px na atramencie
   dawały 4,45:1. Stopień „jeszcze niezrobiony" niesie tu numer bez wypełnienia,
   więc rozróżnienie nie stoi na samej barwie i wolno ją podnieść. */
.dn-tor-krokow--na-ramie { color: var(--dn-rama-tekst-2); }
.dn-tor-krokow--na-ramie .dn-tor-krokow-nr {
  border-color: var(--dn-rama-obrys-mocny);
  color: var(--dn-rama-tekst-2);
}
.dn-tor-krokow--na-ramie .dn-tor-krokow-poz[data-zrobiony='tak'] { color: var(--dn-rama-tekst-2); }
.dn-tor-krokow--na-ramie .dn-tor-krokow-poz[data-zrobiony='tak'] .dn-tor-krokow-nr {
  border-color: var(--dn-rama-sukces);
  background: transparent;
  color: var(--dn-rama-sukces);
}
.dn-tor-krokow--na-ramie .dn-tor-krokow-poz[aria-current='step'] { color: var(--dn-rama-tekst); }
.dn-tor-krokow--na-ramie .dn-tor-krokow-poz[aria-current='step'] .dn-tor-krokow-nr {
  border-color: var(--dn-rama-sygnal);
  background: var(--dn-rama-sygnal-wypelnienie);
  color: var(--dn-szary-0);
}

/* ==========================================================================
   WYBÓR W POSTACI POLA
   --------------------------------------------------------------------------
   Odsłona wyboru blokowego dla dróg równorzędnych, między którymi trzeba
   rozstrzygnąć raz na całą instalację: wariant, magazyn, tryb pracy. Cała
   pozycja jest celem wskazania, a stan wybrania niesie wstęga przy krawędzi
   i zaznaczona kontrolka — nie sama barwa tła.
   ========================================================================== */

.dn-wybor--pole {
  gap: var(--dn-od-3);
  padding: var(--dn-od-4);
  border: 1px solid var(--dn-obrys-mocny);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia);
  transition:
    border-color var(--dn-czas-2) var(--dn-ease),
    background-color var(--dn-czas-2) var(--dn-ease),
    box-shadow var(--dn-czas-2) var(--dn-ease);
}
.dn-wybor--pole:hover { border-color: var(--dn-tekst-3); background: var(--dn-hover); }
.dn-wybor--pole:active { box-shadow: var(--dn-cien-1); }
.dn-wybor--pole:focus-within {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: var(--dn-wym-fokus-odsuniecie);
}
.dn-wybor--pole:has(:checked) {
  border-color: var(--dn-sygnal-obrys);
  background: var(--dn-sygnal-tlo);
  box-shadow: inset var(--dn-wym-wstega) 0 0 var(--dn-kropka);
}
.dn-wybor--pole:has([aria-busy='true']) { cursor: progress; }
.dn-wybor--pole:has([aria-invalid='true']) {
  border-color: var(--dn-blad-obrys);
  background: var(--dn-blad-tlo);
  box-shadow: inset var(--dn-wym-wstega) 0 0 var(--dn-blad-tekst);
}
/* Nota maszynowa pod opisem wyboru — miara miejsca, czas, wydanie. */
.dn-wybor-opis > .dn-meta { display: block; margin-top: var(--dn-od-2); }

/* ==========================================================================
   POLE Z CZYNNOŚCIĄ · POLA W RZĘDZIE
   --------------------------------------------------------------------------
   Kontrolka, przy której stoi czynność: wskazanie katalogu, odsłonięcie hasła,
   skopiowanie klucza. Odsłona osadzona kładzie czynność w świetle pola —
   tak, jak wskazują wytyczne Windows dla pól hasła.
   ========================================================================== */

.dn-pole-zestaw {
  position: relative;
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
}
.dn-pole-zestaw > .dn-pole-kontrolka { flex: 1 1 auto; min-width: 0; }
.dn-pole-zestaw > .dn-btn,
.dn-pole-zestaw > .dn-btn-ikona { flex: none; }

.dn-pole-zestaw--osadzona { gap: 0; }
.dn-pole-zestaw--osadzona > .dn-pole-kontrolka {
  padding-right: calc(var(--dn-od-16) + var(--dn-od-2));
}
.dn-pole-zestaw--osadzona > .dn-btn {
  position: absolute;
  top: 50%;
  right: var(--dn-od-1);
  translate: 0 -50%;
}
.dn-pole-zestaw--osadzona > .dn-btn:hover { transform: none; }

/* Dwa pola w jednym rzędzie — para równorzędnych krótkich wartości. */
.dn-pole-grupa--rzad {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--dn-od-4);
  margin: 0;
}

/* ==========================================================================
   POSTĘP Z GŁOWĄ
   --------------------------------------------------------------------------
   `.dn-postep` jest wierszem: tor i miara obok siebie. Głowa stoi NAD torem,
   więc odsłona z głową układa te same części w kolumnie.
   ========================================================================== */

.dn-postep--z-glowa {
  flex-direction: column;
  align-items: stretch;
  gap: var(--dn-od-2);
}
.dn-postep--z-glowa > .dn-postep-tor { flex: none; width: 100%; }

/* Tor bez miary — praca, której postępu nie da się wyrazić liczbą: wycofywanie
   zmian, oczekiwanie na odpowiedź. Rola `progressbar` zostaje wtedy BEZ
   `aria-valuenow`, i to ona, nie animacja, ogłasza stan nieokreślony.
   Przy ograniczonym ruchu tor stoi wypełniony i przygaszony — nieokreśloność
   niesie brak wartości, więc gaszenie ruchu niczego nie zabiera. */
.dn-postep-tor--nieokreslony > .dn-postep-wartosc {
  width: 35%;
  transition: none;
  animation: dn-postep-przebieg 1.4s var(--dn-ease) infinite;
}
@media (prefers-reduced-motion: reduce) {
  .dn-postep-tor--nieokreslony > .dn-postep-wartosc {
    width: 100%;
    animation: none;
    opacity: 0.45;
  }
}

/* ==========================================================================
   STRUKTURA DOKUMENTU W TEKŚCIE CIĄGŁYM
   --------------------------------------------------------------------------
   Akt prawny, regulamin albo instrukcja wyświetlana w całości: śródtytuły
   dwóch stopni, wykazy, uwagi redakcyjne i zestawienia. Osobne od `.dn-tabela`,
   która jest tabelą danych z nagłówkiem przyklejonym do góry — tutaj tabela
   jest częścią czytanego tekstu i przewija się razem z nim.
   ========================================================================== */

.dn-tekst-ciagly h2 {
  margin: var(--dn-od-8) 0 var(--dn-od-3);
  font-family: var(--dn-ff-naglowek);
  font-size: var(--dn-fs-md);
  font-weight: var(--dn-fw-polgruba);
  line-height: var(--dn-lh-ciasny);
  letter-spacing: -0.01em;
  color: var(--dn-tekst);
}
.dn-tekst-ciagly h3 {
  margin: var(--dn-od-6) 0 var(--dn-od-2);
  font-size: var(--dn-fs-base);
  font-weight: var(--dn-fw-polgruba);
  line-height: var(--dn-lh-bazowy);
  color: var(--dn-tekst-wiodacy);
}
.dn-tekst-ciagly > :first-child { margin-top: 0; }

.dn-tekst-ciagly ol,
.dn-tekst-ciagly ul {
  margin: 0 0 var(--dn-od-4);
  padding-left: var(--dn-od-5);
}
.dn-tekst-ciagly li { margin-bottom: var(--dn-od-2); }
.dn-tekst-ciagly li:last-child { margin-bottom: 0; }
.dn-tekst-ciagly li::marker { color: var(--dn-tekst-3); }

/* Uwaga redakcyjna — wyróżniona kreską, nie tłem: w długim dokumencie tło
   powtórzone kilkadziesiąt razy zamienia tekst w pasy. */
.dn-tekst-ciagly blockquote {
  margin: 0 0 var(--dn-od-4);
  padding-left: var(--dn-od-4);
  border-left: 2px solid var(--dn-sygnal-500);
  color: var(--dn-tekst-3);
}
.dn-tekst-ciagly blockquote > p:last-child { margin-bottom: 0; }

.dn-tekst-ciagly code {
  font-family: var(--dn-ff-mono);
  font-size: 0.92em;
  color: var(--dn-tekst-wiodacy);
}
.dn-tekst-ciagly hr {
  margin: var(--dn-od-6) 0;
  border: 0;
  border-top: 1px solid var(--dn-obrys);
}

/* Zestawienie wewnątrz dokumentu. Węższe pole niż tabela danych, więc szeroka
   tabela przewija się we własnym pojemniku — nigdy nie rozpycha kolumny tekstu. */
.dn-zestawienie-pole {
  margin: 0 0 var(--dn-od-4);
  overflow-x: auto;
}
.dn-tekst-ciagly table {
  width: 100%;
  border-collapse: collapse;
  font-size: var(--dn-fs-xs);
  line-height: var(--dn-lh-bazowy);
}
.dn-tekst-ciagly th,
.dn-tekst-ciagly td {
  padding: var(--dn-od-2) var(--dn-od-3);
  border-bottom: 1px solid var(--dn-obrys);
  text-align: left;
  vertical-align: top;
}
.dn-tekst-ciagly th {
  font-weight: var(--dn-fw-polgruba);
  color: var(--dn-tekst);
  white-space: nowrap;
}

/* ==========================================================================
   SPIS TREŚCI
   --------------------------------------------------------------------------
   Wykaz odsyłaczy do rozdziałów dokumentu czytanego w jednym polu. Dwa stopnie
   zagłębienia; stopień drugi wciśnięty i drobniejszy.
   ========================================================================== */

.dn-spis-tresci { margin: 0 0 var(--dn-od-6); }
.dn-spis-tresci ol,
.dn-spis-tresci ul { margin: 0; padding: 0; list-style: none; }
.dn-spis-tresci li { margin-bottom: var(--dn-od-1); }
.dn-spis-tresci ul { margin-top: var(--dn-od-1); padding-left: var(--dn-od-4); }
.dn-spis-tresci ul li { font-size: var(--dn-fs-xs); }
.dn-spis-tresci a {
  color: var(--dn-tekst-2);
  text-decoration: none;
  border-bottom: 1px solid transparent;
}
.dn-spis-tresci a:hover { color: var(--dn-sygnal-mocny); border-bottom-color: currentColor; }
.dn-spis-tresci a:focus-visible {
  outline: var(--dn-wym-fokus) solid var(--dn-fokus);
  outline-offset: 2px;
}
.dn-spis-tresci > ol > li > a { color: var(--dn-tekst); font-weight: var(--dn-fw-polgruba); }

/* ==========================================================================
   SZYNA MODUŁU — boczny wykaz wewnątrz płótna modułu
   --------------------------------------------------------------------------
   Nie mylić z `.dn-szyna-nawigacji` z `rama.css`: tamta jest pasem ikon ramy
   aplikacji, szerokim na 40 px i atramentowym. Ta stoi wewnątrz modułu, niesie
   nazwy i grupy, i odcina się od płótna barwą panelu z kreską po prawej.

   Składnik powstał z wyniesienia: te same siedem reguł stało dosłownie
   w blokach <style> czternastu okien modułów. Grupa w wykazie nie dostaje
   własnego przepisu — bierze `.dn-etyk-mono`, bo to dokładnie ta rola:
   zapowiedź grupy kontrolek. Nie `.dn-panel-grupa`: tamta stoi w `panel-sesji.css`,
   którego okna modułów nie wczytują. Wcześniejsza kopia okienna miała 10 px poza
   skalą pisma i krój szeryfowy; przepis biblioteki daje 12 px w mono.
   ========================================================================== */

.dn-szyna-modulu {
  display: flex;
  flex-direction: column;
  min-height: 0;
  background: var(--dn-panel);
  border-right: 1px solid var(--dn-obrys);
}

.dn-szyna-modulu-glowa {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
  padding: var(--dn-od-2);
  border-bottom: 1px solid var(--dn-obrys-subtelny);
}

/* Przewija się sam wykaz, nie cała szyna: głowa z wyszukiwaniem ma stać. */
.dn-szyna-modulu-lista {
  flex: 1 1 auto;
  min-height: 0;
  overflow: auto;
}

/* Etykieta grupy sama nie niesie wyściółki — w szynie równa się do jej wnętrza,
   czyli do od-2, żeby nie wisieć w prawo względem pozycji pod sobą. */
.dn-szyna-modulu-lista > .dn-etyk-mono { display: block; padding: var(--dn-od-2) var(--dn-od-2) 0; }

/* --------------------------------------------------------------------------
   WYKAZ MODUŁU — zwarta lista wierszy stanu w panelu modułu
   Wiersz jest pasem: znacznik, treść, nota maszynowa dosunięta do prawej.
   -------------------------------------------------------------------------- */

.dn-wykaz-modulu {
  display: flex;
  flex-direction: column;
  gap: var(--dn-od-2);
  padding: var(--dn-od-2);
  font-size: var(--dn-fs-sm);
}

.dn-wykaz-modulu-poz {
  display: flex;
  align-items: center;
  gap: var(--dn-od-2);
}

/* Nota kończy wiersz i sama się do niego dosuwa — dosunięcie należy do wiersza,
   przepis pisma do `.dn-meta`. */
.dn-wykaz-modulu-poz > .dn-meta { margin-left: auto; }

/* Wiersz zamykający wykaz czynnością, nie daną. Kreska oddziela go od wierszy
   z danymi — bez niej przycisk czyta się jak kolejna pozycja wykazu. */
.dn-wykaz-modulu-poz--dzialanie {
  border-top: 1px solid var(--dn-obrys-subtelny);
  padding-top: var(--dn-od-2);
}

/* Dosunięcie do końca pasa dla wszystkiego, co notą nie jest — plakietki stanu,
   żetonu, przycisku. Wcześniej te elementy nosiły klasę `meta`, przez co brały
   też jej pismo i przestawały wyglądać jak plakietki. Rozmieszczenie i wygląd
   to dwie różne decyzje, więc są dwiema różnymi klasami. */
.dn-na-koniec { margin-left: auto; }

/* ==========================================================================
   WNĘTRZA KART OKNA ROBOCZEGO — kanwa, różnice, wersje, podgląd wydruku
   --------------------------------------------------------------------------
   Role wyniesione z arkusza okna Studia. Żadna nie jest własnością Studia:
   kanwę dokumentu ma także Developer i Translate, wykaz różnic — Developer
   i Design, repozytorium wersji — każdy moduł z historią, podgląd wydruku —
   każdy moduł, który cokolwiek drukuje.
   ========================================================================== */

/* Nota pomocnicza — drobny tekst pod wierszem wykazu. Pismo bezszeryfowe:
   to zdanie do czytania, nie miara (miarę niesie `.dn-meta`). */
.dn-nota { font-size: var(--dn-fs-xs); color: var(--dn-tekst-2); }

/* ── Pasek narzędzi edytora ──────────────────────────────────────────────── */

.dn-edytor-pasek {
  display: flex;
  align-items: center;
  gap: var(--dn-od-1);
  flex-wrap: wrap;
  padding: var(--dn-od-2);
  border-bottom: 1px solid var(--dn-obrys-subtelny);
}
.dn-edytor-grupa {
  display: inline-flex;
  gap: var(--dn-od-05);
  padding-right: var(--dn-od-2);
  border-right: 1px solid var(--dn-obrys-subtelny);
}

/* ── Kanwa dokumentu ─────────────────────────────────────────────────────── */

/* Powierzchnia redakcji. Różna od `.dn-tekst-ciagly`: tam tekst się CZYTA,
   tutaj się go PISZE, więc miara wiersza jest szersza, a barwa pełna. */
.dn-kanwa {
  max-width: 78ch;
  margin: 0 auto;
  padding: var(--dn-od-4) var(--dn-od-6);
  min-height: 0;
  overflow: auto;
  line-height: var(--dn-lh-luzny);
  color: var(--dn-tekst);
}
.dn-kanwa h1 { font-size: var(--dn-fs-xl); margin: 0 0 var(--dn-od-3); }
.dn-kanwa h2 { font-size: var(--dn-fs-lg); margin: var(--dn-od-4) 0 var(--dn-od-2); }
.dn-kanwa p { margin: 0 0 var(--dn-od-3); }

/* Zaznaczenie w kanwie jest kontenerem odniesienia dla przybornika
   pływającego — bez tego przybornik ląduje na akapicie, nie nad nim. */
.dn-zazn {
  position: relative;
  padding: 1px var(--dn-od-1);
  border-radius: var(--dn-r-md);
  background: var(--dn-sygnal-tlo);
  box-shadow: 0 0 0 1px var(--dn-sygnal);
}
.dn-plyw {
  position: absolute;
  bottom: calc(100% + var(--dn-od-1));
  left: 0;
  z-index: 3;
  display: inline-flex;
  align-items: center;
  gap: var(--dn-od-05);
  padding: var(--dn-od-05);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-md);
  background: var(--dn-powierzchnia);
  box-shadow: var(--dn-cien-3);
  white-space: nowrap;
}

/* ── Wykaz różnic ────────────────────────────────────────────────────────── */

/* Trzy rodzaje zmiany, trzy rozpoznania: dodanie tłem zieleni, usunięcie
   przekreśleniem NA TLE czerwieni, zmiana formatu samym konturem. Stan nigdy
   samym kolorem — usunięcie niesie przekreślenie, format niesie kontur. */
.dn-diff-dod,
.dn-diff-usu,
.dn-diff-fmt { padding: 1px var(--dn-od-1); border-radius: var(--dn-r-md); }
.dn-diff-dod { background: var(--dn-sukces-tlo); color: var(--dn-tekst); }
.dn-diff-usu { background: var(--dn-blad-tlo); text-decoration: line-through; }
.dn-diff-fmt { box-shadow: inset 0 0 0 1px var(--dn-ostrzezenie-tekst); }

/* ── Repozytorium wersji ─────────────────────────────────────────────────── */

.dn-wersja {
  display: flex;
  flex-direction: column;
  gap: var(--dn-od-05);
  padding: var(--dn-od-2);
  border-bottom: 1px solid var(--dn-obrys-subtelny);
}
.dn-wersja-akcje { display: flex; gap: var(--dn-od-1); margin-top: var(--dn-od-05); }

/* ── Podgląd wydruku ─────────────────────────────────────────────────────── */

/* Kartka — arkusz papieru na gruncie panelu. Jedyne miejsce, gdzie `--dn-tlo`
   jest wypełnieniem elementu, a nie gruntem: kartka MA być tłem, tylko
   uniesionym i obrysowanym. */
.dn-kartka {
  max-width: 60ch;
  margin: 0 auto;
  padding: var(--dn-od-4);
  border: 1px solid var(--dn-obrys);
  border-radius: var(--dn-r-lg);
  /* Papier bierze POWIERZCHNIĘ, nie grunt: w motywie jasnym grunt jest szary,
     a kartka ma być białą stroną leżącą na nim. */
  background: var(--dn-powierzchnia);
  box-shadow: var(--dn-cien-1);
  color: var(--dn-tekst);
}
.dn-kartka-tytul {
  margin-bottom: var(--dn-od-3);
  font-size: var(--dn-fs-lg);
  font-weight: var(--dn-fw-polgruba);
}
.dn-kartka p { font-size: var(--dn-fs-sm); }
.dn-kartka-numer { color: var(--dn-tekst-2); }
