/* ============================================================
   SKÓRA WSPÓLNA — jeden system wizualny dla całego serwisu.
   Etap 14.

   DLACZEGO JASNO. Do trzynastego etapu każde miasto miało własną
   ciemną skórę: Kraków mosiądz na grafitzie, Warszawa rdza,
   Przemyśl patyna na atramentowym granacie. Wyglądało to dobrze
   przy jednym zdjęciu i źle przy wszystkim innym — właściciel
   powiedział wprost, że „strona jest tak ciemna, że ciężko coś
   dostrzec”. Przy kilkuset słowach noty ma rację: jasnoszara
   szaryfowa czcionka na prawie czarnym tle to nie jest krój do
   czytania, tylko do oglądania.

   Doszło do tego drugie: w serwisie mają stanąć aparaty i artykuły.
   Siedem osobnych rejestrów barwnych nie da się rozciągnąć na
   działy, których jeszcze nie ma. Stąd JEDEN system — jedna paleta,
   jedna typografia, jedna siatka — a nie siedem wariantów.

   Stara jasność tła nie zniknęła bez śladu: skan nadal leży na
   passe-partout, tyle że teraz to jest jasny karton na jasnym
   stole, a nie biała kartka w ciemnym pokoju. Fotografia z XIX
   wieku ma półtony w sepii i szarościach — na ciemnym tle oko
   traci je pierwsze.

   CO SIĘ NIE ZMIENIŁO: skan idzie w całości, w naturalnych
   proporcjach, bez kadrowania i bez korekty (WYMAGANIA 21).
   Nigdzie nie ma object-fit.

   ZMIANA Z 29.08.2026 — CIEMNO, ALE INACZEJ NIŻ WTEDY.
   Właściciel poprosił, żeby ten serwis „nie odbiegał tak od stronki
   Janusza i był w podobnym stylu". To odwraca decyzję Etapu 14, więc
   trzeba powiedzieć wprost, co się zmieniło wobec wersji, którą wtedy
   odrzucił jako nieczytelną.

   Tamta ciemność to była jasnoszara szaryfowa czcionka na prawie
   czarnym tle — kontrast rzędu 4:1, siedem różnych rejestrów barwnych.
   Ta ma jeden system: atrament #ece5d8 na tle #0b0a09, czyli około
   14:1, i jeden akcent — złoto zamiast patyny.

   Najważniejsze: SKAN DALEJ LEŻY NA JASNYM PASSE-PARTOUT. `--mat`
   zostaje kartonowo jasny, więc półtony sepii mają na czym stanąć.
   Ciemna jest ŚCIANA, nie karton pod fotografią — dokładnie jak
   w muzeum. To jest odpowiedź na tamten zarzut, a nie jego zignorowanie.

   POTWIERDZONE 29.08.2026, PO OBEJRZENIU NA PRODUKCJI. Powyższe było
   wykonaniem prośby; to jest ocena gotowej strony. Właściciel zobaczył
   serwis pod adresem silverandglass.pl i rozstrzygnął: „ta co jest
   ciemna jak u Edwarda mi odpowiada". Ciemna skóra ZOSTAJE.

   Kto tu kiedyś trafi z zamiarem „przywrócenia jasnej wersji zgodnie
   z Etapem 14" — nie rób tego. Etap 14 jest świadomie odwrócony,
   sprawdzony na żywym serwisie i zatwierdzony po fakcie, a nie
   przeoczony.

   RAMKA BIERZE PROPORCJE ZE SKANU. Wcześniej gablota miała sztywną
   wysokość, ustawioną pod pocztówkę — czyli pod format poziomy.
   Na stronach z fotografią gabinetową (Mielec 66 pionowych na 68,
   Rzeszów 41 na 44) pionowy skan kurczył się do jednej trzeciej
   szerokości i pływał w pustce. Teraz `--ar` niesie proporcje
   awersu, a gablota układa się pod nie.
   ============================================================ */

:root{
  /* papier i atrament — paleta wspólna ze stroną Edwarda Janusza */
  --bg:            #0b0a09;   /* tło strony — ciemna ściana */
  --bg-deep:       #100e0c;   /* tło gabloty */
  --bg-raise:      #15120f;   /* płaszczyzny wyniesione: powiększenie */
  --mat:           #efe9dd;   /* passe-partout pod skanem — ZOSTAJE JASNY */
  --mat-edge:      #6b6252;

  --line:          #241f1a;
  --line-soft:     #1c1815;

  --ink:           #ece5d8;   /* tekst główny — kontrast ok. 14:1 na tle */
  --ink-soft:      #b3aa9b;   /* nota, wstęp — ok. 8,6:1 */
  --ink-faint:     #8b8375;   /* podpisy techniczne — ok. 5:1 */

  /* Jeden akcent na cały serwis. Złoto zamiast dawnej patyny — ten sam,
     którym mówi strona Janusza, żeby oba serwisy czytały się jak jedna
     rodzina. Nazwy zmiennych zostają (--pat...), bo używa ich cały
     arkusz; zmienia się wartość, nie mechanizm. */
  --pat:           #c9a961;
  --pat-soft:      #e0c485;
  --pat-dim:       #6b5a35;

  /* Na ciemnym tle cień nie istnieje. Rolę oddzielenia przejmuje
     delikatna krawędź i głęboki, rozmyty cień pod gablotą. */
  --shadow-card:   0 1px 0 rgba(255,255,255,.04), 0 14px 34px rgba(0,0,0,.55);
  --shadow-deep:   0 30px 84px rgba(0,0,0,.72);

  /* zapasowe proporcje gabloty, gdy karta nie poda własnych */
  --ar:            4/3;
  /* dokąd może urosnąć gablota bardzo wysokiego skanu */
  --stage-max:     540px;
}

*{box-sizing:border-box}
html{scroll-behavior:smooth; -webkit-text-size-adjust:100%}
@media (prefers-reduced-motion: reduce){
  html{scroll-behavior:auto}
  *{animation-duration:.001ms !important; animation-iteration-count:1 !important; transition-duration:.001ms !important;}
}

