/* ===========================================================================
   components.css — elements used across several pages
   ===========================================================================
   Naming convention: .block  +  .block--modifier  +  .block__part
   One level of nesting in selectors. No !important.
   Colors come EXCLUSIVELY from semantic tokens.
   =========================================================================== */

/* ===========================================================================
   BUTTONS
   =========================================================================== */
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: var(--space-2);
  padding: var(--space-3) var(--space-5);
  border: 1px solid transparent;
  border-radius: var(--radius-sm);
  font-family: var(--font-body);
  font-size: var(--text-body-sm);
  font-weight: var(--weight-medium);
  line-height: 1.2;
  text-align: center;
  text-decoration: none;
  white-space: nowrap;
  cursor: pointer;
  transition: background-color var(--duration-fast) var(--ease-out),
    border-color var(--duration-fast) var(--ease-out),
    color var(--duration-fast) var(--ease-out),
    transform var(--duration-fast) var(--ease-out),
    box-shadow var(--duration-base) var(--ease-out);
}

.btn:active {
  transform: translateY(1px);
}

/* Main call to action. It appears rarely on the site — hence its impact. */
.btn--primary {
  background-color: var(--color-accent);
  color: var(--color-text-on-accent);
  box-shadow: var(--shadow-sm);
}

.btn--primary:hover {
  background-color: var(--color-accent-hover);
  color: var(--color-text-on-accent);
  box-shadow: var(--shadow-accent);
}

/* Secondary action — outlined, no fill. */
.btn--secondary {
  background-color: transparent;
  border-color: var(--color-border-control);
  color: var(--color-text-primary);
}

.btn--secondary:hover {
  border-color: var(--color-accent);
  color: var(--color-accent-text);
  background-color: var(--color-accent-quiet);
}

/* Quiet action — text only, with an arrow. */
.btn--ghost {
  padding-inline: 0;
  background-color: transparent;
  color: var(--color-accent-text);
}

.btn--ghost:hover {
  color: var(--color-accent-hover);
  gap: var(--space-3);
}

.btn--lg {
  padding: var(--space-4) var(--space-6);
  font-size: var(--text-body);
}

.btn--block {
  width: 100%;
}

.btn__arrow {
  transition: transform var(--duration-fast) var(--ease-out);
}

.btn:hover .btn__arrow {
  transform: translateX(3px);
}

/* ===========================================================================
   STATUS BADGES
   Color is NEVER the only carrier of information — there is always a label.
   =========================================================================== */
.badge {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2);
  padding: var(--space-1) var(--space-3);
  border: 1px solid transparent;
  border-radius: var(--radius-pill);
  font-family: var(--font-mono);
  font-size: var(--text-label);
  font-weight: var(--weight-medium);
  letter-spacing: 0.04em;
  text-transform: uppercase;
  white-space: nowrap;
}

.badge::before {
  content: '';
  width: 6px;
  height: 6px;
  border-radius: 50%;
  background-color: currentcolor;
  flex-shrink: 0;
}

/* Live in production. */
.badge--available {
  background-color: var(--color-ok-quiet);
  border-color: color-mix(in srgb, var(--color-ok) 32%, transparent);
  color: var(--color-ok-text);
}

/* Partially implemented / behind a configuration flag. */
.badge--progress {
  background-color: var(--color-accent-quiet);
  border-color: var(--color-accent-border);
  color: var(--color-accent-text);
}

/* Planned / roadmap — NOT working yet. */
.badge--planned {
  background-color: color-mix(in srgb, var(--color-text-muted) 12%, transparent);
  border-color: color-mix(in srgb, var(--color-text-muted) 30%, transparent);
  color: var(--color-text-muted);
}

.badge--info {
  background-color: var(--color-info-quiet);
  border-color: color-mix(in srgb, var(--color-info) 32%, transparent);
  color: var(--color-info-text);
}

/* Dot-less variant — for labels that do not denote a status. */
.badge--plain::before {
  display: none;
}

/* ===========================================================================
   CARDS
   =========================================================================== */
.card {
  display: flex;
  flex-direction: column;
  gap: var(--space-4);
  padding: var(--space-6);
  background-color: var(--color-surface);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-md);
  transition: border-color var(--duration-base) var(--ease-out),
    background-color var(--duration-base) var(--ease-out),
    transform var(--duration-base) var(--ease-out);
}

