/* ============================================================
   DEIN-VERTRIEB.DE — Design-System
   Basis: Ink-Navy / Weiß / Logo-Blau
   Typo-Skala & Spacing-Skala: konsistent, fluid (clamp)
   ============================================================ */

/* ---------- Schriften (self-hosted, Fontshare FFL) ----------
   General Sans: Headlines/Statements (Gewichte 200–700)
   Switzer: Fließtext/UI (Gewichte 100–900)                    */
@font-face {
  font-family: "General Sans";
  src: url("../assets/fonts/GeneralSans-Variable.woff2") format("woff2");
  font-weight: 200 700;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "Switzer";
  src: url("../assets/fonts/Switzer-Variable.woff2") format("woff2");
  font-weight: 100 900;
  font-style: normal;
  font-display: swap;
}

/* ---------- Custom Properties ---------- */
:root {
  /* Farben — durchgängig dunkles System mit Royalblau-Akzent */
  --ink:        #060B16;   /* Seitenhintergrund (Nachtblau-Schwarz)  */
  --ink-soft:   #0B1526;   /* Abschnitts-Panels                      */
  --surface:    #0D1830;   /* Karten-Flächen                         */
  --navy:       #1A2854;   /* Logo-Navy (Kachelfläche, pixelgemessen) */
  /* Off-White: minimal gebrochen (kühler Hauch), site-weit einziger
     sichtbarer Weißton. Alle Texte/Überschriften/UI referenzieren
     var(--white); durchscheinende rgba(255,255,255,x)-Ränder bleiben. */
  --white:      #F4F7FC;
  --paper:      #0B1526;   /* ehem. helle Sektionen -> dunkles Panel */
  /* Marken-Primärfarbe = „.DE" der Logo-Wortmarke, verbindlich #1976D2.
     Am 01.08.2026 pixelgenau nachgemessen (assets/logo.png, 6300 px):
     die .de-Fläche besteht zu 98,1 % aus exakt #1976D2, der Rest ist
     Kantenglättung. Der wahrgenommene Flächenton (Oklab-Mittel über
     alle 243.998 Kernpixel) ergibt ebenfalls #1976D2 — die Farbe ist
     damit eindeutig belegt. Alle Blau-Akzente der Site sind
     Ableitungen dieser einen Basis:
       --accent-deep  = dunklerer Hover/Active-Ton
       --blue-soft    = aufgehellter Text-Akzent (Eyebrows, Nummern)
       --blue/-deep   = Aliasse (Icons, Ränder, Fokus, Legacy)       */
  --accent:      #1976D2;   /* Logo-Blau (.de), Pixel-gemessen 30.07.26 */
  --accent-deep: #145EA8;   /* dunklere Stufe desselben Blaus (Hover/Fill) */
  --blue:       var(--accent);
  --blue-deep:  var(--accent-deep);
  --blue-soft:  #92B3E2;
  --muted-d:    rgba(244, 247, 252, 0.64);   /* Fließtext            */
  --muted-l:    rgba(244, 247, 252, 0.60);   /* Sekundärtext         */
  --line-d:     rgba(140, 162, 210, 0.16);   /* Hairlines            */
  --line-l:     rgba(140, 162, 210, 0.16);   /* Hairlines (Panels)   */

  /* ZWEI getrennte Rundungssysteme (bewusst entkoppelt):
     --button-radius     NUR Buttons: fester Wert, eckige Grundform
                         mit weichen Ecken — nie Pill/50%/999px, und
                         nie vom Container-Radius abgeleitet.
     --container-radius  Alle größeren Flächen: Bilder, Videos,
                         Cards, Kacheln, Container.
     (Funktionale Kreise wie Fill/Play/Spotlight: 50%.) */
  --button-radius:    10px;
  --container-radius: 1.25rem;

  /* Kartentiefe — ein Token für die ganze Karten-Familie (.fact,
     .showcase-card, .principle, .process-card, .testimonial-card),
     damit die Karten nicht auseinanderlaufen können.

     BEWUSST OHNE SCHLAGSCHATTEN. Gemessen (headless, 2x, Delta gegen
     schattenlos, nur Kartenbereich):
        0 2px 10px rgba(0,0,0,0.12)  ->  max. 3 RGB-Stufen, Mittel 1,4
        inset 0 1px 0 rgba(255,255,255,0.035) -> max. 8 Stufen, Mittel 7,5
     Der Schatten lag dabei schon am oberen Ende des Vertretbaren und war
     trotzdem unsichtbar: Auf --paper (#0B1526) hat Schwarz nichts mehr
     abzudunkeln. Er hätte je Karte eine Compositing-Ebene gekostet und
     dafür nichts geliefert -> raus.

     Das Randlicht zeichnet stattdessen die Oberkante nach (Licht von
     oben) und verankert die Karte, ohne sie anzuheben. Kein neuer
     Farbton — Weiß mit 3,5 % Deckkraft. Sollte hier je ein Schatten
     nötig werden, gehört er nicht ins Schwarze, sondern in eine
     Aufhellung der Fläche. */
  --card-depth: inset 0 1px 0 rgba(255, 255, 255, 0.035);

  /* Karten-Innenabstand — EIN Wert für die Familie (.fact, .process-card,
     .showcase-card seitlich, .testimonial-card). Fluid: 40px auf kleinen
     Breiten (dort ist Fläche das knappe Gut — fixe 48px drückten die
     min-content-Breite der Panels @390 um 1px über den Viewport), 48px
     am Desktop: Karten atmen, statt zu füllen. .principle bleibt auf
     --s-5 (64px, ohnehin großzügiger). */
  --card-pad: clamp(2.5rem, 1.75rem + 1.5vw, 3rem);

  /* Typografie */
  --font: "Switzer", -apple-system, BlinkMacSystemFont, "Helvetica Neue",
          Helvetica, "Segoe UI", Arial, sans-serif;
  --font-display: "General Sans", var(--font);

  /* Typo-Skala (fluid) — modulare Skala, Verhältnis 1,25.
     Anker ist das Statement (6,6vw, bewusster Einzelmoment). Jede Stufe
     darunter = /1,25:  6,6 → 5,28 → 4,224(≈4,2) → 3,38 → 2,7(≈2,6) vw.
     --fs-d2 (4,2vw) und --fs-h3 (2,6vw) lagen bereits auf dieser Kurve;
     ausgerissen ist allein --fs-d1: mit 6vw stand es zwischen Statement
     und H1 UND trug die Sektions-Headlines — die H1 hing an --fs-lead
     (3vw) und war damit nur fünftgrößte Ebene (Hierarchie-Inversion).
     Seit dem Modern-Ausroll ist die H1 der Anker der Hierarchie:
     Rangfolge @1440: H1/page-title 95,0 > Statement 76,0 > H2 60,5
     > H3 36,0 — auf jeder Seite, lückenlos von 320px bis 2560px
     (Floors und Caps der Stufen schneiden sich nirgends).
     Das Footer-Wortzeichen (9,6vw) steht als Bildmarke außerhalb
     der Text-Hierarchie. */
  --fs-d1:        clamp(2.4rem, 6.6vw, 6.6rem);   /* H1 / page-title     */
  --fs-statement: clamp(2.1rem, 5.28vw, 5.28rem); /* Statement-Ebene     */
  --fs-d2:        clamp(1.85rem, 4.2vw, 4rem);    /* Sektions-Headline   */
  --fs-h3:     clamp(1.5rem, 2.6vw, 2.25rem);   /* Karten-Headline       */
  --fs-h4:     1.25rem;                         /* Sub-Headline          */
  --fs-h5:     1.125rem;                        /* Kleinste Headline     */
  --fs-lead:   clamp(1.8rem, 3vw, 2.9rem);      /* Marquee / große Copy  */
  --fs-body-l: clamp(1.08rem, 1.4vw, 1.3rem);   /* Große Copy            */
  --fs-body:   1.0625rem;                       /* Fließtext             */
  --fs-small:  0.875rem;                        /* Labels, Meta          */
  --fs-tiny:   0.75rem;                         /* Feinstes              */
  --fs-btn-sm: 0.9375rem;                       /* Kompakt-Buttons       */

  /* Spacing-Skala */
  --s-1: 0.5rem;
  --s-2: 1rem;
  --s-3: 1.5rem;
  --s-4: 2.5rem;
  --s-5: 4rem;
  --s-6: clamp(4rem, 8vw, 7rem);
  --s-7: clamp(6rem, 11vw, 10rem);
  --s-8: clamp(8rem, 14vw, 13rem);

  /* Layout */
  --gutter: clamp(1.25rem, 4vw, 4rem);
  --max-w: 100rem;

  /* Motion */
  --ease: cubic-bezier(0.22, 1, 0.36, 1);
  --dur: 0.9s;       /* Reveal-Einblendungen        */
  --dur-slow: 1.1s;  /* Karten-Kipp / Wortmarke     */
  --t-fast: 0.35s;   /* Farben, Rahmen, Opacity     */
  --t-med: 0.45s;    /* Bewegung (Underline, Plus)  */
  --stagger: 0.09s;  /* EIN Stagger-Schritt site-weit (Reveal-Folgen) */
}

/* ---------- Reset / Basis ---------- */
*, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }

html {
  scroll-behavior: smooth;
  -webkit-text-size-adjust: 100%;
}

body {
  font-family: var(--font);
  -webkit-tap-highlight-color: transparent;
  font-size: var(--fs-body);
  line-height: 1.6;
  color: var(--white);
  background: var(--ink);
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
  overflow-x: hidden;
}

img, svg, video { display: block; max-width: 100%; }

/* Typo-Geste (Redesign 17.07.): GENAU EIN inhaltlich starkes Wort pro
   Seite in Markenblau — ruhiger Ankermoment in der prominenten H1.
   Kontrast --accent auf --ink: 4,2:1 — über der 3:1-Schwelle für
   Display-Größen. Nie zwei Wörter pro Seite; Legal-Seiten bewusst ohne. */
.accent-word { color: var(--accent); }

/* Anker landen nicht unter der fixen Navigation */
[id] { scroll-margin-top: 7rem; }
/* Erstgespräch-Anker (kontakt.html): Die Formularsektion trägt das große
   Sektions-Padding (--s-8) — mit dem Standard-scroll-margin stünde nach
   dem Sprung erst 200px Leerraum im Viewport. Der negative Anteil zieht
   die Sektionskante über den Viewportrand, sodass der INHALT (Kontakt-
   block + Formular) knapp unter dem fixierten Header beginnt. Skaliert
   mit, weil --s-8 selbst fluid ist. */
#erstgespraech { scroll-margin-top: calc(7.5rem - var(--s-6)); }
/* Startseiten-Kontaktsektion: volles Sektionspolster, daher derselbe Ausgleich. */
#kontakt { scroll-margin-top: calc(7.5rem - var(--s-8)); }
/* Bewerbungs-Anker (karriere.html): tiefer kalibriert (Runde 3, Block 7) —
   „In 2 Minuten bewerben" landet direkt unter der Header-Unterkante
   (gemessen: Abstand ~9 px @1440, ~13 px @768/@390; Ziel ≤ 24 px), damit
   oberhalb kein dunkler Streifen steht und Bild/Formular maximal sichtbar
   sind. Mobil ist der Header flacher → eigener Wert. */
#bewerbung { scroll-margin-top: calc(5rem - var(--s-8)); }
@media (max-width: 900px) {
  #bewerbung { scroll-margin-top: calc(4.5rem - var(--s-8)); }
}
/* kontakt: Das Formular steht im DOM zuerst (Sprungziel + mobile
   Reihenfolge), optisch bleibt es am Desktop in Spalte 2 — die Info-
   Spalte in Spalte 1. Ab <=900px (einspaltiges Grid) hebt der Reset die
   Platzierung auf, sonst erzeugte grid-column:2 eine implizite Spalte. */
#erstgespraech .contact-grid > .contact-form { grid-column: 2; grid-row: 1; }
#erstgespraech .contact-grid > div { grid-column: 1; grid-row: 1; }
@media (max-width: 900px) {
  #erstgespraech .contact-grid > .contact-form,
  #erstgespraech .contact-grid > div { grid-column: auto; grid-row: auto; }
}

/* Ausgewogene Zeilenumbrueche, keine Einwort-Waisen */
h1, h2, h3, h4, .statement-text { text-wrap: balance; }

/* ------------------------------------------------------------
   WORTTRENNUNG — Grundsatz (Runde 52)
   Das Trennwoerterbuch von macOS/iOS trennt nach Silben und kennt keine
   Wortfugen. Es zerlegte „Zufallskontakten" zu „Zufall-skontakten",
   „Datenschutzerklaerung" zu „Datenschut-zerklaerung" und trennte sogar
   Kuerzel („DS-GVO") und E-Mail-Adressen. Gegenmittel, ohne die
   automatische Trennung ganz aufzugeben (schmale Spalten ab 320px
   brauchen sie):
   1. Mindestlaengen — nur Woerter ab 6 Buchstaben, je Zeile mindestens 3.
      Das beseitigt getrennte Kuerzel und Zwei-Buchstaben-Reste
      („Adres-se", „Provisi-on"). Standard-Eigenschaft ab Safari 17 /
      Chrome 109; die -webkit-Paare greifen in aelteren WebKit-Fassungen.
   2. Seitentitel trennen nur an gesetzten Stellen — siehe .page-title
      im 700px-Block. Ein Fehler in 38px-Schrift ist dauerhaft sichtbar.
   3. Adressen und Eigennamen per .kein-trenn ausnehmen.
   ------------------------------------------------------------ */
body {
  -webkit-hyphenate-limit-before: 3;
  -webkit-hyphenate-limit-after: 3;
  hyphenate-limit-chars: 6 3 3;
}

/* Nie trennen: Kuerzel, Eigennamen, zusammengesetzte Fachbegriffe, deren
   Wortfuge das Woerterbuch verfehlt. */
.kein-trenn {
  -webkit-hyphens: manual;
  hyphens: manual;
}

/* Adressen duerfen bei Platzmangel umbrechen, aber ohne Trennstrich —
   er wuerde als Teil der Adresse mitgelesen. */
a[href^="mailto:"],
a[href^="tel:"] {
  -webkit-hyphens: manual;
  hyphens: manual;
  overflow-wrap: anywhere;
}

/* Display-Schrift für die grosse Typo-Ebene.
   font-synthesis: none — deklarierte 800er-Gewichte clampen sauber
   auf das General-Sans-Maximum 700, ohne Faux-Bold. */
h1, h2, h3,
.statement-text,
.footer-wordmark,
.hero-marquee__group {
  font-family: var(--font-display);
  font-synthesis: none;
}

a { color: inherit; text-decoration: none; }

button {
  font: inherit;
  color: inherit;
  background: none;
  border: 0;
  cursor: pointer;
}

::selection { background: var(--blue); color: var(--white); }

:focus-visible {
  outline: 2px solid var(--blue);
  outline-offset: 3px;
}

.skip-link {
  position: absolute;
  top: -100%;
  left: var(--gutter);
  z-index: 200;
  padding: 0.75rem 1.25rem;
  /* Runde 26: --accent-deep statt --blue. Weiß auf dem hellen Marken-Blau
     erreicht 4,29:1 und verfehlt die Barrierefreiheits-Norm (4,5:1) knapp;
     mit der dunkleren Hover-Farbe des Design-Systems sind es 6,12:1. */
  background: var(--accent-deep);
  color: var(--white);
  font-size: var(--fs-small);
  transition: top 0.2s var(--ease);
}
.skip-link:focus { top: 1rem; }

/* Nur für Screenreader sichtbar (z. B. Struktur-Überschriften ohne visuelle Wirkung) */
.visually-hidden {
  position: absolute;
  width: 1px; height: 1px;
  margin: -1px; padding: 0; border: 0;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
}

.container {
  width: 100%;
  max-width: var(--max-w);
  margin-inline: auto;
  padding-inline: var(--gutter);
}

/* Kleine zentrierte Sektions-Labels */
.section-label {
  display: block;
  text-align: center;
  font-size: var(--fs-small);
  font-weight: 400;
  letter-spacing: 0.04em;
  margin-bottom: var(--s-5);
}
.section-dark .section-label,
.section-light .section-label,
.section-paper .section-label { color: var(--blue-soft); }
.process-head .section-label { text-align: left; margin-bottom: var(--s-3); }

/* ============================================================
   BUTTON-SYSTEM (einheitlich, global)
   Jeder Button nutzt .btn. Origin-Fill-Hover ergänzt das JS
   (.has-fill / .btn-fill / .btn-label); ohne JS greift der
   Farb-Hover-Fallback. Varianten: .btn--ghost, .btn--sm.
   Neue Buttons übernehmen Design + Animation automatisch.
   ============================================================ */
.btn {
  position: relative;
  overflow: hidden;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.5rem;
  background: var(--accent);
  color: var(--white);
  font-family: inherit;
  font-size: var(--fs-body);
  font-weight: 700;
  letter-spacing: 0.02em;
  line-height: 1.1;
  padding: 0.95rem 1.9rem;
  border: 0;
  border-radius: var(--button-radius);
  cursor: pointer;
  white-space: nowrap;
  /* Alle drei Kanäle auf --t-fast: transform lief als einziger auf einer
     freien 0,25s und damit 0,1s vor den beiden anderen — beim Hover, der
     Farbe und Rahmen gleichzeitig bewegt, ein sichtbarer Versatz. */
  transition: background-color var(--t-fast) var(--ease),
              border-color var(--t-fast) var(--ease),
              transform var(--t-fast) var(--ease);
}
.btn:hover { background: var(--accent-deep); }      /* Fallback ohne JS */
.btn.has-fill:hover { background: var(--accent); }   /* mit JS: Farbe kommt aus der Füllung */
.btn:active { transform: scale(0.985); }

/* Kompakte Größe (Header) — gleiche Optik/Animation, nur kleiner */
.btn--sm {
  font-size: var(--fs-btn-sm);
  font-weight: 600;
  padding: 0.62rem 1.4rem;
}

/* Ghost/Outline-Variante — dezent, zurückhaltend.
   Padding um die Randstärke reduziert → exakt gleiche
   Gesamthöhe wie die randlosen Primärbuttons. */
.btn--ghost {
  background: transparent;
  color: var(--white);
  border: 1px solid rgba(255, 255, 255, 0.28);
  padding: calc(0.95rem - 1px) calc(1.9rem - 1px);
  font-weight: 600;
}
.btn--ghost:hover,
.btn--ghost.has-fill:hover {
  background: transparent;
  border-color: rgba(255, 255, 255, 0.55);
}
.btn--ghost .btn-fill { background: rgba(255, 255, 255, 0.08); }
/* Die frühere „+"-Glyphe im Ghost-Button ist entfernt (Runde 3, Block 3) —
   die zugehörigen Regeln ebenfalls, kein Ghost-Button trägt mehr ein Plus. */

/* Origin-Fill-Kreis + Label-Ebene */
.btn-fill {
  position: absolute;
  border-radius: 50%;
  background: var(--accent-deep);
  transform: translate(-50%, -50%) scale(0);
  /* Vorher: 0,5s cubic-bezier(0.16,1,0.3,1) — eine eigene Kurve, die der
     Signatur-Ease optisch fast gleicht, aber ohne Grund danebenlag (die
     dokumentiert kalibrierten Panel-FX-Kurven sind davon unberührt).
     Jetzt --ease + --t-med, dieselbe Sprache wie jede andere Bewegung. */
  transition: transform var(--t-med) var(--ease);
  pointer-events: none;
}
.btn-fill.is-active { transform: translate(-50%, -50%) scale(1); }
.btn-label {
  position: relative;
  z-index: 1;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.5rem;
  color: #fff;   /* reines Weiß auf Akzent-Blau → 4,64:1 (AA), statt Off-White 4,32:1 */
}
/* Ghost-Button liegt auf Dunkel, nicht auf Blau → Off-White beibehalten (Weißton-Konsistenz) */
.btn--ghost .btn-label { color: var(--white); }

/* Hero-Aktionen: unter dem Nutzensatz, above the fold.
   Runde 12: kein grid-column mehr — die Buttons liegen jetzt im einspaltigen
   .hero-lead-Grid und würden mit grid-column:2 eine zweite Spalte aufziehen. */
/* Runde 13: Button-Paare site-weit exakt gleich groß — jede Aktionszeile
   ist ein Grid mit gleich breiten Spalten (eine je Button); gleiche Höhe
   folgt aus identischem Padding. Gilt für Hero, Zwischen-CTAs und die
   mobile Leiste. */
.hero-actions {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: 1fr;
  align-items: stretch;
  gap: var(--s-3);
}
.hero-actions .btn { justify-content: center; text-align: center; }

/* Utilities (ersetzen Inline-Styles) */
.pt-0 { padding-top: 0; }
.content-media { padding-block: var(--s-5); }
/* Kö-Bogen-Bild (nur kontakt.html): füllt die Info-Spalte auf voller Breite —
   die frühere 32rem-Kappung ließ rechts einen sichtbaren Reststreifen stehen
   und machte die Spalte unruhig (Runde 7). Höhe folgt dem 4:3-Verhältnis. */
.contact-media { margin-top: var(--s-5); }
/* Karriere-Ghost-Button direkt unter der Karte, harmonischer Abstand */
.career-cta { margin-top: var(--s-4); max-width: 32rem; }
/* .contact-heading--sm entfernt: Der Modifier setzte --fs-d2 und stand auf
   beiden Live-Instanzen (index, karriere) IMMER neben .contact-heading —
   die Basisgröße war also nie sichtbar. Seit .contact-heading selbst auf
   --fs-d2 sitzt, wäre die Regel ein exaktes Duplikat. Die Klasse darf im
   HTML stehen bleiben, sie greift ins Leere. */
/* Lange Titel eine Stufe tiefer (Statement-Stufe) statt freier clamp.
   Doppelklasse nötig: Die einfache Klasse verlor per Quelltext-Reihenfolge
   gegen .page-title (steht später in der Datei, gleiche Spezifität) und
   war seit jeher wirkungslos — dritter Fund derselben Reihenfolgen-Falle
   (.fact-strip-Media-Query, .pt-0, hier). */
.page-title.page-title--long {
  font-size: var(--fs-statement);
  max-width: 20ch;
}

/* ============================================================
   NAVIGATION
   ============================================================ */
.site-header {
  position: fixed;
  inset: 0 0 auto 0;
  z-index: 100;
  transition: background-color var(--t-med) var(--ease),
              box-shadow var(--t-med) var(--ease),
              transform var(--t-med) var(--ease);
}

.site-header.is-scrolled {
  background: rgba(6, 11, 22, 0.86);
  -webkit-backdrop-filter: blur(14px);
  backdrop-filter: blur(14px);
  box-shadow: 0 1px 0 var(--line-d);
}

.site-header.is-hidden { transform: translateY(-100%); }

