/* ============================================================
   LabCeny — demo makiety porównywarki badań
   4 palety kolorystyczne (przełącznik w prawym dolnym rogu).
   Domyślna: mięta. Warianty: [data-palette="blue|slate|coral"].
   ============================================================ */

:root {
  /* --- PALETA 1: Mięta (teal) --- */
  --ground:#F5F8F9; --surface:#FFFFFF; --surface-2:#F0F5F6;
  --ink:#0F2A31; --ink-2:#47616A; --ink-3:#7E959C;
  --border:#E1EAED; --border-2:#D2DFE3;
  --accent:#0C8C86; --accent-ink:#0A6F6A; --accent-soft:#E4F3F1;
  --save:#158A46; --save-soft:#E4F4EA; --save-cell:#EDF8F1;
  --promo:#D2610F; --promo-soft:#FBEEE1;

  --shadow:0 1px 2px rgba(15,42,49,.05), 0 8px 24px -12px rgba(15,42,49,.14);
  --shadow-lg:0 1px 2px rgba(15,42,49,.06), 0 20px 44px -20px rgba(15,42,49,.24);
  --radius:14px;
  --font:"Segoe UI Variable Display","Segoe UI",-apple-system,BlinkMacSystemFont,system-ui,Roboto,Helvetica,Arial,sans-serif;
  --maxw:1080px;
}

/* --- PALETA 2: Błękit medyczny (biało-niebieska), neutrale z odcieniem granatu --- */
[data-palette="blue"] {
  --ground:#F4F7FC; --surface:#FFFFFF; --surface-2:#EDF3FB;
  --ink:#0F2547; --ink-2:#46586F; --ink-3:#8091A8;
  --border:#E2E9F3; --border-2:#CFDCEC;
  --accent:#2563EB; --accent-ink:#1D4FD0; --accent-soft:#E6EDFD;
  --save:#128A43; --save-soft:#E3F4E9; --save-cell:#ECF7F0;
  --promo:#C85A10; --promo-soft:#FBEDE0;
  --shadow:0 1px 2px rgba(15,37,71,.06), 0 8px 24px -12px rgba(15,37,71,.16);
  --shadow-lg:0 1px 2px rgba(15,37,71,.07), 0 20px 44px -20px rgba(15,37,71,.26);
}

/* --- PALETA 3: Grafit (biało-szara), czyste chłodne szarości + grafitowy akcent --- */
[data-palette="slate"] {
  --ground:#F6F7F8; --surface:#FFFFFF; --surface-2:#EFF1F3;
  --ink:#1A2126; --ink-2:#4B5560; --ink-3:#828C96;
  --border:#E5E7EA; --border-2:#D6DADE;
  --accent:#25313B; --accent-ink:#131C23; --accent-soft:#EDF0F2;
  --save:#137A3D; --save-soft:#E5F3EA; --save-cell:#EEF6F0;
  --promo:#C05A18; --promo-soft:#F9ECE1;
  --shadow:0 1px 2px rgba(26,33,38,.06), 0 8px 24px -12px rgba(26,33,38,.16);
  --shadow-lg:0 1px 2px rgba(26,33,38,.07), 0 20px 44px -20px rgba(26,33,38,.24);
}

/* --- PALETA 4: Koral (ciepła, nowoczesna), ciepłe szarości, kod rabatowy w śliwce --- */
[data-palette="coral"] {
  --ground:#FAF7F5; --surface:#FFFFFF; --surface-2:#F5EFEC;
  --ink:#2A211D; --ink-2:#6B5A52; --ink-3:#A2938B;
  --border:#EDE5E0; --border-2:#E0D5CE;
  --accent:#E15A47; --accent-ink:#C6412F; --accent-soft:#FCE9E5;
  --save:#188A50; --save-soft:#E4F4EB; --save-cell:#EDF8F0;
  --promo:#8A3FA6; --promo-soft:#F3E9F8;
  --shadow:0 1px 2px rgba(42,33,29,.06), 0 8px 24px -12px rgba(42,33,29,.16);
  --shadow-lg:0 1px 2px rgba(42,33,29,.07), 0 20px 44px -20px rgba(42,33,29,.24);
}

* { box-sizing:border-box; }
html { scroll-behavior:smooth; }
/* UWAGA na `body:not(.labceny-strona)` w tym pliku (dodane 2026-09-04):
   ten arkusz jest WSPÓŁDZIELONY przez demo-www (samodzielna makieta, gdzie
   <header>/<main>/<footer> to NASZE elementy) i wtyczkę WP (gdzie te same
   znaczniki należą do motywu Astra!). Bez tego zawężenia nasze reguły dla
   `header`, `main`, `footer` łapały elementy Astry - np. tytuł strony
   (<header class="entry-header">) robił się przyklejony i półprzezroczysty,
   co wyglądało jak przypadkowy biały pasek. Klasę `labceny-strona` dokłada
   wtyczka tylko na stronach z porównywarką, więc:
     - demo (brak klasy)  -> reguły działają jak dotąd,
     - WordPress (klasa jest) -> ruszamy WYŁĄCZNIE to, co w .labceny-app. */
body:not(.labceny-strona) { margin:0; font-family:var(--font); background:var(--ground); color:var(--ink); line-height:1.5; -webkit-font-smoothing:antialiased; }
.wrap { max-width:var(--maxw); margin:0 auto; padding:0 20px; }
button { font-family:inherit; cursor:pointer; }
/* `a{color:inherit}` bez zawężenia odbierało kolor WSZYSTKIM linkom Astry
   (menu, stopka) na naszych stronach - stąd .labceny-app przed spodem. */
body:not(.labceny-strona) a, .labceny-app a { color:inherit; }
img { max-width:100%; }
:focus-visible { outline:2px solid var(--accent); outline-offset:2px; border-radius:4px; }