/* Whole card clickable (wrapping link). */
.card--link:hover {
  border-color: var(--color-accent-border);
  background-color: var(--color-surface-raised);
  transform: translateY(-2px);
}

@media (hover: hover) {
  .card[data-glow]:hover {
    border-color: var(--color-accent-border);
    transform: translateY(-2px);
  }
}

.card--flush {
  padding: 0;
  background-color: transparent;
  border: 0;
}

/* A card inside a .section--surface background needs its own contrast. */
.section--surface .card {
  background-color: var(--color-surface-sunken);
}

.card__title {
  font-family: var(--font-display);
  font-size: var(--text-title);
  font-weight: var(--weight-semibold);
  letter-spacing: -0.015em;
  line-height: var(--leading-snug);
  color: var(--color-text-primary);
}

.card__body {
  color: var(--color-text-secondary);
  font-size: var(--text-body-sm);
  line-height: var(--leading-relaxed);
}

.card__foot {
  margin-top: auto;
  padding-top: var(--space-2);
}

/* Number/icon in the card corner — monospace, because it is an ordinal marker. */
.card__index {
  font-family: var(--font-mono);
  font-size: var(--text-label);
  font-weight: var(--weight-medium);
  letter-spacing: var(--tracking-label);
  color: var(--color-text-muted);
}

/* ===========================================================================
   FEATURE LIST
   =========================================================================== */
.feature-list {
  display: flex;
  flex-direction: column;
  gap: var(--space-3);
}

/* IMPORTANT: this is NOT a grid.
   An earlier version used `display: grid` with two columns, and the `::before`
   marker was the first cell. Result: EVERY inline tag in the content
   (<strong>, <a>, <em>) became a separate grid cell and landed on a new row —
   a bullet containing bold text fell apart into three lines with a hole in the
   middle. The bug only became visible after the first <strong> was added.

   Hence the marker is absolutely positioned and the content flows normally. */
.feature-list__item {
  position: relative;
  padding-left: calc(10px + var(--space-3));
  color: var(--color-text-secondary);
  font-size: var(--text-body-sm);
  line-height: var(--leading-normal);
}

/* List marker: a thin dash, not a checkmark — calmer and less boilerplate. */
.feature-list__item::before {
  content: '';
  position: absolute;
  left: 0;
  /* 2 px, not 1 px: with a line height of 1.55 successive lines land on half
     pixels, so a 1 px dash was antialiased and every other bullet had a crisp
     marker while the rest looked washed out. Verified on a screenshot. */
  top: 0.68em;
  width: 10px;
  height: 2px;
  border-radius: 1px;
  background-color: var(--color-accent);
}

.feature-list--check .feature-list__item {
  padding-left: calc(14px + var(--space-3));
}

.feature-list--check .feature-list__item::before {
  content: '✓';
  top: 0;
  width: auto;
  height: auto;
  background: none;
  color: var(--color-ok-text);
  font-size: var(--text-body-sm);
  line-height: var(--leading-normal);
}

/* ===========================================================================
   DATA FIELD — the visual carrier of the product's core claim
   Field name in monospace, value in the regular typeface.
   =========================================================================== */
.datafield {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--space-1);
  padding: var(--space-3) var(--space-4);
  background-color: var(--color-surface-sunken);
  border: 1px solid var(--color-border-subtle);
  border-left: 2px solid var(--color-accent-border);
  border-radius: var(--radius-xs);
}

.datafield__key {
  font-family: var(--font-mono);
  font-size: var(--text-label);
  letter-spacing: 0.02em;
  color: var(--color-text-muted);
}

.datafield__value {
  font-size: var(--text-body-sm);
  font-weight: var(--weight-medium);
  color: var(--color-text-primary);
  overflow-wrap: anywhere;
}

.datafield--ok {
  border-left-color: var(--color-ok);
}

.datafield--warn {
  border-left-color: var(--color-warn);
}

.datafield--crit {
  border-left-color: var(--color-crit);
}

/* ===========================================================================
   NAVIGATION
   =========================================================================== */
.nav {
  position: sticky;
  top: 0;
  z-index: var(--z-nav);
  background-color: var(--color-nav-bg);
  border-bottom: 1px solid var(--color-nav-border);
  backdrop-filter: blur(14px) saturate(140%);
}

.nav__inner {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-5);
  min-height: var(--nav-height);
}