.nav {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--s-4);
  padding-block: 1.25rem;
}

.nav-logo { flex: 0 0 auto; }
.nav-logo img {
  height: clamp(2.6rem, 4vw, 3.3rem);
  width: auto;
}

.nav-links {
  display: flex;
  align-items: center;
  gap: clamp(1.25rem, 2.6vw, 2.75rem);
  list-style: none;
}

.nav-links a {
  position: relative;
  font-size: 1rem;
  color: var(--white);
  padding-block: 0.4rem;
}

/* Unterstrich-Animation */
.nav-links a::after {
  content: "";
  position: absolute;
  left: 0; bottom: 0;
  width: 100%;
  height: 1px;
  background: currentColor;
  transform: scaleX(0);
  transform-origin: right;
  transition: transform var(--t-med) var(--ease);
}
.nav-links a:hover::after,
.nav-links a[aria-current="page"]::after {
  transform: scaleX(1);
  transform-origin: left;
}

/* Header-CTA (ersetzt die frühere Telefonnummer oben rechts) —
   nutzt das globale .btn/.btn--sm-System, hier nur Layout im Header */
.nav-cta { flex: 0 0 auto; }

/* CTA im mobilen Menü (Desktop: eigener Header-Button) */
.nav-links-cta { display: none; }
.nav-links-cta a::after { content: none; }

/* Burger (mobil) */
.nav-burger {
  display: none;
  position: relative;
  z-index: 120;
  width: 2.5rem;
  height: 2.5rem;
}
/* R4: Trefferfläche auf ≥44×44px erweitern ohne das Icon zu verschieben
   (transparentes Overlay, kein visueller Eingriff). */
.nav-burger::before {
  content: "";
  position: absolute;
  inset: -2px;
}
.nav-burger span {
  position: absolute;
  left: 50%;
  width: 1.5rem;
  height: 1.5px;
  background: var(--white);
  transform: translateX(-50%);
  transition: transform var(--t-med) var(--ease), opacity var(--t-fast);
}
.nav-burger span:nth-child(1) { top: 0.9rem; }
.nav-burger span:nth-child(2) { top: 1.5rem; }
.nav-burger[aria-expanded="true"] span:nth-child(1) {
  transform: translateX(-50%) translateY(0.3rem) rotate(45deg);
}
.nav-burger[aria-expanded="true"] span:nth-child(2) {
  transform: translateX(-50%) translateY(-0.3rem) rotate(-45deg);
}

/* ============================================================
   HERO
   ============================================================ */
.hero {
  position: relative;
  min-height: 100svh;
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  background: var(--ink);
  color: var(--white);
  padding-top: clamp(6.5rem, 12vh, 9rem);
  overflow: hidden;
}

/* Einspaltig (Modern-Ausroll): Eyebrow ÜBER der Headline. Die H1 hat
   die volle Breite und hält die 95px-Stufe zweizeilig — im alten
   5fr/7fr-Grid bräuchte sie drei Zeilen und risse die Falz. */
.hero-grid {
  display: grid;
  grid-template-columns: 1fr;
  gap: var(--s-3);
  align-items: start;
}

/* Eyebrow: bewusst leise gegen die H1 (Spreizung ~8x). Weit gesperrt
   wie die übrigen Kleinst-Labels der Site (0,14em). Kontrast --muted-d
   auf --ink: 7,45:1 -> AA auch bei 12px. */
.hero-label {
  grid-column: 1;
  /* Runde 16: von 10px auf 12px vergrößert (Josh) und dafür auf die Breite
     des Handlungsblocks begrenzt — die Zeile schließt links wie rechts
     bündig mit dem Button-Paar darunter ab. Die Breite ist dieselbe Rechnung
     wie Spalte 1 der Medienzeile (5 von 12 Spalten, abzüglich des Rasterspalts),
     deshalb sitzt die Kante exakt. Sie läuft damit auch nicht mehr in das
     Motiv hinein — der frühere Grund für die 10px entfällt.
     Kontrast --muted-d auf --ink = 7,45:1 → AA. */
  font-size: 0.75rem;
  color: var(--muted-d);
  letter-spacing: 0.1em;
  max-width: calc((100% - var(--s-4)) * 5 / 12);
}
@media (max-width: 900px) {
  /* Einspaltig gibt es keinen Handlungsblock daneben — volle Breite. */
  .hero-label { max-width: none; }
}

/* Hero-H1 — größte Text-Ebene der Site (95px-Stufe). line-height 0,98
   und Tracking -0,03em = Kurvenwert dieser Stufe. */
.hero-statement {
  grid-column: 1;
  font-size: var(--fs-d1);
  font-weight: 700;
  line-height: 0.98;
  letter-spacing: -0.03em;
  max-width: 22ch;
}

.hero-media-row {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
  gap: var(--s-4);
  /* Runde 13: stretch statt start — der Handlungsblock (.hero-lead) nimmt
     die Höhe des Motivs an, seine Vertrauenszeile schließt unten bündig
     mit der Bildunterkante ab. */
  align-items: stretch;
  margin-top: var(--s-5);   /* Luft um die Kernaussage (Pilot-Maß) */
}

.hero-media {
  grid-column: 2;
}


/* Lauftext-Marquee: zwei gegenläufige Endloszeilen (ersetzt die frühere Wortmarke) */
.hero-marquee {
  margin-top: var(--s-4);
  padding-block: var(--s-2) clamp(1rem, 3vh, 2.5rem);
  display: grid;
  gap: 0.25rem;   /* kompakter; Zeilen berühren sich nie (line-height 1.1) */
  user-select: none;
}
.hero-marquee__row { overflow: hidden; }
.hero-marquee__track {
  display: flex;
  width: max-content;
  animation: hero-marquee 120s linear infinite;   /* Faktor 2 langsamer, bewusster Dauerlauf */
  will-change: transform;
}
/* Untere Zeile: identisch, nur gegenläufig */
.hero-marquee__track--reverse { animation-direction: reverse; }
.hero-marquee__group {
  flex: none;
  white-space: nowrap;
  /* --fs-lead bleibt hier bewusst stehen und folgt der H1 NICHT nach oben:
     Die Marquee-Geschwindigkeit ergibt sich aus Track-Breite / 120s. Eine
     größere Schrift verbreitert den Track und würde das eingefrorene Tempo
     verändern. Größe daher an das Tempo gebunden, nicht an die H1. */
  font-size: var(--fs-lead);
  font-weight: 700;
  line-height: 1.1;
  letter-spacing: -0.04em;
  color: var(--muted-d);       /* selber gedämpfter Weißton wie der Hero-Fließtext */
}
@keyframes hero-marquee {
  from { transform: translateX(0); }
  to   { transform: translateX(-50%); }
}
/* Lauftext läuft dauerhaft durch — bewusst kein Hover-Stopp. */

/* ============================================================
   MEDIEN-PLATZHALTER
   Feste Container (aspect-ratio) — finale Medien später 1:1
   per <img>/<video> mit object-fit: cover austauschbar.
   ============================================================ */
.media-ph {
  position: relative;
  width: 100%;
  overflow: hidden;
  border-radius: var(--container-radius);
  background:
    radial-gradient(120% 140% at 85% 10%, rgba(25, 118, 210, 0.18), transparent 60%),
    linear-gradient(160deg, var(--ink-soft) 0%, var(--navy) 130%);
  /* Innenliegende Hairline rahmt auch spätere echte Medien hochwertig */
  box-shadow: inset 0 0 0 1px rgba(255, 255, 255, 0.08);
}
.media-ph.ratio-21-9  { aspect-ratio: 21 / 9; }
.media-ph.ratio-16-9  { aspect-ratio: 16 / 9; }
.media-ph.ratio-4-3   { aspect-ratio: 4 / 3; }

/* Feine Passermarken-Linien */
.media-ph::before,
.media-ph::after {
  content: "";
  position: absolute;
  background: rgba(255, 255, 255, 0.22);
}
.media-ph::before {
  left: 8%; right: 8%;
  top: 50%;
  height: 1px;
}
.media-ph::after {
  top: 32%; bottom: 32%;
  left: 50%;
  width: 1px;
}

/* Panel-Variante (ehem. helle Sektionen) */
.media-ph.light {
  background:
    radial-gradient(120% 140% at 85% 10%, rgba(25, 118, 210, 0.2), transparent 60%),
    linear-gradient(160deg, var(--surface) 0%, var(--ink-soft) 130%);
}
.media-ph.light::before,
.media-ph.light::after { background: rgba(255, 255, 255, 0.22); }

/* Video-Platzhalter-Variante (Play-Symbol + Beschriftung, ohne Passermarken) */
.hero-video-slot {
  max-width: 72rem;
  margin: var(--s-6) auto 0;
}

/* Scroll-Aufricht-Effekt des Videos (Basis: amphora-website-v11
   „Augenweide"/initTabletStraighten): Perspektive 1500px am Slot — bewusst
   etwas weiter als das Original (1200px), damit der nun stärkere Startwinkel
   (34°) elegant statt verzerrt wirkt. Die 3D-Neigung liegt auf .video-tilt;
   der Cursor-Hover-Tilt ist für dieses Video entfernt (main.js: :not(.is-video)),
   es gibt also nur diesen einen Effekt. Nur transform (GPU-freundlich); die
   scrollgekoppelten Werte setzt main.js. Ruhe-/No-JS-Zustand &
   prefers-reduced-motion: Video steht gerade. */
.hero-video-slot { perspective: 1500px; }
.video-tilt {
  transform-origin: center center;
  will-change: transform;
}
@media (prefers-reduced-motion: reduce) {
  .video-tilt { transform: none !important; }
}
.media-ph.is-video::before,
.media-ph.is-video::after { display: none; }

/* Austausch-Slot: finale Medien füllen den Container exakt */
.media-ph > img,
.media-ph > video,
.media-ph > svg {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
}

/* Kacheln mit Inline-SVG-Motiv: flächiger fast-schwarzer Grund (= Kachel),
   Platzhalter-Passermarken entfernt. Der Kipp-Hover auf .media-ph bleibt
   unberührt (die SVG ist Kind des Hover-Containers und kippt mit). */
.media-ph.has-art { background: var(--surface); }
.media-ph.has-art::before,
.media-ph.has-art::after { display: none; }

/* ============================================================
   HOVER-ANIMATIONEN DER LEISTUNGS-SVG-KACHELN (.has-art / .art-0N)
   Grundsatz (bindend): Ruhezustand vollständig & unverändert — die
   Grafik selbst (Linien, Punkte, Position, Form) bleibt absolut stabil.
   System „Lichtimpuls" (Panels 01/02/03/06/07): Bei Hover wandert EINMAL
   ein dezenter Glow-Punkt (eigenes, im Ruhezustand unsichtbares
   FX-Overlay) entlang der bestehenden Linien/Pfade; Knoten glühen als
   reines Helligkeits-Overlay auf. ~1 s, ease-out, kein Loop. Panel 02
   nutzt translateX (gerade Linie), 01/03/06/07 nutzen offset-path.
   Panels 04/05 behalten ihre gestaffelten Helligkeits-/Scale-Impulse
   auf den Bestandselementen. Kipp-Hover ist für diese Kacheln im JS
   deaktiviert (.media-ph:not(.has-art)). Immer nur das gehoverte Panel;
   prefers-reduced-motion schaltet alles ab.
   ============================================================ */

/* Animierte SVG-Teile skalieren/erhellen um die eigene Mitte. Ohne
   Transform (= Ruhezustand) hat dies keinerlei visuelle Wirkung. */
.media-ph.has-art svg circle,
.media-ph.has-art svg path,
.media-ph.has-art svg line,
.media-ph.has-art svg g {
  transform-box: fill-box;
  transform-origin: center;
}
/* FX-Ebene (.artfx / .art02-fx / .art04-coreblue) nutzt BEWUSST dieselbe
   fill-box wie das Basismotiv (Regel oben) — hier KEINE eigene transform-box.
   Die Bewegung läuft über offset-path (Panels 01/03/04/05/06/07), translateX
   (Panel 02) und opacity; alle drei sind unter fill-box korrekt (Punkt liegt
   auf der Linie). Siehe docs/Panel-FX-Diagnose.md.
   AUDIT-P5 / FALLE (dokumentiert statt „gefixt"): Ein view-box-Override auf der
   FX-Ebene verlegt transform-origin:center auf die viewBox-Mitte (300,200) und
   schiebt die offset-path-Punkte ~360–390 Einheiten aus der viewBox (unsichtbar).
   Daher: KEIN CSS-`transform` mit skalar-/prozent-relativen bzw. origin-
   abhängigen Werten (rotate, scale, %-translate) auf FX-Elemente ergänzen und
   die transform-box hier NICHT auf view-box stellen — sonst lebt P5 wieder auf.
   Braucht ein künftiges FX-Element ein solches transform, transform-box gezielt
   NUR an diesem Element setzen, nicht pauschal auf der FX-Ebene. */

/* ---- Gemeinsames Lichtimpuls-System der Panels 01/03/06/07 ----
   Exakt das Panel-02-Prinzip (dort translateX auf gerader Linie, hier
   offset-path/offset-distance für Polylinien und Kurven): Ruhezustand =
   FX-Overlays unsichtbar (opacity 0), Grafik vollständig statisch. Hover =
   ein Glow-Punkt fährt EINMAL den bestehenden Pfad ab (gleiche Glow-
   Gradients, gleiches Timing ~1 s, gleiche Kurve wie Panel 02); Knoten
   glühen als reines Helligkeits-Overlay auf (keine Skalierung). Nur
   offset-distance/opacity → GPU-freundlich. Browser ohne offset-path-
   Support (@supports-Guard): alles bleibt statisch. reduced-motion wird
   über die bestehende has-art-Regel unten abgeschaltet. */
.artfx { pointer-events: none; }
.artfx circle { opacity: 0; }

@supports (offset-path: path("M0 0H10")) {
  @keyframes artfx-ride {
    0%   { offset-distance: 0%;   opacity: 0; }
    12%  { opacity: 1; }
    86%  { opacity: 1; }
    100% { offset-distance: 100%; opacity: 0; }
  }
  /* dezente Variante (Panel 07: Schimmer statt voller Lichtpunkt) */
  @keyframes artfx-ride-soft {
    0%   { offset-distance: 0%;   opacity: 0; }
    12%  { opacity: 0.65; }
    86%  { opacity: 0.65; }
    100% { offset-distance: 100%; opacity: 0; }
  }
  /* Knoten-Aufglühen — identisch zu art02-nodepulse (Panel 02) */
  @keyframes artfx-node {
    0%   { opacity: 0; }
    42%  { opacity: 0.9; }
    100% { opacity: 0; }
  }

  /* 01 Leadgenerierung — zwei Lichtimpulse laufen die bestehenden
     Verbindungspfade von außen nach innen zum blauen Zielknoten (das
     letzte kurze Stück 430→460 führt in die Knotenmitte); der Knoten
     glüht beim Eintreffen einmal sanft auf. Einzelpunkte bleiben ruhig. */
  .art01-spark--a { offset-path: path("M95,120 L165,155 L240,182 L315,196 L430,200 L460,200"); offset-rotate: 0deg; }
  .art01-spark--b { offset-path: path("M95,285 L165,250 L240,220 L315,205 L430,200 L460,200"); offset-rotate: 0deg; }
  .showcase-row:hover .art-01 .art01-spark--a,
  .showcase-row:hover .art-01 .art01-spark--b {
    animation: artfx-ride 1000ms cubic-bezier(0.22,0,0.15,1) 1 both;
    will-change: offset-distance, opacity;
  }
  .showcase-row:hover .art-01 .art01-node {
    animation: artfx-node 480ms cubic-bezier(0.33,0,0.2,1) 720ms 1 both;
    will-change: opacity;
  }
}

/* 02 Direktvertrieb — ECHTER wandernder Lichtimpuls: ein separates Glow-
   Overlay (.art02-spark) läuft einmal von links (x=80) bis zum Kreis
   (x=512, Weg = 432 Nutzereinheiten) über die bestehende Leitung; die
   Linie, das blaue Segment und der Kreis bleiben absolut stabil (kein
   Move/Scale der Grafik selbst). Beim Ankommen glüht der Kreis über
   .art02-node einmal sanft auf (reines Helligkeits-/Opacity-Overlay,
   keine Skalierung). Ruhezustand: beide Overlays opacity:0 = statisch.
   Abschluss: weiches Auslaufen zurück in den statischen Zustand
   (kein sichtbarer Rücksprung). Nur opacity/transform → GPU-freundlich. */
.art02-fx { pointer-events: none; }
.art02-spark { opacity: 0; transform: translateX(0); }
.art02-node  { opacity: 0; }
.showcase-row:hover .art-02 .art02-spark {
  animation: art02-travel 1000ms cubic-bezier(0.22,0,0.15,1) 1 both;
  will-change: transform, opacity;
}
.showcase-row:hover .art-02 .art02-node {
  animation: art02-nodepulse 480ms cubic-bezier(0.33,0,0.2,1) 720ms 1 both;
  will-change: opacity;
}
@keyframes art02-travel {
  0%   { transform: translateX(0);     opacity: 0; }
  12%  { opacity: 1; }
  86%  { opacity: 1; }
  100% { transform: translateX(432px); opacity: 0; }
}
@keyframes art02-nodepulse {
  0%   { opacity: 0; }
  42%  { opacity: 0.9; }
  100% { opacity: 0; }
}

/* 03 Kundenbindung — der Lichtpunkt läuft einmal ruhig die GESAMTE
   Achterschleife ab (beide Kreise, Kreuzung im Berührpunkt 300,200) und
   kehrt zum Ausgangspunkt zurück: wiederkehrender Kreislauf. Sanftes
   Ease-in-out = an den Kurvenenden minimal langsamer; Dauer leicht über
   Panel 02, da der Weg (~754 Einheiten) deutlich länger ist — die
   wahrgenommene Lichtgeschwindigkeit bleibt dadurch gleich ruhig. */
@supports (offset-path: path("M0 0H10")) {
  .art03-spark {
    offset-path: path("M300,200 A60,60 0 1 1 180,200 A60,60 0 1 1 300,200 A60,60 0 1 0 420,200 A60,60 0 1 0 300,200");
    offset-rotate: 0deg;
  }
  .showcase-row:hover .art-03 .art03-spark {
    /* 1750 ms = Schleifenlänge (~754 E) / Panel-02-Tempo (432 E/s) —
       damit ist die wahrgenommene Lichtgeschwindigkeit identisch zu 02 */
    animation: artfx-ride 1750ms cubic-bezier(0.37,0,0.63,1) 1 both;
    will-change: offset-distance, opacity;
  }
}

/* 04 Vertriebskampagnen — statisches Motiv (Ringe + blauer Bogen) bleibt
   unangetastet; animiert wird NUR die FX-Overlay-Ebene. Ein weißer Kopf-
   Punkt läuft bei Hover einmal von außen nach innen und folgt dabei EXAKT
   den vorhandenen Linien: Der unsichtbare Bewegungspfad (offset-path,
   keine gezeichnete Linie) besteht aus 150°-Bögen exakt AUF jedem der
   fünf Ringradien (180/152/124/96/68), verbunden durch kurze tangentiale
   45°-Übergänge, mit 90°-Einlauf, der exakt auf dem Innenring (r 16)
   endet. Hinter dem Kopf zieht ein blauer Energie-Schweif (#1976D2) auf
   DERSELBEN Bahn her: sechs zeitversetzte Follower (40 ms Staffel) mit
   nach hinten fallendem Radius (13 → 5) und fallender Peak-Deckkraft
   (0,62 → 0,14, per --o in den Keyframes) — vorne kräftig, nach hinten
   fein auslaufend (Taper), ruhig statt grell. Länge ≈ 2114 E → 3800 ms,
   sanftes Ease-in-out, kein Loop. Am Ende (ab 3400 ms) blendet das
   Zentrum-Overlay ein (blauer Ring auf dem Innenring + weicher Glow)
   und BLEIBT stehen (forwards), solange der Hover anhält. Kein
   transform-Attribut auf FX-Elementen → die Altregel
   (transform-box: fill-box) kann hier nicht greifen. */