body{
  margin:0;
  background:
    radial-gradient(1020px 560px at 6% -10%, rgba(201,169,97,.06), transparent 60%),
    radial-gradient(900px 520px at 96% 0%, rgba(201,169,97,.04), transparent 58%),
    var(--bg);
  color:var(--ink);
  font-family:"Source Serif 4", Georgia, serif;
  font-size:17.5px;
  line-height:1.68;
  -webkit-font-smoothing:antialiased;
  text-rendering:optimizeLegibility;
}

h1,h2,h3{font-family:"Old Standard TT", Georgia, serif; font-weight:700; margin:0; text-wrap:balance}
a{color:var(--pat); text-underline-offset:3px}
a:hover{color:var(--pat-soft)}
button{font:inherit; color:inherit}
:focus-visible{outline:2px solid var(--pat); outline-offset:3px}

.skip-link{
  position:absolute; left:-999px; top:0; z-index:300;
  background:var(--pat); color:#14110a; padding:10px 16px;
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:13px;
}
.skip-link:focus{left:12px; top:12px}

/* ---------- pasek przyklejony do góry (Etap 15, D-42) ----------

   Do czternastego etapu nagłówek wymieniał sześć miast obok siebie,
   zawijał się na telefonie do dwóch rzędów i ODJEŻDŻAŁ przy przewijaniu.
   Przy ósmym mieście urósłby do trzech rzędów: rząd odsyłaczy rośnie
   z liczbą stron, a miejsca na ekranie nie przybywa.

   Teraz jest wąski pasek, który zostaje na wierzchu: znak i nazwa po
   lewej (odsyłacz na stronę główną), nazwa bieżącej strony pośrodku,
   rozwijana lista siedmiu podstron po prawej. Lista nie rośnie wszerz
   — rośnie w dół, we własnym okienku.

   DWA PRZYKLEJONE PASKI NA PULPICIE, JEDEN NA TELEFONIE. Pod tym stoi
   drugi: filtry (.index). Oba miały `top:0`, więc drugi wjechałby pod
   pierwszy i zniknął. Dlatego wysokość paska jest zapisana w `--nav-h`
   i filtry przyklejają się DOKŁADNIE POD nim. Jedna liczba rządzi obiema
   rzeczami — inaczej przy każdej zmianie wysokości paska trzeba by
   pamiętać o drugim miejscu, a nikt nie pamięta.

   ETAP 17 (D-45): na telefonie drugiego paska już nie ma. Filtry są
   szufladą wysuwaną spod paska przyciskiem „Filtry", obok „Miasta" —
   szczegóły przy `@media (max-width:720px)` na końcu pliku. */

:root{ --nav-h:48px; }

.sg-bar{
  position:sticky; top:0; z-index:120;
  background:rgba(11,10,9,.92);
  backdrop-filter:blur(9px);
  border-bottom:1px solid var(--line);
}
.sg-bar-inner{
  max-width:1320px; margin:0 auto; padding:0 32px; height:var(--nav-h);
  display:flex; align-items:center; gap:16px;
}

/* znak + nazwa = odsyłacz na stronę główną. To jest cały „powrót
   na stronę główną" — nie ma osobnego przycisku, bo logo w nagłówku
   jest miejscem, w które i tak każdy klika. */
.sg-home{
  display:flex; align-items:center; gap:9px; flex:0 0 auto;
  text-decoration:none; color:var(--pat); transition:color .18s ease;
}
.sg-home:hover{color:var(--pat-soft)}
.sg-mark{display:block; flex:0 0 auto}
.sg-word{
  font-family:"Old Standard TT", Georgia, serif; font-style:italic;
  font-size:16.5px; line-height:1; white-space:nowrap;
}
.sg-here{
  flex:1 1 auto; min-width:0; margin:0; text-align:center;
  font-family:"Old Standard TT", Georgia, serif; font-style:italic;
  font-size:15.5px; color:var(--ink);
  white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
}

/* Rozwijana lista miast. <details>/<summary> — działa BEZ JavaScriptu,
   także wtedy, gdy skrypt strony się nie wczyta. Skrypty różnią się
   między miastami (Jarosław umie karty jednostronne, Kraków ma starszy
   filtr) i nawigacja nie ma prawa od nich zależeć. */
.sg-menu{flex:0 0 auto; position:relative}
.sg-menu > summary, .ix-drawer > summary{
  list-style:none; cursor:pointer; -webkit-user-select:none; user-select:none;
  display:inline-flex; align-items:center; gap:7px;
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:12.5px; letter-spacing:.03em; color:var(--ink-soft);
  background:var(--bg-raise); border:1px solid var(--line);
  padding:6px 12px; transition:color .18s ease, border-color .18s ease;
}
.sg-menu > summary::-webkit-details-marker,
.ix-drawer > summary::-webkit-details-marker{display:none}
.sg-menu > summary::marker, .ix-drawer > summary::marker{content:""}
.sg-menu > summary::after, .ix-drawer > summary::after{
  content:""; width:0; height:0; margin-top:1px;
  border-left:4px solid transparent; border-right:4px solid transparent;
  border-top:5px solid var(--pat-soft);
}
.sg-menu > summary:hover, .ix-drawer > summary:hover{color:var(--pat); border-color:var(--pat-soft)}
.sg-menu[open] > summary, .ix-drawer[open] > summary{color:var(--pat); border-color:var(--pat-soft)}
.sg-menu[open] > summary::after, .ix-drawer[open] > summary::after{transform:rotate(180deg)}

/* WEJŚCIE DO WYSZUKIWARKI (Etap 27, TOR 2/3 z D-58). Stoi w pasku obok
   „Miasta", czyli w jedynym miejscu, które jest takie samo na wszystkich
   34 stronach serwisu. Wygląda jak sąsiednie rozwijaki i tak samo się
   zachowuje — z jedną różnicą: to zwykły odsyłacz, nie <details>, bo
   prowadzi na inną stronę, a nie otwiera okienka.

   Szkło powiększające jest `aria-hidden` — obok stoi słowo „Szukaj”
   napisane literami, więc czytnik ekranu ma przeczytać je, a nie opisywać
   obrazek drugi raz (tak samo jak znak w pasku, D-43). */