/* --- Logo --- */
.brand {
  display: inline-flex;
  align-items: center;
  gap: var(--space-3);
  font-family: var(--font-display);
  font-size: 1.0625rem;
  font-weight: var(--weight-bold);
  letter-spacing: -0.02em;
  color: var(--color-text-primary);
  text-decoration: none;
  white-space: nowrap;
}

.brand:hover {
  color: var(--color-text-primary);
}

.brand__mark {
  flex-shrink: 0;
}

/* --- Links --- */
.nav__links {
  display: none;
  align-items: center;
  gap: var(--space-2);
}

@media (min-width: 64rem) {
  .nav__links {
    display: flex;
  }

}

.nav__link {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2);
  padding: var(--space-2) var(--space-3);
  border-radius: var(--radius-sm);
  color: var(--color-text-secondary);
  font-size: var(--text-body-sm);
  text-decoration: none;
  transition: color var(--duration-fast) var(--ease-out),
    background-color var(--duration-fast) var(--ease-out);
}

.nav__link:hover {
  color: var(--color-text-primary);
  background-color: var(--color-accent-quiet);
}

/* The current page — also marked with the aria-current attribute. */
.nav__link[aria-current='page'] {
  color: var(--color-accent-text);
}

.nav__actions {
  display: flex;
  align-items: center;
  gap: var(--space-3);
}

/* On a narrow screen the main call to action does not fit next to the logo, the
   theme toggle and the menu button — we move it to the bottom of the mobile menu (.nav__cta-mobile). */
.nav__cta {
  display: none;
}

@media (min-width: 64rem) {
  .nav__cta {
    display: inline-flex;
  }

}

.nav__cta-mobile {
  margin-top: var(--space-3);
}

@media (min-width: 64rem) {
  .nav__cta-mobile {
    display: none;
  }

}

/* --- Products dropdown menu --- */
.dropdown {
  position: relative;
}

.dropdown__trigger {
  background: none;
  border: 0;
  cursor: pointer;
}

.dropdown__chevron {
  transition: transform var(--duration-fast) var(--ease-out);
}

.dropdown__trigger[aria-expanded='true'] .dropdown__chevron {
  transform: rotate(180deg);
}

.dropdown__panel {
  position: absolute;
  top: calc(100% + var(--space-3));
  left: 0;
  min-width: 340px;
  padding: var(--space-3);
  display: flex;
  flex-direction: column;
  gap: var(--space-1);
  background-color: var(--color-surface);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-md);
  box-shadow: var(--shadow-lg);
  /* Hidden via the hidden attribute on the element — see nav.js */
}

.dropdown__panel[hidden] {
  display: none;
}

.dropdown__item {
  display: grid;
  grid-template-columns: 1fr auto;
  gap: var(--space-1) var(--space-3);
  padding: var(--space-3);
  border-radius: var(--radius-sm);
  text-decoration: none;
  transition: background-color var(--duration-fast) var(--ease-out);
}

.dropdown__item:hover {
  background-color: var(--color-surface-raised);
}

.dropdown__item-name {
  font-weight: var(--weight-medium);
  font-size: var(--text-body-sm);
  color: var(--color-text-primary);
}

.dropdown__item-desc {
  grid-column: 1 / -1;
  font-size: var(--text-caption);
  line-height: var(--leading-normal);
  color: var(--color-text-muted);
}

/* --- Theme toggle --- */

/* The sun icon is shown in the dark theme (click -> light) and vice versa. */

/* --- Mobile menu --- */
.nav__burger {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 38px;
  height: 38px;
  padding: 0;
  background-color: transparent;
  border: 1px solid var(--color-border);
  border-radius: var(--radius-sm);
  color: var(--color-text-primary);
  cursor: pointer;
}

@media (min-width: 64rem) {
  .nav__burger {
    display: none;
  }

}

.nav__mobile {
  display: flex;
  flex-direction: column;
  gap: var(--space-1);
  padding-block: var(--space-4) var(--space-6);
  border-top: 1px solid var(--color-border-subtle);
}

.nav__mobile[hidden] {
  display: none;
}

@media (min-width: 64rem) {
  .nav__mobile {
    display: none;
  }

}

.nav__mobile-link {
  padding: var(--space-3) var(--space-2);
  border-radius: var(--radius-sm);
  color: var(--color-text-secondary);
  font-size: var(--text-body);
  text-decoration: none;
}

.nav__mobile-link:hover {
  background-color: var(--color-accent-quiet);
  color: var(--color-text-primary);
}