@supports (offset-path: path("M0 0H10")) {
  .art04-mover {
    offset-path: path("M300.0,20.0 L315.7,20.7 L331.3,22.7 L346.6,26.1 L361.6,30.9 L376.1,36.9 L390.0,44.1 L403.2,52.6 L415.7,62.1 L427.3,72.7 L437.9,84.3 L447.4,96.8 L455.9,110.0 L463.1,123.9 L469.1,138.4 L473.9,153.4 L477.3,168.7 L479.3,184.3 L480.0,200.0 L479.3,215.7 L477.3,231.3 L473.9,246.6 L469.1,261.6 L463.1,276.1 L455.9,290.0 L447.4,303.2 L437.9,315.7 L427.3,327.3 L415.7,337.9 L403.2,347.4 L390.0,355.9 L374.8,360.3 L359.4,363.3 L344.2,364.9 L329.1,365.0 L314.3,363.8 L300.0,361.3 L286.2,357.6 L273.1,352.8 L260.7,346.8 L248.0,342.8 L235.8,337.8 L224.0,331.6 L212.8,324.5 L202.3,316.4 L192.5,307.5 L183.6,297.7 L175.5,287.2 L168.4,276.0 L162.2,264.2 L157.2,252.0 L153.2,239.3 L150.3,226.4 L148.6,213.2 L148.0,200.0 L148.6,186.8 L150.3,173.6 L153.2,160.7 L157.2,148.0 L162.2,135.8 L168.4,124.0 L175.5,112.8 L183.6,102.3 L192.5,92.5 L202.3,83.6 L212.8,75.5 L224.0,68.4 L235.8,62.2 L248.0,57.2 L260.7,53.2 L274.1,53.4 L287.3,54.8 L300.0,57.3 L312.2,61.0 L323.7,65.6 L334.5,71.2 L344.5,77.6 L353.7,84.8 L362.0,92.6 L371.1,98.4 L379.7,105.0 L387.7,112.3 L395.0,120.3 L401.6,128.9 L407.4,138.0 L412.4,147.6 L416.5,157.6 L419.8,167.9 L422.1,178.5 L423.5,189.2 L424.0,200.0 L423.5,210.8 L422.1,221.5 L419.8,232.1 L416.5,242.4 L412.4,252.4 L407.4,262.0 L401.6,271.1 L395.0,279.7 L387.7,287.7 L379.7,295.0 L371.1,301.6 L362.0,307.4 L352.4,312.4 L342.4,316.5 L332.1,319.8 L321.5,322.1 L310.8,323.5 L300.0,324.0 L289.5,320.4 L279.5,316.0 L270.3,310.8 L261.8,304.8 L254.2,298.3 L247.3,291.2 L241.4,283.7 L236.3,275.9 L232.1,267.9 L226.5,261.7 L221.4,255.1 L216.9,248.0 L213.0,240.6 L209.8,232.8 L207.3,224.8 L205.5,216.7 L204.4,208.4 L204.0,200.0 L204.4,191.6 L205.5,183.3 L207.3,175.2 L209.8,167.2 L213.0,159.4 L216.9,152.0 L221.4,144.9 L226.5,138.3 L232.1,132.1 L238.3,126.5 L244.9,121.4 L252.0,116.9 L259.4,113.0 L267.2,109.8 L275.2,107.3 L283.3,105.5 L291.6,104.4 L300.0,104.0 L308.4,104.4 L316.7,105.5 L324.8,107.3 L331.8,112.7 L337.9,118.6 L343.3,124.9 L347.9,131.6 L351.7,138.4 L354.7,145.3 L356.9,152.3 L358.3,159.2 L358.9,166.0 L361.6,171.3 L363.9,176.7 L365.7,182.4 L367.0,188.2 L367.7,194.1 L368.0,200.0 L367.7,205.9 L367.0,211.8 L365.7,217.6 L363.9,223.3 L361.6,228.7 L358.9,234.0 L355.7,239.0 L352.1,243.7 L348.1,248.1 L343.7,252.1 L339.0,255.7 L334.0,258.9 L328.7,261.6 L323.3,263.9 L317.6,265.7 L311.8,267.0 L305.9,267.7 L300.0,268.0 L294.1,267.7 L288.2,267.0 L282.4,265.7 L276.7,263.9 L271.3,261.6 L266.0,258.9 L262.7,253.3 L260.0,247.7 L258.0,242.0 L256.8,236.3 L256.1,230.7 L256.1,225.3 L256.7,220.2 L257.8,215.4 L259.4,210.9 L261.5,206.8 L263.9,203.2 L266.7,200.0 L269.7,197.3 L272.9,195.2 L276.2,193.6 L279.5,192.6 L282.9,192.0 L286.1,192.0");
    offset-rotate: 0deg;
  }
  @keyframes artfx04-run {
    0%   { offset-distance: 0%;   opacity: 0; }
    6%   { opacity: var(--o, 1); }
    92%  { opacity: var(--o, 1); }
    100% { offset-distance: 100%; opacity: 0; }
  }
  .showcase-row:hover .art-04 .art04-mover {
    animation: artfx04-run 3800ms cubic-bezier(0.37,0,0.63,1) both;
    will-change: offset-distance, opacity;
  }
  .showcase-row:hover .art-04 .art04-t1 { animation-delay: 40ms; }
  .showcase-row:hover .art-04 .art04-t2 { animation-delay: 80ms; }
  .showcase-row:hover .art-04 .art04-t3 { animation-delay: 120ms; }
  .showcase-row:hover .art-04 .art04-t4 { animation-delay: 160ms; }
  .showcase-row:hover .art-04 .art04-t5 { animation-delay: 200ms; }
  .showcase-row:hover .art-04 .art04-t6 { animation-delay: 240ms; }
  @keyframes artfx04-core {
    from { opacity: 0; }
    to   { opacity: 1; }
  }
  /* Sichtbarkeit steuert die GRUPPE (0 → 1, bleibt via both stehen);
     ihre Kinder müssen daher von der globalen Ruhe-Regel
     „.artfx circle { opacity: 0 }" ausgenommen werden. */
  .art04-coreblue { opacity: 0; }
  .artfx .art04-coreblue circle { opacity: 1; }
  .showcase-row:hover .art-04 .art04-coreblue {
    animation: artfx04-core 500ms cubic-bezier(0.33,0,0.2,1) 3400ms both;
    will-change: opacity;
  }
}

/* 05 Vertriebsoptimierung — „aus Chaos wird Ordnung": Illustration bleibt
   vollständig statisch; EIN weißer Lichtpunkt (Werte identisch Panel 02:
   r 24, gleicher Glow-Gradient, 432 E/s → 650,7 E = 1500 ms, lineares =
   gleichmäßiges Timing) folgt EXAKT dem vierten Chaos-Pfad
   (80,305 → 150,195 → 220,300 → 290,180 → 330,225) und dann der blauen
   Geraden bis zum Linienende (525,225). Der Pfad ist 1:1 aus den
   vorhandenen Linienkoordinaten übernommen (unsichtbarer offset-path,
   kein CSS-Transform → keine Kollision mit der transform-box-Altregel).
   Phase 1 (Chaos, 0–70 % = bis 330,225): Punkt OHNE Schweif. Phase 2
   (Ordnung): Follower blenden ein, sobald sie selbst die Gerade
   erreichen — dezenter, sich verjüngender #1976D2-Energieschweif nur
   auf der blauen Geraden. Am Ende klingt der Punkt weich aus
   (Opacity-Envelope) und die blaue Linie glimmt einmal ruhig auf
   (reiner Helligkeits-Puls, kein Scale). Kein Loop; Reset über
   Hover-Ende wie bei allen Panels. */
@supports (offset-path: path("M0 0H10")) {
  .art05-mover {
    offset-path: path("M80,305 L150,195 L220,300 L290,180 L330,225 L525,225");
    offset-rotate: 0deg;
  }
  @keyframes artfx05-run {
    0%   { offset-distance: 0%;   opacity: 0; }
    4%   { opacity: 1; }
    92%  { opacity: 1; }
    100% { offset-distance: 100%; opacity: 0; }
  }
  /* Schweif: unsichtbar bis zum eigenen Geraden-Eintritt (70 % der Bahn;
     linear → Zeit = Distanz), dann weich auf var(--o) */
  @keyframes artfx05-trail {
    0%   { offset-distance: 0%;   opacity: 0; }
    70%  { opacity: 0; }
    75%  { opacity: var(--o, 0.5); }
    90%  { opacity: var(--o, 0.5); }
    100% { offset-distance: 100%; opacity: 0; }
  }
  .showcase-row:hover .art-05 .art05-mover {
    animation: artfx05-run 1500ms linear both;
    will-change: offset-distance, opacity;
  }
  .showcase-row:hover .art-05 .art05-t1 { animation-name: artfx05-trail; animation-delay: 40ms; }
  .showcase-row:hover .art-05 .art05-t2 { animation-name: artfx05-trail; animation-delay: 80ms; }
  .showcase-row:hover .art-05 .art05-t3 { animation-name: artfx05-trail; animation-delay: 120ms; }
  /* Blaue Gerade glimmt bei Ankunft einmal ruhig auf (Peak ≈ 1500 ms) */
  @keyframes artfx05-lineglow {
    0%   { filter: brightness(1); }
    42%  { filter: brightness(1.5); }
    100% { filter: brightness(1); }
  }
  .showcase-row:hover .art-05 svg > line {
    animation: artfx05-lineglow 480ms cubic-bezier(0.33,0,0.2,1) 1300ms 1 both;
    will-change: filter;
  }
}

/* 06 Terminierung — der Lichtimpuls fährt den bestehenden rechtwinkligen
   Pfad ab (160,250 → 300,250 → 300,175 → 440,175 → 440,250); die drei
   blauen Knoten glühen nacheinander sanft auf, exakt wenn der Impuls sie
   passiert (Knoten bei 0 % / 50 % / 82,6 % der Pfadlänge; Delays an die
   Ease-out-Kurve angepasst). Rasterpunkte bleiben unbewegt. */
@supports (offset-path: path("M0 0H10")) {
  .art06-spark { offset-path: path("M160,250 H300 V175 H440 V250"); offset-rotate: 0deg; }
  .showcase-row:hover .art-06 .art06-spark {
    /* 1400 ms statt 1000 ms: durch die drei Richtungswechsel + drei
       Glow-Events wirkte das rechnerische Panel-02-Tempo hektisch;
       gestreckt auf dieselbe ruhige Wirkung. */
    animation: artfx-ride 1400ms cubic-bezier(0.22,0,0.15,1) 1 both;
    will-change: offset-distance, opacity;
  }
  /* Knoten-Delays an die gestreckte Ease-out-Kurve angepasst: der Spark
     passiert Knoten 2 (50 % Pfad) bei ~370 ms und Knoten 3 (82,6 %) bei
     ~695 ms; Delay = Passage − 202 ms Puls-Anlauf → Peak exakt bei Passage. */
  .showcase-row:hover .art-06 .art06-node--1 { animation: artfx-node 480ms cubic-bezier(0.33,0,0.2,1) 1 both; will-change: opacity; }
  .showcase-row:hover .art-06 .art06-node--2 { animation: artfx-node 480ms cubic-bezier(0.33,0,0.2,1) 170ms 1 both; will-change: opacity; }
  .showcase-row:hover .art-06 .art06-node--3 { animation: artfx-node 480ms cubic-bezier(0.33,0,0.2,1) 490ms 1 both; will-change: opacity; }
}

/* 07 Digitale Tools — zwei SEHR dezente Schimmer (kleinerer Radius,
   reduzierte Deckkraft) laufen die Gitterlinien entlang zum blauen Kreuz:
   einer horizontal auf y=230, einer vertikal auf x=340; sie treffen
   gleichzeitig ein, dann glüht das Kreuz einmal sanft auf. Das Gitter
   selbst bleibt vollständig statisch. */
@supports (offset-path: path("M0 0H10")) {
  .art07-spark--h { offset-path: path("M70,230 L340,230"); offset-rotate: 0deg; }
  .art07-spark--v { offset-path: path("M340,70 L340,230"); offset-rotate: 0deg; }
  .showcase-row:hover .art-07 .art07-spark--h,
  .showcase-row:hover .art-07 .art07-spark--v {
    animation: artfx-ride-soft 1000ms cubic-bezier(0.22,0,0.15,1) 1 both;
    will-change: offset-distance, opacity;
  }
  .showcase-row:hover .art-07 .art07-node {
    animation: artfx-node 480ms cubic-bezier(0.33,0,0.2,1) 720ms 1 both;
    will-change: opacity;
  }
}

@media (prefers-reduced-motion: reduce) {
  .showcase-row:hover .media-ph.has-art svg,
  .showcase-row:hover .media-ph.has-art svg * { animation: none !important; }
}

/* Spotlight: bewusst sehr dezenter Lichthauch, folgt dem Zeiger
   (JS setzt die Position per transform). Soll erst auf den zweiten
   Blick wahrnehmbar sein — nur leichte räumliche Tiefe, nie ein
   Blickfang. Kein harter Lichtrand, keine Farbwirkung. */
.media-spot {
  position: absolute;
  left: -6.5rem;
  top: -6.5rem;
  width: 13rem;
  height: 13rem;
  border-radius: 50%;
  background: radial-gradient(circle at center,
    rgba(255, 255, 255, 0.045),
    rgba(255, 255, 255, 0.018) 40%,
    transparent 70%);
  filter: blur(40px);
  opacity: 0;
  transition: opacity 0.6s var(--ease);
  pointer-events: none;
  z-index: 1;
}
.media-ph:hover .media-spot { opacity: 1; }

/* ============================================================
   SEKTIONS-BASIS (für die nächsten Bauabschnitte)
   ============================================================ */
.section-dark  { background: var(--ink);      color: var(--white); }
.section-light { background: var(--ink);      color: var(--white); }
.section-paper { background: var(--ink-soft); color: var(--white); }

/* Sektions-Raster (Modern-Ausroll): oben --s-8, unten --s-7 — das im
   Piloten etablierte Maß, jetzt für ALLE section-pad-Sektionen. Der
   Abstand zwischen zwei Sektionen ist damit überall gleich:
   s-7 (unten) + s-8 (oben) — ein Raster, keine Sonderfälle. */
.section-pad { padding-block: var(--s-8) var(--s-7); }
/* Das .pt-0-Utility (oben bei den Utilities) verlor gegen diese Regel:
   gleiche Spezifität, aber padding-block steht später in der Datei —
   dieselbe Quelltext-Reihenfolgen-Falle wie beim dokumentierten
   .fact-strip-Bug. .pt-0 war damit seit jeher wirkungslos; erst das
   größere Raster hat es sichtbar gemacht. Doppelklasse gewinnt sicher. */
.section-pad.pt-0 { padding-top: 0; }
/* Abschluss-Sektion mit leiser Schlusszeile: Bodenpolster deutlich kürzer,
   damit die Zeile knapp über dem Footer sitzt. Der freie Raum steht dafür
   über ihr (Abstand am .easter-egg). Doppelklasse wegen Quelltext-Reihenfolge. */
.section-pad.section-pad--tail { padding-bottom: var(--s-4); }

/* ============================================================
   FOOTER (Basisversion — wird in Schritt 4 ausgebaut)
   ============================================================ */
.site-footer {
  background: var(--ink);
  color: var(--white);
}
.footer-bar {
  display: flex;
  flex-wrap: wrap;
  gap: var(--s-2) var(--s-4);
  align-items: center;
  justify-content: space-between;
  padding-block: var(--s-3);
  border-top: 1px solid var(--line-d);
  font-size: var(--fs-small);
  color: var(--muted-d);
}
.footer-bar a { transition: color var(--t-fast) var(--ease); }
.footer-bar a:hover { color: var(--white); }

/* ============================================================
   REVEAL-ANIMATIONEN
   ============================================================ */
.reveal {
  opacity: 0;
  transform: translateY(1.4rem);
  transition: opacity var(--dur) var(--ease), transform var(--dur) var(--ease);
  transition-delay: var(--reveal-delay, 0s);
}
.reveal.in-view {
  opacity: 1;
  transform: none;
}

/* Kopfgruppe einer Sektion (Label -> Lede -> Copy): 0 / 90 / 180 ms —
   die Staffelung des Piloten, jetzt überall wo die Klassen vorkommen. */
.intro-lede.reveal { --reveal-delay: var(--stagger); }
.intro-copy.reveal { --reveal-delay: calc(var(--stagger) * 2); }

/* Wortmarke: leichtes Hochschieben */
.reveal-rise {
  opacity: 0;
  transform: translateY(38%);
  transition: opacity var(--dur-slow) var(--ease), transform var(--dur-slow) var(--ease);
  transition-delay: var(--reveal-delay, 0s);
}
.reveal-rise.in-view {
  opacity: 1;
  transform: none;
}

/* Above-the-fold-Cluster (Hero / Seiten-Hero) sofort mit voller Deckkraft rendern —
   NICHT über JS-.reveal/.in-view gaten, damit das LCP-Element (Hero-Bild index /
   page-title-H1 der übrigen Seiten) ohne JS-Verzögerung paintet. Reveal bleibt für
   alle Sektionen unterhalb des Folds aktiv. Kein Layout-Shift (Startzustand =
   Endzustand). Unter prefers-reduced-motion ohnehin identisch (siehe reduced-motion-
   Block: .reveal → opacity:1). */
.hero .reveal,
.page-hero .reveal {
  opacity: 1;
  transform: none;
  transition: none;
}

/* ============================================================
   RESPONSIVE
   ============================================================ */
@media (max-width: 900px) {
  .nav-cta { display: none; }

  .nav-burger { display: block; }

  .nav-links {
    position: fixed;
    inset: 0;
    z-index: 110;
    flex-direction: column;
    justify-content: center;
    gap: 2.25rem;
    background: var(--ink);
    opacity: 0;
    pointer-events: none;
    transition: opacity var(--t-med) var(--ease);
  }
  .nav-links.is-open {
    opacity: 1;
    pointer-events: auto;
  }
  .nav-links a { font-size: 1.6rem; }

  /* CTA im mobilen Menü: globales .btn-System, nur Größe im Menü-Kontext */
  .nav-links-cta { display: block; }
  .nav-links .nav-links-cta .btn {
    font-size: 1.15rem;
    padding: 0.85rem 1.9rem;
  }

  .hero-actions { grid-column: 1; }
  /* .fact-strip stand hier — wirkungslos, siehe Kommentar an der Basisregel.
     Die zweispaltige Regel steht jetzt direkt hinter .fact-strip. */

  .hero-grid,
  .hero-media-row {
    grid-template-columns: 1fr;
    gap: var(--s-3);
  }
  .hero-label,
  .hero-statement,
  .hero-media { grid-column: 1; }

  /* Mobil-Reihenfolge: H1 → Illustration → Intro */
  .hero-media { order: -1; }

  .hero-statement { max-width: none; }

  /* Hero-Video mobil im 16:9-Ausschnitt (Container bleibt austauschbar) */
  .hero-media .media-ph { aspect-ratio: 16 / 9; }

}

/* ============================================================
   GESTAFFELTE KIND-REVEALS
   Listen und Fakten treten nacheinander auf, sobald der
   Eltern-Block sichtbar wird — ruhiger als ein Block-Fade.
   ============================================================ */
/* EINE Bewegungssignatur (Modern-Ausroll): Reveal-Kanäle laufen auf
   --dur wie jedes andere Reveal; Fläche/Rand bleiben auf --t-fast —
   das ist der Hover, nicht das Reveal. box-shadow ist raus: die
   Randlicht-Kante der Karten ist statisch. */
.split.reveal .plist li,
.split.reveal .benefit li,
.fact-strip.reveal .fact {
  opacity: 0;
  transform: translateY(0.8rem);
  transition: opacity var(--dur) var(--ease), transform var(--dur) var(--ease),
              background-color var(--t-fast) var(--ease),
              border-color var(--t-fast) var(--ease);
}
.split.reveal.in-view .plist li,
.split.reveal.in-view .benefit li,
.fact-strip.reveal.in-view .fact {
  opacity: 1;
  transform: none;
}
/* Stagger auf dem site-weiten 90ms-Schritt (vorher eigenes 80ms-Raster). */
.split.reveal.in-view .plist li:nth-child(2),
.split.reveal.in-view .benefit li:nth-child(2) { transition-delay: var(--stagger); }
.split.reveal.in-view .plist li:nth-child(3),
.split.reveal.in-view .benefit li:nth-child(3) { transition-delay: calc(var(--stagger) * 2); }
.split.reveal.in-view .plist li:nth-child(4),
.split.reveal.in-view .benefit li:nth-child(4) { transition-delay: calc(var(--stagger) * 3); }
.split.reveal.in-view .plist li:nth-child(5),
.split.reveal.in-view .benefit li:nth-child(5) { transition-delay: calc(var(--stagger) * 4); }
.split.reveal.in-view .plist li:nth-child(6),
.split.reveal.in-view .benefit li:nth-child(6) { transition-delay: calc(var(--stagger) * 5); }

/* Fakten-Kacheln: Aufsteigen 1.25rem (20px) statt 0.8rem — nur hier, damit
   .plist/.benefit oben unverändert bleiben. Stagger 90 ms je Kachel; einmalig
   (Reveal-Klasse bleibt gesetzt), kein Overshoot (--ease läuft aus). Der
   Hover-Reset (transition-delay:0s) steht weiter unten und gewinnt bei
   gleicher Spezifität über die Delays hier. */
.fact-strip.reveal .fact { transform: translateY(1.25rem); }
.fact-strip.reveal.in-view .fact:nth-child(2) { transition-delay: var(--stagger); }
.fact-strip.reveal.in-view .fact:nth-child(3) { transition-delay: calc(var(--stagger) * 2); }
.fact-strip.reveal.in-view .fact:nth-child(4) { transition-delay: calc(var(--stagger) * 3); }

@media (prefers-reduced-motion: reduce) {
  .split.reveal .plist li,
  .split.reveal .benefit li,
  .fact-strip.reveal .fact {
    opacity: 1;
    transform: none;
  }
}

/* ============================================================
   REDUCED MOTION
   ============================================================ */
@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
  }
  .reveal, .reveal-rise,
  .split.reveal .plist li,
  .split.reveal .benefit li,
  .fact-strip.reveal .fact {
    opacity: 1;
    transform: none;
    transition-delay: 0s !important;
  }
}

/* ============================================================
   S2 — POSITIONIERUNG (dunkel)
   ============================================================ */
.intro-lede {
  max-width: 62ch;
  margin-inline: auto;
  text-align: center;
  font-size: clamp(1.35rem, 2.3vw, 2.1rem);
  font-weight: 600;
  line-height: 1.35;
  letter-spacing: -0.01em;
}
.intro-copy {
  max-width: 52ch;
  margin: var(--s-4) auto 0;
  text-align: center;
  font-size: var(--fs-body-l);
  color: var(--muted-d);
}

/* Fakten-Leiste: belegbare Arbeitsprinzipien als Vertrauensanker */
/* Runde 14: DREI Spalten statt vier. Seit Runde 12 stehen hier nur noch drei
   Kacheln — die vierte Spur blieb leer, die Reihe endete sichtbar vor dem
   rechten Containerrand. Mit drei Spalten füllen die Kacheln die volle
   Containerbreite (@1600+: 464px je Kachel, 368px Textbreite). */
.fact-strip {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: var(--s-4);
  margin-top: var(--s-6);
}
/* ≤1100 einspaltig: Drei Spalten nur, solange jede Kachel etwa 240px
   Textbreite behält (Maßgabe für alle Kachelraster) — bei 1100px sind es
   noch 232px, darunter reißt der einzeilige Kacheltitel (nowrap) in den
   Innenabstand. Ein 2er-Raster wäre bei drei Kacheln immer ein Waisenkind.
   WICHTIG (Reihenfolgen-Falle): Diese Regel MUSS hinter der Basisregel
   stehen — Media Queries erhöhen die Spezifität nicht. */
@media (max-width: 1100px) {
  .fact-strip { grid-template-columns: 1fr; gap: var(--s-3); }
}
/* Vier gleich große Cards, identisches Padding, im Grid aligned */
.fact-strip .fact {
  display: flex;
  flex-direction: column;
  background: var(--surface);
  border: 1px solid var(--line-d);
  border-radius: var(--container-radius);
  box-shadow: var(--card-depth);
  padding: var(--card-pad);
  will-change: transform;
}
/* Dezente, seriöse Hover-Animation: leichtes Anheben + Schatten +
   sanfte Aufhellung. transition-delay wird zurückgesetzt, damit der
   Hover unmittelbar reagiert (Reveal-Delay wirkt nur beim Einblenden). */
/* Hover ohne Bewegung: nur sanfte Aufhellung von Fläche und Rand */
.fact-strip.reveal.in-view .fact:hover {
  transition-delay: 0s;
  background: #101d38;
  border-color: rgba(140, 162, 210, 0.34);
}
/* Erste Kachel = CTA: dezent abgesetzt über einen Akzent-Rand. Kein neuer Farbton —
   das ist --accent (#1976D2 = rgb(25,118,210)) mit reduzierter Deckkraft, damit
   die Kachel sich abhebt, ohne aus der Reihe zu fallen. Eigener Hover-Rand,
   sonst würde die neutrale Hover-Regel oben den Akzent überschreiben. */