/* ---------- header ---------- */
body:not(.labceny-strona) header { position:sticky; top:0; z-index:50; background:color-mix(in srgb, var(--surface) 88%, transparent); backdrop-filter:saturate(1.4) blur(10px); border-bottom:1px solid var(--border); }
.bar { display:flex; align-items:center; gap:16px; height:64px; }
.logo { display:flex; align-items:center; gap:9px; font-weight:700; font-size:20px; letter-spacing:-.02em; text-decoration:none; white-space:nowrap; color:var(--ink); }
.logo .mark { width:30px; height:30px; border-radius:9px; display:grid; place-items:center; background:linear-gradient(145deg,var(--accent),var(--accent-ink)); color:#fff; font-size:17px; }
.logo b { color:var(--accent-ink); }
nav.main { display:flex; gap:22px; margin-left:auto; font-size:14.5px; color:var(--ink-2); }
nav.main a { text-decoration:none; }
nav.main a.on { color:var(--accent-ink); font-weight:600; }
nav.main a:hover { color:var(--ink); }
.login { margin-left:4px; border:1px solid var(--border-2); background:var(--surface); color:var(--ink); padding:8px 14px; border-radius:10px; font-size:14px; font-weight:600; text-decoration:none; white-space:nowrap; }
.login:hover { border-color:var(--accent); color:var(--accent-ink); }
@media (max-width:820px){ nav.main{ display:none; } }

/* ============================================================
   OSADZENIE W WORDPRESSIE (Astra) - odtworzenie wyglądu z demo-www
   ============================================================
   W demie tłem CAŁEJ strony był delikatny odcień (--ground), a białe karty
   ofert leżały na nim - dzięki temu było widać ich krawędzie i cienie.
   Po przeniesieniu do WP reguła `body{background:var(--ground)}` wyżej
   przegrywa z Astrą (białe body), więc karty robiły się BIAŁE NA BIAŁYM =
   "pusto" (user, 2026-09-04). Klasę `labceny-strona` dokłada do <body>
   wtyczka (labceny_klasa_body) TYLKO na stronach z naszym shortcode - strony
   informacyjne (Kontakt, Regulamin) zostają normalne, białe.
   Sprawdzone na żywej stronie: wszystkie kontenery Astry między <body>
   a .labceny-app są przezroczyste, więc wystarczy pomalować samo <body>.
   (W demo-www te dwie reguły są nieużywane - demo ma własny <body> i .wrap -
   ale plik musi zostać IDENTYCZNY z kopią we wtyczce, taka jest konwencja.) */
body.labceny-strona { background:var(--ground); }

/* Kontener aplikacji. W demie odpowiadał mu `.wrap` (max 1080px + padding);
   przy przenoszeniu do wtyczki ta reguła nie powstała w ogóle, więc treść
   rozjeżdżała się na całą szerokość Astry (1200px) i przylegała do krawędzi. */
.labceny-app {
  max-width:var(--maxw); margin:0 auto; padding:24px;
  /* Typografia, którą w demie dawał `body` - tu podana wprost, bo regułę dla
     body zawęziliśmy wyżej, żeby nie nadpisywała czcionek całego motywu. */
  font-family:var(--font); color:var(--ink); line-height:1.5; -webkit-font-smoothing:antialiased;
}

/* ---------- search band ---------- */
.searchband { background:var(--surface); border-bottom:1px solid var(--border); padding:22px 0; }
/* Wtyczka: bez białego pasa - w kolumnie Astry wisiał jako osobny prostokąt wokół wyszukiwarki (audyt UX 2026-09-12). */
.searchband-bleed { background:transparent; border-bottom:0; padding:0; margin:0 0 20px; }
@media (max-width:600px){
  .labceny-app { padding:14px; }
  .searchband-bleed { margin:0 0 16px; }
}
.searchform { display:grid; grid-template-columns:2fr 1fr auto; gap:10px; background:var(--surface); border:1px solid var(--border-2); border-radius:16px; padding:8px; box-shadow:var(--shadow); }
.field { display:flex; align-items:center; gap:10px; padding:8px 12px; border-radius:11px; }
.field:hover { background:var(--surface-2); }
.field .ic { color:var(--ink-3); font-size:17px; }
/* "Badanie"/"Miasto" - user 2026-09-01: zbędne, ikonka + placeholder ("np.
   morfologia..."/"np. Warszawa") już mówią, o co chodzi. Zostawione w DOM
   (nie usunięte) dla czytników ekranu - to prawdziwe <label for="">,
   wizualnie tylko schowane (standardowy wzorzec "sr-only"), nie zniknęła
   dostępność, zniknął tylko wizualny szum. */
.field label { position:absolute; width:1px; height:1px; padding:0; margin:-1px; overflow:hidden; clip:rect(0,0,0,0); white-space:nowrap; border:0; }
.field .val { font-size:16px; font-weight:600; color:var(--ink); }
.field + .field { border-left:1px solid var(--border); }
.go { border:0; background:linear-gradient(145deg,var(--accent),var(--accent-ink)); color:#fff; font-weight:700; font-size:15px; padding:0 24px; border-radius:11px; display:flex; align-items:center; justify-content:center; gap:8px; text-decoration:none; }
.go:hover { filter:brightness(1.06); }
@media (max-width:680px){
  .searchform { grid-template-columns:1fr; }
  .field + .field { border-left:0; border-top:1px solid var(--border); }
  .go { padding:14px; }
}

/* ---------- results head ---------- */
body:not(.labceny-strona) main { padding:26px 0 60px; }
.crumbs { font-size:13px; color:var(--ink-3); margin-bottom:14px; }
.crumbs a { text-decoration:none; }
.crumbs a:hover { color:var(--accent-ink); }
.rhead { display:flex; align-items:flex-end; justify-content:space-between; gap:20px; flex-wrap:wrap; margin-bottom:6px; }
/* h1 jest NASZ (tytuł wyników) i w demie, i we wtyczce - ale w WP musi być
   zawężony do .labceny-app, żeby nie przejmować tytułu strony z Astry. */
body:not(.labceny-strona) h1, .labceny-app h1 { font-size:clamp(24px,4vw,33px); letter-spacing:-.025em; margin:0; text-wrap:balance; }
/* #tytul-wynikow zmienione z h1 na h2 (audyt SEO 2026-09-15, jeden H1 na stronę) - ten sam wygląd co h1 wyżej. */
.rhead h2#tytul-wynikow { font-size:clamp(24px,4vw,33px); letter-spacing:-.025em; margin:0; text-wrap:balance; }
body:not(.labceny-strona) h1 span, .labceny-app h1 span { color:var(--accent-ink); }
.meta { display:flex; gap:16px; flex-wrap:wrap; font-size:13px; color:var(--ink-2); margin:10px 0 4px; align-items:center; }
.meta .dot { width:3px; height:3px; border-radius:50%; background:var(--ink-3); }
.meta b { color:var(--ink); }
/* Astra wypisuje własny <h1 class="entry-title"> z tytułem strony ("Badania",
   "Koszyk badań"), a zaraz pod nim stoi PRAWDZIWY nagłówek aplikacji
   ("Morfologia krwi — ceny w Warszawie"). Efekt: dwa H1 na stronie (źle dla
   czytników ekranu i dla Google) plus na telefonie cały ekran zjedzony przez
   napis, który nic nie wnosi - użytkownik przewijał półtora ekranu, zanim
   zobaczył cenę. Chowamy TYLKO na stronach z porównywarką; Kontakt czy
   Regulamin swój tytuł zachowują. */
.labceny-strona .entry-title,
.labceny-strona .ast-single-entry-banner { display:none !important; }

.fresh { display:inline-flex; align-items:center; gap:6px; }
.fresh::before { content:""; width:7px; height:7px; border-radius:50%; background:var(--save); box-shadow:0 0 0 3px var(--save-soft); }
.sort { display:flex; gap:7px; align-items:center; font-size:13px; color:var(--ink-2); flex-wrap:wrap; }
.chip { border:1px solid var(--border-2); background:var(--surface); padding:6px 12px; border-radius:999px; font-size:13px; font-weight:600; color:var(--ink-2); cursor:pointer; }
.chip.on { background:var(--accent-soft); border-color:transparent; color:var(--accent-ink); }

.disclaimer { margin:16px 0 22px; font-size:12.5px; color:var(--ink-2); background:var(--surface-2); border:1px solid var(--border); border-radius:10px; padding:10px 14px; display:flex; gap:9px; align-items:flex-start; }
.disclaimer a { color:var(--accent-ink); }

/* ---------- offer cards ---------- */
.offers { display:flex; flex-direction:column; gap:14px; }
.offer { position:relative; background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); box-shadow:var(--shadow); display:grid; grid-template-columns:190px 1fr 250px; overflow:hidden; }
.offer.best { border-color:color-mix(in srgb, var(--save) 55%, var(--border)); box-shadow:var(--shadow-lg); }
.ribbon { position:absolute; top:0; left:0; background:var(--save); color:#fff; font-size:11px; font-weight:700; letter-spacing:.04em; text-transform:uppercase; padding:4px 12px 4px 14px; border-bottom-right-radius:12px; }
.brand { padding:26px 20px 20px; border-right:1px solid var(--border); display:flex; flex-direction:column; gap:10px; }
.brand .lab { display:flex; align-items:center; gap:10px; }
.badge { border-radius:10px; display:grid; place-items:center; font-weight:800; color:#fff; }
.brand .badge { width:40px; height:40px; font-size:15px; }
.b-alab { background:#0090D4; } .b-diag { background:#005144; } .b-syn { background:#1B3A6B; }
.brand .name { font-weight:700; font-size:16px; }
.brand .subname { font-size:11.5px; color:var(--ink-3); margin-top:1px; max-width:150px; line-height:1.3; }
.stars { font-size:12.5px; color:var(--ink-2); display:flex; align-items:center; gap:5px; }
.stars b { color:var(--ink); }
.brand .tag { font-size:12px; color:var(--ink-3); }

.detail { padding:20px; display:flex; flex-direction:column; gap:11px; justify-content:center; }
.drow { display:flex; gap:9px; font-size:13.5px; color:var(--ink-2); align-items:flex-start; }
.drow .ic { width:17px; text-align:center; color:var(--ink-3); flex:none; margin-top:1px; }
.drow b { color:var(--ink); font-weight:600; }
.feetxt { color:var(--ink-3); font-size:12.5px; }

.buy { padding:20px; border-left:1px solid var(--border); display:flex; flex-direction:column; align-items:flex-end; justify-content:center; gap:4px; text-align:right; }
.code { display:inline-flex; align-items:center; gap:6px; background:var(--promo-soft); color:var(--promo); border:1px dashed color-mix(in srgb, var(--promo) 45%, transparent); font-weight:700; font-size:12px; padding:3px 9px; border-radius:7px; margin-bottom:4px; }
.old { font-size:14px; color:var(--ink-3); text-decoration:line-through; }
.row-price { display:flex; align-items:baseline; gap:10px; justify-content:flex-end; }
.price { font-size:30px; font-weight:800; letter-spacing:-.02em; font-variant-numeric:tabular-nums; line-height:1; }
.price small { font-size:15px; font-weight:700; color:var(--ink-2); }
.price.win { color:var(--save); }
.cart-note { font-size:11.5px; color:var(--ink-3); max-width:210px; }
.cart-note b { color:var(--ink-2); }

/* color/text-decoration z !important ponizej (2026-09-17) - user zlapal na
   zywo, ze "Otworz porownywarke koszyka" (link-koszyk, class-shortcodes.php)
   mial czarny tekst i podkreslenie zamiast bialego/bez podkreslenia jak reszta
   przyciskow .cta. Przyczyna: to <a>, nie <button> - motyw Astra narzuca
   wlasny globalny styl linkow (kolor+podkreslenie) silniejszy niz .cta bez
   !important. Ten sam mechanizm juz raz naprawiony w tym pliku dla
   .step-kup/.kw-kopiuj (patrz nizej) - dotyczy WSZYSTKICH <a class="cta">
   w tej wtyczce (m.in. "Kup w X", "Znajdz placowke", "Policz caly koszyk"),
   nie tylko tego jednego linku, wiec naprawione u zrodla klasy. */
.cta { display:inline-flex; align-items:center; justify-content:center; gap:8px; background:var(--accent); color:#fff !important; font-weight:700; font-size:14.5px; padding:11px 20px; border-radius:10px; text-decoration:none !important; border:0; }
.cta:hover { background:var(--accent-ink); }
.cta.block { width:100%; padding:11px; }
.cta.ghost { background:var(--surface); color:var(--accent-ink) !important; border:1px solid var(--border-2); }
.cta.ghost:hover { border-color:var(--accent); background:var(--surface); }
.addcart { margin-top:8px; font-size:12.5px; color:var(--accent-ink); text-decoration:none; font-weight:600; }
.addcart:hover { text-decoration:underline; }
/* "od" przed ceną, gdy placówki miasta mają różne ceny (silnik.js: opisRozjazdu) */
.od-cena { font-size:.62em; font-weight:500; color:var(--ink-3); margin-right:2px; letter-spacing:0; }
.rozjazd-cen a { color:var(--accent-ink); }

/* Kwota, którą klient NAPRAWDĘ zapłaci (cena + pobranie). Wcześniej na karcie
   była tylko cena badania, a opłata za pobranie wisiała małym szarym drukiem
   w innej kolumnie - przy morfologii w Warszawie wyglądało to na 14,40 vs
   28,00 (2x taniej), a realnie jest 25,40 vs 36,00. */
.razem-box { display:flex; flex-direction:column; align-items:flex-end; gap:1px; margin-top:8px; padding:8px 12px; border-radius:10px; background:var(--surface-2); width:100%; }
.razem-box.razem-win { background:var(--save-soft); }
.razem-l { font-size:11px; text-transform:uppercase; letter-spacing:.06em; font-weight:700; color:var(--ink-3); }
.razem-box.razem-win .razem-l { color:var(--save); }
.razem-k { font-size:20px; font-weight:800; letter-spacing:-.02em; font-variant-numeric:tabular-nums; line-height:1.15; }
.razem-box.razem-win .razem-k { color:var(--save); }
.razem-s { font-size:11.5px; color:var(--ink-3); }

@media (max-width:820px){
  .offer { grid-template-columns:1fr; }
  .brand { flex-direction:row; align-items:center; justify-content:space-between; border-right:0; border-bottom:1px solid var(--border); padding:16px 18px; }
  /* Miejsce na .ribbon (position:absolute, ~25px wysokości) TYLKO w karcie,
     która ją ma - przy 16px wstążka "✓ Najtańsze" nachodziła na logo sieci
     i jej nazwę. Na desktopie robi to 26px z reguły bazowej wyżej, ale tam
     .brand jest osobną kolumną, więc problem nie był widoczny. */
  .offer.best .brand { padding-top:34px; }
  .detail { border-bottom:1px solid var(--border); padding:16px 18px; }
  .buy { border-left:0; align-items:stretch; text-align:left; padding:16px 18px; }
  .row-price { justify-content:flex-start; }
  .cart-note { max-width:none; }
}

/* ---------- feature panels (results) ---------- */
.grid2 { display:grid; grid-template-columns:1.3fr 1fr; gap:16px; margin-top:30px; }
@media (max-width:820px){ .grid2 { grid-template-columns:1fr; } }
.panel { background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); padding:22px; box-shadow:var(--shadow); }
.panel h2 { font-size:18px; margin:0 0 4px; letter-spacing:-.02em; }
p.sub { margin:0 0 16px; font-size:13.5px; color:var(--ink-2); }
.kicker { font-size:11px; text-transform:uppercase; letter-spacing:.09em; font-weight:700; color:var(--accent-ink); margin-bottom:8px; }

.cartline { display:flex; align-items:center; justify-content:space-between; padding:9px 0; border-top:1px solid var(--border); font-size:14px; }
.cartline:first-of-type { border-top:0; }
.cartline .lab-mini { display:flex; align-items:center; gap:9px; font-weight:600; }
.mini { width:22px; height:22px; border-radius:6px; flex:none; }
.cartline .sum { font-variant-numeric:tabular-nums; font-weight:700; }
.cartline.win { color:var(--save); }
.flag { font-size:11px; background:var(--save-soft); color:var(--save); font-weight:700; padding:2px 8px; border-radius:6px; margin-left:8px; }

.alert-in { display:flex; gap:8px; margin-top:6px; }
.alert-in input { flex:1; min-width:0; border:1px solid var(--border-2); background:var(--ground); border-radius:10px; padding:11px 13px; font-size:14px; color:var(--ink); font-family:inherit; }
.alert-in input::placeholder { color:var(--ink-3); }
.alert-in button { border:0; background:var(--accent); color:#fff; font-weight:700; padding:0 18px; border-radius:10px; font-size:14px; }
.alert-in button:hover { background:var(--accent-ink); }
.consent { font-size:11.5px; color:var(--ink-3); margin-top:10px; display:flex; gap:7px; align-items:flex-start; }
.alert-deadline { margin-top:10px; display:flex; align-items:center; gap:8px; flex-wrap:wrap; font-size:12.5px; color:var(--ink-2); }
.alert-deadline input { border:1px solid var(--border-2); background:var(--ground); border-radius:8px; padding:7px 10px; font-size:13px; color:var(--ink); font-family:inherit; }
.consent a { color:var(--accent-ink); }

.related { display:flex; flex-wrap:wrap; gap:8px; margin-top:26px; }
.related a { text-decoration:none; font-size:13.5px; color:var(--ink-2); background:var(--surface); border:1px solid var(--border); padding:8px 13px; border-radius:999px; }
.related a:hover { border-color:var(--accent); color:var(--accent-ink); }
.sec-label { font-size:12px; text-transform:uppercase; letter-spacing:.08em; color:var(--ink-3); font-weight:700; margin:34px 0 0; }

/* ---------- anti-scrape notice ---------- */
.guard { margin-top:30px; border:1px solid color-mix(in srgb, var(--promo) 30%, var(--border)); background:linear-gradient(180deg, var(--promo-soft), var(--surface)); border-radius:var(--radius); padding:20px 22px; display:flex; gap:15px; align-items:flex-start; }
.guard .shield { font-size:26px; line-height:1; flex:none; }
.guard h3 { margin:0 0 5px; font-size:15.5px; }
.guard p { margin:0; font-size:13px; color:var(--ink-2); max-width:70ch; }
.guard a { color:var(--accent-ink); }
.guard code { background:var(--surface-2); border:1px solid var(--border); border-radius:5px; padding:1px 6px; font-size:12px; }

/* ---------- footer ---------- */
body:not(.labceny-strona) footer { border-top:1px solid var(--border); background:var(--surface); margin-top:20px; }
.fgrid { display:grid; grid-template-columns:1.4fr 1fr 1fr 1fr; gap:28px; padding:40px 0 26px; }
@media (max-width:760px){ .fgrid { grid-template-columns:1fr 1fr; gap:24px; } }
.fcol h4 { font-size:12px; text-transform:uppercase; letter-spacing:.08em; color:var(--ink-3); margin:0 0 12px; }
.fcol a { display:block; text-decoration:none; color:var(--ink-2); font-size:14px; margin-bottom:9px; }
.fcol a:hover { color:var(--accent-ink); }
.fcol p { font-size:13px; color:var(--ink-2); margin:0 0 12px; }
.fbot { border-top:1px solid var(--border); padding:16px 0; display:flex; justify-content:space-between; gap:14px; flex-wrap:wrap; align-items:center; font-size:12.5px; color:var(--ink-3); }
.noscrape { display:inline-flex; align-items:center; gap:8px; background:var(--surface-2); border:1px solid var(--border); border-radius:8px; padding:6px 12px; color:var(--ink-2); font-weight:600; }
.noscrape .d { width:7px; height:7px; border-radius:50%; background:var(--promo); }

/* ============================================================
   KOSZYK
   ============================================================ */
.lead { color:var(--ink-2); font-size:14px; margin:0 0 22px; }
.lead b { color:var(--ink); }
.cols { display:grid; grid-template-columns:300px 1fr; gap:20px; align-items:start; }
/* min-width:0 na dzieciach grida - bez tego element-dziecko nie kurczy się
   poniżej szerokości swojej NAJDŁUŻSZEJ treści (domyślne min-width:auto w
   CSS Grid), co na wąskich telefonach wypychało CAŁĄ stronę w poziomy
   scroll (znalezione 2026-09-01 przy przeglądzie pod kątem "petarda,
   szybko i przyjemnie" - realny bug na mobile, nie tylko na desktopie). */
.cols > * { min-width:0; }
@media (max-width:900px){ .cols { grid-template-columns:1fr; } }

.basket { background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); box-shadow:var(--shadow); padding:18px; position:sticky; top:80px; }
.basket h2 { font-size:15px; margin:0 0 4px; letter-spacing:-.01em; }
.basket .cnt { font-size:12.5px; color:var(--ink-3); margin-bottom:14px; display:flex; align-items:center; gap:8px; flex-wrap:wrap; }
.adder { display:flex; align-items:center; gap:8px; border:1px dashed var(--border-2); border-radius:10px; padding:10px 12px; color:var(--ink-3); font-size:13.5px; margin-bottom:14px; }
.adder input { border:0; background:transparent; outline:none; font-family:inherit; font-size:13.5px; color:var(--ink); width:100%; }
.item { display:flex; align-items:flex-start; gap:10px; padding:11px 0; border-top:1px solid var(--border); }
.item:first-of-type { border-top:0; }
.item .x { border:0; background:var(--surface-2); color:var(--ink-3); width:22px; height:22px; border-radius:6px; font-size:13px; line-height:1; flex:none; }
.item .x:hover { background:var(--promo-soft); color:var(--promo); }
.item .nm { font-weight:600; font-size:14px; }
/* "Jak się przygotować" - zasady dla całej wizyty, nie dla pojedynczego
   badania. Najważniejsze wiersze (na czczo, pora dnia) dostają .pw-mocny. */
/* Przycisk "do góry" z Astry siedzi w prawym dolnym rogu i na telefonie
   potrafi przykryć kwotę "Zapłacisz razem" albo kartę sieci - czyli
   dokładnie tę liczbę, po którą człowiek tu przyszedł. Nie usuwamy go
   (na tych długich stronach jest przydatny), tylko wyciszamy: przezroczysty,
   gdy się z niego nie korzysta, pełny po dotknięciu/najechaniu. */
#ast-scroll-top { opacity:.28; transition:opacity .18s ease; }
#ast-scroll-top:hover, #ast-scroll-top:focus { opacity:1; }
@media (max-width:768px){
  #ast-scroll-top { transform:scale(.82); transform-origin:bottom right; }
}

/* Zwijane paski "Co to za badanie?" i "Jak się przygotować" NAD ofertami
   (2026-09-21, user: "jak Ceneo"). Zwinięty pasek = ok. 44 px zamiast 270 px
   opisu i 506 px przygotowania. Natywne <details>, ten sam markup w widoku
   JS (app-widok-v11.js) i na stronach /cena/ (szablon-strona-ceny.php).
   Cel dotyku min. 44 px - to jest strona głównie z telefonu. */
.zwin { margin-top:8px; background:var(--surface); border:1px solid var(--border); border-radius:12px; }
.zwin > summary { list-style:none; cursor:pointer; display:flex; align-items:center; justify-content:space-between; gap:10px; min-height:44px; padding:10px 14px; font-size:14px; font-weight:600; color:var(--ink); border-radius:12px; }
.zwin > summary::-webkit-details-marker { display:none; }
.zwin > summary::after { content:"▾"; flex:none; color:var(--ink-3); transition:transform .15s ease; }
.zwin[open] > summary::after { transform:rotate(180deg); }
.zwin > summary:focus-visible { outline:2px solid var(--accent-ink); outline-offset:2px; }
.zwin-tresc { padding:0 14px 14px; font-size:14px; line-height:1.65; color:var(--ink-2); }
.zwin-tresc p { margin:0; }
.zwin-zrodlo { margin-top:8px; font-size:11.5px; color:var(--ink-3); }
@media (prefers-reduced-motion:reduce){ .zwin > summary::after { transition:none; } }

.przyg-wizyty { margin-top:14px; padding-top:13px; border-top:1px solid var(--border); }
.pw-h { font-size:11px; text-transform:uppercase; letter-spacing:.09em; font-weight:700; color:var(--accent-ink); margin-bottom:9px; }
.przyg-wizyty ul { margin:0; padding:0; list-style:none; display:flex; flex-direction:column; gap:9px; }
.przyg-wizyty li { display:flex; gap:9px; font-size:12.5px; color:var(--ink-2); line-height:1.5; align-items:flex-start; }
.przyg-wizyty .pw-ic { flex:none; width:17px; text-align:center; margin-top:1px; }
.przyg-wizyty li b { color:var(--ink); }
.przyg-wizyty .pw-mocny { background:var(--promo-soft); border-radius:9px; padding:9px 11px; color:var(--ink-2); }
.przyg-wizyty .pw-mocny b { color:var(--promo); }

.item .opisik { font-size:12px; color:var(--ink-2); margin-top:3px; line-height:1.45; }
.item .cheap { font-size:11.5px; color:var(--ink-3); margin-top:4px; }
.item .cheap b { color:var(--save); }
.basket .foot { border-top:1px solid var(--border); margin-top:6px; padding-top:14px; font-size:12.5px; color:var(--ink-3); }
.basket .foot b { color:var(--ink-2); }

/* "Wyczyść koszyk" - celowo dyskretny link-przycisk, nie kolejny duży CTA:
   to akcja niszcząca, ma być dostępna, ale nie kusić kliknięciem (2026-09-07). */
.link-akcja { background:none; border:0; padding:6px 0; font:inherit; font-size:12.5px; color:var(--ink-3); text-decoration:underline; text-underline-offset:3px; cursor:pointer; }
.link-akcja:hover { color:var(--promo); }

/* Pasek propozycji przywrócenia uśpionego koszyka (>24 h) */
.uspiony-pasek { display:flex; gap:16px; align-items:center; flex-wrap:wrap; justify-content:space-between;
  background:var(--accent-soft); border:1px solid color-mix(in srgb, var(--accent) 30%, var(--border));
  border-radius:var(--radius); padding:14px 18px; margin-bottom:18px; }
.uspiony-pasek .txt { flex:1; min-width:240px; }
.uspiony-pasek .txt b { font-size:14.5px; color:var(--accent-ink); }
.uspiony-pasek .txt p { margin:4px 0 0; font-size:13px; color:var(--ink-2); }
.uspiony-pasek .akcje { display:flex; gap:8px; flex-wrap:wrap; }
.uspiony-pasek .cta { padding:9px 16px; font-size:13.5px; }
.city-pill { display:inline-flex; align-items:center; gap:6px; background:var(--accent-soft); color:var(--accent-ink); font-weight:600; font-size:12.5px; padding:5px 11px; border-radius:999px; }
.city-pill:hover { background:color-mix(in srgb, var(--accent-soft) 60%, var(--accent)); }
.city-pill-edit { opacity:.6; font-size:11px; }
@media (max-width:900px){ .basket { position:static; } }

.matrix { background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); box-shadow:var(--shadow); overflow:hidden; }
.matrix-h { padding:16px 20px; border-bottom:1px solid var(--border); display:flex; justify-content:space-between; align-items:center; gap:12px; flex-wrap:wrap; }
.matrix-h h2 { font-size:15px; margin:0; letter-spacing:-.01em; }
.matrix-h .hint { font-size:12px; color:var(--ink-3); }
.tscroll { overflow-x:auto; }

/* ---------- porównanie koszyka: tabela (szeroki ekran) vs karty (telefon) ----------
   Tabela ma min-width:560px. W oknie 375px kontener ma ~306px, więc kolumna
   "Badanie" zabierała 158px (52%), kolumna pierwszej sieci była ucięta
   w połowie liczby, a dwie kolejne w ogóle poza ekranem - użytkownik nie
   wiedział, że istnieją. Dlatego na wąskim ekranie te same dane idą jako
   karty, po jednej na sieć. */
.cmp-waski { display:none; }
@media (max-width:760px){
  .cmp-szeroki { display:none; }
  .cmp-waski { display:flex; flex-direction:column; gap:12px; padding:14px; }
}
.kk { border:1px solid var(--border); border-radius:12px; padding:14px 16px; background:var(--surface); }
.kk-win { border-color:color-mix(in srgb, var(--save) 50%, var(--border)); background:var(--save-cell); }
.kk-h { display:flex; align-items:center; gap:9px; margin-bottom:10px; }
.kk-h .badge { width:30px; height:30px; font-size:12px; }
.kk-nazwa { font-weight:700; font-size:15px; }
.kk-tag { margin-left:auto; font-size:11px; font-weight:700; color:var(--save); background:var(--save-soft); padding:2px 8px; border-radius:6px; }
.kk-row { display:flex; justify-content:space-between; align-items:baseline; gap:12px; padding:7px 0; border-top:1px solid var(--border); font-size:14px; }
.kk-row:first-of-type { border-top:0; }
.kk-n { color:var(--ink-2); display:flex; flex-direction:column; }
.kk-n small { font-size:11px; color:var(--ink-3); }
.kk-c { font-variant-numeric:tabular-nums; text-align:right; white-space:nowrap; }
.kk-taniej { color:var(--save); font-weight:700; }
.kk-brak .kk-c { color:var(--ink-3); font-style:italic; white-space:normal; }
.kk-sum .kk-n, .kk-sum .kk-c { font-weight:600; }
/* Wiersz kodu układamy pionowo: przy podziale na dwie kolumny sama etykieta
   łamała się na "Kod / rabatowy", a tekst rabatu wchodził w wąski słupek. */
.kk-kod { flex-direction:column; align-items:stretch; gap:3px; }
.kk-kod .kk-c { font-size:12px; white-space:normal; font-variant-numeric:normal; text-align:left; }
.kk-kod .kk-c .note { text-align:left !important; line-height:1.45; }
.kk-przed { color:var(--ink-3); font-weight:400; margin-right:5px; }
.kk-total { border-top:2px solid var(--border-2); margin-top:2px; padding-top:10px; }
.kk-total .kk-n { font-weight:700; color:var(--ink); }
.kk-total .kk-c { font-size:19px; font-weight:800; letter-spacing:-.02em; }
.kk-win .kk-total .kk-c { color:var(--save); }
.kk-brakinfo { margin-top:10px; font-size:12px; color:var(--ink-3); border-top:1px solid var(--border); padding-top:9px; }
/* Tabela porównania koszyka. Zawężona tak samo jak h1 - bez tego stylowałaby
   KAŻDĄ tabelę na naszych stronach WP (także wstawioną przez motyw/inną wtyczkę). */
body:not(.labceny-strona) table, .labceny-app table { border-collapse:collapse; width:100%; min-width:560px; font-size:14px; }
body:not(.labceny-strona) thead th, .labceny-app thead th { font-weight:600; text-align:right; padding:14px 18px; background:var(--surface-2); border-bottom:1px solid var(--border); vertical-align:bottom; }
body:not(.labceny-strona) thead th:first-child, .labceny-app thead th:first-child { text-align:left; }
.provh { display:inline-flex; flex-direction:column; align-items:flex-end; gap:6px; }
.provh .badge { width:34px; height:34px; font-size:13px; }
.provh .nm { font-weight:700; font-size:13.5px; }
/* Odległość do najbliższej placówki - przy cenie widocznej różnicy 50 gr warto wiedzieć, która sieć jest bliżej. */
.km-badge { font-size:11px; font-weight:400; color:var(--ink-3); white-space:nowrap; }
.kk-h .km-badge { margin-left:-3px; }
th.wincol, td.wincol { background:var(--save-cell); }
th.wincol { box-shadow:inset 0 3px 0 var(--save); }
body:not(.labceny-strona) tbody td, .labceny-app tbody td { padding:12px 18px; text-align:right; border-bottom:1px solid var(--border); font-variant-numeric:tabular-nums; }
body:not(.labceny-strona) tbody td:first-child, .labceny-app tbody td:first-child { text-align:left; color:var(--ink-2); }
tbody td.cheap { color:var(--save); font-weight:700; position:relative; }
tbody td.cheap::after { content:"✓"; font-size:10px; position:absolute; top:8px; right:6px; opacity:.6; }
tr.sep td { border-bottom:1px solid var(--border-2); }
tr.subtotal td { background:var(--surface-2); font-weight:600; }
tr.fee td:first-child { color:var(--ink-2); }
tr.fee .note { display:block; font-size:11px; color:var(--ink-3); font-weight:400; }
tr.total td { padding:16px 18px; font-size:16px; font-weight:800; border-top:2px solid var(--border-2); border-bottom:0; }
tr.total td .win { color:var(--save); }
tr.total td:first-child { font-size:14px; }
.rank { display:inline-block; font-size:11px; font-weight:700; color:var(--save); background:var(--save-soft); padding:2px 8px; border-radius:6px; margin-left:8px; }

.promo-strip { margin-top:20px; border:1px dashed color-mix(in srgb, var(--promo) 45%, transparent); background:var(--promo-soft); border-radius:12px; padding:14px 18px; font-size:13px; color:var(--ink-2); display:flex; gap:10px; align-items:center; }
.promo-strip b { color:var(--promo); }

/* minmax(0,1fr), NIE goły 1fr - ślepy tor 1fr ma domyślne minimum
   szerokości równe min-content, więc wiersz "Kup w X" (nowrap) rozpychał
   kartę SZERZEJ niż ekran telefonu (user 2026-09-13, zrzut ekranu: zielona
   karta ucięta z prawej, mimo że karty sieci nad nią mieściły się bez
   problemu). min-width:0 na samych kartach z tego samego powodu - inaczej
   karta jako flex/grid item i tak nie chce się zrobić węższa niż jej treść. */
.verdict { margin-top:20px; display:grid; grid-template-columns:minmax(0,1fr) minmax(0,1fr); gap:16px; }
@media (max-width:760px){ .verdict { grid-template-columns:minmax(0,1fr); margin-bottom:70px; } }
.win-card, .split-card, .pakiet-card { min-width:0; }
.win-card { background:linear-gradient(180deg, var(--save-soft), var(--surface)); border:1px solid color-mix(in srgb, var(--save) 45%, var(--border)); border-radius:var(--radius); padding:22px; box-shadow:var(--shadow); }
.win-card .k, .split-card .k { font-size:11px; text-transform:uppercase; letter-spacing:.08em; font-weight:700; margin-bottom:8px; }
.win-card .k { color:var(--save); }
.split-card .k { color:var(--ink-3); }
.win-card .big { display:flex; align-items:center; gap:12px; margin-bottom:6px; }
.win-card .badge { width:40px; height:40px; font-size:15px; }
.win-card .amt { font-size:30px; font-weight:800; letter-spacing:-.02em; font-variant-numeric:tabular-nums; }
.win-card .amt small { font-size:16px; font-weight:700; color:var(--ink-2); }
.win-card p { font-size:13px; color:var(--ink-2); margin:6px 0 0; }
.win-card .cta { margin-top:16px; }
.split-card { background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); padding:22px; box-shadow:var(--shadow); }
.split-card .amt { font-size:24px; font-weight:800; font-variant-numeric:tabular-nums; letter-spacing:-.02em; }
.split-card .amt small { font-size:14px; color:var(--ink-2); font-weight:600; }

/* Trzecia karta (koszyk pakietów, 2026-09-08) - pełna szerokość pod dwiema
   głównymi kolumnami, bo pojawia się rzadziej (tylko gdy realnie taniej) i
   ma charakter "dodatkowej dobrej wiadomości", nie równorzędnej opcji. */
.pakiet-card { grid-column:1 / -1; background:linear-gradient(180deg, var(--accent-soft), var(--surface)); border:1px solid color-mix(in srgb, var(--accent) 40%, var(--border)); border-radius:var(--radius); padding:22px; box-shadow:var(--shadow); }
.pakiet-card .k { font-size:11px; text-transform:uppercase; letter-spacing:.08em; font-weight:700; margin-bottom:8px; color:var(--accent-ink); }
.pakiet-card .amt { font-size:26px; font-weight:800; letter-spacing:-.02em; font-variant-numeric:tabular-nums; margin-bottom:10px; }
.pakiet-card .amt small { font-size:14px; font-weight:700; color:var(--ink-2); }
/* Wyjaśnienie U GÓRY karty, czym w ogóle jest "pakiet" - user 2026-09-13: cała
   karta była "niezrozumiała" bez tego zdania, bo od razu wchodziła w listę
   pozycji i przyciski. */
.pakiet-wyjasnienie { margin:0 0 14px; color:var(--ink-2); font-size:13.5px; }
.warnrow { margin-top:14px; font-size:12.5px; color:var(--promo); background:var(--promo-soft); border-radius:8px; padding:9px 12px; display:flex; gap:8px; }
.warnrow b { color:var(--promo); }

/* Linki "Kup w X" PRZY KAŻDEJ pozycji (badanie/pakiet) w kartach werdyktu -
   user 2026-09-13: jeden zbiorczy przycisk na cały koszyk/sieć nie mówił,
   czego tam szukać. `.grp` grupuje pozycje jednej sieci (kafelki "Rozdzielone"
   i "Z pakietem" mają kilka grup); `.step-list` używana samodzielnie w
   kafelku "Najtaniej w jednym punkcie", gdzie jest tylko jedna sieć. */
.grp { margin-top:14px; }
.grp:first-of-type { margin-top:12px; }
.grp-label { font-size:12.5px; color:var(--ink-2); margin-bottom:6px; display:flex; align-items:center; gap:7px; }
/* Adres najbliższej placówki, widoczny wprost (nie tylko w tytule/tooltipie,
   martwym na dotyk) - user 2026-09-13: "zgubiło się info o punkcie pobrań i
   odległości" po przebudowie kart werdyktu na linki per badanie. Patrz
   opisNajblizszejPlacowki() w app-koszyk.js - renderuje się TYLKO gdy user
   podał adres (są dane o odległości), więc bez adresu ten wiersz po prostu
   nie istnieje, nie zostaje pusty. */
.miejsce-info { font-size:11.5px; color:var(--ink-3); margin:-2px 0 8px; }
.win-card .step-list, .split-card .grp:first-of-type .step-list, .pakiet-card .grp:first-of-type .step-list { margin-top:12px; }
.step-list { list-style:none; margin:0; padding:0; border:1px solid var(--border); border-radius:10px; overflow:hidden; background:var(--surface); }
/* Bez numerka (.step-num) i kwadracika sieci (.mini) - sieć jest już nazwana
   nad listą (nagłówek karty "Alab · 1 wizyta" albo .grp-label z kolorową
   kropką), więc przy KAŻDYM wierszu były zbędnym powtórzeniem, a na
   375px zjadały ok. 50px, których brakowało nazwie badania (user
   2026-09-13, zrzut ekranu z telefonu).
   Układ .step-tresc jako grid 2 kolumny (nazwa | kwota, wiersz drugi na
   podpis pakietu) na desktopie; na wąskim ekranie przełącza się we
   flex-column (patrz media query niżej), żeby kwota wylądowała POD nazwą,
   a nie po prawej - bez przerysowywania w JS przy obrocie telefonu. */
.step-row { display:flex; align-items:center; gap:10px; padding:9px 12px; border-top:1px solid var(--border); min-width:0; }
.step-row:first-child { border-top:0; }
.step-tresc { display:grid; grid-template-columns:1fr auto; column-gap:10px; align-items:baseline; flex:1 1 auto; min-width:0; }
.step-nazwa { grid-column:1; grid-row:1; min-width:0; font-size:13.5px; }
.step-podpis { grid-column:1 / -1; grid-row:2; font-size:11px; font-weight:400; color:var(--ink-3); }
.step-kwota { grid-column:2; grid-row:1; color:var(--ink-2); font-variant-numeric:tabular-nums; font-size:12.5px; white-space:nowrap; }
/* text-decoration:none!important - same style motywu Astra podbija podkreślenie
   linków własną specyficznością (user 2026-09-13, telefon: "Kup w Alab →"
   było podkreślone mimo tej samej reguły bez !important). */
.step-kup { flex:none; font-size:12.5px; font-weight:700; color:var(--accent-ink) !important; white-space:nowrap; text-decoration:none !important; padding:5px 10px; border-radius:7px; background:var(--accent-soft); }
.step-kup:hover, .step-kup:focus { background:var(--accent); color:#fff !important; }

@media (max-width:480px) {
  /* Nazwa badania może się zawinąć do 2 linii - NIGDY nie ucinamy tekstu
     (user: "nazwy badań mają znaczenie"), więc kwota schodzi pod nią jako
     osobna, mniejsza szara linia zamiast stać w tej samej kolumnie. */
  .step-row { align-items:flex-start; }
  .step-tresc { display:flex; flex-direction:column; gap:2px; }
  .step-kwota { font-size:12px; color:var(--ink-3); }
  /* Przycisk "Kup" był "ciężki" i zjadał sporo miejsca (user 2026-09-13,
     drugi zrzut z telefonu) - dwie zmiany naraz: 1) tekst "w Alab" znika,
     sieć jest już nazwana nad listą (nagłówek karty/.grp-label), więc na
     przycisku zostaje samo "Kup →"; 2) wypełnione tło zamienione na ramkę
     ("ghost") - mniej wizualnej masy przy takiej samej wysokości do kciuka. */
  .step-kup-siec { display:none; }
  .step-kup { display:inline-flex; align-items:center; justify-content:center; min-height:38px; padding:7px 14px; text-align:center; background:transparent; border:1.5px solid var(--accent); }
  .step-kup:hover, .step-kup:focus { background:var(--accent-soft); }
}

/* Pasek "wpisz kod X w koszyku Y" NAD listą "Kup w..." danej grupy/sieci -
   user 2026-09-13: rabat już wliczony w cenę, ale KLIENT musi wpisać kod
   sam po stronie sieci - wcześniej ten fakt był widoczny tylko w tabeli
   porównawczej na desktopie, nie przy samych linkach zakupowych. Stylistyka
   pokrewna .modal .kod-r/code (ten sam pomysł: kod w "pigułce" + Kopiuj), ale
   dużo bardziej kompaktowa - to pasek nad listą, nie treść modala na cały
   ekran. flex-wrap, żeby kilka kodów naraz mieściło się na 375px. */
.kw-pasek { display:flex; flex-wrap:wrap; gap:8px; margin-bottom:10px; }
.kw-chip { display:flex; flex-wrap:wrap; align-items:center; gap:6px; font-size:12px; color:var(--ink); background:var(--promo-soft); border:1px solid color-mix(in srgb, var(--promo) 35%, var(--border-2)); border-radius:9px; padding:6px 10px; }
.kw-chip code { font-family:ui-monospace,SFMono-Regular,Menlo,monospace; font-size:12.5px; font-weight:700; letter-spacing:.04em; background:var(--surface); border:1px solid var(--border-2); border-radius:6px; padding:2px 7px; color:var(--ink); }
.kw-kopiuj { flex:none; background:var(--promo); color:#fff !important; border:0; border-radius:6px; padding:4px 9px; font-size:11.5px; font-weight:700; font-family:inherit; cursor:pointer; text-decoration:none !important; }
.kw-kopiuj:hover { opacity:.9; }

/* ============================================================
   Przełącznik palet (tylko demo)
   ============================================================ */
.theme-switch { position:fixed; right:16px; bottom:16px; z-index:100; display:flex; align-items:center; gap:8px; background:color-mix(in srgb, var(--surface) 92%, transparent); backdrop-filter:blur(10px); border:1px solid var(--border-2); box-shadow:var(--shadow-lg); border-radius:999px; padding:8px 12px; }
.theme-switch .ts-label { font-size:12px; font-weight:600; color:var(--ink-2); }
.sw { width:24px; height:24px; border-radius:50%; border:2px solid var(--surface); cursor:pointer; padding:0; box-shadow:0 0 0 1px var(--border-2); transition:transform .12s ease; }
.sw:hover { transform:scale(1.12); }
.sw[aria-pressed="true"] { box-shadow:0 0 0 2px var(--surface), 0 0 0 4px var(--ink-3); transform:scale(1.12); }
.sw-teal { background:#0C8C86; }
.sw-blue { background:#2563EB; }
.sw-slate { background:#25313B; }
.sw-coral { background:#E15A47; }
@media (max-width:520px){
  .theme-switch { right:10px; bottom:10px; padding:7px 10px; gap:6px; }
  .theme-switch .ts-label { display:none; }
}
@media (prefers-reduced-motion:reduce){ *{ scroll-behavior:auto; transition:none!important; } }

/* ============================================================
   Podpowiedzi wyszukiwarki (autouzupełnianie)
   Trzy miejsca z tym samym wzorcem: #podpowiedzi (strona badania),
   #miasto-podpowiedzi (pole miasta), #k-podpowiedzi (koszyk - "Dodaj
   badanie..."). #k-podpowiedzi TU BRAKOWAŁO - stąd na koszyku podpowiedzi
   wyglądały jak surowy, nieostylowany HTML: nazwa i kategoria sklejone bez
   odstępu ("FT4Tarczyca"), bez obramowania między wierszami, bez tła przy
   najechaniu (user 2026-09-11, telefon). */
#podpowiedzi, #miasto-podpowiedzi, #k-podpowiedzi { position:absolute; top:calc(100% + 6px); left:0; right:0; background:var(--surface); border:1px solid var(--border-2); border-radius:12px; box-shadow:var(--shadow-lg); overflow:hidden; z-index:40; max-height:260px; overflow-y:auto; }
#podpowiedzi .sugestia, #miasto-podpowiedzi .sugestia, #k-podpowiedzi .sugestia { display:flex; align-items:center; justify-content:space-between; gap:10px; padding:11px 14px; cursor:pointer; font-size:14px; }
#podpowiedzi .sugestia:hover, #podpowiedzi .sugestia.aktywna, #miasto-podpowiedzi .sugestia:hover, #miasto-podpowiedzi .sugestia.aktywna, #k-podpowiedzi .sugestia:hover, #k-podpowiedzi .sugestia.aktywna { background:var(--surface-2); }
#podpowiedzi .sugestia .kat, #k-podpowiedzi .sugestia .kat { font-size:11.5px; color:var(--ink-3); flex:none; }
#podpowiedzi .sugestia + .sugestia, #miasto-podpowiedzi .sugestia + .sugestia, #k-podpowiedzi .sugestia + .sugestia { border-top:1px solid var(--border); }
/* "… jest w kilku miejscowościach. Którą masz na myśli?" - na stronie głównej w liście podpowiedzi miast, gdzie indziej we własnej ramce */
.wybor-pytanie { padding:10px 14px 6px; font-size:12.5px; font-weight:600; color:var(--ink-2); }
.wybor-adresu .sugestia { display:flex; align-items:center; gap:10px; padding:10px 14px; cursor:pointer; font-size:14px; color:var(--ink); border-top:1px solid var(--border); }
.wybor-adresu .sugestia:hover, .wybor-adresu .sugestia:focus, .wybor-adresu .sugestia.aktywna { background:var(--surface-2); outline:none; }
.wybor-dopisek { padding:8px 14px 10px; font-size:12px; color:var(--ink-3); border-top:1px solid var(--border); }
#adres-status .wybor-adresu, #k-miasto-blad .wybor-adresu { margin-top:6px; background:var(--surface); border:1px solid var(--border-2); border-radius:12px; overflow:hidden; }

.mk-row { display:flex; align-items:center; justify-content:space-between; padding:8px 0; border-top:1px solid var(--border); font-size:13.5px; }
.mk-row:first-child { border-top:0; }
.mk-total { display:flex; justify-content:space-between; padding-top:10px; margin-top:4px; border-top:1px solid var(--border-2); font-weight:700; font-size:14px; }

/* ============================================================
   Dymek z wyjaśnieniem - działa na dotyk (patrz popover.js)
   ============================================================ */
[data-wyjasnienie] { cursor:pointer; }
.wyjasnienie-popover {
  position:fixed; left:12px; right:12px; bottom:12px; max-width:440px; margin:0 auto;
  background:var(--surface); border:1px solid var(--border-2); border-radius:14px;
  box-shadow:var(--shadow-lg); padding:14px 42px 14px 16px; font-size:13.5px; color:var(--ink-2);
  z-index:300; transform:translateY(16px); opacity:0; pointer-events:none;
  transition:transform .15s ease, opacity .15s ease;
}
.wyjasnienie-popover.widoczny { transform:translateY(0); opacity:1; pointer-events:auto; }
.wyjasnienie-zamknij { position:absolute; top:8px; right:8px; border:0; background:var(--surface-2); color:var(--ink-3); width:26px; height:26px; border-radius:8px; font-size:13px; cursor:pointer; }
@media (prefers-reduced-motion:reduce){ .wyjasnienie-popover{ transition:none; } }

/* ============================================================
   LANDING SEO — karta pojedynczego badania
   ============================================================ */
.seo-demo { margin:0 0 22px; border:1px dashed var(--border-2); background:var(--surface-2); border-radius:12px; padding:14px 16px; font-size:12.5px; color:var(--ink-2); }
.seo-demo .h { font-weight:700; color:var(--ink); font-size:12px; text-transform:uppercase; letter-spacing:.06em; margin-bottom:10px; display:flex; align-items:center; gap:7px; }
.seo-demo dl { display:grid; grid-template-columns:130px 1fr; gap:6px 12px; margin:0; }
.seo-demo dt { color:var(--ink-3); }
.seo-demo dd { margin:0; color:var(--ink); }
.seo-demo code { background:var(--surface); border:1px solid var(--border); border-radius:5px; padding:1px 5px; font-size:11.5px; }
@media (max-width:560px){ .seo-demo dl { grid-template-columns:1fr; gap:2px; } .seo-demo dt { margin-top:8px; } }

.lp-hero { display:grid; grid-template-columns:1fr 320px; gap:26px; margin:6px 0 8px; align-items:start; }
@media (max-width:880px){ .lp-hero { grid-template-columns:1fr; } }
/* Bez max-width:60ch (usunięte 2026-09-13) - user: opis miał "ten sam błąd"
   co wcześniej naprawiony box "Jak się przygotować" tuż pod nim - węższy niż
   wszystko dookoła, mimo wolnego miejsca z boku. 60ch jest dobrą szerokością
   dla ciągłego czytania, ale wygląda źle jako jedyny wąski element na stronie
   pełnej szerokich kart - spójność z resztą strony wygrywa tu z podręcznikową
   szerokością wiersza. */
.lp-intro { font-size:15px; color:var(--ink-2); margin:12px 0 0; }
.lp-facts { display:flex; flex-wrap:wrap; gap:8px; margin:18px 0 0; }
.fact { display:inline-flex; align-items:center; gap:7px; background:var(--surface); border:1px solid var(--border); border-radius:999px; padding:7px 13px; font-size:13px; color:var(--ink-2); }
.fact b { color:var(--ink); font-weight:600; }
/* Nie wiemy (na_czczo=NULL) - MUSI wyglądać inaczej niż potwierdzony fakt,
   inaczej pigułka udaje pewność, której nie ma (user 2026-09-01). */
.fact-niepewne { background:var(--surface-2); border-style:dashed; color:var(--ink-3); }
.fact-niepewne b { color:var(--ink-2); }
/* Pigułka faktu = ikona / etykieta / wartość (osobne pola, patrz
   app-wyniki.js i szablon-strona-ceny.php). Wygląd jak przed 2026-09-21
   (płaskie pigułki, jedna pod drugą na telefonie) - user obejrzał wersję z
   kartą 2x2 na telefonie i uznał ją za "okropną", ale spodobało mu się
   formatowanie: POGRUBIONA JEST WARTOŚĆ ("Krew żylna"), a nie etykieta
   ("Materiał"). Ta sama zasada w kartach ofert (.drow) - patrz niżej. */
.fact-i { flex:none; }
.fact .fact-l { color:var(--ink-2); font-weight:400; }
.fact .fact-l::after { content:":"; }
.fact .fact-v { color:var(--ink); font-weight:600; }
.fact-niepewne .fact-v { color:var(--ink-2); }

@media (max-width:520px){
  /* Linia pod tytułem: trzy krótkie linie jedna pod drugą, bez kropek -
     kropka-separator lądowała na początku zawiniętej linii. */
  .meta { flex-direction:column; align-items:flex-start; gap:3px; }
  .meta .dot { display:none; }
}

/* Rytm pionowy nad ofertami w widoku wyników i na stronach /cena/ (2026-09-21):
   wcześniej odstępy pochodziły z kilku różnych reguł (34 px + 26 px nad
   "Powiązane badania", 0 px między paskiem a kartą oferty) i strona wyglądała
   nierówno. Teraz: fakty -> 18 px -> "Powiązane" -> 8 px -> chipy -> 14 px ->
   paski (8 px między nimi) -> 16 px -> oferty. */
#fakty-badania { margin:14px 0 0; }
#fakty-badania + .sec-label { margin:18px 0 0; }
#powiazane { margin-top:8px; margin-bottom:6px; }
#widok-wynikow .related a { text-decoration:none; }
#lista-ofert, .lc-cena .offers { margin-top:16px; }
.lc-cena .lp-facts + .zwin { margin-top:14px; }

.pricebox { background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); box-shadow:var(--shadow); padding:20px; position:sticky; top:80px; }
@media (max-width:880px){ .pricebox { position:static; } }
.pricebox .from { font-size:12px; text-transform:uppercase; letter-spacing:.07em; color:var(--ink-3); font-weight:700; }
.pricebox .big { font-size:34px; font-weight:800; letter-spacing:-.02em; line-height:1; margin:4px 0 2px; font-variant-numeric:tabular-nums; }
.pricebox .big small { font-size:16px; color:var(--ink-2); font-weight:700; }
.pricebox .pbnote { font-size:12px; color:var(--ink-3); margin-bottom:14px; }
.pb-row { display:flex; align-items:center; justify-content:space-between; padding:9px 0; border-top:1px solid var(--border); font-size:13.5px; }
.pb-row .l { display:flex; align-items:center; gap:8px; font-weight:600; }
.pb-row .mini { width:20px; height:20px; border-radius:6px; }
.pb-row .p { font-variant-numeric:tabular-nums; font-weight:700; }
.pb-row .p.win { color:var(--save); }

.section-block { margin-top:38px; }
.section-block > h2 { font-size:21px; letter-spacing:-.02em; margin:0 0 12px; text-wrap:balance; }
.prose { font-size:14.5px; color:var(--ink-2); max-width:70ch; }
.prose p { margin:0 0 12px; }
.prose ul { margin:0 0 12px; padding-left:20px; }
.prose li { margin:4px 0; }
.prose b { color:var(--ink); }

.params { display:grid; grid-template-columns:repeat(auto-fill, minmax(150px,1fr)); gap:8px; margin-top:4px; }
.param { background:var(--surface); border:1px solid var(--border); border-radius:10px; padding:10px 12px; font-size:13px; }
.param b { display:block; color:var(--ink); }
.param span { color:var(--ink-3); font-size:12px; }

.tbl-wrap { border:1px solid var(--border); border-radius:var(--radius); overflow:hidden; background:var(--surface); box-shadow:var(--shadow); }
.cities-table { width:100%; border-collapse:collapse; font-size:14px; }
.cities-table th, .cities-table td { text-align:left; padding:11px 14px; border-bottom:1px solid var(--border); }
.cities-table th { font-size:12px; text-transform:uppercase; letter-spacing:.05em; color:var(--ink-3); font-weight:600; background:var(--surface-2); }
.cities-table td.num { text-align:right; font-variant-numeric:tabular-nums; font-weight:700; }
.cities-table a { color:var(--accent-ink); text-decoration:none; font-weight:600; }
.cities-table a:hover { text-decoration:underline; }
.cities-table tr:last-child td { border-bottom:0; }

.pkg-grid { display:grid; grid-template-columns:1fr 1fr; gap:14px; margin-top:4px; }
@media (max-width:680px){ .pkg-grid { grid-template-columns:1fr; } }
.pkg { background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); padding:18px; box-shadow:var(--shadow); display:flex; flex-direction:column; gap:5px; }
.pkg .nm { font-weight:700; font-size:15px; }
.pkg .inc { font-size:12.5px; color:var(--ink-3); }
.pkg .pr { margin-top:6px; font-size:20px; font-weight:800; font-variant-numeric:tabular-nums; }
.pkg .pr small { font-size:12px; color:var(--ink-2); font-weight:600; }
.pkg .cta { margin-top:10px; align-self:flex-start; }

.faq details { border:1px solid var(--border); border-radius:12px; background:var(--surface); padding:0 16px; margin-bottom:10px; box-shadow:var(--shadow); }
.faq summary { cursor:pointer; padding:14px 0; font-weight:600; font-size:14.5px; list-style:none; display:flex; justify-content:space-between; align-items:center; gap:12px; }
.faq summary::-webkit-details-marker { display:none; }
.faq summary::after { content:"+"; color:var(--accent-ink); font-size:20px; font-weight:400; line-height:1; }
.faq details[open] summary::after { content:"\2013"; }
.faq .ans { padding:0 0 14px; font-size:14px; color:var(--ink-2); max-width:70ch; }

/* ===== v1.1 — widok pojedynczego badania: krok 0, koszyk-przycisk, adres
   placówki, ostrzeżenie przed przejściem, opis_wlasny (patrz app-widok-v11.js
   / SCOPE_podpowiedzi_badan.md). Sprawdzone najpierw w demo-www. ===== */

/* Krok 0 - "często zlecane razem" */
.krok0{margin:0 0 20px;background:var(--surface);border:1px solid var(--border);border-left:3px solid var(--accent);border-radius:var(--radius);padding:16px 18px;box-shadow:var(--shadow)}
.krok0 .k{font-size:11px;text-transform:uppercase;letter-spacing:.08em;font-weight:700;color:var(--accent-ink);margin-bottom:4px}
.krok0 .lead{font-size:12.5px;color:var(--ink-3);margin:0 0 10px}
.k0row{display:flex;gap:14px;align-items:center;padding:11px 0;border-top:1px solid var(--border)}
.k0row .txt{flex:1;min-width:0}
.k0row .nm{font-size:14px;font-weight:700}
.k0row .why{font-size:12.5px;color:var(--ink-2);margin-top:3px}
.k0row .why.pusty{color:var(--ink-3);font-style:italic;background:var(--surface-2);border:1px dashed var(--border-2);border-radius:6px;padding:4px 9px;display:inline-block;font-size:12px}
.k0row .cena{font-size:12.5px;color:var(--save);font-weight:600;margin-top:3px}
.k0row .akcja{flex:none}
.krok0 .foot{margin-top:12px;padding-top:10px;border-top:1px solid var(--border);font-size:11px;color:var(--ink-3)}

/* Przycisk koszyka - widoczny obok "Kup", nie chowany na dole karty */
/* Dwa przyciski JEDEN POD DRUGIM, nie obok siebie (poprawione 2026-09-04).
   Wcześniej `flex:1` na "Kup w ..." obok nieściśliwego "Do koszyka" wyciskało
   główny przycisk do ~59px i łamało napis na 3 linie ("Kup w / Alab / →") -
   kolumna oferty ma tylko ~210px użytecznej szerokości, więc na dwa przyciski
   w rzędzie po prostu nie ma miejsca przy żadnej szerokości ekranu. */
.buy .akcje{display:flex;flex-direction:column;gap:8px;width:100%;margin-top:8px}
.buy .akcje .cta{flex:none;width:100%;padding:11px 14px}
.buy .akcje .addcart2{flex:none;width:100%;display:inline-flex;align-items:center;justify-content:center;gap:6px;background:var(--surface);color:var(--accent-ink);border:1px solid var(--border-2);border-radius:10px;padding:11px 14px;font-size:14px;font-weight:700;font-family:inherit;cursor:pointer;white-space:nowrap}
.buy .akcje .addcart2:hover{border-color:var(--accent)}
.buy .akcje .addcart2.dodane{background:var(--save-soft);border-color:color-mix(in srgb,var(--save) 45%,transparent);color:var(--save)}

/* Adres najbliższej placówki - mocniej wyeksponowany */
.drow.placowka{background:var(--accent-soft);border-radius:8px;padding:8px 10px;margin-top:2px}
.drow.placowka .feetxt{color:var(--accent-ink)}

/* Ostrzeżenie przed przejściem do sieci */
.modal-tlo{position:fixed;inset:0;background:rgba(15,42,49,.55);display:flex;align-items:center;justify-content:center;z-index:200;padding:20px}
.modal{background:var(--surface);border-radius:var(--radius);box-shadow:var(--shadow-lg);max-width:480px;width:100%;padding:26px}
.modal h3{margin:0 0 10px;font-size:19px;letter-spacing:-.02em}
.modal p{margin:0 0 12px;font-size:13.5px;color:var(--ink-2);line-height:1.55}
.modal ol{margin:0 0 14px;padding-left:20px;font-size:13.5px;color:var(--ink-2)}
.modal ol li{margin-bottom:5px}
.modal .wip{background:var(--accent-soft);border-radius:9px;padding:11px 13px;font-size:12.5px;color:var(--accent-ink);margin-bottom:16px}
/* Kod rabatowy do skopiowania - ostatni moment, żeby go klientowi podać,
   zanim wyjdzie na stronę sieci. Bez tego widzi u nas cenę po rabacie,
   a płaci pełną. */
.modal .kod-box{background:var(--promo-soft);border:1px dashed color-mix(in srgb, var(--promo) 45%, transparent);border-radius:10px;padding:12px 14px;margin-bottom:16px}
.modal .kod-l{font-size:12px;font-weight:700;color:var(--promo);margin-bottom:8px}
.modal .kod-r{display:flex;align-items:center;gap:10px;flex-wrap:wrap}
.modal .kod-r code{font-family:ui-monospace,SFMono-Regular,Menlo,monospace;font-size:19px;font-weight:700;letter-spacing:.08em;background:var(--surface);border:1px solid var(--border-2);border-radius:8px;padding:6px 12px;color:var(--ink)}
.modal .kod-r button{background:var(--promo);color:#fff;border:0;border-radius:8px;padding:9px 14px;font-size:13px;font-weight:700;font-family:inherit;cursor:pointer}
.modal .kod-s{margin-top:9px;font-size:12px;color:var(--ink-2);line-height:1.5}
.modal .akcje{display:flex;gap:10px;justify-content:flex-end;flex-wrap:wrap}
.modal .anuluj{background:none;border:1px solid var(--border-2);border-radius:10px;padding:11px 16px;font-size:14px;font-weight:600;color:var(--ink-2);font-family:inherit;cursor:pointer}

/* Krótki opis badania (pb_badania.opis_wlasny), pod pigułkami faktów.
   Gdy pusty: pokazujemy pigułkę .fact.fact-niepewne (ta sama konwencja co
   niepewne "na czczo" w fakty-badania) zamiast notatki deweloperskiej -
   user 2026-09-01: opis pusty widzi PACJENT, nie admin. */
#opis-badania.opis-pusty{margin-top:10px}

/* ============================================================
   EKRAN STARTOWY i WIDEŁKI CEN (2026-09-04)
   ============================================================
   Dwa stany, które istnieją, ODKĄD strona nie udaje już, że użytkownik
   wybrał morfologię w Warszawie:
     1. .start-panel - nic nie wpisano (brak ?b= w adresie),
     2. .widelki     - wpisano badanie, ale nie podano jeszcze miasta:
                       pokazujemy OGÓLNOPOLSKI ZAKRES min-max, nie "cenę od X"
                       (ceny tego samego badania różnią się między miastami
                       średnio o 90%, więc samo minimum kotwiczyłoby kwotę,
                       której większość ludzi u siebie nie zobaczy). */
.start-panel { background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); box-shadow:var(--shadow); padding:34px 28px; text-align:center; }
.start-tytul { font-size:clamp(21px,3.4vw,28px); letter-spacing:-.02em; margin:0 0 10px; text-wrap:balance; }
.start-sub { margin:0 auto 22px; max-width:56ch; color:var(--ink-2); font-size:15px; }
.start-przyklady { display:flex; flex-wrap:wrap; gap:8px; justify-content:center; align-items:center; }
.start-etykieta { font-size:12px; text-transform:uppercase; letter-spacing:.05em; color:var(--ink-3); font-weight:600; margin-right:2px; }
.start-przyklady .chip { text-decoration:none; }
.start-przyklady .chip:hover { border-color:var(--accent); color:var(--accent-ink); }

.widelki { background:var(--surface); border:1px solid var(--border); border-radius:var(--radius); box-shadow:var(--shadow); padding:28px 24px; text-align:center; }
.widelki-kwota { font-size:clamp(28px,5vw,40px); font-weight:700; letter-spacing:-.03em; color:var(--accent-ink); font-variant-numeric:tabular-nums; }
.widelki-tekst { margin:10px auto 20px; max-width:54ch; color:var(--ink-2); font-size:14.5px; }
.widelki .cta { display:inline-block; width:auto; }