.nav__mobile-group {
  padding: var(--space-2);
  font-family: var(--font-mono);
  font-size: var(--text-label);
  letter-spacing: var(--tracking-label);
  text-transform: uppercase;
  color: var(--color-text-muted);
}

/* ===========================================================================
   ACCORDION (FAQ)
   Built on <details>/<summary> — works without JavaScript.
   =========================================================================== */
.faq {
  display: flex;
  flex-direction: column;
  gap: var(--space-3);
}

.faq__item {
  background-color: var(--color-surface);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-md);
  overflow: hidden;
  transition: border-color var(--duration-base) var(--ease-out),
    background-color var(--duration-base) var(--ease-out);
}

.faq__item[open] {
  border-color: var(--color-accent-border);
  background-color: var(--color-surface-raised);
}

.faq__question {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-4);
  padding: var(--space-5);
  cursor: pointer;
  font-family: var(--font-display);
  font-size: var(--text-body-lg);
  font-weight: var(--weight-medium);
  letter-spacing: -0.015em;
  color: var(--color-text-primary);
  list-style: none;
}

.faq__question::-webkit-details-marker {
  display: none;
}

.faq__question:hover {
  color: var(--color-accent-text);
}

.faq__icon {
  flex-shrink: 0;
  color: var(--color-accent-text);
  transition: transform var(--duration-base) var(--ease-out);
}

.faq__item[open] .faq__icon {
  transform: rotate(45deg);
}

.faq__answer {
  padding: 0 var(--space-5) var(--space-5);
  color: var(--color-text-secondary);
  font-size: var(--text-body-sm);
  line-height: var(--leading-relaxed);
  max-width: var(--width-prose);
  display: flex;
  flex-direction: column;
  gap: var(--space-3);
}

.has-js .faq__item[open] .faq__answer {
  animation: faq-answer-in var(--duration-base) var(--ease-out) both;
}

@keyframes faq-answer-in {
  from { opacity: 0; transform: translateY(-8px); }
  to { opacity: 1; transform: none; }
}

@media (prefers-reduced-motion: reduce) {
  .has-js .faq__item[open] .faq__answer {
    animation: none;
  }
}

/* ===========================================================================
   FORM
   =========================================================================== */
.form {
  display: flex;
  flex-direction: column;
  gap: var(--space-5);
}

.form__row {
  display: grid;
  gap: var(--space-5);
}

@media (min-width: 40rem) {
  .form__row--2 {
    grid-template-columns: 1fr 1fr;
  }

}

.field {
  display: flex;
  flex-direction: column;
  gap: var(--space-2);
}

.field__label {
  font-family: var(--font-mono);
  font-size: var(--text-label);
  font-weight: var(--weight-medium);
  letter-spacing: var(--tracking-label);
  text-transform: uppercase;
  color: var(--color-text-muted);
}

.field__required {
  color: var(--color-accent-text);
}

.field__input,
.field__textarea,
.field__select {
  width: 100%;
  padding: var(--space-3) var(--space-4);
  background-color: var(--color-surface-sunken);
  border: 1px solid var(--color-border-control);
  border-radius: var(--radius-sm);
  color: var(--color-text-primary);
  font-size: var(--text-body-sm);
  transition: border-color var(--duration-fast) var(--ease-out),
    background-color var(--duration-fast) var(--ease-out);
}

.field__input::placeholder,
.field__textarea::placeholder {
  color: var(--color-text-muted);
}

.field__input:hover,
.field__textarea:hover,
.field__select:hover {
  border-color: var(--color-border-strong);
}

.field__textarea {
  min-height: 130px;
  resize: vertical;
}

/* Error message — appears together with aria-invalid on the field. */
.field__error {
  display: none;
  font-size: var(--text-caption);
  color: var(--color-crit-text);
}

.field__input[aria-invalid='true'],
.field__textarea[aria-invalid='true'],
.field__select[aria-invalid='true'] {
  border-color: var(--color-crit);
}

.field__input[aria-invalid='true'] ~ .field__error,
.field__textarea[aria-invalid='true'] ~ .field__error,
.field__select[aria-invalid='true'] ~ .field__error {
  display: block;
}

.field__hint {
  font-size: var(--text-caption);
  color: var(--color-text-muted);
}