.fact-strip .fact--cta { border-color: rgba(25, 118, 210, 0.55); }
.fact-strip.reveal.in-view .fact--cta:hover { border-color: rgba(25, 118, 210, 0.85); }
/* Kein letter-spacing: .fact-title ist ein <span> in der Fließtext-Schrift
   (Switzer), nicht auf der Display-Ebene. Am unteren Ende der Kurve läuft
   das Tracking gegen 0; die Nachbarn dieser Stufe (<h4> 20px und 17px)
   stehen auf normal. Das vorherige -0,01em machte die KLEINERE Größe
   negativer als die größeren — die Kurve genau falsch herum. */
.fact .fact-title {
  display: block;
  font-size: var(--fs-h5);
  font-weight: 800;
  margin-bottom: 0.4rem;
  /* Runde 3 (Block 1): fixe einzeilige Titelzone — alle vier Fließtexte
     beginnen auf identischer Höhe. white-space:nowrap hält die Titel auf
     einer Zeile; bei knappen 4-Spalten-Breiten (1440–1500) läuft der
     längste Titel wenige Pixel in den Kachel-Innenabstand (48px) —
     gemessen nie bis an den Kachelrand. Darunter greift das 2er-Raster. */
  min-height: 1.6em;
  white-space: nowrap;
}
/* Runde 14: statt 26ch (Text stand als schmale Säule in der breiten Kachel)
   eine reine Lesbarkeitsgrenze. Im Drei-Spalten-Zustand greift sie nie — die
   Kachel ist schmaler (366px @1920) als 58ch. Sie wirkt nur einspaltig
   (≤1100px), wo die Kachel sonst über 900px breite Zeilen bekäme. */
.fact p {
  font-size: var(--fs-body);
  color: var(--muted-d);
  max-width: 58ch;
}

/* ============================================================
   TEXT-CYCLE — „Mehr [Wort]", zweizeilig + zentriert
   Zeile 1 „Mehr", Zeile 2 das wechselnde Wort. „Mehr" steht allein in
   Zeile 1 → kein Positionskonflikt; das Wort in Zeile 2 zentriert sich
   je Wort selbst (keine feste Breite, keine Breiten-Animation). Wechsel
   = ruhiges, weiches Fade (Opacity + minimaler Versatz). Platzierung:
   Leistungen-Seite neben dem „Faire Modelle"-Block (.pricing-intro).
   ============================================================ */
.text-cycle {
  max-width: 68rem;                 /* minimal schmaler als das Video (72rem) */
  margin: var(--s-6) auto 0;
  padding-inline: var(--gutter);
  text-align: center;
}
.text-cycle__line {
  margin: 0;
  font-family: var(--font-display);
  font-weight: 700;
  /* Statement-Stufe (76px): lag vorher mit eigener clamp bei 70,4px
     ZWISCHEN den Skalenstufen — einziger Ausreißer nach dem Ausroll. */
  font-size: var(--fs-statement);
  line-height: 1.12;
  letter-spacing: -0.025em;
  color: var(--white);
}
.text-cycle__lead {
  display: block;                   /* Zeile 1 — statischer Vortext, eigene Zeile */
  color: var(--white);              /* Weiß wie die Hauptüberschriften */
}
.text-cycle__word {
  display: block;                   /* Zeile 2 — Container des Wechselworts */
}
.text-cycle__word-item {
  display: inline-block;            /* zentriert sich je Wort selbst */
  white-space: nowrap;
  color: var(--muted-d);            /* hellgrauer Fließtext-Ton (bestehende Variable) */
  opacity: 1;
  transform: translateY(0);
  /* 0,7s ohne Token — die Dauer MUSS mit der FADE-Konstante in js/main.js
     (700 ms) übereinstimmen: das JS tauscht den Text exakt nach dieser
     Zeit. Bewusst weicher als --t-med, ruhiger Wechsel. */
  transition: opacity 0.7s var(--ease), transform 0.7s var(--ease);
}
.text-cycle__word-item.is-hidden {
  opacity: 0;
  transform: translateY(4px);       /* nur wenige Pixel, sehr dezent */
}
/* prefers-reduced-motion: reines Fade, keine Bewegung. Das !important
   überstimmt gezielt die globale 0.01ms-Transition-Regel, damit hier
   ein weiches Ein-/Ausblenden ohne Versatz erhalten bleibt. */
@media (prefers-reduced-motion: reduce) {
  .text-cycle__word-item {
    transition: opacity var(--dur) var(--ease) !important;
    transform: none !important;
  }
  .text-cycle__word-item.is-hidden { transform: none !important; }
}

/* ------------------------------------------------------------
   Leistungen — „Faire Modelle"-Block zweispaltig:
   links Textblock, rechts die Text-Cycle-Animation als optische
   Einheit (vertikal zentriert zum Text, deutlich größer). Auf
   schmalen Viewports gestapelt (Animation unter den Text).
   ------------------------------------------------------------ */
.pricing-intro {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 6fr);
  gap: var(--s-6);
  align-items: center;
  margin-bottom: var(--s-6);
}
.pricing-intro .process-head { margin-bottom: 0; }
.pricing-intro .text-cycle {
  margin: 0;
  max-width: none;
  padding-inline: 0;
}
/* Erst-Einblendung dieses Blocks zügiger als das Standard-Reveal (0,9s):
   Der animierte Text soll schnell präsent sein, sobald er in den Viewport
   kommt. Nur die Dauer — Ease und Mechanik bleiben die der Signatur. */
.pricing-intro .text-cycle.reveal { transition-duration: var(--t-med); }
.pricing-intro .text-cycle__line {
  /* An die längeren Begriffe angepasst, damit der längste („Gemeinsame
     Verantwortung") einzeilig in die Spalte passt — einzige, abgestimmte
     Größen-Abweichung; Fade/Speed/Position bleiben unverändert. */
  font-size: clamp(1.4rem, 3vw, 3rem);
  /* Kurvenwert der 43px-Stufe — die geerbten -0,025em der Statement-
     Stufe wären hier negativer als bei der größeren H2 (Kurvenbruch). */
  letter-spacing: -0.015em;
}
@media (max-width: 900px) {
  .pricing-intro {
    grid-template-columns: 1fr;
    gap: var(--s-4);
  }
  .pricing-intro .text-cycle { margin-top: var(--s-2); }
}

/* ============================================================
   S3 — LEISTUNGS-SHOWCASE (dunkel)
   ============================================================ */
/* Runde 14: Kopf einspaltig. Der Untertext stand vorher rechts NEBEN der
   Überschrift (Spalte 2, rechtsbündig, unten bündig) — jetzt linksbündig
   direkt darunter, damit Überschrift und Erläuterung eine Leserichtung
   haben und der Blick nicht zwischen zwei Spalten springt. */
.showcase-head {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--s-3);
  margin-bottom: var(--s-6);
}
/* Überschrift über die volle Kopfbreite (fester 2-Zeilen-Umbruch per <br>). */
.showcase-display {
  grid-column: 1;
  grid-row: 1;
  font-size: var(--fs-d2);
  font-weight: 700;
  line-height: 1.05;
  letter-spacing: -0.02em;
}
.showcase-note {
  grid-column: 1;
  grid-row: 2;
  font-size: var(--fs-body-l);
  color: var(--muted-d);
  max-width: 58ch;
  justify-self: start;
}

.showcase-row {
  display: grid;
  grid-template-columns: minmax(0, 6fr) minmax(0, 6fr);
  gap: var(--s-4);
  align-items: stretch;
  margin-bottom: var(--s-6);
  perspective: 1400px;
}
.showcase-card {
  background: var(--surface);
  color: var(--white);
  border: 1px solid var(--line-d);
  border-radius: var(--container-radius);
  box-shadow: var(--card-depth);
  padding: var(--s-5) var(--card-pad);
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  text-align: left;
}
/* Bereichs-Nummer: verortet die Karte in der 7er-Serie (wie „01/07" auf den Detailseiten) */
/* Nummer bewusst zurückgenommen (kleiner + 72 % Deckkraft): stärkerer
   Kontrast zur Titel-Ebene, der Titel führt. */
.showcase-no {
  display: block;
  font-size: var(--fs-tiny);
  font-weight: 700;
  color: var(--blue-soft);
  opacity: 0.72;
  letter-spacing: 0.08em;
  margin-bottom: var(--s-3);
}

/* Tracking auf den Kurvenwert der 36px-Stufe (wie .topic-row h3,
   .split h3, .phase-block > h3). Vorher +0,01em — das einzige positive
   Tracking auf Display-Ebene und damit der einzige Bruch der Kurve
   „größer = negativer". Versalien vertragen den Wert auf dieser Größe;
   die weite Sperrung bleibt den echten Labels (0,04em) vorbehalten. */
.showcase-title {
  margin-top: 0;
  font-size: var(--fs-h3);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: -0.015em;
  line-height: 1.12;
  max-width: 18ch;
}
.showcase-slogan {
  margin-top: var(--s-3);
  font-size: var(--fs-body-l);
  color: var(--muted-l);
  max-width: 38ch;
}
.showcase-link {
  /* margin-top:auto drückt den Link im Flex-Kasten an die Unterkante —
     konsistenter Abschluss aller Karten; padding-top sichert den
     Mindestabstand zum Text darüber. */
  margin-top: auto;
  padding-top: var(--s-4);
  display: inline-flex;
  align-items: baseline;
  gap: 0.5rem;
  font-weight: 700;
  font-size: var(--fs-body);
}
.showcase-link .plus {
  color: var(--blue-soft);   /* 8,7:1 auf Karte (statt --blue 3,8:1) → AA */
  transition: transform var(--t-med) var(--ease);
}
.showcase-link:hover .plus { transform: rotate(90deg); }
.showcase-link .lbl {
  position: relative;
}
.showcase-link .lbl::after {
  content: "";
  position: absolute;
  left: 0; bottom: -3px;
  width: 100%; height: 1px;
  background: currentColor;
  transform: scaleX(0);
  transform-origin: right;
  transition: transform var(--t-med) var(--ease);
}
.showcase-link:hover .lbl::after {
  transform: scaleX(1);
  transform-origin: left;
}

/* Scroll-Effekt: Karten kippen ruhig ein */
.tilt-in {
  opacity: 0;
  transform: rotateX(6deg) translateY(2rem);
  transform-origin: 50% 100%;
  transition: opacity var(--dur-slow) var(--ease), transform var(--dur-slow) var(--ease);
  transition-delay: var(--reveal-delay, 0s);
  will-change: transform, opacity;
}
.tilt-in.in-view {
  opacity: 1;
  transform: none;
}

.showcase-row:last-child { margin-bottom: 0; }

/* Editorial-Rhythmus: jede zweite Zeile spiegelt Karte/Medium */
.showcase-row.is-flipped .showcase-card { order: 2; }
.showcase-row.is-flipped .showcase-media { order: 1; }

/* Medienflächen antworten auf Hover mit Tilt + Spotlight (JS);
   der frühere reine Hover-Zoom ist dadurch ersetzt. */
.showcase-media { border-radius: var(--container-radius); }

/* Runde 10: Alle sieben Panels einer Seite exakt gleich hoch. Zuvor bestimmte
   jede Zeile ihre Höhe selbst — auf der Startseite mit ihren längeren Slogans
   schwankten sie dadurch um bis zu 53px (Panel 3, 5 und 7 waren höher).
   grid-auto-rows:1fr gibt allen Zeilen die Höhe der höchsten. Der Abstand
   läuft jetzt über gap statt über margin-bottom der Zeilen — im Grid würde
   ein Zeilen-Margin die Innenhöhe der gleich hohen Spuren wieder verschieben. */
.showcase-rows {
  display: grid;
  /* minmax(0,1fr) statt der impliziten auto-Spalte: eine auto-Spalte wächst
     auf die Mindestbreite ihres Inhalts (lange Versal-Komposita in den
     Panel-Titeln) und schob die Seite zwischen 730 und 800px um bis zu 7px
     über den Viewport hinaus. Mit minmax(0,1fr) ist die Spalte auf die
     Containerbreite begrenzt und der Inhalt darf umbrechen. */
  grid-template-columns: minmax(0, 1fr);
  gap: var(--s-6);
}
.showcase-rows > .showcase-row { margin-bottom: 0; }
.showcase-list .showcase-rows { gap: var(--s-5); }

/* Illustration füllt die Panel-Zeile immer vollständig aus.
   Vorher hielt sie stur ihr 4:3-Verhältnis — war die Textkachel höher
   (auf der Startseite mit ihren längeren Slogans bei Panel 3, 5 und 7 der
   Fall, gemessen bis 53px), blieb darunter eine sichtbare Lücke und das
   Paar wirkte unausgerichtet. Mit height:100% enden beide Spalten immer
   bündig; das Motiv skaliert per preserveAspectRatio="slice" mit, wird
   also beschnitten statt verzerrt. Die Panel-FX rechnen im viewBox-
   Koordinatensystem und bleiben davon unberührt. */
/* Beides gilt NUR im zweispaltigen Zustand (ab 1100px), wo Textkachel und
   Illustration nebeneinander stehen:
   – grid-auto-rows:1fr macht alle sieben Panels exakt gleich hoch,
   – die Illustration füllt ihre Zeile (height:100%) statt auf ihrem
     4:3-Verhältnis zu beharren und darunter eine Lücke zu lassen.
   aspect-ratio muss dabei weichen, sonst leitet der Browser die BREITE aus
   der gesetzten Höhe ab und die Spalte wird breiter als ihre Zeile.
   Im gestapelten Zustand (<1100px) gilt beides bewusst NICHT: Dort ist die
   Höhe der Illustration nicht auflösbar (height:100% liefe ins Leere und
   die Illustration kollabierte auf wenige Pixel) — sie behält ihr
   4:3-Verhältnis, und die Zeilen wachsen mit ihrem Inhalt. */
@media (min-width: 1100px) {
  .showcase-rows { grid-auto-rows: 1fr; }
  .showcase-row .showcase-media .media-ph {
    height: 100%;
    aspect-ratio: auto;
  }
}
/* Karteninhalt vertikal zentriert — bisher nur auf der Leistungsseite
   (.showcase-list), jetzt für beide Seiten gleich. */
.showcase-card { justify-content: center; }

/* ------------------------------------------------------------
   Leistungs-ÜBERSICHT (leistungen.html): ruhigerer, leichterer
   Rhythmus als auf der Startseite. Karteninhalt vertikal
   zentriert (keine leeren Kartenunterkanten), flachere Medien,
   dichtere Abfolge — bessere Scanbarkeit ohne Inhaltsänderung.
   ------------------------------------------------------------ */
.showcase-list .showcase-row { margin-bottom: var(--s-5); }
.showcase-list .showcase-card { justify-content: center; }
/* Panels 4:3 wie auf der Startseite (Master) — Frame-0-identischer Slice-Crop.
   .has-art nutzt bereits ratio-4-3; diese Zeile hält Nicht-Panel-Medien der
   Liste konsistent bei 4:3 (früher 3:2, vor der Master-Synchronisierung). */
.showcase-list .showcase-media .media-ph { aspect-ratio: 4 / 3; }

/* ============================================================
   S4 — STATEMENT-SEQUENZ (hell)
   ============================================================ */
.statements { overflow: hidden; }
/* Runde 2 (Block 4): kein 48vh-Leerraum mehr — die Sektion trägt Headline +
   Klammer und leitet direkt in die fünf Grundsatz-Zeilen darunter über. */
.statement {
  position: relative;
  display: grid;
  place-items: center;
  padding-block: var(--s-7) var(--s-5);
}
.statement-text {
  position: relative;
  z-index: 1;
  /* Dekorativer Text greift den Zeiger nicht ab, damit das dahinter
     liegende .float-media (media-ph) auf voller Fläche denselben
     Tilt/Spotlight-Hover wie alle anderen Medien erhält. */
  pointer-events: none;
  /* Eine Stufe unter der H1 (76px-Stufe): das Statement bleibt ein
     bewusster Moment, überholt die Hauptaussage aber nicht mehr.
     Tracking -0,025em = Kurvenwert dieser Stufe. */
  font-size: var(--fs-statement);
  font-weight: 700;
  letter-spacing: -0.025em;
  line-height: 1.05;
  text-align: center;
  max-width: 20ch;
}
/* Klammer unter der Statement-Headline: verbindet die Headline mit den
   fünf Grundsatz-Zeilen (Stil der Sektions-Intros, zentriert). */
/* Runde 15: Zwei feste Zeilen (Umbruch per <br>) — der erste Satz muss dafür
   in eine Zeile passen, deshalb 80ch statt 52ch. Auf schmalen Breiten bricht
   Zeile 1 zusätzlich natürlich um; die Zweiteilung bleibt erhalten. */
.statement-sub {
  margin-top: var(--s-3);
  font-size: var(--fs-body-l);
  color: var(--muted-l);
  text-align: center;
  max-width: 80ch;
}
.statement .float-media {
  position: absolute;
  z-index: 0;
  width: clamp(9rem, 17vw, 15rem);
}
.statement .float-a { left: 7%; top: 10%; transform: rotate(-8deg); }
/* float-b bewusst weiter nach unten/rechts gerückt: durch die neuen
   Texte lag das Bild zu weit hinter dem Text. Jetzt sichtbarer im offenen
   Raum rechts, überlappt aber weiterhin teilweise den Text (Gestaltung
   „Text über Bild" bleibt). Overlap-/Rotationswert unverändert. */
.statement .float-b { right: 2%; bottom: 2%; transform: rotate(6deg); }

/* Hover-Lichtimpuls — exakt das System der Leistungs-Panels (.artfx):
   Ruhezustand bleibt vollständig unangetastet (.artfx circle{opacity:0}),
   Bewegung nur über die unsichtbare FX-Ebene; der Glow-Punkt läuft per
   offset-path auf den BESTEHENDEN Linien, Knoten glühen als reines
   Helligkeits-Overlay auf. Blau bleibt konstant. Tempo wie dort:
   432 Einheiten/s → Dauer = Pfadlänge/432 (hier gemessen). Kein Loop.
   ACHTUNG: fill-box UND transform-origin:center hier explizit setzen — die
   has-art-Altregel (siehe oben, Panels) greift nur innerhalb .media-ph.
   SVG-Elemente haben per Default transform-origin 0 0; ohne center liefe der
   Lichtpunkt exakt um seinen eigenen Radius versetzt neben der Linie
   (im Hover-Test gemessen). transform-box NICHT auf view-box stellen (P5).
   FX-Elemente daher auch hier NIE mit transform/dasharray versehen. */
.principle-art .artfx circle {
  transform-box: fill-box;
  transform-origin: center;
}

/* Bewegung respektieren: Grafik bleibt vollständig statisch. */
@media (prefers-reduced-motion: reduce) {
  .principle:hover .principle-art svg * { animation: none; }
}

/* ============================================================
   S5 — KERNTHEMEN (hell, editorial)
   ============================================================ */
.topic-rows { border-bottom: 1px solid var(--line-l); }
.topic-row {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
  gap: var(--s-4);
  padding-block: var(--s-5);
  border-top: 1px solid var(--line-l);
  align-items: start; /* Überschrift-Oberkante = Inhalts-Oberkante */
}
.topic-row h3 {
  font-size: var(--fs-h3);
  font-weight: 700;
  letter-spacing: -0.015em;
  line-height: 1.12;
  max-width: 18ch;
}
.topic-row p {
  font-size: var(--fs-body-l);
  color: var(--muted-l);
  max-width: 58ch;
}

/* ============================================================
   S6 — ABLAUF (paper)
   ============================================================ */
.process-head {
  max-width: 60ch;
  margin-bottom: var(--s-6);
}
.process-head h2 {
  font-size: var(--fs-d2);
  font-weight: 700;
  letter-spacing: -0.02em;
  line-height: 1.05;
}
.process-head p {
  margin-top: var(--s-3);
  font-size: var(--fs-body-l);
  color: var(--muted-l);
  max-width: 52ch;
}
.process-grid {
  display: grid;
  perspective: 1400px;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--s-4);
}
/* 4er-Variante (Vergütungsmodelle, Garantie, Karriere-Kennzahlen).
   Runde 8: Vier Spalten nur, solange jede Kachel mindestens ~240px
   Textbreite behält — gemessen sind das mit dem knapperen 4er-Innenabstand
   (2rem, s. u.) 247px bei 1440. Darunter zerfiele der Fließtext auf ein bis
   zwei Wörter je Zeile. Die Stufen stehen im Responsive-Block weiter unten. */
.process-grid--4 { grid-template-columns: repeat(4, minmax(0, 1fr)); gap: var(--s-3); }
/* 3er-Variante (Befunde, Startseite); @≤900 greift die 1-Spalten-Basisregel
   im Responsive-Block weiter unten (Quelltext-Reihenfolge). */
.process-grid--3 { grid-template-columns: repeat(3, minmax(0, 1fr)); gap: var(--s-3); }
/* ---- Befund- und Garantie-Kacheln: Titelzeile + bündiger Textbeginn ----
   (Runde 6) Statt fester min-height richtet subgrid die Titelzeile jeder
   Kachel-REIHE automatisch auf dieselbe Höhe aus — der Fließtext startet
   damit auf jeder Breite bündig, egal wie viele Zeilen ein Titel braucht.
   Fallback ohne subgrid: zwei Zeilen reservieren (sichere Ausrichtung). */
.befunde-grid .process-card h3,
.garantie-grid .process-card h3,
.model-grid .process-card h3 { min-height: 3.2em; }

@supports (grid-template-rows: subgrid) {
  .befunde-grid .process-card,
  .garantie-grid .process-card,
  .model-grid .process-card {
    display: grid;
    grid-template-rows: subgrid;
    align-content: start;
  }
  .befunde-grid .process-card { grid-row: span 3; }   /* Label · Titel · Text        */
  .garantie-grid .process-card { grid-row: span 2; }  /* Titel · Text                */
  .model-grid .process-card { grid-row: span 3; }     /* Tag · Titel · Text          */
  .befunde-grid .process-card h3,
  .garantie-grid .process-card h3,
  .model-grid .process-card h3 {
    min-height: 0;
    /* Grid-Items wachsen sonst auf ihre Inhaltsbreite und würden die
       Kachel sprengen — hier soll der Titel die Spaltenbreite achten. */
    min-width: 0;
  }
}
/* Abschluss-Statement der Befunde: linke 2px-Akzentleiste, links ausgerichtet */
/* Runde 14: Breite so gesetzt, dass der Satz auf großen Breiten GENAU zwei
   Zeilen belegt (vorher 62ch → drei Zeilen, „teuer." stand allein auf der
   dritten). Schriftgröße bleibt unverändert (--fs-body-l, einheitlich mit
   den übrigen Sektions-Intros); text-wrap:balance verteilt die beiden Zeilen
   gleichmäßig, statt die zweite kurz auslaufen zu lassen. */