.sg-szukaj{
  flex:0 0 auto; display:inline-flex; align-items:center; gap:7px;
  text-decoration:none;
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:12.5px; letter-spacing:.03em; color:var(--ink-soft);
  background:var(--bg-raise); border:1px solid var(--line);
  padding:6px 12px; transition:color .18s ease, border-color .18s ease;
}
.sg-szukaj:hover{color:var(--pat); border-color:var(--pat-soft)}
.sg-szukaj[aria-current="page"]{color:var(--pat); border-color:var(--pat-soft)}
.sg-szukaj svg{display:block; flex:0 0 auto}

/* Rozwijak „Filtry" — od Etapu 23 wejście do filtrów NA OBU SZEROKOŚCIACH.
   D-45 świadomie zostawił pulpit nietknięty (rzędy stały rozwinięte,
   przycisku nie było). Pomiar Etapu 23 pokazał cenę: pasek + rozwinięte
   rzędy = 209–211 px z 900, czyli 23% pulpitu na stałe — i właściciel
   odrzucił to przy odbiorze. Odwrócenie jest świadome, z pomiarem: D-54. */
.ix-drawer{display:block; flex:0 0 auto}
.sg-list{
  position:absolute; right:0; top:calc(100% + 8px); z-index:130;
  min-width:232px; margin:0; padding:5px 0; list-style:none;
  background:var(--bg-raise); border:1px solid var(--line);
  box-shadow:var(--shadow-card);
}
.sg-list a{
  display:flex; align-items:baseline; justify-content:space-between; gap:16px;
  padding:8px 16px; text-decoration:none; color:var(--ink);
  font-family:"Old Standard TT", Georgia, serif; font-size:17px; line-height:1.3;
}
.sg-list a:hover{background:rgba(201,169,97,.10); color:var(--pat-soft)}
.sg-list a[aria-current="page"]{color:var(--pat); font-style:italic}
.sg-list .sg-n{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:11.5px; color:var(--ink-faint); flex:0 0 auto;
  font-variant-numeric:tabular-nums;
}
.site-foot-x{color:var(--pat); text-decoration:none; border-bottom:1px solid var(--line)}
.site-foot-x:hover{border-bottom-color:var(--pat-soft)}

/* ---------- wstęp ----------
   Etap 23 (D-54): strona miejska ma pokazywać zdjęcia, nie ścianę tekstu.
   Odstępy wstępu zwężone (72/52 → 46/34 itd.) i widoczny zostaje TYLKO
   PIERWSZY AKAPIT — dalsze akapity wchodzą pod „czytaj dalej"
   (.lede-more). Proza właściciela zostaje co do słowa; zmienia się
   wyłącznie to, czy jest rozwinięta na wejściu. */
.hero{padding:46px 0 34px; max-width:1320px; margin:0 auto; padding-left:32px; padding-right:32px}
.hero-inner{max-width:800px}
.eyebrow{
  margin:0 0 14px; font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:12px;
  letter-spacing:.2em; text-transform:uppercase; color:var(--pat);
}
.hero h1{
  font-size:clamp(33px, 5.2vw, 54px); line-height:1.12; font-style:italic;
  margin-bottom:18px; letter-spacing:-.01em;
}
.lede{font-size:18.6px; line-height:1.7; color:var(--ink-soft); max-width:64ch; margin:0}
.lede + .lede{margin-top:15px}
/* rozwijak dalszych akapitów wstępu — <details>, bez JavaScriptu,
   tym samym mechanizmem co lista miast (D-42) i filtry (D-45) */
.lede-more{margin:0}
.lede-more > summary{
  list-style:none; cursor:pointer; -webkit-user-select:none; user-select:none;
  display:inline-flex; align-items:center; margin-top:12px; width:fit-content;
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:12px; letter-spacing:.08em; text-transform:uppercase;
  color:var(--pat); padding:2px 1px 4px; border-bottom:1px solid var(--pat-dim);
  transition:color .18s ease, border-color .18s ease;
}
.lede-more > summary::-webkit-details-marker{display:none}
.lede-more > summary::marker{content:""}
.lede-more > summary:hover{color:var(--pat-soft); border-bottom-color:var(--pat)}
.lede-more[open] > summary .lm-w{display:none}
.lede-more:not([open]) > summary .lm-z{display:none}
.lede-more > .lede{margin-top:15px}
.hero-rule{border:0; border-top:1px solid var(--line); margin:24px 0 16px; max-width:800px}
.hero-stats{display:flex; gap:52px; flex-wrap:wrap}
.hero-stats > div{display:flex; flex-direction:column; gap:5px}
.hero-stats b{
  font-family:"Old Standard TT", serif; font-weight:700; font-size:30px;
  color:var(--pat); font-variant-numeric:tabular-nums; line-height:1;
}
.hero-stats span{
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11.5px; letter-spacing:.13em;
  text-transform:uppercase; color:var(--ink-faint);
}

/* ---------- zdjęcie na wejściu (Etap 28, D-60) ----------
   Kolumna tekstu `.hero-inner` ma 800 px w środku 1320-pikselowego `.hero`
   — na pulpicie stoi obok niej puste miejsce, dokładnie tam, gdzie wchodzi
   zdjęcie. `.hero--foto` dostają WYŁĄCZNIE strony, których warstwa niesie
   `hero.zdjecie: true` (dziś: Przemyśl, Jarosław, Warszawa) — Kraków,
   Rzeszów, Jasło i Mielec przeszły odbiór i tej klasy nigdy nie dostają,
   więc te reguły nie zmieniają ani piksela na ich stronach.

   W znaczniku zdjęcie stoi PO `.hero-inner` — na pulpicie flex w wierszu
   kładzie je naturalnie po prawej, bez sztucznego `order`. Na telefonie
   marginesu nie ma (D-60: „tam odpowiedź musi być inna”) i dopiero tam
   `order:-1` przenosi zdjęcie NAD wstęp. */
.hero--foto{display:flex; flex-wrap:wrap; align-items:flex-start; gap:44px}
.hero--foto .hero-inner{flex:1 1 420px; max-width:800px}
.hero-photo{
  display:block; flex:1 1 320px; max-width:420px;
  border:1px solid var(--line); box-shadow:var(--shadow-card);
  text-decoration:none; overflow:hidden; background:var(--bg-raise);
  transition:border-color .18s ease;
}
.hero-photo:hover, .hero-photo:focus-visible{border-color:var(--pat-soft)}
.hero-photo img{display:block; width:100%; height:auto}