/* Consent / checkbox */
.checkbox {
  display: grid;
  grid-template-columns: auto 1fr;
  gap: var(--space-3);
  align-items: start;
  font-size: var(--text-caption);
  line-height: var(--leading-normal);
  color: var(--color-text-secondary);
  cursor: pointer;
}

.checkbox__input {
  width: 18px;
  height: 18px;
  margin-top: 0.15em;
  accent-color: var(--color-accent);
  cursor: pointer;
}

/* Form feedback message */
.form__status {
  padding: var(--space-4) var(--space-5);
  border: 1px solid transparent;
  border-radius: var(--radius-sm);
  font-size: var(--text-body-sm);
}

.form__status[hidden] {
  display: none;
}

.form__status--ok {
  background-color: var(--color-ok-quiet);
  border-color: color-mix(in srgb, var(--color-ok) 32%, transparent);
  color: var(--color-ok-text);
}

.form__status--error {
  background-color: var(--color-crit-quiet);
  border-color: color-mix(in srgb, var(--color-crit) 32%, transparent);
  color: var(--color-crit-text);
}

/* ===========================================================================
   FOOTER
   =========================================================================== */
.footer {
  background-color: var(--color-canvas-deep);
  border-top: 1px solid var(--color-border-subtle);
  padding-block: var(--space-9) var(--space-6);
}

.footer__grid {
  display: grid;
  gap: var(--space-8);
  grid-template-columns: 1fr;
}

@media (min-width: 48rem) {
  .footer__grid {
    grid-template-columns: 1.4fr 1fr 1fr 1fr;
    gap: var(--space-6);
  }

}

.footer__heading {
  font-family: var(--font-mono);
  font-size: var(--text-label);
  font-weight: var(--weight-medium);
  letter-spacing: var(--tracking-label);
  text-transform: uppercase;
  color: var(--color-text-muted);
}

.footer__list {
  display: flex;
  flex-direction: column;
  gap: var(--space-3);
}

.footer__link {
  color: var(--color-text-secondary);
  font-size: var(--text-body-sm);
  text-decoration: none;
}

.footer__link:hover {
  color: var(--color-accent-text);
}

.footer__bottom {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-4);
  margin-top: var(--space-8);
  padding-top: var(--space-5);
  border-top: 1px solid var(--color-border-subtle);
  font-size: var(--text-caption);
  color: var(--color-text-muted);
}

/* ===========================================================================
   REVEAL ON SCROLL
   ===========================================================================
   CRITICAL: the hiding applies ONLY when <html> carries the .has-js class
   (added by the inline script in <head>, before the first paint).

   Reason: if `.reveal { opacity: 0 }` were unconditional, then with JavaScript
   disabled or blocked — a corporate proxy, an old browser, a failed file
   load — half of the page would be BLANK. The animation is decoration and
   must be layered on top of a working page, not a precondition for the page
   being visible at all.
   =========================================================================== */
.has-js .reveal {
  opacity: 0;
  transform: translateY(14px);
  transition: opacity var(--duration-slow) var(--ease-out),
    transform var(--duration-slow) var(--ease-out);
}

.has-js .reveal.is-visible {
  opacity: 1;
  transform: none;
}

@media (prefers-reduced-motion: reduce) {
  .has-js .reveal {
    opacity: 1;
    transform: none;
  }

}

/* ===========================================================================
   CARD HEADER WITH ICON
   ===========================================================================
   The icon and the title sit ON ONE LINE, not stacked.

   Reason: an icon tile placed on its own above the heading eats vertical space
   and forms no visual relation with the title — it reads like an ornament
   wedged between the card edge and the content. On one line the icon works as
   a topic marker: the eye enters the card at the icon and the title is right there.

   Usage:
     <div class="card__head">
       <span class="ico-tile" aria-hidden="true"><span class="ico ico--telefon"></span></span>
       <h3 class="card__title">Tytul</h3>
     </div>
   =========================================================================== */
.card__head {
  display: flex;
  align-items: center;
  gap: var(--space-4);
}

/* The title may run longer than one line — we do not let it push the icon out. */
.card__head .card__title,
.card__head .autocard__title,
.card__head .channel__name {
  min-width: 0;
  text-wrap: balance;
}

/* Icon tile: smaller than in the first version (44 -> 40 px) and with a radius
   consistent with the rest of the site. It should support the title, not compete with it. */
.ico-tile {
  width: 40px;
  height: 40px;
  border-radius: var(--radius-sm);
}