.befund-closing {
  margin-top: var(--s-5);
  border-left: 2px solid var(--accent);
  padding-left: var(--s-3);
  font-size: var(--fs-body-l);
  color: var(--white);
  max-width: 92ch;
  text-wrap: balance;
}
.process-card {
  background: var(--surface);
  border: 1px solid var(--line-d);
  border-radius: var(--container-radius);
  box-shadow: var(--card-depth);
  padding: var(--card-pad);
}
.process-card h3 {
  font-size: var(--fs-h4);
  font-weight: 700;
  letter-spacing: -0.01em;
  margin-bottom: var(--s-3);
}
.process-card ol {
  list-style: none;
}
.process-card li {
  display: flex;
  gap: var(--s-2);
  align-items: baseline;
  padding-block: 0.75rem;
  border-top: 1px solid var(--line-l);
  font-size: var(--fs-body-l);
}
.process-card li .step-no {
  font-size: var(--fs-small);
  font-weight: 700;
  color: var(--blue-soft);
  min-width: 2rem;
}

/* ------------------------------------------------------------
   Kompakte Prozess-Leiste (Startseite, Runde 2 Block 5): alle fünf
   Schritte in EINER schlanken Karte statt zweier großer Boxen.
   @1440: Phase A (3 Schritte) links, Phase B (2 Schritte) rechts,
   alle fünf in einer Zeile. @≤900: Phasen untereinander (3+2).
   @≤700: vertikale Liste. Headline der Sektion eine Stufe kleiner
   (36px-Stufe), damit Überschrift und Inhalt im Verhältnis stehen.
   ------------------------------------------------------------ */
.process-compact .process-head { margin-bottom: var(--s-4); }
.process-compact .process-head h2 {
  font-size: var(--fs-h3);
  letter-spacing: -0.015em;
  line-height: 1.12;
}
/* Runde 4 (Block 1): links Einleitung (Zeile 1) + Ghost-Button (Zeile 2,
   unten), rechts der Phasen-Kasten über BEIDE Zeilen. Dadurch gilt:
   Unterkante Button = Unterkante Kasten (Δ 0). Der Kasten beginnt nicht
   am Zeilenanfang, sondern auf Headline-Höhe: --strip-align ist so
   kalibriert, dass die Baseline von „Phase A" auf der Baseline der ersten
   Headline-Zeile liegt (gemessen @1440). */
.process-split {
  --strip-align: 1.4rem;   /* gemessen @1440: Baseline „Phase A" = Baseline Headline */
  display: grid;
  grid-template-columns: minmax(0, 2fr) minmax(0, 3fr);
  grid-template-rows: 1fr auto;
  grid-template-areas:
    "head strip"
    "btn  strip";
  gap: 0 var(--s-5);
}
/* Runde 11: Oberkante Eyebrow = Oberkante Kasten. Der Kasten sitzt um
   --strip-align tiefer als der Zeilenanfang, deshalb erhält der Textblock
   denselben Versatz — beide Spalten starten damit exakt bündig. */
.process-split .process-head {
  grid-area: head;
  margin-bottom: 0;
  margin-top: var(--strip-align);
}
.process-split .process-strip { grid-area: strip; margin-top: var(--strip-align); }
/* Runde 14: Selektor auf .btn verallgemeinert — der Button ist jetzt ein
   blauer Voll-CTA (kein Ghost mehr). margin-top hält den Mindestabstand zur
   Einleitung darüber; die frühere Extra-Regel .process-compact .btn--ghost
   ist damit entfallen. */
.process-split > .btn {
  grid-area: btn;
  justify-self: start;
  align-self: end;
  margin-top: var(--s-4);
}
.process-strip {
  display: grid;
  grid-template-columns: 1fr;   /* Phase A oben, Phase B darunter */
  gap: var(--s-4);
  padding: var(--s-4) var(--card-pad);
  background: var(--surface);
  border: 1px solid var(--line-d);
  border-radius: var(--container-radius);
  box-shadow: var(--card-depth);
}
.process-phase__label {
  display: block;
  font-size: var(--fs-small);
  font-weight: 700;
  color: var(--blue-soft);
  letter-spacing: 0.04em;
  margin-bottom: var(--s-2);
}
/* Runde 4: Schritte VOLLSTÄNDIG untereinander (vorher horizontal) —
   jede Zeile trägt ihre Trennlinie als border-top. */
.process-phase__steps {
  list-style: none;
  display: grid;
  grid-auto-flow: row;
  gap: var(--s-2);
}
.process-phase__steps li {
  display: flex;
  gap: var(--s-2);
  align-items: baseline;
  padding-top: 0.75rem;
  border-top: 1px solid var(--line-l);
  font-size: var(--fs-body);
}
.process-phase__steps .step-no {
  font-size: var(--fs-small);
  font-weight: 700;
  color: var(--blue-soft);
}
@media (max-width: 900px) {
  .process-split {
    grid-template-columns: 1fr;
    grid-template-rows: auto;
    grid-template-areas: "head" "strip" "btn";
    gap: var(--s-4);
  }
  .process-split .process-head { margin-top: 0; }
  .process-split .process-strip { margin-top: 0; }
  .process-split > .btn { align-self: start; margin-top: 0; }
}

/* ------------------------------------------------------------
   Prozess-Langfassung (ueber-uns, Runde 2 Block 8): visuell
   verdichtet, kein Text gekürzt. Schritt-Zeilen enger,
   @1440 zweispaltig (Phase A | Phase B), @≤900 einspaltig.
   ------------------------------------------------------------ */
/* Runde 11: Der Kopf dieser Sektion war die einzige Ausnahme im Raster —
   Headline eine Stufe kleiner als alle anderen Sektions-H2. Jetzt läuft er
   über die Basisregeln (.process-head h2 = --fs-d2, Abstand --s-6), damit
   die Überschrift genauso wirkt wie auf allen anderen Seiten. Deshalb hier
   bewusst KEINE Sonderregel mehr für .process-detail .process-head. */
.phase-grid {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 0 var(--s-6);
  align-items: start;
}
/* Runde 11: Zweispaltig steht der Kopfabstand (--s-6, wie in allen anderen
   Sektionen) über den Phasen — der frühere Zusatzabstand wäre doppelt.
   Einspaltig trennt er weiterhin Phase A von Phase B (Regel unten). */
.phase-grid .phase-block { margin-top: 0; }
.phase-grid .phase-step { padding-block: var(--s-3); }

/* Runde 7 (Block 1): Schritte zeilenweise gegenüberstellen — 01/04, 02/05,
   03/06 beginnen exakt auf derselben Höhe, die Trennlinien laufen in beiden
   Spalten durch. subgrid gibt jeder Zeile die Höhe ihres höheren Inhalts;
   ohne subgrid bleibt das bisherige Verhalten (Spalten laufen frei). */
@supports (grid-template-rows: subgrid) {
  @media (min-width: 901px) {
    .phase-grid .phase-block {
      display: grid;
      grid-template-rows: subgrid;
      grid-row: span 4;      /* Phasen-Titel + drei Schritte */
      align-self: stretch;
    }
    /* Der Phasen-Titel trägt seinen Abstand selbst; in der Grid-Zeile
       darf er nicht zusätzlich gestreckt werden. */
    .phase-grid .phase-block > h3 { align-self: start; }
  }
}
@media (max-width: 900px) {
  .phase-grid { grid-template-columns: 1fr; }
  /* Gestapelt: Abstand zwischen Phase A und Phase B (erste Phase bleibt
     ohne Zusatzabstand, sonst doppelt sie den Kopfabstand). */
  .phase-grid .phase-block + .phase-block { margin-top: var(--s-5); }
}

/* ============================================================
   S7 — KONTAKT-CTA (Blau-Gradient)
   ============================================================ */
.contact-cta {
  background:
    radial-gradient(90% 130% at 80% -10%, rgba(25, 118, 210, 0.25), transparent 55%),
    radial-gradient(70% 100% at 10% 110%, rgba(25, 118, 210, 0.12), transparent 60%),
    var(--ink-soft);
  color: var(--white);
}
.contact-grid {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 6fr);
  gap: var(--s-6);
  align-items: start;
}
/* Runde 17 · Kontaktseite: Vorspann aus zwei Kästen ÜBER dem Formular.
   Links die Erwartungen (mehr Text), rechts der Telefonweg. */
.contact-prelude {
  display: grid;
  grid-template-columns: minmax(0, 8fr) minmax(0, 4fr);
  gap: var(--s-3);
  align-items: stretch;
  /* Runde 34: Der Block steht jetzt UNTER dem Formular — der Abstand
     wandert entsprechend von unten nach oben. */
  margin-top: var(--s-5);
}
/* Der Telefon-Kasten trägt wenig Text — sein Inhalt sitzt mittig, damit
   der Kasten neben dem längeren Erwartungsblock nicht hohl wirkt. */
.expect-card--call {
  display: flex;
  flex-direction: column;
  justify-content: center;
}
@media (max-width: 900px) {
  .contact-prelude { grid-template-columns: minmax(0, 1fr); }
}
/* Runde 17 · Kontaktseite: Beide Spalten enden auf gleicher Höhe, damit der
   Block als geschlossenes Feld liest. Die Kontaktdaten beginnen oben (auf
   Höhe des Feldes „Name"), das Kö-Bogen-Bild nimmt den Rest der Spalte auf.
   Nur hier — auf der Startseite bleibt das Raster oben ausgerichtet. */
@media (min-width: 901px) {
  .contact-grid--flush { align-items: stretch; }
  .contact-grid--flush > div {
    display: flex;
    flex-direction: column;
  }
  .contact-grid--flush .contact-media {
    flex: 1 1 auto;
    min-height: 0;
    margin-top: var(--s-4);
  }
  .contact-grid--flush .contact-media .media-ph {
    height: 100%;
    min-height: 15rem;
    aspect-ratio: auto;
  }
}
.contact-heading {
  font-size: var(--fs-d2);
  font-weight: 700;
  letter-spacing: -0.02em;
  line-height: 1.05;
}
.contact-direct {
  margin-top: var(--s-5);
  display: grid;
  gap: var(--s-2);
  font-size: var(--fs-body-l);
}
/* Kontakt-Seite: Der Info-Block (Telefon/E-Mail/Adresse) ist dort das
   ERSTE Element der linken Spalte — der Basis-Abstand oben (--s-5, gedacht
   für die Position unter einer Überschrift wie auf index/karriere) schob
   ihn 64px unter die Oberkante des Formulars. Ohne ihn beginnt der Block
   auf gleicher Höhe wie „Wir antworten …" rechts; alles darunter
   (Kö-Bogen-Bild, Karriere-Hinweis) rückt als Einheit mit. karriere ist
   nicht betroffen (dort setzt ein Inline-Style den Abstand explizit). */
.contact-grid > div > .contact-direct:first-child { margin-top: 0; }
.contact-direct a:not(.btn) {
  width: fit-content;
  border-bottom: 1px solid rgba(255, 255, 255, 0.4);
  transition: border-color var(--t-fast) var(--ease);
  padding-bottom: 2px;
}
.contact-direct a:not(.btn):hover { border-color: var(--white); }
.contact-direct address {
  font-style: normal;
  color: rgba(244, 247, 252, 0.78);
  margin-top: var(--s-2);
}

/* Runde 20 · Ortsbild unter den Kontaktdaten der Startseite.
   Dieser Wert gilt seit Runde 23 nur noch im gestapelten Zustand
   (< 901px): dort bleibt das Motiv ein flacher Streifen von 2,289:1,
   aus der 3:2-Datei mittig beschnitten. Am Desktop füllt die Fläche
   den Rest der Spalte (siehe Runde-23-Block am Dateiende). Bewusst
   KEIN .ratio-*-Utility: die Standardmaße würden anders anschneiden. */
.contact-place { margin-top: var(--s-5); }
.media-ph--place { aspect-ratio: 1536 / 671; }

/* Rechte Spalte des Kontaktblocks: Formular + statisches Kö-Bogen-Bild.
   Wrapper, damit das Bild NICHT im <form> liegt (Semantik) und trotzdem
   exakt auf der Formularbreite sitzt. */
.contact-col { min-width: 0; }
/* Kö-Bogen unter dem Formular — rein statisch (kein .media-ph → kein Tilt,
   kein Scroll-3D, kein Hover). 2:1 via aspect-ratio + object-fit:cover:
   horizontales Motiv, oben/unten leichter Beschnitt, kein Verzerren.
   Breite = Formularbreite → links/rechts bündig mit den Feldkanten.
   Mobil skaliert das Seitenverhältnis mit, daher kein Overflow. */
.contact-figure {
  margin: var(--s-4) 0 0;
  aspect-ratio: 2 / 1;
  border-radius: var(--container-radius);
  overflow: hidden;
}
.contact-figure picture { display: block; width: 100%; height: 100%; }
.contact-figure img {
  display: block;
  width: 100%;
  height: 100%;
  object-fit: cover;
  object-position: center;
}

.contact-form .field { margin-bottom: var(--s-4); }
.contact-form .sr-label {
  position: absolute;
  width: 1px; height: 1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
}
/* ------------------------------------------------------------------
   Runde 19 — Eingabefelder als Fläche statt als Linie („Variante A").
   Vorher trug ein Feld nur eine Unterlinie; wo es beginnt und endet, war
   nicht erkennbar. Jetzt: Fläche eine Stufe dunkler als der Untergrund,
   feine Hairline aus der Kartenfamilie und der Button-Radius (10px) —
   Bedienelemente tragen damit site-weit dasselbe Maß, während die
   1,25rem-Rundung weiterhin Karten und Bildern vorbehalten bleibt.
   Kein Schlagschatten; Tiefe entsteht wie überall über Kante und
   Abstufung. Gilt für alle drei Formulare (Start, Kontakt, Karriere).
   ------------------------------------------------------------------ */
.contact-form input,
.contact-form textarea,
.contact-form select {
  width: 100%;
  background: rgba(6, 11, 22, 0.55);
  border: 1px solid var(--line-d);
  border-radius: var(--button-radius);
  padding: 0.95rem 1.1rem;
  color: var(--white);
  font: inherit;
  font-size: var(--fs-body-l);
  /* Feste Zeilenhöhe: Ohne sie rendert der Browser das Auswahlfeld rund 6px
     flacher als die Textfelder — bei reinen Unterlinien unsichtbar, als
     Fläche aber ein sichtbarer Versatz in der Feldreihe. */
  line-height: 1.5;
  transition: border-color var(--t-fast) var(--ease),
              background-color var(--t-fast) var(--ease),
              box-shadow var(--t-fast) var(--ease);
}
.contact-form input::placeholder,
.contact-form textarea::placeholder { color: rgba(244, 247, 252, 0.62); }
/* Maus-Fokus: Rand nimmt den Akzent an, dazu ein weicher Ring. */
.contact-form input:focus,
.contact-form textarea:focus,
.contact-form select:focus {
  outline: none;
  border-color: var(--accent);
  background: rgba(6, 11, 22, 0.75);
  box-shadow: 0 0 0 3px rgba(25, 118, 210, 0.22);
}
.contact-form textarea { resize: vertical; min-height: 3.5rem; }
/* Auswahlfeld: Der Browser baut die innere Zeilenbox flacher als bei einem
   Textfeld. Zwei zusätzliche Pixel oben und unten gleichen das aus, damit
   alle einzeiligen Felder exakt gleich hoch sind. */
.contact-form select { padding-block: calc(0.95rem + 2px); }

/* Tastatur-Fokus: derselbe Zustand, nur mit kräftigerem Ring — die
   Fokus-Reihenfolge muss auch ohne Maus deutlich ablesbar sein. */
.contact-form input:focus-visible,
.contact-form textarea:focus-visible,
.contact-form select:focus-visible {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(25, 118, 210, 0.45);
}
.contact-form select option { color: var(--ink); }
.contact-form select:invalid { color: rgba(244, 247, 252, 0.62); }

/* Runde 48: .contact-intro entfernt. Die Zeile „Wir antworten innerhalb eines
   Werktags." stand auf der Startseite über dem Formular UND als .form-service
   unter dem Button — dieselbe Aussage zweimal im selben Block. Das Formular
   beginnt jetzt wie auf kontakt.html direkt mit dem ersten Feld und steht damit
   oben bündig zur Headline der linken Spalte. */

/* Einleitungstext unter Kontakt-Überschrift */
.contact-lead {
  margin-top: var(--s-3);
  font-size: var(--fs-body-l);
  color: rgba(244, 247, 252, 0.78);
  max-width: 44ch;
}

/* Beschriftete Direktkontakte */
.contact-direct .clabel {
  display: block;
  font-size: var(--fs-small);
  color: rgba(244, 247, 252, 0.55);
  letter-spacing: 0.04em;
  margin-bottom: 0.25rem;
}

/* Vorteils-Punkte auf Blau-Flächen */
.cta-points {
  list-style: none;
  display: grid;
  gap: 0.5rem;
  margin-top: var(--s-3);
  font-size: var(--fs-body);
  color: rgba(244, 247, 252, 0.85);
}
.cta-points li { display: flex; gap: 0.5rem; align-items: baseline; }
.cta-points li::before { content: "+"; font-weight: 800; flex: 0 0 auto; }

/* Modell-/Kennungs-Zeile in Karten */
.model-tag {
  display: block;
  font-size: var(--fs-small);
  font-weight: 700;
  color: var(--blue-soft);
  letter-spacing: 0.04em;
  margin-bottom: var(--s-2);
}
/* Kursive Einstiegsaussage am Anfang des Kachel-Fließtextes (Runde 9).
   Ersetzt die frühere eigenständige Überzeile (.model-claim, entfernt):
   Sie steht jetzt im Textfluss, hebt sich aber durch Kursive und den
   volleren Weißton vom Rest ab. */
.model-grid .process-card p em {
  font-style: italic;
  color: var(--white);
}
/* Vergütungsmodelle: Titel- und Textausrichtung laufen seit Runde 8 über
   subgrid (s. Abschnitt „Befund- und Garantie-Kacheln") — dadurch beginnt
   der Fließtext bei allen vier Kacheln auf derselben Höhe. Die frühere
   feste min-height richtete nur die Überzeile aus; der Fließtext lief um
   bis zu 27px auseinander (gemessen). */
/* Abschluss-Zeile unter den Modellen: Frage links in der großen Statement-
   Typo (wie .cta-strip h2), Button rechtsbündig zur Kachel-Reihe darüber
   (space-between → rechte Button-Kante = rechte Kante Modell 04) und mit
   der Oberkante auf Höhe der ersten Textzeile (flex-start; ersetzt die
   Baseline-Regel aus Runde 3). Bewusst KEIN Kasten.
   @≤700 bricht der Button unter den Text (Text über Button). */
.model-cta {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  align-items: flex-start;
  gap: var(--s-3) var(--s-4);
  margin-top: var(--s-5);
}
.model-cta p {
  font-family: var(--font-display);
  font-size: var(--fs-d2);
  font-weight: 700;
  letter-spacing: -0.02em;
  line-height: 1.05;
  color: var(--white);
  max-width: 20ch;
}
@media (max-width: 700px) {
  .model-cta { flex-direction: column; align-items: flex-start; }
}

/* Easter Egg am Seitenende (Runde 9): bewusst sehr klein und leise —
   ein Fund für Aufmerksame, kein zweiter CTA. Deutlicher Abstand nach oben
   trennt es vom Abschluss-CTA, der Rest der Sektion bleibt unberührt.
   Runde 11: zentriert am Fuß der Sektion, Schriftgrad zwischen --fs-tiny
   und dem Fließtext der Kacheln (12px ↔ 17px). */
.easter-egg {
  margin-top: var(--s-7);
  margin-inline: auto;
  font-size: 0.9375rem;
  font-style: italic;
  color: rgba(146, 179, 226, 0.55);
  max-width: 60ch;
  text-align: center;
}

/* Datei-Upload (optional, Bewerbungsformular) */
.contact-form .field-file label {
  display: block;
  font-size: var(--fs-body-l);
  color: rgba(244, 247, 252, 0.62);
  margin-bottom: var(--s-2);
}
/* Datei-Auswahl in derselben Bauart wie die übrigen Felder (Runde 19). */
.contact-form .field-file input[type="file"] {
  width: 100%;
  background: rgba(6, 11, 22, 0.55);
  border: 1px solid var(--line-d);
  border-radius: var(--button-radius);
  padding: 0.7rem 0.8rem;
  color: rgba(244, 247, 252, 0.85);
  font-size: var(--fs-small);
  transition: border-color var(--t-fast) var(--ease), box-shadow var(--t-fast) var(--ease);
}
.contact-form .field-file input[type="file"]:focus-visible {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(25, 118, 210, 0.45);
}
.contact-form .field-file input[type="file"]::file-selector-button {
  font: inherit;
  font-size: var(--fs-small);
  color: var(--white);
  background: transparent;
  border: 1px solid rgba(255, 255, 255, 0.45);
  border-radius: 6px;
  padding: 0.5rem 1rem;
  margin-right: var(--s-2);
  cursor: pointer;
  transition: border-color var(--t-fast) var(--ease);
}
.contact-form .field-file input[type="file"]::file-selector-button:hover {
  border-color: var(--white);
}
/* Submit-Button: nutzt .btn, hier nur der Formular-Abstand */
.contact-submit { margin-top: var(--s-2); }

/* Servicehinweise unter dem Absenden-Button (Runde 5) */
.form-service {
  margin-top: var(--s-3);
  font-size: var(--fs-small);
  color: var(--blue-soft);
}
.form-note {
  margin-top: var(--s-3);
  font-size: var(--fs-small);
  color: rgba(244, 247, 252, 0.66);
  max-width: 46ch;
}