/* ---------- filtry w szufladzie (Etap 17 telefon, Etap 23 wszędzie) ----------

   Do Etapu 22 to były DWA różne układy: na telefonie szuflada wysuwana
   spod paska (D-45), na pulpicie drugi przyklejony pasek z rozwiniętymi
   rzędami. Pomiar Etapu 23 pokazał, że rozwinięte rzędy kosztują pulpit
   170–211 px z 900 (do 23% ekranu) na stałe, na każdej stronie — a
   właściciel odrzucił stronę przy odbiorze właśnie za „menu, które
   zabiera pół strony". Od Etapu 23 szuflada jest JEDNA, ta sama na obu
   szerokościach: panel schowany, wysuwa się przyciskiem „Filtry" w pasku.

   STEROWANIE BEZ JAVASCRIPTU, jak dotąd: `<details class="ix-drawer">`
   w pasku trzyma stan, `body:has(.ix-drawer[open])` przenosi go na panel.
   Panel nie siedzi wewnątrz `<details>` — uzasadnienie w D-45. Przyciski
   to te same elementy `.ix[data-cat]`/`.ix[data-era]`, skrypty miast
   nietknięte. */
/* Filtr stoi na wierzchu, nad siatką — nie jest już szufladą wysuwaną
   spod paska. Powód w nagłówku generator_stron.py: zostały trzy stałe
   przyciski, te same na każdym mieście, i chowanie ich za rozwijakiem
   kosztowało kliknięcie oraz wiedzę, że wybór w ogóle istnieje. */
.index{
  border-top:1px solid var(--line-soft);
  border-bottom:1px solid var(--line-soft);
  background:rgba(255,255,255,.015);
}
.index-inner{max-width:1320px; margin:0 auto; padding:2px 32px 16px}
.index-row{display:flex; align-items:center; flex-wrap:wrap; gap:6px; padding:12px 0 2px}
.index-row + .index-row{border-top:1px solid var(--line-soft)}
.index-label{
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11px; letter-spacing:.16em;
  text-transform:uppercase; color:var(--ink-faint);
  display:block; width:100%; margin:0 0 3px;
}
.ix{
  appearance:none; cursor:pointer;
  font-family:"Old Standard TT", Georgia, serif; font-size:15.5px; letter-spacing:.015em;
  color:var(--ink-soft); position:relative; white-space:nowrap; line-height:1.25;
  padding:8px 13px; border:1px solid var(--line); background:var(--bg);
  transition:color .18s ease, border-color .18s ease;
}
.ix:hover{color:var(--ink)}
.ix.is-on{color:var(--pat); border-color:var(--pat)}
.ix sup{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:10.5px; vertical-align:super;
  margin-left:5px; color:var(--ink-faint); letter-spacing:0;
}
.ix.is-on sup{color:var(--pat-soft)}
.ix[disabled]{opacity:.4; cursor:default}
.ix[disabled]:hover{color:var(--ink-soft)}
/* kreski między nazwami działów miały sens w jednym rzędzie; w zawiniętej
   siatce guzików rozjeżdżają się na końcach wierszy */
.ix-sep{display:none}
.index-row-era .ix{font-size:14.5px; font-style:italic}
.ix-count{
  display:block; width:100%; margin:14px 0 0; padding-left:0;
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:12px; letter-spacing:.06em;
  color:var(--ink-faint); white-space:nowrap;
}
.ix-reset{
  appearance:none; background:none; border:0; cursor:pointer; white-space:nowrap;
  padding:8px 0 8px 4px;
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11px; letter-spacing:.12em;
  text-transform:uppercase; color:var(--ink-faint); transition:color .18s ease;
}
.ix-reset:hover{color:var(--pat)}
.ix-reset[hidden]{display:none}

/* ---------- siatka kart ---------- */
/* filtry nie stoją już nad siatką (Etap 23), więc zjazd do niej omija
   wyłącznie pasek */
.plates{max-width:1320px; margin:0 auto; padding:30px 32px 20px;
  scroll-margin-top:calc(var(--nav-h) + 8px)}
/* Nota nad siatką i stopka to ZDANIA, nie etykiety — Etap 15, D-41.
   Do czternastego etapu obie stały w kroju maszynowym w 11 px, czyli
   w tym samym, co sygnatura katalogowa. Zdanie czyta się inaczej niż
   numer: idzie w nim o ciąg, nie o pojedynczy znak. Wracają więc do
   kroju tekstu czytanego i do stopnia, w którym da się je przeczytać. */
.plate-note{
  margin:0 0 34px; max-width:66ch;
  font-family:"Source Serif 4", Georgia, serif; font-size:14.5px; line-height:1.75;
  color:var(--ink-faint); letter-spacing:0;
}
.plate-grid{
  display:grid; grid-template-columns:repeat(auto-fill, minmax(300px, 1fr));
  gap:54px 34px; align-items:start;
}
/* KOTWICA KARTY (Etap 27). Od tego etapu każda karta ma `id` z sygnatury
   (`#pt-4-72`), bo wynik wyszukiwarki musi mieć dokąd prowadzić. Bez tej
   linijki przeglądarka ustawia kartę DOKŁADNIE przy górnej krawędzi okna,
   czyli pod przyklejonym paskiem — karta jest wtedy na ekranie, ale jej
   góra siedzi za paskiem i wygląda to na chybienie. Ta sama poprawka,
   co przy `.plates` wyżej, i z tego samego powodu. */
.pc{display:flex; flex-direction:column; min-width:0;
  scroll-margin-top:calc(var(--nav-h) + 16px)}
.pc[hidden]{display:none}

/* GABLOTA. Proporcje bierze ze skanu (--ar podaje generator z nagłówka
   pliku JPEG), nie odwrotnie. `max-height` chroni przed kartami bardzo
   wysokimi — wtedy skan zmniejsza się sam, dalej w swoich proporcjach. */