.ico-tile .ico {
  --ico-size: 20px;
}

/* On very narrow screens the icon steps down a size so the title gets the full
   line width instead of wrapping onto four lines. */
@media (max-width: 26rem) {
  .card__head {
    gap: var(--space-3);
  }

  .ico-tile {
    width: 34px;
    height: 34px;
  }

  .ico-tile .ico {
    --ico-size: 18px;
  }

}

/* ===========================================================================
   PODKREŚLENIA I ZNACZNIKI ODRĘCZNE
   ===========================================================================
   A drawn underline under two or three words, in the same hand as the icon
   set: one stroke, no fill, slightly irregular so it reads as drawn rather
   than as a border-bottom.

   WHY A MASK AND NOT A BACKGROUND IMAGE: the accent differs between themes
   (--blue-500 dark, --blue-650 light). A colour baked into a data URI would
   be right in one theme and wrong in the other. Masking a plain background
   colour keeps the token in charge.

   USE IT ON SHORT PHRASES ONLY. The stroke is one box under one run of text,
   so a phrase that wraps to a second line gets one long underline across
   both. That is a limitation of the device, not a bug to fix — emphasis
   underlines belong under two or three words anyway.
   =========================================================================== */
.mark {
  position: relative;
  white-space: nowrap;
}

.mark::after {
  content: '';
  position: absolute;
  inset-inline: -0.08em;
  inset-block-end: -0.18em;
  block-size: 0.30em;
  background-color: var(--color-accent);
  opacity: 0.85;
  pointer-events: none;
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 200 14' preserveAspectRatio='none'%3E%3Cpath d='M4 9.6C38 4.8 66 11.4 101 7.2c30-3.6 62 1.8 95 3' fill='none' stroke='%23000' stroke-width='4.2' stroke-linecap='round'/%3E%3C/svg%3E");
  mask-size: 100% 100%;
  mask-repeat: no-repeat;
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 200 14' preserveAspectRatio='none'%3E%3Cpath d='M4 9.6C38 4.8 66 11.4 101 7.2c30-3.6 62 1.8 95 3' fill='none' stroke='%23000' stroke-width='4.2' stroke-linecap='round'/%3E%3C/svg%3E");
  -webkit-mask-size: 100% 100%;
  -webkit-mask-repeat: no-repeat;
}

/* A second stroke, doubled back, for the one phrase per page that carries the
   whole argument. Used sparingly — two on a page and neither one reads. */
.mark--strong::after {
  block-size: 0.42em;
  opacity: 1;
  mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 200 20' preserveAspectRatio='none'%3E%3Cpath d='M5 12C40 6 68 13.5 103 9c30-3.8 61 1.6 92 2.6' fill='none' stroke='%23000' stroke-width='3.6' stroke-linecap='round'/%3E%3Cpath d='M12 17.2c36-3.4 70 2.2 104-1.4 22-2.4 46-1 68 0' fill='none' stroke='%23000' stroke-width='2.4' stroke-linecap='round' opacity='.55'/%3E%3C/svg%3E");
  -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 200 20' preserveAspectRatio='none'%3E%3Cpath d='M5 12C40 6 68 13.5 103 9c30-3.8 61 1.6 92 2.6' fill='none' stroke='%23000' stroke-width='3.6' stroke-linecap='round'/%3E%3Cpath d='M12 17.2c36-3.4 70 2.2 104-1.4 22-2.4 46-1 68 0' fill='none' stroke='%23000' stroke-width='2.4' stroke-linecap='round' opacity='.55'/%3E%3C/svg%3E");
}

/* ===========================================================================
   ILUSTRACJE LINIOWE
   ===========================================================================
   Inline SVG scenes drawn in the same hand as tools/build-icons.mjs:
   stroke only, no fills, round caps. Two colours and no more — the text
   colour for structure and the accent for the one thing the picture is
   about — so a scene never turns into decoration competing with the copy.

   Inline rather than a sprite or <img>: `currentColor` has to resolve
   against the surface the scene sits on, and the accent has to follow the
   theme token. Both break the moment the SVG is loaded from a separate file.
   =========================================================================== */
.illus {
  display: block;
  inline-size: 100%;
  block-size: auto;
  color: var(--color-text-muted);
  overflow: visible;
}

:is(.illus, .isoicon) .illus__ink {
  fill: none;
  stroke: currentColor;
  stroke-width: 1.5;
  stroke-linecap: round;
  stroke-linejoin: round;
}