/* Formular-Validierung: sichtbares Feedback statt stummem Fokus */
.field-error {
  display: none;
  margin-top: 0.5rem;
  font-size: var(--fs-small);
  color: #FFB4B4;
}
.field.has-error .field-error { display: block; }
.field.has-error input,
.field.has-error select,
.field.has-error textarea { border-color: #FF8A8A; }

/* Statusmeldung nach dem Absenden (aria-live-Region) */
.form-status {
  display: none;
  margin-top: var(--s-3);
  padding: var(--s-2) var(--s-3);
  font-size: var(--fs-body);
  color: var(--white);
  background: rgba(25, 118, 210, 0.16);
  border: 1px solid rgba(146, 179, 226, 0.4);
  border-radius: var(--container-radius);
}
.form-status.is-visible { display: block; }
/* Erfolg und Fehler unterscheidbar machen — vorher sahen beide gleich aus.
   Bewusst nur Rahmen und dezente Tönung, keine neue Farbe, kein Schatten. */
.form-status.is-ok    { border-color: rgba(146, 179, 226, 0.55); }
.form-status.is-error { background: rgba(255, 138, 138, 0.12); border-color: #FF8A8A; color: var(--white); }

/* ============================================================
   FOOTER (ausgebaut)
   ============================================================ */
.footer-cols {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: var(--s-4);
  align-items: start;
  padding-block: var(--s-6) var(--s-5);
}
/* Footer-Spaltenüberschriften: h2 (A4 – kein Ebenensprung h2→h4), Optik wie zuvor.
   font-family:var(--font) hält den Body-Font (h1–h3 tragen sonst den Display-Font). */
.footer-col h2 {
  font-family: var(--font);
  font-size: var(--fs-small);
  font-weight: 400;
  color: var(--muted-d);
  margin-bottom: var(--s-3);
  letter-spacing: 0;
}
.footer-col ul { list-style: none; display: grid; gap: 0.75rem; }
.footer-col a {
  width: fit-content;
  transition: color var(--t-fast) var(--ease);
}
.footer-col a:hover { color: var(--blue-soft); }
.footer-col address {
  font-style: normal;
  color: var(--white);
  line-height: 1.7;
}
.footer-col address a { color: var(--white); }

.footer-wordmark {
  font-size: clamp(2.6rem, 9.6vw, 10.5rem);
  font-weight: 700;
  line-height: 0.9;
  letter-spacing: -0.035em;
  white-space: nowrap;
  padding-block: var(--s-2) var(--s-4);
  user-select: none;
}
.footer-wordmark .dotde { color: var(--accent); }

/* ============================================================
   RESPONSIVE — Sektionen
   ============================================================ */
/* Leistungs-Panels (Runde 8, Block 1): Der Links/Rechts-Wechsel gilt nur,
   solange die Textkachel ihr Entwurfsmaß hält. Gemessen: Der Panel-Titel
   (max-width 18ch = 408px) wird ab ~1350px beschnitten und ist bei 1100px
   auf 324px (79 %) geschrumpft — darunter wird die zweispaltige Anordnung
   eng und der Wechsel wirkt unruhig. Ab hier daher EINHEITLICH für alle
   sieben Panels: Textkachel oben, Illustration darunter. Text- und
   Illustrationskachel liegen ohnehin je Panel in einem eigenen Grid
   (.showcase-row) — ein Paar kann also nie getrennt werden. */
@media (max-width: 1099px) {
  /* minmax(0,1fr): Eine reine 1fr-Spalte hat ein auto-Minimum und wächst auf
     die Mindestbreite langer Versal-Komposita in den Panel-Titeln — einzelne
     Kacheln wurden dadurch breiter als ihre Zeile. */
  .showcase-row { grid-template-columns: minmax(0, 1fr); gap: var(--s-3); }
  .showcase-row.is-flipped .showcase-card { order: 0; }
  .showcase-row.is-flipped .showcase-media { order: 1; }
}

@media (max-width: 900px) {
  /* Die frühere Umschaltung des .showcase-head (zweispaltig → einspaltig)
     ist mit Runde 14 entfallen: Der Kopf ist jetzt überall einspaltig. */

  .topic-row { grid-template-columns: 1fr; gap: var(--s-3); padding-block: var(--s-4); }

  .process-grid { grid-template-columns: 1fr; }

  .contact-grid { grid-template-columns: 1fr; gap: var(--s-5); }

  .footer-cols { grid-template-columns: 1fr 1fr; }
  .footer-wordmark { white-space: normal; word-break: break-word; line-height: 0.95; }
}

@media (max-width: 700px) {
  .statement .float-media { display: none; }
  .footer-cols { grid-template-columns: 1fr; }
  .fact-strip { grid-template-columns: 1fr; }

  /* Haupt-CTA mobil in voller Breite — bequem erreichbar */
  .hero-actions { width: 100%; }

  /* Lange Kompositum-H1 (Leistungs-Detailseiten) brechen mobil um statt
     rechts abgeschnitten zu werden.
     RUNDE 52: hyphens:manual statt auto. Das Woerterbuch trennte hier
     „Außendiens-tsteuerung" und „Datenschut-zerklaerung" — und ignorierte
     dabei die im Text gesetzte Trennstelle, weil die automatische Trennung
     Vorrang hat. Jetzt gilt allein das &shy; im Titel; jeder H1 mit einem
     Wort ueber 13 Zeichen traegt eines. overflow-wrap bleibt als Notausgang
     fuer kuenftige Titel ohne gesetzte Trennstelle. */
  .page-title {
    overflow-wrap: break-word;
    -webkit-hyphens: manual;
    hyphens: manual;
  }

  /* Kontakt: 1fr-Grid darf unter die min-content-Breite des nowrap-Ghost-Buttons
     schrumpfen (min-width:0 auf den Spaltenkindern), Ghost-Button umbricht mobil
     statt die Spalte über 390px hinaus aufzublähen; lange Direktwerte brechen um. */
  .contact-grid > * { min-width: 0; }
  .contact-direct,
  .contact-direct > * { min-width: 0; }
  .contact-direct a:not(.btn) { overflow-wrap: anywhere; }
  .career-cta .btn { white-space: normal; }

  /* CTA-Strip-Überschrift: langes Kompositum („…Vertriebsunterstützung.") sprengte
     als min-content den Flex-Item bei max-width:16ch. min-width:0 lässt den Item
     schrumpfen, break-word/hyphens brechen das Wort um → kein Rest-Überlauf @390. */
  .cta-strip h2 {
    min-width: 0;
    overflow-wrap: break-word;
    -webkit-hyphens: auto;
    hyphens: auto;
  }

  /* R4: Touch-Trefferflächen ≥44px (nur mobil → 768/1440 unverändert).
     Schriftgröße bleibt gleich, nur die klickbare Höhe wächst. */
  .footer-col a,
  .showcase-link,
  .process-link,
  .contact-direct a:not(.btn) {
    min-height: 44px;
    display: inline-flex;
    align-items: center;
  }
}

/* Porträt mit Bildunterschrift (Über uns) */
.portrait {
  max-width: 16rem;
  margin-top: var(--s-4);
}
.portrait figcaption {
  margin-top: var(--s-2);
  font-size: var(--fs-small);
}
.portrait figcaption strong {
  display: block;
  font-weight: 700;
  color: var(--white);
}
.portrait figcaption span { color: var(--muted-l); }

/* ============================================================
   UNTERSEITEN — Page-Hero
   ============================================================ */
.page-hero {
  background: var(--ink);
  color: var(--white);
  padding-top: clamp(8rem, 18vh, 12rem);
  padding-bottom: var(--s-6);
}
.page-label {
  font-size: var(--fs-tiny);
  color: var(--blue-soft);
  letter-spacing: 0.14em;
  margin-bottom: var(--s-3);
}
/* Größte Ebene der jeweiligen Unterseite — dieselbe Stufe wie die
   Hero-H1 der Startseite (95px), nicht mehr darüber (vorher 118px,
   außerhalb der Skala). line-height 0,98 wie die Hero-H1. */
.page-title {
  font-size: var(--fs-d1);
  font-weight: 700;
  line-height: 0.98;
  letter-spacing: -0.03em;
  max-width: 12ch;
}
.page-title .dotde { color: var(--accent); }
/* Subtext-Profil des Piloten (hero-sub): Body-Größe, ruhig, gedämpft.
   Spreizung page-title:page-lead damit 5,6x — identisch zur Startseite.
   Vorher 31,7px halbfett: konkurrierte mit dem Titel statt ihn zu tragen. */
.page-lead {
  margin-top: var(--s-4);
  font-size: var(--fs-body);
  font-weight: 400;
  line-height: 1.6;
  color: var(--muted-d);
  max-width: 38ch;
}

/* ============================================================
   UNTERSEITEN — Inhalts-Layout
   ============================================================ */
.content { padding-block: var(--s-6); }

.split {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
  gap: var(--s-4);
  padding-block: var(--s-5);
  border-top: 1px solid var(--line-l);
  align-items: start; /* Überschrift-Oberkante = Inhalts-Oberkante */
}
.split:first-child { border-top: 0; padding-top: 0; }
.split-head .kicker {
  display: block;
  font-size: var(--fs-small);
  color: var(--blue-soft);
  letter-spacing: 0.04em;
  margin-bottom: var(--s-2);
}
.split-head h2 {
  font-size: var(--fs-h3);
  font-weight: 700;
  letter-spacing: -0.015em;
  line-height: 1.12;
  max-width: 18ch;
}
.split-body { font-size: var(--fs-body-l); color: var(--muted-l); max-width: 52ch; }
/* T1 Lesbarkeit: Fließtext auf ≤66 Zeichen/Zeile (52ch ≈ 603px bei dieser Schrift;
   ch ≈ 1,16× mittlere Zeichenbreite → 52ch ≈ 64 Zeichen). Auch Ablauf-/Prozess-Absätze. */
.phase-step p,
.process-head p { max-width: 52ch; }
.split-body p + p { margin-top: 1em; }
.split-body strong { color: var(--white); font-weight: 700; }
/* Tracking auf dem Kurvenwert der 20px-Stufe (wie .process-card h3). Ohne die
   Regel waren die Zwischentitel der sieben Leistungsseiten die einzigen
   Display-Titel dieser Größe ohne Verengung — Bruch der Kurve „größer = enger". */
.split-body h3 {
  font-size: var(--fs-h4);
  font-weight: 700;
  letter-spacing: -0.01em;
  color: var(--white);
  margin-top: var(--s-4);
  margin-bottom: var(--s-1);
}
.split-body h3:first-child { margin-top: 0; }
/* Erstes Body-Element bündig zur Überschrift-Oberkante (kein Vorlauf-Abstand) */
.split-body > :first-child { margin-top: 0; }

/* Leistungs-Listen mit Plus-Marker */
.plist {
  list-style: none;
  margin-top: var(--s-3);
}
.plist li {
  position: relative;
  padding-block: 0.75rem;
  padding-left: 1.75rem;
  border-top: 1px solid var(--line-l);
  font-size: var(--fs-body-l);
  line-height: 1.6;
  color: var(--white);
}
.plist li::before {
  content: "+";
  position: absolute;
  left: 0;
  top: 0.75rem;
  color: var(--blue-soft);
  font-weight: 800;
}

/* P2/17: Kompakte Variante für die Liste „Woran Sie es messen" auf den
   Detailseiten. Gleiche Bauart wie .plist (Plus-Glyphe, Trennlinien), nur
   eine Textstufe kleiner und enger gesetzt — die Hauptliste „Was wir konkret
   leisten" darüber soll die führende bleiben. */
.plist--compact li {
  font-size: var(--fs-body);
  padding-block: 0.5rem;
  color: var(--muted-d);
}
.plist--compact li::before { top: 0.5rem; }

/* Einzelner Vorteils-Satz */
.vorteil-card {
  margin-top: var(--s-3);
  padding: var(--s-3);
  background: var(--ink-soft);
  border-left: 2px solid var(--blue);
  border-radius: var(--container-radius);
  font-size: var(--fs-body-l);
  color: var(--white);
}
.vorteil-card .vorteil-kicker {
  display: block;
  font-size: var(--fs-small);
  color: var(--blue-soft);
  margin-bottom: 0.5rem;
  letter-spacing: 0.04em;
}

/* Vorteils-Blöcke (fett + Erklärung) */
.benefit { list-style: none; margin-top: var(--s-3); }
.benefit li {
  padding-block: var(--s-3);
  border-top: 1px solid var(--line-l);
}
.benefit li strong {
  display: block;
  font-weight: 800;
  color: var(--white);
  margin-bottom: 0.5rem;
}
.benefit li p { color: var(--muted-l); }

/* ---------- Stellen-Akkordeon (Karriere) ----------
   Natives <details>/<summary>: Aufklappen, Tastaturbedienung (Enter/Space),
   Fokus und Screenreader-Semantik (expanded/collapsed) kommen vom Browser —
   deshalb kein JS, kein Fokus-Trap, kein ESC-Handling nötig. Das „+" dreht
   beim Öffnen zum „×" — dieselbe Bewegungssprache wie .showcase-link. */
.job summary {
  cursor: pointer;
  list-style: none;
  position: relative;
  padding-right: 2.5rem;
}
.job summary::-webkit-details-marker { display: none; }
.job summary strong { margin-bottom: 0.35rem; }
.job-meta { display: block; color: var(--muted-l); }
.job summary::after {
  content: "+";
  position: absolute;
  top: 0;
  right: 0.25rem;
  color: var(--blue-soft);          /* 8,7:1 auf dunklem Grund → AA */
  font-weight: 700;
  line-height: 1;
  transition: transform var(--t-med) var(--ease);
}
.job[open] summary::after { transform: rotate(45deg); }
.job summary:hover strong { color: var(--blue-soft); }
.job-detail { padding-top: var(--s-3); color: var(--muted-l); }
.job-detail > p { max-width: 62ch; }
.job-detail h3 {
  margin-top: var(--s-3);
  margin-bottom: 0.4rem;
  color: var(--white);
  font-family: var(--font);
  font-size: var(--fs-body);
  font-weight: 700;
}
.job-detail ul {
  list-style: disc;
  padding-left: 1.15rem;
  display: grid;
  gap: 0.3rem;
  max-width: 62ch;
}
.job-detail ul li { padding-block: 0; border-top: 0; }  /* .benefit-Regeln neutralisieren */
.job-detail .btn { margin-top: var(--s-4); }

@media (prefers-reduced-motion: reduce) {
  .job summary::after { transition: none; }
}

/* ============================================================
   UNTERSEITEN — Ablauf-Schritte (Über uns)
   ============================================================ */
.phase-block { margin-top: var(--s-5); }
.phase-block > h3 {
  font-size: var(--fs-h3);
  font-weight: 700;
  letter-spacing: -0.015em;
  margin-bottom: var(--s-3);
}
.phase-step {
  display: grid;
  grid-template-columns: 2.5rem minmax(0, 1fr);
  gap: var(--s-2);
  padding-block: var(--s-4);
  border-top: 1px solid var(--line-l);
  align-items: baseline;
}
.phase-step .no {
  font-weight: 800;
  color: var(--blue-soft);
  font-size: var(--fs-h5);
}
/* Gleiche Größenstufe, gleiches Tracking wie .process-card h3 / .split-body h3.
   Das Gewicht 800 bleibt — es unterscheidet den Prozess-Schritt bewusst von der
   normalen Sub-Headline und gehört zur Rolle, nicht zur Tracking-Kurve. */
.phase-step h4 {
  font-size: var(--fs-h4);
  font-weight: 800;
  letter-spacing: -0.01em;
  margin-bottom: 0.5rem;
}
.phase-step p {
  font-size: var(--fs-body-l);
  color: var(--muted-l);
}

/* ============================================================
   UNTERSEITEN — Pager (vorheriger/nächster Bereich)
   ============================================================ */
.pager {
  display: grid;
  grid-template-columns: 1fr 1fr;
  border-top: 1px solid var(--line-l);
}
.pager a {
  display: grid;
  gap: 0.5rem;
  padding: var(--s-4) var(--s-2);
  transition: background-color var(--t-fast) var(--ease);
}
.pager a:hover { background: var(--paper); }
.pager .pager-dir {
  font-size: var(--fs-small);
  color: var(--muted-l);
  letter-spacing: 0.04em;
}
/* Gleiche 18px-Stufe wie .fact-title -> ebenfalls ohne Tracking. */
.pager .pager-title { font-weight: 800; font-size: var(--fs-h5); }
.pager .next { text-align: right; border-left: 1px solid var(--line-l); }
.pager a:only-child { grid-column: 2; }

/* ============================================================
   CTA-STRIP (wiederverwendbar auf Unterseiten)
   ============================================================ */
.cta-strip {
  background: var(--ink);
  color: var(--white);
  padding-block: var(--s-6);
}
.cta-strip-inner {
  display: flex;
  flex-wrap: wrap;
  align-items: stretch;
  justify-content: space-between;
  gap: var(--s-4);
  padding: var(--s-6) clamp(1.5rem, 5vw, 4rem);
  background:
    radial-gradient(120% 160% at 50% -30%, rgba(25, 118, 210, 0.28), transparent 60%),
    var(--surface);
  border: 1px solid var(--line-d);
  border-radius: var(--container-radius);
}
.cta-strip h2 {
  font-size: var(--fs-d2);
  font-weight: 700;
  letter-spacing: -0.02em;
  line-height: 1.05;
  max-width: 16ch;
}

.cta-actions {
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  justify-content: flex-end;
  gap: 0.5rem;
  font-size: var(--fs-body-l);
}
/* P2/17: Button-Paar im CTA-Streifen der Detailseiten — dieselbe Machart wie
   Hero, Zwischen-CTAs und Handy-Leiste: ein Grid mit gleich breiten Spalten,
   gleiche Höhe folgt aus identischem Padding. Unter 560px untereinander. */
.cta-actions--pair {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: 1fr;
  align-items: stretch;
  align-self: flex-end;
  gap: var(--s-3);
}
.cta-actions--pair .btn { justify-content: center; text-align: center; }
@media (max-width: 560px) {
  .cta-actions--pair { grid-auto-flow: row; width: 100%; }
}
/* Unterstrich-Stil nur für Nicht-Button-Links (Telefon, E-Mail) */
.cta-actions a:not(.btn) {
  border-bottom: 1px solid rgba(255, 255, 255, 0.4);
  padding-bottom: 2px;
  transition: border-color var(--t-fast) var(--ease);
}
.cta-actions a:not(.btn):hover { border-color: var(--white); }

/* Fokus-Ringe auf blauen Flaechen: weiss statt blau */
.contact-cta :focus-visible,
.cta-strip :focus-visible { outline-color: var(--white); }

/* ============================================================
   RESPONSIVE — Unterseiten
   ============================================================ */
@media (max-width: 900px) {
  .split { grid-template-columns: 1fr; gap: var(--s-3); padding-block: var(--s-4); }
  .split-body, .topic-row p, .intro-copy { hyphens: auto; }
  .pager { grid-template-columns: 1fr; }
  .pager .next { border-left: 0; border-top: 1px solid var(--line-l); text-align: left; }
  .phase-step { grid-template-columns: 2.5rem minmax(0, 1fr); gap: var(--s-2); }
}

/* ============================================================
   KUNDENSTIMMEN — Testimonials-Marquee (Über uns, nach „Partnerschaft…")
   Vanilla-Adaption des React/Marquee-Musters: horizontal endlos laufende
   Karten, Hover-Pause, weiche Fade-Kanten. Ruhig, linear (konstantes Tempo
   = kein Ruckeln), reduced-motion schaltet den Lauf ab (statisch scrollbar).
   Nahtlose Schleife: zwei identische Kartensätze, translateX(-50%); jede
   Karte trägt margin-right = --tm-gap → gleichmäßige Zellen, exakter Loop.
   ============================================================ */
.testimonials {
  --tm-gap: clamp(1rem, 1.6vw, 1.5rem);
  /* Runde 5: 9 statt 6 Karten je Satz → Dauer ×1,5 (80s → 120s), damit die
     Laufgeschwindigkeit in px/s exakt gleich bleibt (Weg = eine Satzbreite).
     js/testimonials.js liest die Dauer aus dem CSS und übernimmt sie. */
  --tm-duration: 120s;
  /* Abstands-Rhythmus 1:1 wie die .split-Abschnitte (Hairline + s-5) */
  border-top: 1px solid var(--line-l);
  padding-block: var(--s-5);
}
/* Runde 15: keine 52ch-Kappung mehr auf der Kopfgruppe — die Headline steht
   zweizeilig („Was unsere Kunden" / „über uns sagen", fester Umbruch per
   <br>), und dafür braucht die erste Zeile die volle Breite. Die Begrenzung
   wandert auf den Fließtext darunter. Auf schmalen Breiten bricht die Zeile
   zusätzlich natürlich um — der feste Umbruch bleibt der Ankerpunkt. */
.testimonials-head { margin-bottom: var(--s-5); }
/* Eyebrow linksbündig zur Headline (Base .section-label ist zentriert) — wie .process-head */
.testimonials-head .section-label { text-align: left; margin-bottom: var(--s-3); }
.testimonials-head h2 {
  font-size: var(--fs-d2);
  font-weight: 700;
  letter-spacing: -0.02em;
  line-height: 1.05;
}
.testimonials-lead {
  margin-top: var(--s-3);
  font-size: var(--fs-body-l);
  color: var(--muted-l);
  max-width: 52ch;   /* trägt jetzt die Kappung der früheren Kopfgruppe */
}

.testimonials-marquee {
  position: relative;
  width: 100%;
  overflow: hidden;
  /* weiche Fade-Kanten links/rechts (blenden zum Seiten-Hintergrund --ink) */
  -webkit-mask-image: linear-gradient(90deg, transparent 0, #000 9%, #000 91%, transparent 100%);
          mask-image: linear-gradient(90deg, transparent 0, #000 9%, #000 91%, transparent 100%);
}
.testimonials-track {
  display: flex;
  width: max-content;
  animation: testimonials-marquee var(--tm-duration) linear infinite;
  will-change: transform;
}
.testimonials-marquee:hover .testimonials-track { animation-play-state: paused; }
.testimonials-marquee:focus-within .testimonials-track { animation-play-state: paused; }

@keyframes testimonials-marquee {
  from { transform: translateX(0); }
  to   { transform: translateX(-50%); }
}

/* Manuelle Navigation: greift nur, wenn JS den Lauf übernimmt (Klasse .js-drag).
   Reduced-Motion nutzt weiter den nativen Scroll-Fallback und bleibt unberührt. */
.testimonials-marquee.js-drag {
  cursor: grab;
  touch-action: pan-y;            /* horizontale Wische steuern wir, vertikal scrollt die Seite */
  overscroll-behavior-x: contain; /* kein versehentliches Zurück-Wischen des Browsers */
}
.testimonials-marquee.js-drag.is-grabbing {
  cursor: grabbing;
  -webkit-user-select: none;
          user-select: none;
}

.testimonial-card {
  flex: 0 0 auto;
  width: min(24rem, 82vw);
  margin: 0 var(--tm-gap) 0 0;
  display: flex;
  flex-direction: column;
  gap: var(--s-3);
  padding: var(--card-pad);
  background: var(--surface);
  border: 1px solid var(--line-d);
  border-radius: var(--container-radius);
  /* Vorher ein eigenes, allseitiges Randlicht (0,02). Auf das Familien-
     Token vereinheitlicht — sonst hätten die Karten zwei Tiefen-Sprachen. */
  box-shadow: var(--card-depth);
}
.testimonial-quote {
  font-size: var(--fs-body-l);
  line-height: 1.5;
  color: var(--white);
  /* dezente typografische Anführung */
  text-wrap: pretty;
}
.testimonial-quote::before { content: "„"; }
.testimonial-quote::after  { content: "\201C"; }
.testimonial-author {
  display: flex;
  align-items: center;
  gap: 0.85rem;
  margin-top: auto;
  padding-top: var(--s-2);
}
.testimonial-avatar {
  flex: 0 0 auto;
  width: 3rem;
  height: 3rem;
  display: grid;
  place-items: center;
  border-radius: 50%;
  background: var(--navy);
  color: var(--blue-soft);
  font-family: var(--font-display);
  font-weight: 700;
  font-size: var(--fs-small);
  letter-spacing: 0.03em;
}
.testimonial-meta { display: flex; flex-direction: column; min-width: 0; }
.testimonial-name { font-weight: 700; color: var(--white); }
.testimonial-role { font-size: var(--fs-small); color: var(--muted-d); }

/* Diskretions-Satz unter dem Marquee (Runde 5; Linien Runde 6):
   Text mittig, links und rechts je eine 1px-Linie, die nach AUSSEN
   ausfadet. Die Linien nehmen den Restplatz (flex:1), die Gesamtbreite
   ist begrenzt, damit sie nicht über die volle Sektionsbreite laufen. */
.testimonials-note {
  margin-top: var(--s-3);
  margin-inline: auto;
  max-width: 56rem;
  display: flex;
  align-items: center;
  gap: var(--s-2);
  text-align: center;
  font-size: var(--fs-small);
  color: var(--blue-soft);
}
.testimonials-note__rule {
  flex: 1 1 0;
  min-width: 0;
  height: 1px;
  /* innen sichtbar (blue-soft bei ~25 %), nach außen transparent */
  background: linear-gradient(to left, rgba(146, 179, 226, 0.25), transparent);
}
.testimonials-note__rule:last-child {
  background: linear-gradient(to right, rgba(146, 179, 226, 0.25), transparent);
}
.testimonials-note__text { flex: 0 1 auto; }
/* @390 bricht der Satz zweizeilig um — dann haben die Linien Vorrang zu
   weichen: Lesbarkeit des Satzes geht vor Dekoration. */
@media (max-width: 560px) {
  .testimonials-note__rule { display: none; }
}

/* ============================================================
   GARANTIE + ABSCHLUSS-CTA (ueber-uns, Runde 5)
   ============================================================ */
/* Eyebrow in --accent (Sperrung wie die Seiten-Eyebrows). Doppelklasse:
   gewinnt per Quelltext-Reihenfolge gegen .section-dark .section-label. */
.section-label.garantie-label {
  color: var(--accent);
  text-transform: uppercase;
  letter-spacing: 0.14em;
}
/* Garantie-Headline (Runde 9): möglichst ZWEI Zeilen. Die Kopfgruppe ist
   sonst auf 60ch begrenzt — auf der Display-Stufe (--fs-d2) reicht das nur
   für drei Zeilen. Hier daher die volle Sektionsbreite freigeben und die
   Zeilenlänge über die Headline selbst begrenzen (24ch ≈ zwei Zeilen).
   text-wrap: balance (global für h2) verteilt sie gleichmäßig; wird der
   Platz zu knapp (schmales Fenster, mobil), bricht sie von selbst auf
   drei Zeilen — „Risiko" bleibt in beiden Fällen blau. */
.process-head:has(> .garantie-head) { max-width: none; }
.garantie-head { max-width: 24ch; }
/* Unter 340px reicht die Breite auch für zwei Zeilen nicht mehr. Dort greift
   der sonst abgeschaltete Umbruch nach „Risiko" und erzwingt exakt die
   vorgegebene Dreiteilung: „Ihr Risiko" / „haben wir schon" / „übernommen." */
.br-schmal { display: none; }
@media (max-width: 339px) {
  .br-schmal { display: inline; }
}
/* Einzeilige Kachel-Titel (Runde 6) — nur in den Breiten, in denen die
   Titel auch wirklich in die Kachel passen (gemessen). Der längste Titel
   läuft dabei um wenige Pixel in den Innenabstand, nie an den Kachelrand.
   Der 4er-Grid bekommt dafür einen etwas knapperen Innenabstand — bei vier
   Kacheln nebeneinander sind 48px Rand je Seite unverhältnismäßig viel. */
@media (min-width: 1400px) {
  .befunde-grid .process-card h3,
  .garantie-grid .process-card h3 { white-space: nowrap; }
  /* Knapperer Innenabstand für ALLE 4er-Raster (Runde 8): Bei vier Kacheln
     nebeneinander kosten 48px je Seite so viel Fläche, dass der Fließtext
     unter 240px fällt. Mit 2rem misst er bei 1440 gemessene 247px. */
  .process-grid--4 > .process-card { padding-inline: 2rem; }
}
/* Gestufte Spaltenreduktion (Runde 8, Block 2). Unterhalb 1400px reicht die
   Spaltenbreite weder für die langen Titel noch für einen lesbaren Fließtext
   (gemessen: 4-spaltig bei 1100px nur noch 144px Textbreite = ein Wort je
   Zeile). Daher: Befunde 3 → 2 Spalten, alle 4er-Raster (Modelle, Garantie,
   Karriere-Kennzahlen) 4 → 2 Spalten; unter 768px durchgehend einspaltig.
   Muss NACH dem 900er-Responsive-Block stehen (Media Queries erhöhen die
   Spezifität nicht); der 901er-Riegel hält die Mobil-Regeln unangetastet. */
@media (min-width: 741px) and (max-width: 1399px) {
  .process-grid--4 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
/* Unter 741px fällt auch die zweispaltige Textbreite unter 240px (gemessen
   bei 700px: 228px) — ab hier einspaltig. */
@media (max-width: 740px) {
  .process-grid--4 { grid-template-columns: 1fr; }
}
/* Befunde: zweispaltig nur zwischen 901 und 1399px. Darunter einspaltig —
   die Befund-Texte enthalten lange Komposita („Whitepaper-Downloads,"),
   die zweispaltig ab ~900px allein auf einer Zeile stehen würden. */
@media (min-width: 901px) and (max-width: 1399px) {
  .befunde-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (max-width: 900px) {
  .befunde-grid { grid-template-columns: 1fr; }
}

/* Abschluss-CTA: freies, zentriertes Statement ohne Kasten */
.closing-cta .container {
  display: grid;
  justify-items: center;
  text-align: center;
}
.closing-cta h2 {
  font-size: var(--fs-d2);
  font-weight: 700;
  letter-spacing: -0.02em;
  line-height: 1.05;
  max-width: 22ch;
}
.closing-cta__copy {
  margin-top: var(--s-3);
  font-size: var(--fs-body-l);
  color: var(--muted-l);
  max-width: 52ch;
}
.closing-cta .btn { margin-top: var(--s-4); }
.closing-cta__note {
  margin-top: var(--s-3);
  font-size: var(--fs-small);
  color: var(--blue-soft);
}

@media (max-width: 700px) {
  .testimonials { padding-block: var(--s-4); }
  .testimonials-head { margin-bottom: var(--s-4); }
  .testimonial-card { padding: var(--s-3); }
}

/* Bewegung respektieren: kein Auto-Lauf, stattdessen manuell scrollbar */
@media (prefers-reduced-motion: reduce) {
  .testimonials-track { animation: none; }
  .testimonials-marquee {
    overflow-x: auto;
    -webkit-overflow-scrolling: touch;
    scrollbar-width: none;
  }
  .testimonials-marquee::-webkit-scrollbar { display: none; }
}


/* ============================================================
   P1 — CONVERSION-BAUSTEINE (Runde 12)
   Hero-Handlungsblock, Leistungsblöcke, statische Kundenstimmen,
   Zwischen-CTA, FAQ, Erwartungsliste am Formular, mitlaufende
   Handy-Leiste. Alles auf den bestehenden Tokens; keine neuen
   Farben, keine neuen Radien.
   ============================================================ */

/* ---- 7 · Hero: Nutzensatz, zwei CTAs, Vertrauenszeile ----
   Variante B: Handlungsblock in Spalte 1 der Medienzeile, Motiv in
   Spalte 2. Mobil (≤900) muss er VOR dem Bild stehen — .hero-media
   trägt dort order:-1, deshalb hier -2. */
.hero-lead {
  grid-column: 1;
  display: flex;
  flex-direction: column;
  gap: var(--s-3);
}
.hero-value {
  font-size: var(--fs-body-l);
  color: var(--white);
  /* Runde 13: keine ch-Kappung — der Satz füllt die Spalte und schließt
     links wie rechts bündig mit Buttons und Vertrauenszeile ab. */
  max-width: none;
  text-wrap: pretty;
}
/* Buttons ans untere Ende der Spalte (Vertrauenszeile folgt als letzte
   Zeile) — der Freiraum entsteht zwischen Nutzensatz und Buttons. */
.hero-lead .hero-actions { margin-top: auto; }
/* Zweispaltig wachsen BEIDE Spalten auf die Zeilenhöhe: Ist der Text höher
   als das 21:9-Motiv (z. B. um 1100px), zieht min-height das Bild auf
   dieselbe Höhe — Unterkanten bleiben bündig. width ist definit (Grid-
   Stretch), daher leitet aspect-ratio hier KEINE Breite ab (CSS-Falle 2). */
/* ------------------------------------------------------------------
   Runde 16 — URSACHE UND BEHEBUNG des „erster Aufruf verschoben"-Fehlers

   Vorher: Das Motiv trug aspect-ratio 21/9 UND min-height:100%. Damit hing
   seine Höhe an der Zeilenhöhe, während die Zeilenhöhe zugleich aus seiner
   Höhe folgen sollte — ein Zirkelbezug. Safari löste ihn beim ERSTEN Layout
   zugunsten der Textspalte auf: Die Zeile bekam nur die Höhe des Textes,
   das Motiv behielt sein 21:9-Maß und ragte rund 70px unter die Zeile
   hinaus (sichtbar bis in den Lauftext). Weil die Zeile dadurch kürzer war
   und .hero den Inhalt per justify-content:flex-end nach unten schiebt,
   rutschte gleichzeitig alles darüber rund 80px tiefer. Erst ein zweites
   Layout (Reiterwechsel, Neuladen) räumte es auf.

   Jetzt ohne Zirkelbezug: Ein Pseudo-Element gibt die Mindesthöhe der Zeile
   allein aus der BREITE vor (padding-top 9/21 = 42,857 %) — eine Größe, die
   immer definit ist. Das Motiv liegt in derselben Rasterzelle und füllt sie
   vollständig aus (Stretch). Ist die Textspalte höher (um 1100px trägt der
   Nutzensatz eine Zeile mehr), wächst die Zelle mit und das Motiv wächst
   ebenfalls — die Unterkanten bleiben in beiden Richtungen bündig.
   ------------------------------------------------------------------ */
@media (min-width: 901px) {
  .hero-media {
    display: grid;
    grid-template-columns: minmax(0, 1fr);
  }
  .hero-media::before {
    content: "";
    grid-area: 1 / 1;
    padding-top: 42.857%;   /* 9 / 21 — Mindesthöhe aus der Bildbreite */
    pointer-events: none;
  }
  .hero-media .media-ph {
    grid-area: 1 / 1;
    aspect-ratio: auto;     /* Höhe kommt jetzt aus der Rasterzelle */
    min-height: 0;
    height: 100%;
  }
  /* Textspalte nimmt die Zeilenhöhe an — nur dann schiebt margin-top:auto
     die Buttons bis zur Bildunterkante. */
  .hero-lead { align-self: stretch; }
}
/* Runde 13c: Die frühere Vertrauenszeile unter den Buttons ist entfallen —
   ihr Inhalt steht jetzt in der Vorzeile über der Headline (.hero-label).
   Die Buttons sind damit das letzte Element der Textspalte und schließen
   weiterhin bündig mit der Bildunterkante ab (margin-top:auto). */
@media (max-width: 900px) {
  .hero-lead { order: -2; }
}
@media (max-width: 560px) {
  /* Auf schmalen Geräten untereinander, beide volle Breite */
  .hero-actions { grid-auto-flow: row; }
}

/* ---- 13 · Drei Leistungsblöcke ----
   Runde 14: zurück auf die Panel-Anordnung der Leistungsseite (.showcase-rows /
   .showcase-row / .showcase-card / .showcase-media) — abwechselnd Illustration
   links und rechts. Die frühere Drei-Kachel-Reihe (.service-blocks /
   .service-block) ist damit entfallen; ihre Regeln sind gelöscht, weil kein
   Element sie mehr trug. Geblieben ist die Liste der enthaltenen Leistungen,
   die jetzt IN der Panel-Textkachel steht. */
.showcase-card .service-list {
  width: 100%;
  max-width: 38ch;
  margin-top: var(--s-3);
}
/* Panel-Titel dieser drei Blöcke sind Sätze, keine Leistungsnamen — sie
   dürfen etwas breiter laufen als die 18ch der sieben Einzel-Panels. */
.service-rows .showcase-title { max-width: 22ch; }

/* ------------------------------------------------------------------
   Runde 21 — Feste Bildform in den drei Leistungsblöcken.

   Vorher übernahm die Bildfläche die Höhe der Textkachel daneben. Für
   die abstrakten Inline-Grafiken war das richtig, für Fotos nicht: Je
   nach Fensterbreite wurde die Fläche breit, quadratisch oder hochkant,
   und der Browser schnitt das Foto passend zu — bei 1100px verschwanden
   bis zu 31 % der Bildbreite (gemessen). Jetzt hat die Fläche fest 4:3,
   also exakt das Maß der Bilddateien: Es wird nie wieder beschnitten.
   Die Textkachel ist weiterhin etwas höher; das Bild sitzt deshalb
   mittig in seiner Spalte (15px Luft ab 1600, 40px bei 1440).
   Gilt nur für die Startseite — die sieben Panels auf leistungen.html
   behalten ihr bisheriges Verhalten. */
@media (min-width: 1100px) {
  .service-rows .showcase-media {
    display: flex;
    align-items: center;
  }
  .service-rows .showcase-media .media-ph {
    width: 100%;
    height: auto;
    aspect-ratio: 4 / 3;
  }
}
/* Runde 15: Die Einträge sind Links auf die sieben Detailseiten — das war
   als reine Punktliste nicht erkennbar. Statt des Aufzählungspunkts steht
   jetzt ein Plus in der Sprache der Leistungs-Panels (.showcase-link):
   Beim Überfahren dreht es sich um 90°, das Label bekommt eine von links
   wachsende Unterlinie und die ganze Zeile hellt leicht auf. Die Zeile ist
   vollflächig klickbar (der Link füllt sie aus). */
.service-list {
  list-style: none;
  display: grid;
  gap: 0.55rem;
}
.service-list li {
  border-top: 1px solid var(--line-l);
  font-size: var(--fs-body);
}
.service-list li a {
  display: flex;
  gap: 0.7rem;
  align-items: baseline;
  padding-top: 0.6rem;
  padding-bottom: 0.15rem;
  color: var(--white);
  transition: color var(--t-fast) var(--ease);
}
.service-list .plus {
  flex: 0 0 auto;
  color: var(--blue-soft);   /* 8,7:1 auf der Karte → AA */
  font-weight: 700;
  line-height: 1;
  transition: transform var(--t-med) var(--ease), color var(--t-fast) var(--ease);
}
.service-list li a:hover .plus,
.service-list li a:focus-visible .plus {
  transform: rotate(90deg);
  color: var(--accent);
}
.service-list .lbl { position: relative; }
.service-list .lbl::after {
  content: "";
  position: absolute;
  left: 0; bottom: -3px;
  width: 100%; height: 1px;
  background: currentColor;
  transform: scaleX(0);
  transform-origin: right;
  transition: transform var(--t-med) var(--ease);
}
.service-list li a:hover .lbl::after,
.service-list li a:focus-visible .lbl::after {
  transform: scaleX(1);
  transform-origin: left;
}
.service-list li a:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 4px;
  border-radius: 4px;
}
/* Die Subgrid-Ausrichtung und die Spaltenumschaltung der alten Drei-Kachel-
   Reihe sind mit Runde 14 entfallen. Die Panels stapeln sich ab 1099px über
   die bestehende .showcase-row-Regel (Abschnitt „RESPONSIVE — Sektionen"). */

/* ---- 9 · Kundenstimmen statisch (Startseite) ----
   Drei Karten nebeneinander, ohne Laufband: Zitate soll man lesen.
   Die Marquee-Fassung mit neun Stimmen bleibt auf ueber-uns. */
.quote-grid {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: var(--s-3);
}
.quote-grid .testimonial-card { width: auto; margin: 0; }
@media (max-width: 1000px) {
  .quote-grid { grid-template-columns: 1fr; }
}

/* ---- 10 · Zwischen-CTA: Zeile mit Trennlinie ----
   Bewusst dieselbe Machart wie .model-cta auf der Leistungsseite. */
.mid-cta {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: var(--s-4);
  margin-top: var(--s-6);
  padding-top: var(--s-4);
  border-top: 1px solid var(--line-d);
}
.mid-cta > p {
  font-family: var(--font-display);
  font-weight: 700;
  font-size: var(--fs-h3);
  letter-spacing: -0.015em;
  line-height: 1.1;
  max-width: 26ch;
  margin: 0;
}
.mid-cta-actions {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: 1fr;
  align-items: stretch;
  gap: var(--s-3);
}
.mid-cta-actions .btn { justify-content: center; text-align: center; }
/* Runde 50: Dieses Zweier-Grid teilt seine Breite stur in zwei gleiche Spalten
   (1fr 1fr), unabhängig vom Inhalt. In schmalen Sektionen wurde „Kostenloses
   Erstgespräch" dadurch auch auf großen Bildschirmen beschnitten — bei 1024px
   um gut 50px. Hier darf die Beschriftung deshalb auf jeder Breite umbrechen;
   die Alternative (Spalten nach Inhalt bemessen) würde den Block irgendwann
   über den Container hinausschieben. */
.mid-cta-actions .btn, .mid-cta-actions .btn-label,
.hero-actions .btn,     .hero-actions .btn-label {
  white-space: normal;
  text-wrap: balance;
}
/* Runde 14 · Variante „stack": Der Block unter den Leistungs-Panels soll
   sichtbar zu ihnen gehören — deshalb ohne Trennlinie, mit kurzem Abstand
   und dem Button linksbündig UNTER dem Satz statt rechts daneben. */
.mid-cta--stack {
  flex-direction: column;
  align-items: flex-start;
  gap: var(--s-3);
  margin-top: var(--s-4);
  padding-top: 0;
  border-top: 0;
}
@media (max-width: 700px) {
  .mid-cta { flex-direction: column; align-items: flex-start; }
  .mid-cta-actions { width: 100%; }
  /* In der Stack-Variante steht nur ein Button — der soll seine Breite
     behalten und nicht über die ganze Zeile laufen. */
  .mid-cta--stack .mid-cta-actions { width: auto; }
}

/* Runde 50 · Kern des Problems: `.btn` trägt `white-space: nowrap` zusammen mit
   `overflow: hidden` (Letzteres braucht der Füll-Effekt beim Überfahren). Wird
   der Button schmaler als sein Text, kann dieser weder umbrechen noch überlaufen
   — er wird durch `justify-content: center` mittig gesetzt und deshalb LINKS UND
   RECHTS beschnitten. Auf schmalen Geräten darf die Beschriftung daher umbrechen;
   `text-wrap: balance` verteilt sie dabei gleichmäßig auf die Zeilen.
   Ausgenommen bleibt der Button in der Kopfleiste: Er hat dort genug Platz, und
   ein Umbruch würde die Leiste höher werden lassen. */
@media (max-width: 700px) {
  .btn:not(.nav-cta),
  .btn:not(.nav-cta) .btn-label {
    white-space: normal;
    text-wrap: balance;
  }
}

/* Runde 50: Die beiden Buttons standen bis hinunter zu 320px nebeneinander.
   Auf einem 390px-Gerät blieben je 163px Spaltenbreite, also 102px nutzbarer
   Innenraum — „Kostenloses Erstgespräch" braucht 218px und wurde links und
   rechts angeschnitten. Statt die Beschriftung zu kürzen stapeln sich die
   Buttons jetzt, sobald zwei Spalten rechnerisch nicht mehr reichen
   (2 × 279px + Abstand ≈ 580px zuzüglich Seitenrand). Der Text bleibt damit
   auf jedem Gerät vollständig, unabhängig von seiner Länge. */
@media (max-width: 620px) {
  .mid-cta-actions {
    grid-auto-flow: row;
    grid-auto-columns: auto;
  }
  .mid-cta--stack .mid-cta-actions { width: 100%; }
}

/* ---- 12 · FAQ (natives details/summary, funktioniert ohne JS) ---- */
/* Runde 14: sechs Fragen in zwei Spalten × drei Zeilen über die volle
   Containerbreite (vorher fünf Fragen einspaltig, auf 74ch gekappt).
   Leserichtung bleibt zeilenweise (1|2 · 3|4 · 5|6). Die Grid-Voreinstellung
   align-items:stretch hält die beiden Karten einer Zeile exakt gleich hoch —
   auch wenn eine Frage zweizeilig umbricht. */
.faq-list {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 0.75rem;
}
.faq-list details {
  background: var(--surface);
  border: 1px solid var(--line-d);
  border-radius: var(--container-radius);
  box-shadow: var(--card-depth);
  padding: 1.1rem 1.4rem;
}
.faq-list summary {
  cursor: pointer;
  list-style: none;
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 1rem;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: var(--fs-h5, 1.15rem);
  letter-spacing: -0.01em;
}
.faq-list summary::-webkit-details-marker { display: none; }
.faq-list summary::after {
  content: "+";
  color: var(--blue-soft);
  font-size: 1.4rem;
  line-height: 1;
}
.faq-list details[open] summary::after { content: "–"; }
.faq-list summary:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 4px;
  border-radius: 4px;
}
.faq-list p {
  margin-top: var(--s-2);
  color: var(--muted-l);
}
/* Zweispaltig nur, solange jede Karte genug Textbreite hat; darunter
   untereinander (gleiche Schwelle wie die übrigen Kachelraster). */
@media (max-width: 1000px) {
  .faq-list { grid-template-columns: 1fr; }
}
/* Garantie und Fragen teilen eine Sektion (spart ein großes Polster) — der
   Fragen-Kopf braucht dafür seinen eigenen Abstand nach oben. */
.faq-head {
  margin-top: var(--s-7);
  margin-bottom: var(--s-4);
}

/* ---- 11 · Formular: Erwartungsliste + zweiter Weg ---- */
/* Runde 17: kompakter gesetzt (Zeilenabstand und Punktabstand je eine Stufe
   enger), damit der Block gedrungen wirkt und als Kasten nicht ausufert. */
.contact-expect {
  list-style: none;
  display: grid;
  gap: var(--s-2);
  margin-top: var(--s-2);
}
.contact-expect li {
  display: flex;
  gap: 0.9rem;
  align-items: baseline;
  line-height: 1.45;
  color: var(--muted-l);
}
.contact-expect li strong {
  color: var(--blue-soft);
  font-family: var(--font-display);
  font-size: var(--fs-small);
  min-width: 1.4rem;
}
/* Runde 17: Der Erwartungsblock steht jetzt in einem eigenen, dezenten Kasten
   — gleiche Kartenfamilie wie überall (Fläche, Hairline, Randlicht), nur mit
   knapperem Innenabstand. Auf der Startseite trägt EIN Kasten alles; auf der
   Kontaktseite sind es zwei nebeneinander (.expect-card im Vorspann). */
.contact-expect-block,
.expect-card {
  background: var(--surface);
  border: 1px solid var(--line-d);
  border-radius: var(--container-radius);
  box-shadow: var(--card-depth);
  padding: var(--s-3) var(--s-4);
}
/* Etwas schmaler als die Formularspalte darüber — der Kasten soll ein
   ruhiger Nachsatz sein, keine zweite Hauptfläche. */
.contact-expect-block { margin-top: var(--s-4); max-width: 34rem; }
.contact-expect-block .section-label,
.expect-card .section-label {
  display: block;
  text-align: left;
  margin-bottom: var(--s-2);
}
.contact-call {
  margin-top: var(--s-3);
  padding-top: var(--s-2);
  border-top: 1px solid var(--line-d);
}
/* Im eigenen Kasten braucht der Telefonweg keine Trennlinie mehr. */
.expect-card--call .contact-call {
  margin-top: 0;
  padding-top: 0;
  border-top: 0;
  font-size: var(--fs-body-l);
}
.contact-call a {
  color: var(--white);
  border-bottom: 1px solid var(--accent);
}
.contact-call span {
  display: block;
  margin-top: 0.35rem;
  font-size: var(--fs-small);
  color: var(--muted-d);
}

/* ---- 8 · Mitlaufende Handy-Leiste ----
   Nur ≤900px sichtbar (dort ist der Header-CTA hinter dem Burger).
   Höhe rund 60px; body bekommt entsprechend Bodenpolster. */
.mobile-cta { display: none; }
@media (max-width: 900px) {
  .mobile-cta {
    display: grid;
    position: fixed;
    left: 0; right: 0; bottom: 0;
    z-index: 90;
    grid-template-columns: 1fr 1fr;   /* Runde 13: Button-Paar gleich groß */
    gap: 0.6rem;
    padding: 0.65rem 0.9rem;
    background: rgba(11, 21, 38, 0.95);
    border-top: 1px solid var(--line-d);
    -webkit-backdrop-filter: blur(12px);
    backdrop-filter: blur(12px);
    padding-bottom: max(0.65rem, env(safe-area-inset-bottom));
  }
  /* Runde 15: Innenabstand seitlich von 1rem auf 0,8rem. Damit passt die
     Beschriftung „Kontaktformular" auch auf 320px-Geräten vollständig in den
     Button — vorher fehlten dort 3px und das Wort wurde beschnitten (die
     frühere Beschriftung „Kostenloses Erstgespräch" fehlte um bis zu 38px).
     Die Buttonhöhe und das gleich breite Paar bleiben unverändert. */
  .mobile-cta .btn {
    font-size: 0.9rem;
    padding: 0.72rem 0.8rem;
    justify-content: center;
  }
  .mobile-cta .btn--ghost { padding-inline: 1.1rem; }
  body { padding-bottom: 4.5rem; }
  /* Mobiles Vollbild-Menü liegt darüber → Leiste weg */
  body:has(.nav-links.is-open) .mobile-cta { display: none; }
}

/* Sehr schmale Geräte (≤420px): Die Kacheltitel der Fakten-Leiste stehen
   normalerweise auf einer Zeile (white-space: nowrap) und schoben die Karte
   bei 320px um 8px über den Rand — dort darf der Titel umbrechen. Lange
   Versal-Komposita in Panel- und Blocktiteln werden getrennt (lang="de"). */
@media (max-width: 420px) {
  .fact .fact-title { white-space: normal; }
  /* Nur die im Text gesetzten weichen Trennstellen verwenden — die
     Wörterbuch-Trennung zerlegte Versal-Komposita falsch
     („AUSSENDIENS-/TSTEUERUNG“). */
  .showcase-title { hyphens: manual; }
}

/* ============================================================
   RUNDE 23 — Bündigkeiten
   Vier Stellen, an denen Bild und Nachbarspalte auf gleicher
   Höhe enden sollen. Alle Regeln greifen erst im zweispaltigen
   Zustand; gestapelt (Handy/Tablet) bleibt alles wie bisher.
   ============================================================ */

/* --- Startseite · Ortsbild im Kontaktblock -------------------
   Das Bild hatte ein festes Seitenverhältnis und endete je nach
   Fensterbreite 121px zu früh (1200) oder 16px zu tief (1920).
   Jetzt füllt es den Rest der linken Spalte und schließt damit
   immer exakt mit dem Kasten „Was im Erstgespräch passiert" ab.
   Der Abstand zur Adresse rückt von 4rem auf 2.5rem — das Bild
   beginnt früher und wird dadurch spürbar größer. */
@media (min-width: 901px) {
  #kontakt .contact-grid { align-items: stretch; }
  #kontakt .contact-grid > div:not(.contact-col) {
    display: flex;
    flex-direction: column;
    min-height: 0;
  }
  #kontakt .contact-place {
    flex: 1 1 auto;
    min-height: 0;
    margin-top: var(--s-4);
  }
  #kontakt .media-ph--place {
    height: 100%;
    aspect-ratio: auto;
    min-height: 10rem;
  }
}

/* --- Startseite · die drei Leistungsblöcke -------------------
   Die Textkachel war je nach Breite 29px (1920) bis 133px (1200)
   höher als das Foto daneben. Zwei Schritte:
   1. Das Kartenpolster oben/unten skaliert mit der Fensterbreite
      (statt starrer 4rem) — die Karte wird kompakter, ohne dass
      der Text enger gesetzt wird.
   2. Das Foto füllt die verbleibende Zeilenhöhe. Beide Spalten
      enden dadurch immer bündig. Ab 1600px trifft die Kartenhöhe
      die 4:3-Bildhöhe auf 1px genau, das Foto wird also praktisch
      nicht mehr beschnitten; erst darunter greift der Zuschnitt
      spürbar (Runde 21 hatte ihn ganz vermieden, um den Preis
      unterschiedlich hoher Spalten). */
@media (min-width: 1100px) {
  .service-rows .showcase-card { padding-block: clamp(1.5rem, 3.2vw, 3.2rem); }
  .service-rows .showcase-media { align-items: stretch; }
  .service-rows .showcase-media .media-ph {
    height: 100%;
    aspect-ratio: auto;
  }
}

/* --- Kontaktseite · Bild und Jobs-Button --------------------
   Die linke Spalte war 13 bis 21px höher als das Formular, weil
   das Bild eine Mindesthöhe von 15rem hielt. Mit kleinerer
   Mindesthöhe bestimmt das Formular die Zeilenhöhe: Der
   Jobs-Button endet bündig mit der Zeile „… übermittelt.", das
   Bild darüber bündig mit der Servicezeile. */
@media (min-width: 901px) {
  .contact-grid--flush .contact-media .media-ph { min-height: 9rem; }
}

/* --- Karriereseite · Standortbild ---------------------------
   Das Bild hing mit festem 2:1 rund 106px unter dem Hinweistext
   des Formulars. Jetzt füllt es den Rest der Spalte und endet
   mit der letzten Textzeile. Der Abstand zur Adresse darüber
   bleibt unverändert. */
@media (min-width: 901px) {
  #bewerbung .contact-grid { align-items: stretch; }
  #bewerbung .contact-grid > div {
    display: flex;
    flex-direction: column;
    min-height: 0;
  }
  /* flex-basis 0 statt auto: Mit auto brächte das Bild seine natürliche
     Höhe als Ausgangswert ein (bei 1920px 412px) und machte die linke
     Spalte höher als das Formular — das Bild hing dann wieder 33px zu
     tief. Mit 0 bestimmt allein das Formular die Zeilenhöhe.
     Runde 24: Das Flex-Item ist jetzt der Slot; das <figure> darin trägt
     den Aufricht-Effekt und füllt ihn vollständig aus. */
  #bewerbung .contact-figure-slot {
    display: flex;
    flex: 1 1 0;
    min-height: 10rem;
  }
  #bewerbung .contact-figure-slot .contact-figure {
    flex: 1 1 auto;
    aspect-ratio: auto;
    min-height: 0;
  }
}