.pc-stage{
  position:relative;
  aspect-ratio:var(--ar); max-height:var(--stage-max);
  background:
    linear-gradient(158deg, rgba(255,255,255,.05), transparent 56%),
    var(--bg-deep);
  border:1px solid var(--line);
  display:flex; align-items:center; justify-content:center;
  padding:16px; perspective:1400px;
}
.pc-flipper{
  position:relative; width:100%; height:100%;
  transform-style:preserve-3d; transition:transform .62s cubic-bezier(.4,.05,.2,1);
}
.pc[data-flip="back"] .pc-flipper{transform:rotateY(180deg)}
.pc-face{
  position:absolute; inset:0; margin:0; padding:0; border:0; background:none;
  display:flex; align-items:center; justify-content:center;
  cursor:zoom-in; backface-visibility:hidden; -webkit-backface-visibility:hidden;
}
.pc-face-back{transform:rotateY(180deg)}
/* passe-partout: tło + padding. NIGDY object-fit — skan idzie w całości,
   w naturalnych proporcjach. Obrys robi outline, żeby nie wchodził w pomiar. */
.pc-face img{
  max-width:100%; max-height:100%; width:auto; height:auto; display:block;
  background:var(--mat); padding:6px;
  outline:1px solid var(--mat-edge);
  box-shadow:var(--shadow-card);
  transition:box-shadow .25s ease, transform .25s ease, outline-color .25s ease;
}
.pc-face:hover img{
  box-shadow:0 4px 12px rgba(0,0,0,.5), 0 16px 38px rgba(0,0,0,.42);
  transform:translateY(-2px);
  outline-color:var(--pat-soft);
}

/* pasek pod gablotą: odwracanie karty */
.pc-tools{display:flex; justify-content:flex-end; align-items:center; min-height:30px; padding:7px 0 0}
.pc-flip{
  display:inline-flex; align-items:center; gap:7px;
  background:none; border:0; border-bottom:1px solid var(--line);
  color:var(--ink-faint); cursor:pointer; padding:2px 1px 4px;
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11px; letter-spacing:.13em;
  text-transform:uppercase; transition:color .18s ease, border-color .18s ease;
}
.pc-flip:hover{color:var(--pat); border-bottom-color:var(--pat-soft)}
.pc[data-flip="back"] .pc-flip{color:var(--pat); border-bottom-color:var(--pat-soft)}
.pc-flip .gl{font-size:12px; line-height:1; transition:transform .5s ease}
.pc[data-flip="back"] .pc-flip .gl{transform:rotate(180deg)}
.pc-oneside{
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11px; letter-spacing:.13em;
  text-transform:uppercase; color:var(--ink-faint);
}

/* nota katalogowa */
.pc-text{padding:10px 2px 0; display:flex; flex-direction:column; gap:8px}
.pc-title{font-size:19px; line-height:1.26; font-style:italic; color:var(--ink)}
.pc-meta{
  margin:0; font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11.5px;
  letter-spacing:.075em; text-transform:uppercase; color:var(--ink-faint);
}
.pc-meta .sep{color:var(--pat-dim); margin:0 6px}
.pc-body{margin:2px 0 0; font-size:15.6px; line-height:1.62; color:var(--ink-soft)}
/* NOTA ZWINIĘTA DO DWÓCH LINIJEK (Etap 23, D-54). Etap 22 dał karcie
   bogatą notę z `opis_pl` (200–250 px tekstu) i karta przestała mieścić
   się w oknie razem ze skanem. Zwijamy, NIE skracamy (WYMAGANIA 29):
   w HTML-u stoi cała nota, przycina ją CSS, a skrypt powiększenia czyta
   pełny textContent z .pc-body — w powiększeniu nota jest zawsze cała.
   Steruje <details class="pc-more"> przez :has(), bez JavaScriptu, jak
   szuflada filtrów (D-45). Karta bez .pc-more (krótka nota) nie jest
   przycinana wcale. */
.pc-text:has(.pc-more:not([open])) .pc-body{
  display:-webkit-box; -webkit-box-orient:vertical;
  -webkit-line-clamp:2; line-clamp:2; overflow:hidden;
}
.pc-more{margin:-2px 0 0}
.pc-more > summary{
  list-style:none; cursor:pointer; -webkit-user-select:none; user-select:none;
  display:inline-flex; align-items:center; width:fit-content;
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:11px; letter-spacing:.13em; text-transform:uppercase;
  color:var(--ink-faint); padding:2px 1px 4px; border-bottom:1px solid var(--line);
  transition:color .18s ease, border-color .18s ease;
}
.pc-more > summary::-webkit-details-marker{display:none}
.pc-more > summary::marker{content:""}
.pc-more > summary:hover{color:var(--pat); border-bottom-color:var(--pat-soft)}
.pc-more[open] > summary .pm-w{display:none}
.pc-more:not([open]) > summary .pm-z{display:none}
.pc-sig{
  margin:6px 0 0; padding-top:9px; border-top:1px solid var(--line-soft);
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11.5px; letter-spacing:.09em;
  color:var(--ink-faint);
}
.plates-empty{margin:70px 0; text-align:center; color:var(--ink-faint); font-style:italic}

/* ---------- stopka ---------- */
.site-foot{border-top:1px solid var(--line); margin-top:46px; background:rgba(255,255,255,.02)}
.site-foot-inner{margin:0 auto; padding:32px 32px 78px; max-width:880px}
.site-foot p{
  margin:0; font-family:"Source Serif 4", Georgia, serif; font-size:14.5px; line-height:1.75;
  color:var(--ink-faint);
}
.site-foot p + p{margin-top:14px}

/* ---------- powiększenie ---------- */
.lb{position:fixed; inset:0; z-index:200; display:flex; align-items:center; justify-content:center}
.lb[hidden]{display:none}
/* Zasłona musi być gęsta: pod spodem leży jasna siatka kart i przy
   rzadkiej zasłonie przebijała przez tło powiększenia. */