/* The subject of the picture. One accent group per scene, no more. */
:is(.illus, .isoicon) .illus__key {
  fill: none;
  stroke: var(--color-accent);
  stroke-width: 1.9;
  stroke-linecap: round;
  stroke-linejoin: round;
}

:is(.illus, .isoicon) .illus__fill {
  fill: var(--color-accent-quiet);
  stroke: none;
}

/* Faint construction lines: the grid a drawing sits on. Never load-bearing. */
:is(.illus, .isoicon) .illus__ghost {
  fill: none;
  stroke: currentColor;
  stroke-width: 1;
  stroke-linecap: round;
  opacity: 0.28;
}

.illus__panel {
  display: flex;
  align-items: center;
  justify-content: center;
  padding: var(--space-6);
  background-color: var(--color-surface-sunken);
  border: 1px solid var(--color-border-subtle);
  border-radius: var(--radius-md);
}

.illus__panel--motion {
  --depth-x: 0deg;
  --depth-y: 0deg;
  perspective: calc(var(--space-12) * 7);
  transition: border-color var(--duration-base) var(--ease-out),
    box-shadow var(--duration-base) var(--ease-out);
}

.illus__panel--motion .illus {
  transform: rotateX(var(--depth-y)) rotateY(var(--depth-x));
  transform-style: preserve-3d;
  transition: transform var(--duration-slow) var(--ease-out);
}

.illus__panel--motion:hover {
  border-color: var(--color-accent-border);
  box-shadow: var(--shadow-md);
}

/* ===========================================================================
   GĘSTA LISTA CECH
   ===========================================================================
   Replaces a grid of cards where every card was icon + title + paragraph +
   a labelled "Efekt" box with a second paragraph. Four of those in a row is
   the same shape four times, and the repeated label stops carrying meaning
   by the third repetition.

   A row is one line of substance. If a point needs a second paragraph it is
   two points, or it belongs in a section of its own.

   Pairs with an illustration in the other half of a `.grid--split`: the list
   stays dense, the picture carries the weight.
   =========================================================================== */
.featurelist {
  display: grid;
}

.featurerow {
  display: grid;
  grid-template-columns: auto minmax(0, 1fr);
  gap: var(--space-3) var(--space-4);
  padding-block: var(--space-5);
  border-block-start: 1px solid var(--color-border-subtle);
  transition: background-color var(--duration-base) var(--ease-out),
    padding-inline var(--duration-base) var(--ease-out);
}

.featurerow:first-child {
  padding-block-start: 0;
  border-block-start: 0;
}

.featurerow:last-child {
  padding-block-end: 0;
}

/* Bare icon, no tile. A tile around every icon in a list of six builds a
   column of boxes that competes with the text for attention. */
.featurerow__icon {
  display: grid;
  place-items: center;
  inline-size: 1.75rem;
  block-size: 1.75rem;
  margin-block-start: 0.1rem;
  color: var(--color-accent-text);
  transition: transform var(--duration-base) var(--ease-spring);
}

@media (hover: hover) {
  .featurerow:hover {
    padding-inline: var(--space-3);
    background-color: var(--color-accent-quiet);
  }

  .featurerow:hover .featurerow__icon {
    transform: translateX(var(--space-1));
  }
}

.featurerow__body {
  display: grid;
  gap: var(--space-2);
  align-content: start;
}

.featurerow__title {
  margin: 0;
  font-family: var(--font-display);
  font-size: var(--text-title);
  line-height: 1.3;
  text-wrap: balance;
}

.featurerow__text {
  margin: 0;
  color: var(--color-text-secondary);
  font-size: var(--text-body-sm);
  /* 1.6 was a one-off: every other dense row on the site sits at 1.55 and every
     block of running text at 1.7. A third value that close to its neighbours
     buys nothing and makes the scale look accidental. */
  line-height: var(--leading-normal);
}

/* ===========================================================================
   ILUSTRACJE — OGRANICZENIE ROZMIARU
   ===========================================================================
   A line drawing does not gain from being large. Past roughly 380 px the
   strokes stay 1.5 px while everything around them grows, so the scene turns
   thin and empty and starts taking room without paying for it.
   =========================================================================== */
.illus__panel .illus {
  max-inline-size: 380px;
  margin-inline: auto;
}

/* --- Isometric scenes: the parts the flat drawings did not need ----------- */