/* --- Karriereseite · Rechtshinweis unter dem Absenden-Button -
   Drei Aussagen in drei Zeilen (Runde 23). Der Standard von 46ch
   hätte schon den ersten Satz umbrechen lassen; 64ch hält ihn
   einzeilig und lässt nur den langen dritten Satz umbrechen. */
.form-note--legal { max-width: 64ch; }

/* E-Mail-Adressen in Fließtexten nie mitten im Wort umbrechen lassen —
   „jobs@dein-/vertrieb.de" liest sich wie zwei verschiedene Adressen. */
.nowrap { white-space: nowrap; }

/* --- Karriereseite · Slot des Standortbildes ----------------
   Trägt den Außenabstand, den zuvor das <figure> selbst hatte
   (Runde 24: Einblendung und Aufricht-Effekt sitzen auf
   getrennten Elementen). */
.contact-figure-slot { margin-top: var(--s-4); }
.contact-figure-slot .contact-figure { margin-top: 0; }

/* --- FAQ-Fragen: ausgewogener Umbruch (Runde 25) ------------
   Zweizeilige Fragen ließen bis zu ein Wort allein auf der
   zweiten Zeile stehen. text-wrap:balance verteilt die Wörter
   gleichmäßig auf beide Zeilen; Browser ohne Unterstützung
   brechen wie bisher um. */