.lb-veil{position:absolute; inset:0; background:rgba(6,6,7,.92)}
.lb-shell{
  position:relative; z-index:1; display:flex;
  width:min(1240px, calc(100% - 132px)); max-height:calc(100% - 60px);
  background:var(--bg-raise); border:1px solid var(--line); box-shadow:var(--shadow-deep);
}
.lb-stage{
  position:relative; margin:0; flex:1 1 auto; min-width:0;
  display:flex; align-items:center; justify-content:center;
  background:linear-gradient(160deg, rgba(255,255,255,.05), transparent 58%), var(--bg-deep);
  padding:30px 30px 62px;
  /* Głębokie powiększenie (Etap 30) przybliża `#lb-frame` ponad rozmiar
     okna — bez tego zoomowany skan malowałby się poza gablotą, na panelu
     tekstu obok. Klip przy krawędzi ramki, jak w każdej przeglądarkowej
     przeglądarce zdjęć. */
  overflow:hidden;
}
/* Sama gablota transformacji — patrz komentarz w generator_stron.py przy
   `#lb-frame`. Bez własnego rozmiaru: jako element flex bez rozciągania
   (`align-items:center` w rodzicu) chowa się dokładnie do wymiarów
   `#lb-img`, więc nie zmienia ani piksela wyglądu przy zoomie=100%. */
.lb-frame{touch-action:none; cursor:zoom-in}
.lb-frame.lb-frame--zoom{cursor:grab}
.lb-frame.lb-frame--zoom:active{cursor:grabbing}
.lb-img{
  max-width:100%; max-height:min(78vh, 720px); width:auto; height:auto; display:block;
  background:var(--mat); padding:8px; outline:1px solid var(--mat-edge);
  box-shadow:0 6px 18px rgba(0,0,0,.55), 0 22px 60px rgba(0,0,0,.5);
  -webkit-user-drag:none; user-select:none;
}
.lb-flip{
  position:absolute; left:50%; bottom:18px; transform:translateX(-50%);
  display:inline-flex; align-items:center; gap:8px;
  background:rgba(11,10,9,.92); border:1px solid var(--pat-dim); color:var(--ink-soft);
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:12px; letter-spacing:.12em;
  text-transform:uppercase; padding:9px 18px; cursor:pointer; white-space:nowrap;
}
.lb-flip:hover{color:var(--pat); border-color:var(--pat-soft)}
.lb-side{
  flex:0 0 378px; max-width:378px; padding:34px 32px 28px; overflow-y:auto;
  border-left:1px solid var(--line-soft); display:flex; flex-direction:column; gap:13px;
}
.lb-pos{
  margin:0; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11px;
  letter-spacing:.14em; color:var(--ink-faint); font-variant-numeric:tabular-nums;
}
.lb-meta{
  margin:0; font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11.5px;
  letter-spacing:.09em; text-transform:uppercase; color:var(--ink-faint);
}
.lb-meta .sep{color:var(--pat-dim); margin:0 7px}
.lb-title{font-size:26px; line-height:1.2; font-style:italic; margin:0}
.lb-body{margin:0; font-size:16.5px; line-height:1.7; color:var(--ink-soft)}
.lb-sig{
  margin:auto 0 0; padding-top:16px; border-top:1px solid var(--line-soft);
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:11.5px; letter-spacing:.09em; color:var(--ink-faint);
}
.lb-keys{
  margin:10px 0 0; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:10.5px;
  letter-spacing:.1em; text-transform:uppercase; color:var(--ink-faint);
}
.lb-x, .lb-nav{
  position:absolute; z-index:3; background:rgba(16,14,12,.90);
  border:1px solid var(--pat-dim); color:var(--ink-soft); cursor:pointer;
  display:flex; align-items:center; justify-content:center; line-height:1;
  transition:color .18s ease, border-color .18s ease;
}
.lb-x:hover, .lb-nav:hover{color:var(--pat); border-color:var(--pat-soft)}
.lb-x{top:22px; right:26px; width:42px; height:42px; font-size:20px}
.lb-nav{top:50%; transform:translateY(-50%); width:46px; height:66px; font-size:22px}
.lb-prev{left:26px}
.lb-next{right:26px}
body.lb-open{overflow:hidden}