/* The face turned away from the light. Filled, not stroked — the solid is
   what gives an isometric solid its weight, and it is the one place in these
   drawings where a fill is allowed. */
:is(.illus, .isoicon) .illus__shadow {
  fill: var(--color-illus-shadow);
  stroke: none;
}

/* Construction lines: the grid the object stands on, and the path between two
   objects. They describe where things sit, never what they do. */
:is(.illus, .isoicon) .illus__dotted {
  stroke-dasharray: 3 5;
}

:is(.illus, .isoicon) .illus__label {
  fill: var(--color-accent-text);
  stroke: none;
  font-family: var(--font-mono);
  font-size: 11px;
}

/* Isometric scenes carry more geometry than the flat ones, so they need room
   the flat cap would deny them — but still nowhere near full column width. */
.illus__panel .illus--iso {
  max-inline-size: 460px;
}

/* Feature rows laid out in two columns. `:first-child` only clears the rule on
   the very first row, which in a two-column grid leaves a stray line above the
   second column's first row. Clear the first row of BOTH columns.

   The breakpoint MUST match the one where `.grid--pair` actually splits
   (56rem in layout.css). Clearing the border earlier would leave the second
   row separator-less while the list is still a single column. */
@media (min-width: 56rem) {
  .featurelist--split > .featurerow:nth-child(-n + 2) {
    padding-block-start: 0;
    border-block-start: 0;
  }

}

/* ===========================================================================
   MINIATURY IZOMETRYCZNE
   ===========================================================================
   One chip per row of a feature list, drawn in the same projection as the big
   scene beside it. A flat mask icon next to an isometric drawing reads as a
   different family — the row and the picture stop looking like one design.

   The stroke classes are shared with `.illus` through :is(), so a chip and a
   scene can never drift apart in weight or colour.
   =========================================================================== */
.isoicon {
  display: block;
  inline-size: 2.75rem;
  block-size: 2.75rem;
  color: var(--color-text-muted);
  overflow: visible;
}

/* Chips carry more geometry than a mask icon, so the row's icon slot has to
   grow with them. */
.featurerow--iso {
  grid-template-columns: 2.75rem minmax(0, 1fr);
}

.featurerow--iso .featurerow__icon {
  inline-size: 2.75rem;
  block-size: 2.75rem;
  margin-block-start: 0;
  color: inherit;
}

/* The person a module is for. Sits between title and line, quieter than both. */
.featurerow__who {
  margin: 0;
  font-family: var(--font-mono);
  font-size: var(--text-caption);
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--color-accent-text);
}

/* Centred caption under a scene. Without text-anchor an SVG <text> grows to the
   right of its x, so a label meant to sit under the middle object drifts off it
   and collides with whatever is drawn to the right. */
:is(.illus, .isoicon) .illus__label--mid {
  text-anchor: middle;
}

/* A numbered node on a diagram. Filled with the page ground, not transparent:
   the spoke runs underneath it, and an unfilled disc would let the line cross
   the number. */
:is(.illus, .isoicon) .illus__node {
  fill: var(--color-surface-sunken);
  stroke: var(--color-accent);
  stroke-width: 1.6;
}

/* ===========================================================================
   POWIERZCHNIE: GŁĘBIA CIENIEM, NIE OBRYSEM
   ===========================================================================
   On a light background a 1 px border around a white card reads as an outline
   drawn around it; the references this design follows separate surfaces with a
   soft shadow instead, and look considerably more finished for it.

   The border stays, but quieter — it still does the work the shadow cannot,
   which is holding the edge crisp at the top of a card where the shadow is
   weakest, and keeping the card visible for anyone whose browser or settings
   suppress shadows.

   Applied to the surfaces the eye lands on, not to every bordered element:
   dividers, feature-row rules and data-field outlines are lines by intent and
   would only get muddier with a shadow behind them.
   =========================================================================== */
.card,
.autocard,
.illus__panel,
.panels__body {
  border-color: var(--color-border-subtle);
  box-shadow: var(--shadow-sm);
}

/* Hover lifts the card a little further off the page — the same gesture the
   shadow already implies, just more of it. */
.card:hover,
.autocard:hover {
  box-shadow: var(--shadow-md);
}

@media (prefers-reduced-motion: no-preference) {
  .card,
  .autocard {
    transition: box-shadow var(--duration-base) var(--ease-out);
  }
}