#fragen details summary { text-wrap: balance; }

/* --- 404-Seite (Runde 27) -----------------------------------
   Das Button-Paar stammt aus dem Startseiten-Hero, wo es in einer
   schmalen Rasterspalte sitzt. In der vollen Breite der Fehlerseite
   liefen die beiden Flächen auseinander — hier auf Textbreite
   begrenzt, damit das Paar als Einheit lesbar bleibt. */
.page-hero .hero-actions { max-width: 34rem; }

/* --- Ablauf-Listen auf den Leistungsseiten (Runde 28) --------
   „So arbeiten wir" nummeriert die Schritte im Fettteil (01 · …).
   Die Plus-Glyphe der Standardliste entfällt hier, sonst stünden
   zwei Zeichen vor jedem Schritt. Die Nummer übernimmt die Rolle
   der Marke am Zeilenanfang — dieselbe Sprache wie die
   Grundsatz-Listen auf „Über uns". */
.plist--steps li {
  padding-left: 0;
}
.plist--steps li::before { content: none; }
.plist--steps li strong {
  color: var(--white);
  font-weight: 700;
}

/* Fettung am Listenanfang: hebt den Kern jedes Punktes hervor,
   ohne die Zeile in zwei Absätze zu zerlegen. */
.plist li strong { font-weight: 700; }

/* Fragen-Block auf den Leistungsseiten: gleiche Bauart wie auf der
   Startseite, nur ohne den dortigen Zweispalter. */
.split-body .faq-list { margin-top: var(--s-3); }
.split-body .faq-list summary { text-wrap: balance; }

/* ============================================================
   FRAGEN-BLOCK auf den Leistungsseiten (Runde 30)
   Variante „redaktionell": Frage links, Antwort rechts, nur
   Haarlinien statt Kästen. Nimmt die 5/7-Teilung der übrigen
   Seitenblöcke auf, sodass sich der Block einfügt, statt als
   fünfter Kastenstapel am Seitenende zu wirken. Alle Antworten
   sind sofort sichtbar — nichts zum Aufklappen.
   Runde 31: Rahmenlinie über der Überschrift und Schlusslinie
   unter der letzten Frage entfernt — der Block schließt die Seite
   jetzt offen ab, statt sie doppelt einzurahmen.
   ============================================================ */
.faq-block {
  padding-block: var(--s-5);
}
/* Runde 31: gleiche Größe und Laufweite wie die Sektions-Überschriften
   der übrigen Blöcke (.split-head h2) — der Fragen-Block sitzt zwar
   über die volle Breite, soll aber in derselben Stimme sprechen. */
.faq-block > h2 {
  font-size: var(--fs-h3);
  font-weight: 700;
  letter-spacing: -0.015em;
  line-height: 1.12;
}
.faq-editorial { margin-top: var(--s-3); }
.faq-zeile {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
  gap: var(--s-4);
  padding-block: var(--s-3);
  border-top: 1px solid var(--line-l);
}
.faq-frage {
  font-family: var(--font-display);
  font-size: 1.35rem;
  font-weight: 700;
  line-height: 1.25;
  letter-spacing: -0.015em;
  color: var(--white);
  text-wrap: balance;
}
.faq-antwort {
  color: var(--muted-d);
  line-height: 1.7;
}
.faq-antwort a { border-bottom: 1px solid rgba(255, 255, 255, 0.4); }
/* Gestapelt: Frage über Antwort, enger gesetzt — dieselbe Schwelle,
   an der auch die übrigen Zweispalter der Seite umbrechen. */
@media (max-width: 900px) {
  .faq-zeile {
    grid-template-columns: 1fr;
    gap: var(--s-2);
  }
  .faq-frage { font-size: 1.2rem; }
}

/* ---- Runde 50 · Aufklappbare Fragen auf schmalen Geräten ----------------
   Die sieben Leistungsseiten zeigen ihre Fragen redaktionell, also alle
   Antworten offen. Am Schreibtisch ist das richtig — zum Überfliegen. Auf
   dem Handy standen dadurch bis zu sieben lange Absätze zwischen dem Text
   und dem Abschluss der Seite; man scrollt an Fragen vorbei, die einen gar
   nicht betreffen.

   Umgesetzt als Aufwertung durch JavaScript (`initFaqAkkordeon` in main.js),
   nicht durch geändertes Markup: Die Auszeichnung für Suchmaschinen bleibt
   unangetastet, und ohne JavaScript sieht man weiterhin alles — der heutige
   Zustand also, kein Rückschritt. Erst wenn das Skript die Klasse `.is-faq-
   akkordeon` setzt, greifen die Regeln unten.
   ---------------------------------------------------------------------- */
@media (max-width: 700px) {
  .faq-editorial.is-faq-akkordeon .faq-zeile {
    padding-block: 0;
    gap: 0;
  }
  .faq-editorial.is-faq-akkordeon .faq-frage {
    position: relative;
    padding: var(--s-3) 2.4rem var(--s-3) 0;
    cursor: pointer;
    user-select: none;
    -webkit-tap-highlight-color: transparent;
  }
  /* Plus-Zeichen wie bei den Kachel-Fragen auf Startseite und Kontaktseite,
     damit beide Fragenformate dieselbe Bediensprache sprechen. */
  .faq-editorial.is-faq-akkordeon .faq-frage::after {
    content: "+";
    position: absolute;
    right: 0.2rem;
    top: 50%;
    translate: 0 -50%;
    font-family: var(--font);
    font-size: 1.5rem;
    font-weight: 400;
    line-height: 1;
    color: var(--blue-soft);
    transition: rotate var(--t-fast), color var(--t-fast);
  }
  .faq-editorial.is-faq-akkordeon .faq-zeile.is-offen .faq-frage::after {
    rotate: 45deg;
    color: var(--accent);
  }
  .faq-editorial.is-faq-akkordeon .faq-frage:focus-visible {
    outline: 2px solid var(--accent);
    outline-offset: 4px;
    border-radius: 6px;
  }
  /* Geschlossen: Höhe 0 statt display:none — so bleibt der Text für die
     Seitensuche des Browsers auffindbar und der Wechsel läuft weich. */
  .faq-editorial.is-faq-akkordeon .faq-antwort {
    display: grid;
    grid-template-rows: 0fr;
    opacity: 0;
    transition: grid-template-rows var(--t-fast), opacity var(--t-fast);
  }
  .faq-editorial.is-faq-akkordeon .faq-antwort > * { overflow: hidden; }
  .faq-editorial.is-faq-akkordeon .faq-zeile.is-offen .faq-antwort {
    grid-template-rows: 1fr;
    opacity: 1;
    padding-bottom: var(--s-3);
  }
}
@media (max-width: 700px) and (prefers-reduced-motion: reduce) {
  .faq-editorial.is-faq-akkordeon .faq-antwort,
  .faq-editorial.is-faq-akkordeon .faq-frage::after { transition: none; }
}

/* --- Leistungsübersicht: Einstiegshilfe (Runde 32) ----------
   „Welche Leistung passt zu Ihrer Situation?" — Ausgangslage
   fett, darunter der Link auf die passende Detailseite. Zwei
   Ebenen in einer Zeile, damit die Liste scanbar bleibt. */
.zuordnung li strong { display: block; }
.zuordnung li a {
  display: inline-block;
  margin-top: 0.2rem;
  color: var(--blue-soft);
  font-weight: 600;
  border-bottom: 1px solid transparent;
  transition: border-color var(--t-fast) var(--ease), color var(--t-fast) var(--ease);
}
.zuordnung li a:hover {
  color: var(--white);
  border-bottom-color: var(--white);
}
/* Der Einführungsblock steht direkt unter dem Seitenkopf und
   braucht dort keine Trennlinie nach oben. */
.intro-split { border-top: 0; }

/* --- Leistungsübersicht: Kurztext je Panel (Runde 33) -------
   Die Textkacheln trugen nur Titel und Slogan; darunter stand
   eine große Leerfläche, weil der Link an der Unterkante klebt.
   Ein knapper Absatz füllt die Karte, ohne der Detailseite den
   Rang abzulaufen — eine Stufe kleiner als der Slogan. */
.showcase-text {
  margin-top: var(--s-2);
  font-size: var(--fs-body);
  line-height: 1.65;
  color: var(--muted-d);
  max-width: 42ch;
}

/* --- Kontaktseite: Anschluss an den Seitenkopf (Runde 34) ---
   Seit die Erwartungs-Kästen unter das Formular gewandert sind,
   stand über dem Formular eine auffällig große Leerfläche: Die
   Sektion trug das große Polster (202px), während alle anderen
   Unterseiten hier 112px haben. Angeglichen — der Abstand zum
   Seitenkopf ist jetzt derselbe wie auf Karriere, Über uns und
   den sieben Leistungsseiten. Nur oben; unten bleibt das große
   Polster, weil dort die Kästen und Fragenblöcke folgen. */
#erstgespraech {
  padding-top: var(--s-6);
  /* Unteres Polster auf dasselbe Maß: Die Erwartungs-Kästen sitzen
     dadurch mittig zwischen Formular und Sektionsende, statt oben
     zu kleben (vorher 64px darüber, 158px darunter). */
  padding-bottom: var(--s-5);
}
/* Runde 43: Die Kästen eröffnen den dunklen Inhaltsbereich der Kontaktseite.
   Kein eigener Abstand nach oben (das Sektionspolster liefert ihn), und der
   folgende Textblock verliert seine Trenner-Haarlinie — sie klebte sonst
   direkt an der Kästen-Unterkante. */
.contact-prelude--content { margin-top: 0; }
.contact-prelude--content + .split { border-top: 0; }
/* Anschluss-Sektion: oben gestrafft, damit blauer und dunkler Bereich
   zusammenrücken — unten bleibt das normale Maß. */
.content--anschluss { padding-top: var(--s-4); }
/* Kontaktseite: Die Textspalte behält ihre Lesebreite (52ch), rückt aber an
   die rechte Containerkante — bündig mit den Kästen darüber. */
.content--anschluss .split-body { justify-self: end; width: 100%; }

/* ============================================================
   ÜBERSICHT ZUM WEITERGEBEN (Runde 42)
   Mittige, auslaufende Haarlinie über die volle Containerbreite
   (bündig mit den Kacheln darüber), Versal-Titel, zwei gesetzte
   Textzeilen, Nachsatz, Standard-Button.
   ============================================================ */
.uebersicht-hinweis {
  /* Auf der Startseite liegt der Block im Kontakt-Grid — volle Breite
     spannen, sonst klemmt er in der linken Spalte. */
  grid-column: 1 / -1;
  /* Referenz ist die Startseite (dort liefert der Grid-Zeilenabstand zusätzlich
     Luft, gemessen 128 px Inhalt→Linie) — außerhalb des Grids braucht es dafür
     die größere Stufe plus Ausgleich. */
  margin-top: calc(var(--s-6) + 1rem);
  text-align: center;
}
/* Im Grid liefert der Zeilenabstand (gap) bereits Luft — der volle
   margin-top käme oben drauf und riss das Element vom Inhalt ab. */
.contact-grid .uebersicht-hinweis { margin-top: var(--s-2); }
.uh-rule {
  display: block;
  width: 100%;
  height: 1px;
  margin: 0 auto var(--s-3);
  background: var(--line-d);   /* dieselbe Haarlinie wie überall */
}
.uh-title {
  font-family: var(--font-display);
  font-weight: 700;
  font-size: clamp(1.35rem, 2.6vw, 1.9rem);
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--white);
}
.uh-text {
  margin: var(--s-2) auto 0;
  max-width: 60rem;
  color: var(--muted-d);
  font-size: var(--fs-small);
  line-height: 1.7;
}
.uh-btn {
  margin-top: var(--s-3);
  width: auto;          /* nie über die volle Breite strecken */
  align-self: center;
}

/* ============================================================
   KOPFSPALTE DER TEXTBLÖCKE MITLAUFEN LASSEN (Runde 39)
   Auf den sieben Leistungsseiten stand die linke Spalte über bis zu
   2.518 px leer, während rechts der Fließtext lief (gemessen bei
   1440 px auf direktvertrieb.html). Die Überschrift bleibt jetzt
   beim Lesen stehen: Die Fläche trägt Bedeutung statt Leere, und
   man weiß auf langen Blöcken jederzeit, in welchem Abschnitt man ist.
   Nur ab der zweispaltigen Breite — darunter stehen Kopf und Text
   ohnehin untereinander.
   ============================================================ */
@media (min-width: 901px) {
  .split > .split-head {
    position: sticky;
    top: 7.5rem;
    align-self: start;
  }
}


/* ============================================================
   FOKUS NICHT UNTER DER KOPFLEISTE (WCAG 2.4.11, Runde 40)
   Die Kopfleiste liegt fest über dem Inhalt. Ohne diese Regel
   scrollt der Browser ein per Tabulator angesprungenes Element
   genau darunter — sichtbar ist dann nichts.
   ============================================================ */
:where(a, button, input, textarea, select, summary, [tabindex]):focus-visible {
  scroll-margin-top: 7.5rem;
  scroll-margin-bottom: 2rem;
}
/* Der Hauptbereich ist nur programmatisch fokussierbar (Sprunglink) und
   soll dabei keinen sichtbaren Rahmen bekommen. */
main:focus { outline: none; }