/* ---------- responsywność ---------- */
@media (max-width:1080px){
  .lb-shell{width:calc(100% - 108px)}
  .lb-side{flex-basis:322px}
}
@media (max-width:900px){
  .lb{padding:0}
  .lb-shell{flex-direction:column; width:100%; height:100%; max-height:100%; border:0}
  .lb-stage{flex:0 0 auto; padding:22px 18px 56px}
  .lb-img{max-height:44vh}
  .lb-side{flex:1 1 auto; max-width:none; border-left:0; border-top:1px solid var(--line-soft); padding:24px 22px 84px}
  /* pas wygaszający pod strzałkami — inaczej przewijany tekst noty biegnie
     przez przyciski i robi się nieczytelny w połowie zdania */
  .lb-shell::after{
    content:""; position:absolute; left:0; right:0; bottom:0; height:78px;
    background:linear-gradient(180deg, rgba(21,18,15,0) 0%, var(--bg-raise) 58%);
    pointer-events:none; z-index:2;
  }
  .lb-title{font-size:22px}
  .lb-nav{top:auto; bottom:14px; transform:none; width:44px; height:44px}
  .lb-prev{left:14px}
  .lb-next{right:14px}
  .lb-x{top:12px; right:12px}
  .lb-keys{display:none}
}
@media (max-width:720px){
  /* Pasek niższy o 6 px: przyklejone paski zjadają ekran, na którym mają
     stać skany. Do Etapu 16 stały tu DWA takie paski (nagłówek + filtry)
     i razem zabierały 14,6% ekranu telefonu. Od Etapu 17 zostaje jeden —
     filtry przeniosły się do szuflady (D-45, koniec tego pliku). */
  :root{--nav-h:42px}
  /* jedna kolumna na całą szerokość — gablota może urosnąć, bo skan
     dostaje całą szerokość ekranu i nie ma po co go dławić */
  :root{--stage-max:78vh}
  body{font-size:17px}
  .hero, .index-inner, .plates, .site-foot-inner{padding-left:20px; padding-right:20px}
  .plate-note{font-size:10.5px; line-height:1.8; margin-bottom:28px}
  .sg-bar-inner{padding-left:20px; padding-right:20px; gap:11px}
  /* NAZWA SERWISU SCHODZI Z PASKA NA TELEFONIE (Etap 17). W pasku stoją
     teraz dwa rozwijaki, nie jeden, i zabrakło miejsca: zmierzone przy
     390×844, nazwa bieżącej strony kurczyła się do 38 px, a potrzebowała
     67 px („Warszawa"), więc sześć z siedmiu stron pokazywało „Prz…".
     Po zdjęciu napisu zostaje jej 226 px — mieści się każda.
     Zostaje sam znak: on jest odsyłaczem na stronę główną (D-43), niesie
     nazwę w `aria-label`, a nazwa serwisu i tak stoi w karcie przeglądarki
     i w stopce. Na pulpicie napis zostaje. */
  .sg-word{display:none}
  .sg-home{padding:8px 6px; margin-left:-6px}
  .sg-here{font-size:14.5px}
  .sg-menu > summary, .ix-drawer > summary{font-size:12px; padding:6px 10px}
  /* TRZECI PRZYCISK W PASKU (Etap 27). Na stronie miejskiej stoją teraz
     „Filtry", „Szukaj" i „Miasta" — o jeden więcej, niż mierzył Etap 17.
     Na 390 px słowo „Szukaj" schodzi i zostaje samo szkło powiększające,
     dokładnie tak, jak wcześniej zeszła nazwa serwisu (`.sg-word`):
     ikona niesie znaczenie, `aria-label` niesie słowo dla czytnika ekranu,
     a nazwa bieżącej strony nie ma się z czym bić o miejsce. */
  .sg-szukaj{padding:6px 9px; gap:0}
  .sg-szukaj .sg-szukaj-txt{display:none}
  .sg-list{min-width:210px}
  .hero{padding-top:38px; padding-bottom:28px}
  .lede{font-size:18px}
  .hero-stats{gap:28px}
  /* Na pulpicie zdjęcie stoi obok wstępu, w pustym marginesie po prawej
     (patrz `.hero--foto` wyżej). Telefon tego marginesu nie ma — D-60
     rozstrzyga, że tam zdjęcie idzie NAD wstęp, nie obok niego. */
  .hero--foto{flex-direction:column; gap:20px}
  .hero-photo{order:-1; max-width:none}
  .plate-grid{grid-template-columns:1fr; gap:46px}

  /* SZUFLADA FILTRÓW NIE MA TU JUŻ WŁASNYCH REGUŁ. Od Etapu 17 (D-45)
     szuflada była telefoniczna i cały jej styl siedział w tym bloku;
     historia przewijaka, który zjadał gesty, jest opisana w D-45.
     Etap 23 (D-54) dał tę samą szufladę pulpitowi i reguły przeszły
     do części wspólnej arkusza — sekcja „filtry w szufladzie" wyżej.
     Tu zostają wyłącznie telefoniczne stopnie pisma. */
  .ix{font-size:15px}
  .index-row-era .ix{font-size:14px}
}

/* Wybrany filtr przy ZAMKNIĘTEJ szufladzie: bez tego dałoby się odfiltrować
   kolekcję, zamknąć szufladę i zapomnieć, dlaczego kart jest mniej.
   Nazwa działu i lat nie mieści się w pasku, więc sygnałem jest sam
   przycisk „Filtry" — w barwie patyny, tak jak zaznaczony filtr. */
body:has(.ix[data-cat].is-on:not([data-cat="*"])) .ix-drawer > summary,
body:has(.ix[data-era].is-on:not([data-era="*"])) .ix-drawer > summary{
  color:var(--pat); border-color:var(--pat-soft);
}

/* ---------- strony fotografów (Etap 19, D-48) ----------

   Strona fotografa ma cztery warstwy z czterech różnych źródeł i każda
   musi być rozpoznawalna: liczby policzone, fakty wycięte z kart,
   ustalenia właściciela ze źródłami i życiorys, którego jeszcze nie ma.
   Stąd `.brak` — zdanie o braku życiorysu nie może wyglądać jak treść. */

.brak{color:var(--ink-faint); font-style:italic}

.fg-blok{max-width:1320px; margin:0 auto; padding:0 32px 34px}
.fg-blok h2{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-weight:500; font-size:11px; letter-spacing:.16em; text-transform:uppercase;
  color:var(--ink-faint); padding-bottom:11px; margin:26px 0 18px;
  border-bottom:1px solid var(--line-soft);
}
.fg-tresc{max-width:70ch}
.fg-tresc p{margin:0 0 12px; color:var(--ink-soft)}
/* podnagłówki życiorysu (Etap 31): Jak pracował / Co po nim zostało /
   Wystawy i publikacje / Gdzie szukać dalej / Źródła */
.fg-tresc h3{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-weight:600; font-size:13.5px; letter-spacing:.02em;
  color:var(--ink); margin:22px 0 8px;
}
.fg-tresc h3:first-child{margin-top:0}
.fg-tresc .fg-zrodla{margin:0}
.fg-zrodla{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:12.5px; color:var(--ink-faint);
}
.fg-nota{
  max-width:70ch; margin:0 0 18px;
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:12.5px; line-height:1.7; color:var(--ink-faint);
}

/* fakty z kart: nazwa po lewej, treść po prawej, na telefonie jedno pod drugim */
.fg-fakty{
  display:grid; grid-template-columns:minmax(150px, 210px) 1fr;
  gap:9px 26px; margin:0; max-width:96ch;
}
.fg-fakty dt{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:11.5px; letter-spacing:.06em; text-transform:uppercase;
  color:var(--ink-faint); padding-top:3px;
}
.fg-fakty dd{margin:0; color:var(--ink)}

/* znak zakładu — CAŁE rewersy, nigdy wycinek (WYMAGANIA 21, Z-39) */
.fg-znaki{
  display:grid; grid-template-columns:repeat(auto-fill, minmax(190px, 1fr));
  gap:22px;
}
.fg-znaki figure{margin:0}
.fg-znaki img{
  width:100%; height:auto; display:block;
  background:var(--mat); padding:6px;
  outline:1px solid var(--mat-edge); box-shadow:var(--shadow-card);
}
.fg-znaki figcaption{
  margin-top:7px;
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:11px; letter-spacing:.05em; color:var(--ink-faint);
}

/* spis kart */
.fg-karty{list-style:none; margin:0; padding:0; max-width:96ch}
.fg-karty li{border-bottom:1px solid var(--line-soft)}
.fg-karty a, .fg-karty li.fg-bez{
  display:flex; align-items:baseline; gap:8px 20px; flex-wrap:wrap;
  padding:11px 4px; text-decoration:none; color:inherit;
  transition:background .18s ease;
}
.fg-karty a:hover{background:rgba(201,169,97,.09); color:var(--pat-soft)}
.fg-syg{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:11.5px; letter-spacing:.05em; color:var(--ink-faint);
  flex:0 0 96px; font-variant-numeric:tabular-nums;
}
.fg-tyt{flex:1 1 260px; min-width:0; font-size:16.5px; line-height:1.35}
.fg-mia{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif;
  font-size:11.5px; color:var(--ink-faint); flex:0 0 auto;
}
.fg-bez .fg-tyt{color:var(--ink-faint); font-style:italic; font-size:15px}

/* odsyłacz przy nazwisku na karcie kolekcji */
.pc-autor{color:inherit; text-decoration:none; border-bottom:1px solid var(--pat-dim)}
.pc-autor:hover{color:var(--pat); border-bottom-color:var(--pat-soft)}

@media (max-width:720px){
  .fg-blok{padding-left:20px; padding-right:20px}
  .fg-fakty{grid-template-columns:1fr; gap:2px 0}
  .fg-fakty dd{margin-bottom:12px}
  .fg-znaki{grid-template-columns:repeat(auto-fill, minmax(150px, 1fr)); gap:16px}
  .fg-syg{flex-basis:100%}
}

/* ---------- spis pozycji z liczbami (spis fotografów) ----------
   USTERKA SPRZED TEJ ZMIANY, znaleziona 29.08.2026 przy przeglądzie
   serwisu. Strona `/fotograf/` (spis wszystkich fotografów) używa tej
   samej budowy listy co strona główna — klasy `.miasta`, `.m`,
   `.m-nazwa`, `.m-liczby`, `.m-strzalka` — ale ładuje SKÓRĘ WSPÓLNĄ,
   która ich nie znała. Efekt: goła lista z kropkami i podkreśleniami,
   nazwisko sklejone z liczbą kart. Sprawdzone: tak samo wyglądało na
   żywej stronie, więc to nie skutek przemalowania na ciemno.

   Reguły są przeniesione ze skóry strony głównej co do wartości —
   celowo, żeby oba spisy wyglądały identycznie i żeby nie powstał
   trzeci wariant tej samej listy. */
.miasta{max-width:1320px; margin:0 auto; padding:0 32px 10px}
.miasta h2{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-weight:500; font-size:11.5px;
  letter-spacing:.16em; text-transform:uppercase; color:var(--ink-faint);
  padding-bottom:11px; border-bottom:1px solid var(--line-soft); margin-bottom:0;
}
.miasta-lista{list-style:none; margin:0; padding:0}
.miasta-lista li{border-bottom:1px solid var(--line-soft)}
.m{
  display:flex; align-items:baseline; gap:18px; flex-wrap:wrap;
  padding:19px 4px; text-decoration:none; color:inherit;
  transition:background .18s ease, padding .18s ease;
}
.m:hover, .m:focus-visible{background:rgba(201,169,97,.09); padding-left:12px}
.m-nazwa{
  font-family:"Old Standard TT", serif; font-weight:700; font-style:italic;
  font-size:27px; line-height:1.1; color:var(--ink); flex:0 0 auto;
}
.m:hover .m-nazwa{color:var(--pat)}
.m-liczby{
  font-weight:500; font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:12.5px; letter-spacing:.1em;
  text-transform:uppercase; color:var(--ink-faint); flex:1 1 auto;
}
.m-strzalka{
  font-family:"Inter", system-ui, -apple-system, "Segoe UI", sans-serif; font-size:12.5px; color:var(--pat-soft);
  flex:0 0 auto;
}
@media (max-width:640px){
  .miasta{padding:0 18px 8px}
  .m{padding:15px 2px; gap:10px}
  .m-nazwa{font-size:22px}
}

/* ---------- zaproszenie na serwis siostrzany ----------
   Stoi nad wszystkim na stronie Rzeszowa. Powód: strona pokazuje 22 karty,
   a katalog ma ich 51 — różnicę stanowi dorobek atelier „E. Janusz", który
   ma własny serwis. Bez tego bloku widz widział po prostu ubogą stronę
   i nie miał skąd wiedzieć, gdzie jest reszta. */
.zapro{
  max-width:1320px; margin:0 auto; padding:22px 32px 0;
}
.zapro-link{
  display:grid; grid-template-columns:minmax(0,300px) minmax(0,1fr);
  gap:clamp(18px,3vw,34px); align-items:center;
  text-decoration:none; color:inherit;
  border:1px solid var(--line-strong); border-radius:var(--radius);
  background:linear-gradient(120deg, rgba(201,169,97,.07), transparent 62%), var(--bg-deep);
  padding:clamp(16px,2.4vw,26px);
  transition:border-color .22s ease, background .22s ease;
}
.zapro-link:hover{border-color:var(--pat-soft)}
.zapro-foto{display:block; overflow:hidden; border-radius:var(--radius); background:var(--mat)}
.zapro-foto img{display:block; width:100%; height:auto}
.zapro-tresc{display:flex; flex-direction:column; gap:8px; min-width:0}
.zapro-nad{
  font-family:"Inter", system-ui, sans-serif; font-weight:500; font-size:11px;
  letter-spacing:.16em; text-transform:uppercase; color:var(--pat);
}
.zapro-tytul{
  font-family:"Old Standard TT", Georgia, serif; font-weight:700; font-style:italic;
  font-size:clamp(20px,2.4vw,28px); line-height:1.18; color:var(--ink);
}
.zapro-opis{color:var(--ink-soft); font-size:15px; line-height:1.6}
.zapro-akcja{
  font-family:"Inter", system-ui, sans-serif; font-weight:500; font-size:12.5px;
  letter-spacing:.08em; color:var(--pat-soft); margin-top:4px;
}
.zapro-link:hover .zapro-akcja{color:var(--pat)}
@media (max-width:760px){
  .zapro{padding:16px 18px 0}
  .zapro-link{grid-template-columns:1fr; gap:14px}
}
