/* oow.berlin - CSS-System der statischen Fassung.
 *
 * MASSGEBLICH sind seit dem Vorlagenwechsel die Wireframes unter docs/wireframes/. Die Werte
 * hier sind von dort uebernommen; wo die Wireframes Ersatzschriften nennen (Montserrat,
 * Roboto), steht der OOW-Bestand: ITC Avant Garde Gothic und Roboto Mono, selbst gehostet.
 * Gewichts-Mapping nach DESIGN_OOW-ONLINE.md Abschnitt 2: 400 -> 300, 700 -> 800.
 *
 * Reihenfolge: Schriften, Tokens, Grundlage, Kopf, Menue, Bausteine, Vorlagen, Fuss.
 */

/* ------------------------------------------------------------------ 0. Schriften
 *
 * Selbst gehostet als WOFF2, keine Verbindung zu Google oder Adobe.
 *
 * ITC Avant Garde Gothic W01 aus dem lizenzierten Webfont-Kit (Fonts.com Pay-As-You-Go,
 * Rechnung FSC144926 vom 1.10.2019). Fuenf aufrechte Schnitte; die fuenf schraegen bleiben
 * draussen, weil die Gestaltung keine echte Kursive kennt - das kursive HELLOOW laeuft
 * bewusst als synthetische Schraege, wie am Original gemessen.
 *
 * Roboto Mono steht unter der SIL Open Font License 1.1 - der Lizenztext liegt daneben in
 * schriften/OFL.txt, das verlangt die Lizenz beim Weitergeben.
 */

@font-face {
  font-family: "ITC Avant Garde Gothic";
  font-style: normal;
  font-weight: 100 200; /* Extra Light - Projekttitel, Riesen-Telefonnummer */
  font-display: swap;
  src: url("/schriften/itc-avant-garde-xlight.woff2") format("woff2");
}

@font-face {
  font-family: "ITC Avant Garde Gothic";
  font-style: normal;
  font-weight: 300 400; /* Book - Fliesstext, Sublines, Zitate */
  font-display: swap;
  src: url("/schriften/itc-avant-garde-book.woff2") format("woff2");
}

@font-face {
  font-family: "ITC Avant Garde Gothic";
  font-style: normal;
  font-weight: 500; /* Medium - Labels */
  font-display: swap;
  src: url("/schriften/itc-avant-garde-medium.woff2") format("woff2");
}

@font-face {
  font-family: "ITC Avant Garde Gothic";
  font-style: normal;
  font-weight: 600; /* Demi - Namenszeilen */
  font-display: swap;
  src: url("/schriften/itc-avant-garde-demi.woff2") format("woff2");
}

@font-face {
  font-family: "ITC Avant Garde Gothic";
  font-style: normal;
  font-weight: 700 800; /* Bold - Headlines */
  font-display: swap;
  src: url("/schriften/itc-avant-garde-bold.woff2") format("woff2");
}

@font-face {
  font-family: "Roboto Mono";
  font-style: normal;
  font-weight: 300;
  font-display: swap;
  src: url("/schriften/roboto-mono-300.woff2") format("woff2");
}

@font-face {
  font-family: "Roboto Mono";
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url("/schriften/roboto-mono-500.woff2") format("woff2");
}

/* ------------------------------------------------------------------ 1. Tokens
   Namen und Werte eins zu eins aus den Wireframes. */

:root {
  --c-bg: #232323;
  --c-black: #000;
  --c-white: #fff;
  --c-sec: #bcbcbc;
  --c-accent: #5f33ff;
  --c-accent-dark: #3e1c8e;
  --c-pill: #0c0c0c;
  --c-monotext: #ddd;
  --c-warm: #f9f2ef;
  --c-galerie: #1c1c1c;
  --c-ink: #232323;

  --f-disp: "ITC Avant Garde Gothic", "Century Gothic", "URW Gothic", sans-serif;
  --f-mono: "Roboto Mono", ui-monospace, "SF Mono", Menlo, Consolas, monospace;
  /* Die Wireframes setzen fuer CTA-Knoepfe 'Roboto'. DESIGN_OOW-ONLINE Abschnitt 2 laesst
     genau zwei Schriften zu, Abschnitt 6 nennt fuer Knoepfe Roboto Mono. Also Mono. */
  --f-cta: var(--f-mono);

  --fs-display: 5.7rem;
  --fs-h1: 4.7rem;
  --fs-h2: 3.9rem;
  --fs-h3: 3.5rem;
  --fs-sub: 2rem;
  --fs-body: 1.6rem;
  --fs-filter: 1.4rem;
  --fs-projh1: 3.1rem;
  --lh-projh1: 58px;
  --fs-quote: 1.4rem;
  --fs-counter: 126px;
  --fs-hello: 5.4rem;
  --fs-phone: 4.2rem;
  --fs-name: 3.5rem;
  --fs-quote-h1: 4.2rem;
  --fs-pull: 3.2rem;
  --fs-pull-min: 1.9rem;
  --fs-frage: 1.5rem;
  --fs-bigquote: 2.4rem;
  --fs-h3light: 1.6rem;

  --container: 1140px;
}

@media (max-width: 1024px) {
  :root {
    --fs-display: 3.4rem;
    --fs-h1: 2.9rem;
    --fs-h2: 2.5rem;
    --fs-h3: 2.2rem;
    --fs-sub: 1.9rem;
    --fs-body: 1.3rem;
    --fs-filter: 1.3rem;
    --fs-projh1: 2.5rem;
    --lh-projh1: 60px;
    --fs-quote: 1.3rem;
    --fs-counter: 72px;
    --fs-hello: 3.6rem;
    --fs-phone: 2.8rem;
    --fs-name: 2.2rem;
    --fs-quote-h1: 2.9rem;
    --fs-pull: 2.2rem;
    --fs-pull-min: 1.7rem;
    --fs-frage: 1.3rem;
    --fs-bigquote: 1.9rem;
    --fs-h3light: 1.4rem;
  }
}

@media (max-width: 767px) {
  :root {
    --fs-display: 2.3rem;
    --fs-h1: 2.1rem;
    --fs-h2: 1.9rem;
    --fs-h3: 1.7rem;
    --fs-sub: 1.6rem;
    --fs-body: 1.2rem;
    --fs-filter: 1.1rem;
    --fs-projh1: 1.9rem;
    --lh-projh1: 38px;
    --fs-quote: 1.1rem;
    --fs-counter: 46px;
    --fs-hello: 2.4rem;
    --fs-phone: 1.8rem;
    --fs-name: 1.5rem;
    --fs-quote-h1: 2rem;
    --fs-pull: 1.7rem;
    --fs-pull-min: 1.3rem;
    --fs-frage: 1.15rem;
    --fs-bigquote: 1.5rem;
    --fs-h3light: 1.25rem;
  }
}

/* ------------------------------------------------------------------ 2. Grundlage */

/* Roboto Mono liegt nur in 300 und 500 (Entscheid F2, BRIEFING_DESIGN_UPDATE
   Abschnitt 7). Kein Kunstfett: fehlt ein Gewicht, greift der naechste echte
   Schnitt. Global gesetzt und vererbt; die AGG deckt 100 bis 800 mit echten
   Schnitten ab, wirksam wird die Regel also genau an den Mono-Elementen. */
html {
  font-synthesis-weight: none;
}

*,
*::before,
*::after {
  box-sizing: border-box;
}

* {
  margin: 0;
  padding: 0;
}

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

body {
  font: 300 16px/1.7 var(--f-disp);
  -webkit-font-smoothing: antialiased;
  /* Kein waagerechter Ueberlauf: die vollbreiten Baender rechnen mit 100vw, die
     Bildlaufleiste zaehlt dort mit. */
  overflow-x: hidden;
}

/* Hell und dunkel stehen vollstaendig in Abschnitt 12 - html, body UND die
   body::before-Ebene, wie es DESIGN_OOW-ONLINE Abschnitt 7 verlangt. */

img {
  max-width: 100%;
  height: auto;
  display: block;
  border: 0;
}

a {
  color: inherit;
}

a:focus-visible,
button:focus-visible,
summary:focus-visible,
input:focus-visible,
textarea:focus-visible {
  outline: 2px solid var(--c-accent);
  outline-offset: 3px;
}

.container {
  max-width: var(--container);
  margin: 0 auto;
  padding: 0 24px;
}

/* Raster-Kinder duerfen schrumpfen. Ohne das steht min-width:auto und eine lange
   unzertrennliche Zeile - der Bueroname im Fuss, eine Projektueberschrift - macht die
   Spalte breiter als das Fenster und schiebt die ganze Seite waagerecht auf. */
.f-cols > *,
.projektraster > *,
.teamgrid > *,
.split > *,
.split50 > *,
.interview > *,
.contactrow > *,
.grid-meta > *,
.quote-split > *,
.header-desk .container > * {
  min-width: 0;
}

/* Lange Adressen, Mailadressen und Dateinamen brechen, statt zu ueberlaufen. */
.f-cols a,
.legal a,
.seo-copy a,
.contactrow a {
  overflow-wrap: anywhere;
}

.center {
  text-align: center;
}

.sprung {
  position: absolute;
  left: -9999px;
}

.sprung:focus {
  left: 14px;
  top: 14px;
  z-index: 2000;
  background: var(--c-black);
  color: var(--c-white);
  padding: 12px 20px;
  font: 500 13px/1 var(--f-mono);
  letter-spacing: 2px;
  text-transform: uppercase;
}

/* ------------------------------------------------------------------ 3. Typografie-Rollen */

h1,
h2,
h3 {
  font-family: var(--f-disp);
}

/* Deutsche Komposita sind laenger als eine 390er Spalte - "Berufshaftpflicht-
   versicherung" allein misst bei 30 px Schriftgroesse 383 px. Ohne Trennung schiebt
   eine einzige Ueberschrift die ganze Seite waagerecht auf. lang="de" steht am html,
   also kann der Browser richtig trennen. */
h1,
h2,
h3,
h4,
h5,
h6,
.display,
.statement,
.pull,
.overlay-quote {
  overflow-wrap: break-word;
  hyphens: auto;
}

.display {
  font-size: var(--fs-display);
  font-weight: 800;
  line-height: 1;
  color: var(--c-sec);
}

.subline {
  font: 300 var(--fs-sub) / 1 var(--f-disp);
  letter-spacing: 3.1px;
  text-transform: uppercase;
  color: var(--c-sec);
}

.label {
  font: 500 1rem/1.5 var(--f-mono);
  letter-spacing: 5.5px;
  text-transform: uppercase;
  color: var(--c-sec);
}

.body-copy {
  font: 300 var(--fs-body) / 1.6 var(--f-disp);
  color: var(--c-sec);
}

/* Kicker- und Meta-Zeilen der hellen Vorlagen. */
.kicker {
  font: 500 16px/1.5 var(--f-mono);
  letter-spacing: 5.3px;
  text-transform: uppercase;
  color: var(--c-ink);
  margin-bottom: 22px;
}

.kicker-line {
  padding: 52px 24px 0;
  text-align: center;
  font: 500 16px/1.6 var(--f-mono);
  letter-spacing: 5.3px;
  text-transform: uppercase;
  color: var(--c-ink);
}

.mlabel {
  font: 500 16px/1.5 var(--f-disp);
  letter-spacing: 4.7px;
  text-transform: uppercase;
  color: var(--c-accent);
  margin-bottom: 14px;
}

.mvalue {
  font: 300 18px/1.6 var(--f-mono);
  letter-spacing: 0.9px;
  color: var(--c-ink);
}

.bildtext {
  font: 300 15px/1.7 var(--f-mono);
  letter-spacing: 2.5px;
  color: var(--c-accent);
}

/* ------------------------------------------------------------------ 4. Knoepfe */

.pill {
  font: 300 12.8px/1 var(--f-mono);
  letter-spacing: 2.6px;
  text-transform: uppercase;
  color: var(--c-white);
  background: var(--c-pill);
  border: 0;
  border-radius: 49px;
  padding: 12px 20px;
  text-decoration: none;
  cursor: pointer;
  transition: transform 0.25s;
}

/* Pill-Hover wie live: nur Skalierung, kein Farbwechsel (DESIGN_OOW-ONLINE Abschnitt 6). */
.pill:hover {
  transform: scale(0.9);
}

.pill.is-current {
  background: #1f1f1f;
}

.btn-cta {
  display: inline-block;
  font: 300 20px/1 var(--f-cta);
  letter-spacing: 1.84px;
  text-transform: uppercase;
  color: var(--c-white);
  background: var(--c-accent);
  border: 0;
  border-radius: 50px;
  padding: 18px 34px;
  text-decoration: none;
  cursor: pointer;
  transition: background 0.25s;
}

.btn-cta:hover {
  background: var(--c-accent-dark);
}

@media (max-width: 767px) {
  .btn-cta {
    font-size: 15px;
    padding: 15px 26px;
  }
}

.btn-violet {
  display: inline-block;
  font: 300 15px/1 var(--f-mono);
  letter-spacing: 3.5px;
  text-transform: uppercase;
  color: var(--c-white);
  background: var(--c-accent);
  border: 0;
  border-radius: 50px;
  padding: 18px 38px;
  text-decoration: none;
  cursor: pointer;
  transition: background 0.25s;
}

.btn-violet:hover {
  background: var(--c-accent-dark);
}

/* Outline-Pill weiss auf DUNKLEM Grund - der CTA der Startseiten-Anrisse. Am Original
   gemessen (2026-08-20): 14 px Roboto Mono 300, ls 3.5 px, Rand 2 px weiss, Radius 50,
   Innenabstand 10/20 px, Flaeche transparent, linksbuendig - Kasten 151x40 px.
   Vierte Knopfvariante neben Pill dunkel, Pill violett und Outline auf Violett
   (DESIGN_OOW-ONLINE Abschnitt 6). */
.btn-outline {
  display: inline-block;
  font: 300 14px/16px var(--f-mono);
  letter-spacing: 3.5px;
  text-transform: uppercase;
  color: var(--c-white);
  background: transparent;
  border: 2px solid var(--c-white);
  border-radius: 50px;
  padding: 10px 20px;
  text-decoration: none;
  transition: background 0.25s, color 0.25s;
}

.btn-outline:hover {
  background: var(--c-white);
  color: var(--c-ink);
}

.btn-ghost {
  display: inline-block;
  font: 300 13px/1 var(--f-mono);
  letter-spacing: 3px;
  text-transform: uppercase;
  color: var(--c-white);
  background: transparent;
  border: 1px solid rgba(255, 255, 255, 0.85);
  border-radius: 50px;
  padding: 15px 30px;
  margin: 0 10px 14px;
  text-decoration: none;
  transition: background 0.25s, color 0.25s;
}

.btn-ghost:hover {
  background: var(--c-white);
  color: var(--c-accent);
}

.cta-row {
  text-align: center;
  padding: 26px 0 80px;
}

/* ------------------------------------------------------------------ 5. Kopf */

.header-desk {
  background: var(--c-black);
  height: 90px;
  position: relative;
  z-index: 5;
}

/* Kopfinhalt vollbreit (K1, Nutzer-Entscheid 2026-08-19, analog ST7 beim Fuss):
   kein 1140er-Deckel, Randabstand 25 px - am Original gemessen (Pill-Rechtskante
   konstant 25 px vor der Layout-Kante bei 1440 und 1880). Das symmetrische Padding
   haelt den Claim ueber das 1fr-auto-1fr-Raster exakt auf Fenstermitte. */
.header-desk .container {
  max-width: none;
  padding: 0 25px;
  height: 100%;
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
}

.claim {
  grid-column: 2;
  font: 300 16px/1 var(--f-disp);
  color: #f7f7f7;
  text-decoration: none;
}

.header-actions {
  grid-column: 3;
  justify-self: end;
  display: flex;
  gap: 12px;
}

/* Das Logo-Dreieck: das ORIGINAL-Asset oow.png (223x275, dargestellt 149x184), an der
   Fensterkante fixiert, 94 px Ueberhang unter der 90er Leiste, und der Menue-Ausloeser.
   Kein CSS-Nachbau mehr (Nutzer-Entscheid L1, 2026-08-18). Hover wie das Original:
   sanftes Verkleinern. */
.badge {
  position: fixed;
  top: 0;
  left: 0;
  width: 149px;
  height: 184px;
  background: none;
  border: 0;
  cursor: pointer;
  z-index: 1000;
  padding: 0;
  transition: transform 0.25s ease;
}

.badge img {
  display: block;
  width: 149px;
  height: 184px;
}

.badge:hover {
  transform: scale(0.92);
  transform-origin: top left;
}

.logo {
  font-family: var(--f-disp);
  color: var(--c-white);
  font-size: 27px;
  line-height: 1;
  letter-spacing: 0.5px;
  white-space: nowrap;
}

.logo b {
  font-weight: 800;
}

.logo i {
  font-weight: 300;
  font-style: italic;
}

.header-mob {
  display: none;
  background: var(--c-black);
  min-height: 47px;
  z-index: 999;
  position: relative;
  align-items: center;
  justify-content: space-between;
  padding: 10px 16px;
}

.header-mob .brand {
  display: flex;
  align-items: center;
  gap: 12px;
  text-decoration: none;
}

.header-mob .logo {
  font-size: 20px;
}

.header-mob .brand span {
  font: 300 12px/1 var(--f-mono);
  letter-spacing: 3.5px;
  color: var(--c-white);
}

.ellipsis {
  background: none;
  border: 0;
  cursor: pointer;
  padding: 8px 12px;
  display: flex;
  flex-direction: column;
  gap: 4px;
}

.ellipsis i {
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--c-accent);
}

@media (max-width: 1024px) {
  .header-desk,
  .badge {
    display: none;
  }
  .header-mob {
    display: flex;
  }
}

/* ------------------------------------------------------------------ 6. Menue
   Popover-API: kein JavaScript. Scroll-Lock ueber body:has(:popover-open). */

.menu {
  position: fixed;
  top: 0;
  bottom: 0;
  left: 0;
  right: auto;
  width: 48vw;
  min-width: 480px;
  height: auto;
  max-height: none;
  max-width: none;
  background: var(--c-accent);
  border: 0;
  margin: 0;
  padding: 70px 0 40px;
  overflow-y: auto;
  transform: translateX(-102%);
  transition: transform 0.6s cubic-bezier(0.22, 0.61, 0.36, 1),
    display 0.6s allow-discrete, overlay 0.6s allow-discrete;
}

.menu:popover-open {
  transform: translateX(0);
}

@starting-style {
  .menu:popover-open {
    transform: translateX(-102%);
  }
}

.menu::backdrop {
  background: rgba(0, 0, 0, 0);
  transition: background 0.4s, display 0.4s allow-discrete, overlay 0.4s allow-discrete;
}

.menu:popover-open::backdrop {
  background: rgba(0, 0, 0, 0.5);
}

@starting-style {
  .menu:popover-open::backdrop {
    background: rgba(0, 0, 0, 0);
  }
}

body:has(.menu:popover-open) {
  overflow: hidden;
}

@media (max-width: 1024px) {
  .menu {
    width: 100vw;
    min-width: 0;
  }
}

.menu-close {
  position: absolute;
  top: 56px;
  right: 11%;
  width: 38px;
  height: 38px;
  background: none;
  border: 0;
  cursor: pointer;
  transition: transform 0.3s;
}

.menu-close::before,
.menu-close::after {
  content: "";
  position: absolute;
  top: 50%;
  left: 0;
  width: 100%;
  height: 1px;
  background: var(--c-white);
}

.menu-close::before {
  transform: rotate(45deg);
}

.menu-close::after {
  transform: rotate(-45deg);
}

.menu-close:hover {
  transform: rotate(90deg);
}

.menu nav {
  padding: 60px 0 0 9%;
}

.menu nav ul {
  list-style: none;
}

.menu nav a {
  display: block;
  width: max-content;
  text-decoration: none;
  color: var(--c-white);
  font: 800 var(--fs-h2) / 1.4 var(--f-disp);
  transition: color 0.2s;
}

.menu nav a:hover {
  color: rgba(255, 255, 255, 0.5);
}

.menu nav a.is-active,
.menu nav a[aria-current] {
  color: rgba(255, 255, 255, 0.55);
}

/* ------------------------------------------------------------------ 7. Bild-Slots
   .ph ist der Platzhalter aus den Wireframes und bleibt der Rueckfall, wo kein Bild
   vorliegt. Liegt eines vor, traegt .bildslot dasselbe Mass und zeigt das Bild. */

.ph {
  background: #e6e0dc;
  border: 1px dashed #b8b0aa;
  position: relative;
  background-image: repeating-linear-gradient(
    45deg,
    transparent 0 14px,
    rgba(0, 0, 0, 0.035) 14px 15px
  );
}

.ph::after {
  content: attr(data-label);
  position: absolute;
  inset: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  font: 300 11px/1 var(--f-mono);
  letter-spacing: 2px;
  color: #9a8f88;
  text-transform: uppercase;
}

.ph--dark {
  background: #2c2c2c;
  border-color: #4a4a4a;
  background-image: repeating-linear-gradient(
    45deg,
    transparent 0 14px,
    rgba(255, 255, 255, 0.03) 14px 15px
  );
}

.ph--dark::after {
  color: #7a7a7a;
}

.bildslot {
  position: relative;
  overflow: hidden;
}

/* Seit BZ2 (2026-08-24) kann im Slot ein <picture> stehen - dann liegt das img eine Ebene
   tiefer. display: contents nimmt das picture aus dem Layout, damit das img weiter direkt
   im .bildslot-Kasten misst und object-fit gegen dessen Mass rechnet. */
.bildslot > picture {
  display: contents;
}

.bildslot > img,
.bildslot > picture > img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.hero-img {
  height: 74vh;
  min-height: 420px;
}

/* Interview-Hero auf das Original-Mass (GS1/B5, gemessen 2026-08-19: 760 px bei
   1440x950, also 80vh; Bildschnitt nach Bildschnitt-Standard mit cover, Fokus Mitte -
   das Original setzt dort ein Hintergrundbild mit background-size: cover, 50% 50%). */
body[data-layout="interview"] .hero-img {
  height: 80vh;
}

.hero-img--flach {
  height: 64vh;
  min-height: 380px;
}

/* AN2.3 (Nutzer-Entscheid 2026-08-21): 818 px Breite = 460 px Hoehe im 16:9-Schnitt,
   Teil der Hero-Verdichtung, die den CTA ueber den Falz zieht. .ph-hero setzt
   ausschliesslich layouts/start.njk - andere Vorlagen sind nicht betroffen. */
.ph-hero {
  aspect-ratio: 16 / 9;
  width: min(818px, 100%);
  height: auto;
  margin: 0 auto;
}

.ph-tile {
  aspect-ratio: 3 / 2;
}

/* ------------------------------------------------------------------ 8. Inhaltsbausteine */

section {
  padding: 90px 0;
}

@media (max-width: 767px) {
  section {
    padding: 56px 0;
  }
}

.split {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 56px;
  align-items: center;
}

@media (max-width: 1024px) {
  .split {
    grid-template-columns: 1fr;
    gap: 36px;
  }
}

/* Alternierend gespiegelt: das Bild wandert bei jedem zweiten Anriss nach rechts.
   Unter 1024 px steht das Bild immer oben, wie in den Wireframes. */
.split--gedreht > .bildslot,
.split--gedreht > .ph {
  order: 2;
}

@media (max-width: 1024px) {
  .split--gedreht > .bildslot,
  .split--gedreht > .ph {
    order: 0;
  }
}

.split .ph,
.split .bildslot {
  aspect-ratio: 4 / 3;
}

.intro {
  padding: 90px 0 40px;
  text-align: center;
}

/* NUR der zentrierte Statement-Kopf, nicht jedes h2 im weissen Inhaltsbereich
   (Nutzer-Entscheid 2026-08-21, Auftrag AW Punkt 5). Die Regel hiess bis dahin
   ".intro h2" und traf damit auch die Zwischentitel einer langen Textstrecke
   (.seo-copy h2, weiter unten) - dort schnitt max-width: 22ch die Zeile nach rund
   22 Zeichen ab, gemessen 1440 px: Umbruch bei 470 statt 1100 px Spaltenbreite.
   teile/block.njk setzt den Statement-Kopf immer mit der Klasse .statement; die
   Projekt-Detailseiten aendern sich durch die Verengung deshalb nicht. */
.intro h2.statement {
  font: 800 var(--fs-h2) / 1 var(--f-disp);
  color: var(--c-ink);
  max-width: 22ch;
  margin: 0 auto;
}

/* Bandtitel einer Langtext-Seite: die OBERE der beiden Ueberschriftenebenen von
   /leistungen/ (LST v2 Punkt 4, 2026-08-21). Sie traegt die Statement-Rolle unveraendert -
   AGG 800, --fs-h2, zentriert, 22ch - und bekommt nur den Abstand, der sie als Beginn
   eines neuen Bandes lesbar macht. Werte aus dem Rhythmus der Wireframes (90 / 44,
   DESIGN_OOW-ONLINE Abschnitt 5), nicht geschaetzt. Die untere Ebene steht als h3 links in
   .seo-copy und behaelt dort ihre 52 px - so sind die beiden Ebenen an Groesse, Ausrichtung
   UND Abstand unterscheidbar. Die Projekt-Detailseiten haben nur .statement ohne diesen
   Zusatz und aendern sich nicht. */
.intro h2.statement--band {
  margin: 90px auto 44px;
}

.intro .copy {
  max-width: 900px;
  margin: 44px auto 0;
  text-align: left;
  font: 300 16px/1.7 var(--f-disp);
  color: var(--c-ink);
}

.intro .copy p + p {
  margin-top: 22px;
}

.copy-c {
  max-width: 940px;
  margin: 0 auto;
  padding: 0 24px 70px;
  text-align: center;
  color: var(--c-ink);
  font: 300 1.3rem/1.7 var(--f-disp);
}

.copy-c b {
  font-weight: 800;
}

@media (max-width: 767px) {
  .copy-c {
    font-size: 1.05rem;
  }
}

.frage-c {
  text-align: center;
  font: 800 var(--fs-frage) / 1.4 var(--f-disp);
  letter-spacing: 1.92px;
  color: var(--c-ink);
  margin: 0 auto 22px;
  max-width: 26ch;
  padding: 0 24px;
}

.quote-h1 {
  padding: 26px 24px 40px;
  text-align: center;
}

.quote-h1 h1 {
  font: 800 var(--fs-quote-h1) / 1.15 var(--f-disp);
  color: var(--c-ink);
  max-width: 22ch;
  margin: 0 auto;
}

.lead {
  max-width: 820px;
  margin: 0 auto;
  padding: 0 24px 80px;
  text-align: center;
  color: var(--c-ink);
  font: 300 1.25rem/1.7 var(--f-disp);
}

@media (max-width: 767px) {
  .lead {
    font-size: 1.05rem;
  }
}

.quote-split {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 64px;
  align-items: start;
  padding: 50px 0 80px;
}

@media (max-width: 1024px) {
  .quote-split {
    grid-template-columns: 1fr;
    gap: 36px;
  }
}

/* Bildschnitt-Standard (Nutzer-Entscheid 2026-08-18, DESIGN_OOW-ONLINE Abschnitt 5):
   der Split schneidet sein 4:5 per aspect-ratio + object-fit aus dem Original. */
.quote-split .ph,
.quote-split .bildslot {
  aspect-ratio: 4 / 5;
}

.quote-split .bildtext {
  margin-top: 14px;
}

blockquote {
  border: 0;
}

blockquote p {
  font: 300 var(--fs-quote) / 1.8 var(--f-disp);
  color: var(--c-accent);
}

blockquote footer {
  margin-top: 26px;
  font: 500 15px/1.5 var(--f-disp);
  letter-spacing: 2px;
  text-transform: uppercase;
  color: var(--c-ink);
}

.quote-block {
  max-width: 820px;
  margin: 60px auto;
  padding: 0 24px;
  text-align: center;
}

.quote-block p {
  font: 300 var(--fs-quote) / 1.8 var(--f-disp);
  color: var(--c-accent);
}

.quote-block footer {
  margin-top: 24px;
  font: 500 14px/1.5 var(--f-disp);
  letter-spacing: 2px;
  text-transform: uppercase;
  color: var(--c-ink);
}

.bigquote {
  max-width: 760px;
  margin: 0 auto;
  padding: 30px 24px 70px;
  text-align: center;
  font: 800 var(--fs-bigquote) / 1.5 var(--f-disp);
  letter-spacing: 1.92px;
  color: var(--c-accent);
}

.img-block {
  max-width: 1080px;
  margin: 0 auto 80px;
  padding: 0 24px;
}

.img-block .ph {
  aspect-ratio: 16 / 9;
}

.seo-copy {
  max-width: 1140px;
  margin: 0 auto;
  padding: 0 24px 40px;
  color: var(--c-ink);
}

.seo-copy p {
  margin-bottom: 26px;
}

.seo-copy h2,
.seo-copy h3 {
  font: 300 var(--fs-h3light) / 1.6 var(--f-disp);
  color: var(--c-ink);
  margin: 52px 0 20px;
}

.seo-copy a {
  color: var(--c-accent);
  text-decoration: none;
}

.seo-copy a:hover {
  text-decoration: underline;
}

/* Karussell nativ: Scroll-Snap, ohne Autoplay, ohne Bibliothek. Wo der Browser
   ::scroll-button kann, entstehen Pfeile und Punkte ganz ohne Markup-Zutat. */
.carousel {
  position: relative;
  max-width: 1180px;
  margin: 0 auto 90px;
  padding: 0 24px;
}

.car-scroll {
  display: flex;
  overflow-x: auto;
  scroll-snap-type: x mandatory;
  scroll-behavior: smooth;
  scrollbar-width: none;
  list-style: none;
}

.car-scroll::-webkit-scrollbar {
  display: none;
}

/* KAR (Nutzer-Entscheid 2026-08-21), Begruendung nachgezogen am 2026-08-25 (KTX):
   das Karussell traegt das Format der Slides - 3836 x 2603 px, also 1,4737 : 1 quer, bei
   allen 202 Dateien gleich. Vorher stand hier 16:9 mit Beschnitt (Bildschnitt-Standard),
   weil der Bestand gemischt war.
   KEIN BESCHNITT: `contain` stand hier urspruenglich, weil auf den Slides Text als Pixel
   im Bild stand und jedes `cover` davon etwas abgeschnitten haette. Dieser Grund ist mit
   KTX entfallen - die Slides sind textfrei. `contain` BLEIBT trotzdem (Nutzer-Entscheid
   2026-08-25): bei einheitlichem Quellformat in einem Slot desselben Verhaeltnisses ist
   es deckungsgleich mit `cover`, kostet also nichts - und faengt einen kuenftigen
   Ausreisser im Format ab, statt ihn stillschweigend zu beschneiden. Im Normalfall
   bleibt keine Restflaeche uebrig.
   Die Restflaeche, wo doch eine entsteht, bleibt UNBEMALT: der Slot ist durchsichtig, es
   steht der Seitengrund des Designsystems darunter (Abschnitt 12 - weiss auf hellen,
   #232323 auf dunklen Seiten). Eine eigene Fuellfarbe waere ein zweiter Ort fuer dieselbe
   Angabe und auf einer der beiden Seitenarten falsch.
   Die beiden GRUENDER-Strecken (.streifen, .interview weiter unten) sind davon
   ausgenommen und behalten cover: dort liegen Rohfotos ohne Text im Bild. */
.car-slide {
  flex: 0 0 100%;
  aspect-ratio: 3836 / 2603;
  scroll-snap-align: center;
  scroll-snap-stop: always;
}

/* Die Slides kommen als <picture> mit AVIF/WebP/JPEG-Stufen. picture ist von Haus aus
   inline und gaebe dem Bild keine Hoehe, an der 100 % haengen koennte. */
.car-slide picture {
  display: block;
  height: 100%;
}

.car-slide img {
  width: 100%;
  height: 100%;
  object-fit: contain;
}

.car-dots {
  display: flex;
  justify-content: center;
  gap: 8px;
  margin-top: 16px;
}

.car-dots a {
  width: 9px;
  height: 9px;
  border-radius: 50%;
  background: #cfc7c1;
  display: block;
}

.car-dots a:hover,
.car-dots a:focus-visible {
  background: var(--c-accent);
}

@supports selector(::scroll-button(right)) {
  .car-scroll {
    scroll-marker-group: after;
  }
  .car-scroll::scroll-button(*) {
    position: absolute;
    top: 50%;
    translate: 0 -50%;
    background: none;
    border: 0;
    cursor: pointer;
    color: var(--c-ink);
    font: 100 44px/1 var(--f-disp);
    z-index: 2;
  }
  .car-scroll::scroll-button(left) {
    content: "\2039";
    left: -8px;
  }
  .car-scroll::scroll-button(right) {
    content: "\203A";
    right: -8px;
  }
  .car-scroll::scroll-button(*):disabled {
    opacity: 0.25;
  }
  .car-slide::scroll-marker {
    content: "";
    width: 9px;
    height: 9px;
    border-radius: 50%;
    background: #cfc7c1;
  }
  .car-slide::scroll-marker:target-current {
    background: var(--c-accent);
  }
  .car-scroll::scroll-marker-group {
    display: flex;
    justify-content: center;
    gap: 8px;
    margin-top: 16px;
  }
  .car-dots {
    display: none;
  }
}

.slider-caption {
  max-width: 1180px;
  margin: 0 auto;
  padding: 0 24px 80px;
}

/* Dunkle Bildstrecke */
.galerie {
  background: var(--c-galerie);
  padding: 90px 0;
}

.galerie .stack {
  display: grid;
  gap: 56px;
  max-width: 1180px;
  margin: 0 auto;
  padding: 0 24px;
}

.galerie .ph,
.galerie .bildslot {
  aspect-ratio: 16 / 9;
}

/* ------------------------------------------------------------------ 9. Baender */

/* Meta-Band warmweiss */
.meta {
  background: var(--c-warm);
  padding: 44px 0 42px;
}

/* Zweizeilige Banderole (Nutzer-Entscheid 2026-08-21): Titelzeile ueber die volle
   Breite, darunter die Faktenpaare in einer Zeile. Spaltenbreite am Inhalt (auto),
   Restluft gleichmaessig verteilt. Die Spaltenzahl kommt aus --meta-spalten, das
   projekt.njk nur setzt, wenn eine Seite nicht genau 4 Faktenpaare traegt; der
   Regelfall 4 steht als Ausweichwert hier. Bewusst eine Custom Property und kein
   direktes grid-template-columns im style-Attribut: sonst schluege der Inline-Wert
   die Umbrueche der Media Queries. */
.meta .grid-meta {
  display: grid;
  grid-template-columns: var(--meta-spalten, repeat(4, auto));
  justify-content: space-between;
  gap: 40px 50px;
}

.meta .grid-meta > div:first-child {
  grid-column: 1 / -1;
}

.meta .grid-meta h1 {
  font-size: 2.65rem;
  line-height: 50px;
}

.meta .grid-meta .mlabel {
  margin-bottom: 18px;
}

.meta .grid-meta .mvalue {
  font-size: 16px;
}

@media (max-width: 1024px) {
  .meta .grid-meta {
    grid-template-columns: 1fr 1fr;
  }

  /* Unterhalb der Banderolen-Breite wieder an den Stufen von --fs-projh1: die
     42,4px/50px aus Punkt 1 sind ein Desktop-Mass. */
  .meta .grid-meta h1 {
    font-size: var(--fs-projh1);
    line-height: var(--lh-projh1);
  }
}

@media (max-width: 767px) {
  .meta .grid-meta {
    grid-template-columns: 1fr;
    gap: 28px;
  }
}

.meta h1 {
  font: 100 var(--fs-projh1) / var(--lh-projh1) var(--f-disp);
  text-transform: uppercase;
  color: var(--c-black);
  letter-spacing: 0;
}

/* Die 44px Kopfluft aus Punkt 1 des Auftrags PB1 gelten der Projekt-Banderole. Die
   Bereichs- und Kategorieseiten bleiben laut Auftrag unangetastet und behalten darum
   ihre bisherigen 56px (Nutzer-Entscheid 2026-08-21). */
.meta--bereich {
  padding-top: 56px;
  padding-bottom: 52px;
}

.meta--bereich h1 {
  max-width: 24ch;
  margin-bottom: 44px;
}

.meta--bereich .row {
  margin-top: 26px;
}

/* Zaehlerband */
.facts {
  background: var(--c-bg);
  padding: 90px 0;
  text-align: center;
}

.facts h2 {
  font: 800 calc(var(--fs-h2) * 0.72) / 1 var(--f-disp);
  color: var(--c-white);
  margin-bottom: 64px;
}

.counter {
  margin-bottom: 56px;
}

.counter:last-child {
  margin-bottom: 0;
}

.counter .num {
  font: 500 var(--fs-counter) / 1 var(--f-mono);
  color: var(--c-white);
}

.counter .lbl {
  font: 300 22px/2.5 var(--f-mono);
  color: var(--c-white);
}

@media (max-width: 767px) {
  .counter .lbl {
    font-size: 15px;
  }
}

/* HELLOOW-Band */
.helloow {
  background: var(--c-accent);
  padding: 96px 24px;
  text-align: center;
}

.helloow .hi {
  font: 300 italic var(--fs-hello) / 1.1 var(--f-disp);
  color: var(--c-warm);
  letter-spacing: 2px;
  text-transform: uppercase;
}

.helloow .phone {
  font: 100 var(--fs-phone) / 1.3 var(--f-disp);
  color: var(--c-warm);
  margin: 18px 0 44px;
  text-decoration: none;
  display: block;
}

.helloow .phone:hover {
  color: var(--c-white);
}

.helloow--hero {
  padding: 150px 24px 140px;
}

/* Knopf-Feinmasse des Original-Startbands (gemessen 2026-08-19, Nutzer-Auftrag
   "Knopf-Gestaltung abgleichen"): Roboto Mono 300/16 px, Padding 16/32 px, voller
   weisser Rand. Beide Knoepfe gleich - kein Hell/Dunkel-Paar. Gilt nur im Band,
   damit der Brandband-Knopf seine Wireframe-Masse behaelt. */
.helloow .btn-ghost {
  font-size: 16px;
  padding: 16px 32px;
  border-color: var(--c-white);
}

/* Violettes Brand-Band der Fachbereichsseiten */
.brandband {
  background: var(--c-accent);
  padding: 90px 24px;
  text-align: center;
  overflow: hidden;
}

.brandband h2 {
  font: 800 var(--fs-display) / 1 var(--f-disp);
  color: var(--c-white);
  position: relative;
  z-index: 2;
  margin-bottom: -0.55em;
}

.brandband .ph,
.brandband .bildslot {
  aspect-ratio: 16 / 10;
  max-width: 880px;
  margin: 0 auto;
}

.brandband .copy {
  max-width: 760px;
  margin: 56px auto 40px;
  font: 300 1.15rem/1.7 var(--f-disp);
  color: var(--c-warm);
}

/* ------------------------------------------------------------------ 10. Raster */

/* AN5 (Nutzer-Entscheid 2026-08-21): EIN Projektraster fuer alle sieben Seiten, in der
   Darstellung der Startseite. Abgeloest sind damit die drei bisherigen Varianten -
   .grid/.tile (Titel unter der Kachel, 3:2, gemessen 357x282 bei Fugen 44/30 und 24 px
   Rand), .pgrid/.ptile (Overlay, 100:65, 452x294 bei Fugen 28/24 und 18 px Rand) und
   .startgrid-liste/.starttile (Overlay, 1,52, 328x216 bei Fuge 8 und 220 px Rand).
   Daneben steht nur noch das Portraetraster weiter unten - Personen sind keine Projekte.

   Verhaeltnis 1,52 und Fuge 8 px gibt die Startseite vor (AN4.1). Der AUSSENRAND bleibt
   kontextabhaengig und steht in --raster-rand; Vorgabe sind 24 px. */
.projektraster {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: var(--raster-luecke, 8px);
  list-style: none;
  margin: 0;
  padding: 0 var(--raster-rand, 24px);
}

@media (max-width: 1024px) {
  .projektraster {
    grid-template-columns: repeat(2, 1fr);
  }
}

@media (max-width: 767px) {
  .projektraster {
    grid-template-columns: 1fr;
  }
}

.projektkachel {
  position: relative;
  /* Raster statt Block: die untere Zeile nimmt Titel UND Scrim auf, damit der Scrim ohne
     feste Prozenthoehe genau so hoch wird wie der Titel (Auftrag PR, siehe unten). Das
     Bild liegt absolut ueber beiden Zeilen und ist deshalb kein Rasterelement. */
  display: grid;
  grid-template-rows: 1fr auto;
  grid-template-columns: 1fr;
  text-decoration: none;
  overflow: hidden;
  aspect-ratio: 1.52;
  transition: opacity 0.35s, transform 0.35s;
}

.projektkachel .ph,
.projektkachel .bildslot {
  position: absolute;
  inset: 0;
}

/* PROJEKTRASTER OHNE JAVASCRIPT (Auftrag PR, Nutzer-Entscheid 2026-08-23). Abgeloest sind
   das volltonige Violett-Overlay .ovl mit zentriertem Titel und der Zwei-Tipp-Zustand
   .is-getippt aus MOB2 samt tipp.js. Grund ist die Barrierefreiheits-Pruefung vom
   2026-08-23: der erste Tipp fing das click-Ereignis ab, damit war die Kachel per Tastatur
   nicht in einem Zug erreichbar (WCAG 2.1.1) und VoiceOver/TalkBack meldeten einen Link
   ohne Namen (WCAG 2.4.4, 4.1.2), weil sie beim Doppeltipp genau EIN click senden. Ein
   Ersatz ueber pointerdown/pointerup wurde geprueft und verworfen (WCAG 2.5.2).

   An seine Stelle tritt ein schwarzer Scrim am unteren Kachelrand, unter dem Titel. Der
   Titel steht als Textknoten IM Link und wird nie mit display:none oder visibility:hidden
   entfernt, nur in der Deckkraft gesteuert - er ist der zugaengliche Name des Links.

   DER SCRIM LIEGT AUF DEM TITELFELD, NICHT AUF FESTEN 45 PROZENT DER KACHEL - gemessene
   Abweichung von der Vorgabe des Auftrags, Begruendung in DESIGN_OOW-ONLINE Abschnitt 6.
   Kurz: die Projektnamen sind bis 42 Zeichen lang und brechen je nach Kachelbreite auf ein
   bis vier Zeilen um; der Textblock schwankt damit zwischen 25 und 109 px. Ein Scrim mit
   fester Prozenthoehe deckt entweder zu wenig (gemessen 2,19:1 auf der Startseite bei
   1024 px, Kachel 288x189, vierzeiliger Titel) oder er verschleiert die halbe Aufnahme.
   Kachel und Titel stehen deshalb in einem Raster: der Titel bildet die untere Zeile, der
   Scrim liegt in derselben Zeile und ist damit immer genau so hoch wie der Titel, plus
   64 px Auslauf nach oben, in dem der Verlauf auf durchsichtig faellt. Der Text steht so
   auf jeder Kachelgroesse im dichten Teil des Verlaufs. */
.projektkachel::after {
  content: "";
  grid-row: 2;
  grid-column: 1;
  position: relative;
  z-index: 1;
  /* Auslauf nach oben - der Verlauf braucht Weg, um durchsichtig zu werden. */
  margin-top: -64px;
  pointer-events: none;
  background: linear-gradient(
    to top,
    rgba(0, 0, 0, 0.72) 0%,
    rgba(0, 0, 0, 0.6) calc(100% - 64px),
    rgba(0, 0, 0, 0) 100%
  );
}

/* Typo-Stufe der BILDUNTERSCHRIFT (.bildtext, Abschnitt 3): Roboto Mono 300, 15 px,
   ls 2.5 px - hier weiss statt violett, weil der Titel auf dem Scrim steht. Der Auftrag PR
   verweist fuer Groesse und Schnitt auf das Designsystem und laesst bei fehlender
   Festlegung die Bildunterschrift-Stufe gelten; eine Festlegung fuer DIESE Komponente gibt
   es nicht: die Zeile "Kachel-Hover-Titel" (AGG 800, min(50px, 9cqw)) beschreibt den
   zentrierten Titel IM Violett-Overlay, und genau das Overlay entfaellt hier. Gemessen: bei
   41,6 px laufen lange Projektnamen auf drei bis vier Zeilen und stehen 182 statt 42 px
   hoch - der Titel fuellt dann die halbe Kachel. text-align steht ausdruecklich auf left,
   damit er nicht je nach umgebender Sektion einmal links und einmal mittig steht. */
.projektkachel__titel {
  grid-row: 2;
  grid-column: 1;
  position: relative;
  z-index: 2;
  padding: 16px;
  font: 300 15px/1.7 var(--f-mono);
  letter-spacing: 2.5px;
  color: var(--c-white);
  text-align: left;
}

/* GRUNDZUSTAND IST SICHTBAR - auch mobil, auch ohne Media Query. Das Einblenden auf Hover
   ist ausschliesslich eine Erweiterung fuer echte Zeigergeraete. Auf Hybridgeraeten faellt
   das Fehlverhalten damit bewusst in Richtung "Titel sichtbar" statt "Titel versteckt".
   Der Reveal haengt an :hover UND :focus-visible - die Tastatur sieht dasselbe wie die
   Maus; den sichtbaren Fokusrahmen setzt die a:focus-visible-Regel in Abschnitt 2. */
@media (hover: hover) and (pointer: fine) {
  .projektkachel::after,
  .projektkachel__titel {
    opacity: 0;
    transition: opacity 200ms ease;
  }

  .projektkachel:hover::after,
  .projektkachel:hover .projektkachel__titel,
  .projektkachel:focus-visible::after,
  .projektkachel:focus-visible .projektkachel__titel {
    opacity: 1;
  }
}

@media (prefers-reduced-motion: reduce) {
  .projektkachel::after,
  .projektkachel__titel {
    transition: none;
  }
}

/* Filterbetrieb auf /projekte/: die weggefilterte Kachel raeumt ihren Rasterplatz mit.
   Ohne das bleibt das <li> als leere Zelle stehen, das Raster behaelt Loecher, und es
   gibt keine neuen Plaetze, auf die etwas aufrutschen koennte. */
.projektkachel.is-hidden {
  display: none;
}

.projektraster > li:has(> .projektkachel.is-hidden) {
  display: none;
}

.projektkachel.is-fading {
  opacity: 0;
  transform: scale(0.96);
}

/* AN5.4 Aussenrand je Kontext (Nutzer-Entscheid 2026-08-21): die Darstellung ist ueberall
   gleich, der Rand nicht. Die 220 px der Startseite wandern NICHT mit - dort ist das
   Raster ein Anriss mit neun Kacheln in einer langen Seite, auf /projekte/ IST das Raster
   die Seite und traegt 30 Kacheln; bei 220 px faellt die Kachel dort von 452 auf 328 px
   und die Uebersicht wird deutlich kleinteiliger und laenger. Die Startseite setzt ihren
   Rand an der Sektion .startgrid (Abschnitt 11). */

/* Uebersicht: das Raster IST die Seite, steht in keiner Sektion und traegt den unteren
   Seitenabstand selbst. */
.projektraster--seite {
  --raster-rand: 18px;
  padding-bottom: 90px;
}

@media (max-width: 767px) {
  .projektraster--seite {
    padding-bottom: 56px;
  }
}

/* Fachbereichsseiten zeigen denselben Ausschnitt wie die Uebersicht und liegen mit ihr
   auf einem Rand. */
body[data-layout="fachbereich"] .projektraster {
  --raster-rand: 18px;
}

/* Filterwechsel auf /projekte/ (Nutzer-Entscheid 2026-08-16): wegfallende Kacheln blenden
   aus, bleibende gleiten sichtbar auf ihre neuen Rasterplaetze, neue blenden ein. Die
   Namen der Kacheln stehen im Markup (teile/raster.njk), gestartet wird der Wechsel in
   filter.js. Bei prefers-reduced-motion startet filter.js erst gar keine Transition -
   deshalb steht diese Ausnahme dort und nicht hier ein zweites Mal. */

/* Ohne diese Zeile bekommt die ganze Seite einen Root-Snapshot und wird beim Filtern mit
   ueberblendet: die alte, hoehere Seite liegt als Standbild ueber der neuen, der Fuss
   erscheint doppelt. Die Kacheln tragen eigene Namen und bleiben davon unberuehrt.
   Cross-Document-Uebergaenge gibt es auf der Seite nicht. */
:root {
  view-transition-name: none;
}

::view-transition-group(*) {
  animation-duration: 0.4s;
  animation-timing-function: ease;
}

/* :only-child trifft genau die Kacheln, die nur auf einer Seite des Wechsels vorkommen -
   also wegfallende und neu hinzukommende. Bleibende Kacheln haben old UND new und behalten
   den Standarduebergang; sie sollen nur gleiten, nicht blinken. */
::view-transition-old(*):only-child {
  animation: pt-weg 0.25s ease both;
}

::view-transition-new(*):only-child {
  animation: pt-hin 0.25s ease 0.15s both;
}

@keyframes pt-weg {
  to {
    opacity: 0;
    transform: scale(0.96);
  }
}

@keyframes pt-hin {
  from {
    opacity: 0;
    transform: scale(0.96);
  }
}

/* Portraetraster */
.teamgrid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 52px 30px;
  max-width: 1180px;
  margin: 0 auto;
  padding: 0 24px;
  list-style: none;
}

@media (max-width: 1024px) {
  .teamgrid {
    grid-template-columns: repeat(2, 1fr);
  }
}

@media (max-width: 767px) {
  .teamgrid {
    grid-template-columns: 1fr;
  }
}

.mtile {
  text-decoration: none;
  display: block;
}

.mtile .ph,
.mtile .bildslot {
  aspect-ratio: 3 / 4;
}

.mtile figcaption {
  margin-top: 16px;
  /* Wireframe sagt 600; per Entscheid F2 auf den echten 500er-Schnitt uebersetzt. */
  font: 500 1.35rem/1.4 var(--f-mono);
  color: var(--c-white);
  transition: color 0.2s;
}

.mtile:hover figcaption {
  color: var(--c-sec);
}

/* Bandtitel ueber den Rastern */
.bandtitel {
  font: 800 calc(var(--fs-h2) * 0.72) / 1.15 var(--f-disp);
  color: var(--c-white);
  text-align: center;
  margin-bottom: 56px;
}

.band-dunkel {
  background: var(--c-bg);
  padding: 90px 0;
}

.band-violett {
  background: var(--c-accent);
  padding: 90px 0;
}

/* AN5 (Nutzer-Entscheid 2026-08-21): Das violette Band traegt jetzt dasselbe
   Projektraster wie alle anderen Seiten. Seine eigenen Rastermasse - vollbreit mit
   20 px Rand, Fugen 35/30, Kachelbild 3:2 und zweizeilige Titelzone unter der Kachel -
   sind damit abgeloest; geblieben ist der violette Grund. */

/* Vollbreiter Bilder-Streifen der Gruenderseite (GS1/B3): eigene Sektion wie im
   Original (col-100), Slidehoehe 848 px; die kleinen Strecken in den Spalten bleiben
   bei ihren 400 px. */
.streifen {
  margin: 0 0 90px;
  /* Die nativen Scroll-Pfeile stehen 8 px ausserhalb ihres Rahmens (Abschnitt 8). Im
     vollbreiten Streifen waere das ein Dokument-Ueberlauf - gemessen 1448 statt 1440. */
  overflow-x: clip;
}

@supports selector(::scroll-button(right)) {
  .streifen .car-scroll::scroll-button(left) {
    left: 8px;
  }
  .streifen .car-scroll::scroll-button(right) {
    right: 8px;
  }
}

.streifen .carousel {
  max-width: none;
  padding: 0;
  margin-bottom: 0;
}

.streifen .car-slide {
  aspect-ratio: auto;
  height: 848px;
}

.streifen .car-slide img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

@media (max-width: 1024px) {
  .streifen .car-slide {
    height: 60vh;
    min-height: 380px;
  }
}

.interview .carousel {
  max-width: none;
  padding: 0;
  margin-bottom: 14px;
}

.interview .car-slide {
  aspect-ratio: auto;
  height: 400px;
}

.interview .car-slide img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

/* ------------------------------------------------------------------ 11. Vorlagen */

/* --- start --- */
/* AN2.3 Hero verdichtet (Nutzer-Entscheid 2026-08-21): Innenmasse am Bildschirm
   festgelegt, damit der CTA ueber den Falz kommt. Erwartete CTA-Unterkante 1074 px,
   in jedem Viewport gleich, 300 px hoeher als zuvor. min-height und margin-bottom
   unten bleiben unveraendert - die Ueberlappung mit dem ersten Anriss ist gewollt. */
.hero {
  padding-top: 28px;
}

/* AN1 Punkt 6 (Nutzer-Auftrag 2026-08-20): der Hero traegt die Original-Hoehe von
   1779 px (1440x950 wie 3840x2160). Wie im Original ueberlappt der erste Anriss seine
   unteren 447 px - deshalb der negative Aussenabstand statt einer flacheren Sektion.
   Ohne ihn stuende dort dieselbe Luecke, die im Original der Anriss fuellt. */
@media (min-width: 1140px) {
  .hero {
    min-height: 1779px;
    margin-bottom: -447px;
  }
}

.hero .display {
  max-width: 14ch;
  margin: 0 auto 36px;
}

.hero .body-copy {
  max-width: 760px;
  margin: 28px auto 30px;
}

/* --- 11a. Anriss-Bausteine der Startseite (AN1, Nutzer-Auftrag 2026-08-20) ---
 *
 * VIER eigene Sektionen, je Anriss eine - so fuehrt es auch das Original. Alle Masse
 * sind am 2026-08-20 an https://oow.berlin/ bei 1440x950 erhoben, mit abgeschalteten
 * Transforms und VOLLSTAENDIG geladenen Bildern. Ohne das Vorladen misst man dort die
 * eingeklappten Platzhalter der lazy geladenen Bilder mit - genau daher stammen die
 * kuerzeren Vergleichszahlen frueherer Laeufe (Sektion 4: 566 statt 1404 px).
 *
 * Sektionshoehen 1474 / 1173 / 1480 / 1404 px, Abstaende dazwischen 500 / 399 / 401 px.
 * Die Hoehen halten bei 3840x2160 dieselben Werte, weil die Komposition auf dem
 * zentrierten 1140er Raster sitzt und nicht mitwaechst - so auch im Original.
 *
 * Aufbau je Sektion: eine nullhohe Bildbuehne mit zwei absolut gesetzten Bildern
 * (--x Versatz zur linken Rasterkante, --y Versatz zur Sektionsoberkante, --b Breite,
 * --ar Soll-Format) und darueber die Textspalte. Die Zweitbilder ragen bewusst aus
 * ihrer Sektion heraus - senkrecht wird NICHT geclippt, seitlich sichert
 * overflow-x: clip auf main (Abschnitt 17).
 *
 * Unter 1140 px traegt das feste Raster nicht mehr; dann laufen beide Bilder im Fluss
 * im 4:3-Format der Formatliste (DESIGN_OOW-ONLINE Abschnitt 5). */

/* Die Zweitbilder ragen seitlich aus dem Raster. Waagerecht wird geclippt, senkrecht
   bewusst NICHT (DESIGN_OOW-ONLINE Abschnitt 8, Tabelle E3). Die Regel steht hier und
   nicht im @supports-Block der Scroll-Effekte: der Ueberstand ist Layout, kein Effekt -
   ohne sie schoebe das Overlay des zweiten Anrisses die Seite bei knapp 1140 px
   Fensterbreite auch dort waagerecht auf, wo es keine Scroll-Effekte gibt (Firefox,
   prefers-reduced-motion). */
body[data-layout="start"] main {
  overflow-x: clip;
}

.anriss {
  position: relative;
  /* Die Sektionsmasse stehen unten je Anriss; der 90er Standardabstand aus
     Abschnitt 8 wuerde sie um 180 px verfehlen. */
  padding: 0;
}

.anriss-buehne {
  max-width: var(--container);
  margin: 0 auto;
  padding: 0 24px;
}

.anriss-bild {
  margin: 0 0 40px;
  aspect-ratio: 4 / 3;
}

.anriss-bild a,
.anriss-bild img {
  display: block;
  width: 100%;
  height: 100%;
}

/* Bildschnitt-Standard (Nutzer-Entscheid 2026-08-18): Soll-Format per aspect-ratio,
   Ausschnitt per cover aus der Bildmitte. */
.anriss-bild img {
  object-fit: cover;
}

/* Flex-Spalte, damit die Reihenfolge Schlagzeile / Projektname ueber order steht und
   die Auszeichnung nicht gedoppelt werden muss (AN2.1, 2026-08-21). */
.anriss-text {
  position: relative;
  padding-bottom: 56px;
  display: flex;
  flex-direction: column;
  align-items: stretch;
}

/* Fliesstexte stehen links (DESIGN_OOW-ONLINE Abschnitt 1); der zweite Anriss steht
   rechtsbuendig - so das Original.
   REIHENFOLGE AN2.1 (Nutzer-Entscheid 2026-08-21): die Schlagzeile steht OBEN, darunter
   der Projektname, dieser direkt auf dem Fliesstext. Abstaende 40 px (am Ende der Fahrt,
   reserviert in der Bahn) und 10 px. Das ERSETZT den Entscheid 2026-08-16 samt Vermerk
   2026-08-18, nach dem der Projektname UEBER der Schlagzeile stand. Die Lesereihenfolge
   im Markup ist bereits die der Darstellung; order sichert sie nur ab.
   ACHTUNG margin: in der Flex-Spalte fallen Standardraender NICHT zusammen - Abstaende
   stehen deshalb ausschliesslich unten. */
.anriss .kicker {
  order: 2;
  color: var(--c-sec);
  margin: 0 0 10px;
}

/* Zwei Klassen, damit die Regel das spaeter stehende .statement (22ch, zentriert)
   schlaegt - die Anriss-Schlagzeile steht linksbuendig auf voller Spaltenbreite.
   Ohne eigenen Rand: den Abstand nach unten traegt die Bahn (AN2.2). */
.anriss .anriss-titel {
  font: 800 var(--fs-h2) / 1 var(--f-disp);
  color: var(--c-white);
  max-width: 1008px;
  margin: 0;
}

/* AN2.2 Fahrbahn der Schlagzeile (Nutzer-Entscheid 2026-08-21). Der Reiseweg der
   Slogan-Fahrt steht als padding-bottom im LAYOUT: Projektname und Fliesstext ruecken
   um genau diesen Weg nach unten, die Schlagzeile kann sie also nicht mehr ueberfahren,
   und nach oben ist bei translate 0 Schluss. Die Bahn steht bewusst AUSSERHALB des
   @supports-Blocks der Scroll-Effekte (Abschnitt 17) - sie ist Layout, kein Effekt.
   Ohne animation-timeline (Firefox) steht die Schlagzeile oben in ihrer Bahn, der
   Abstand zum Projektnamen ist dann 40 px plus Reiseweg. Das ist gewollt. */
.slogan-bahn {
  order: 1;
  position: relative;
  padding-bottom: calc(40px + var(--reise));
  max-width: 1008px;
}

.anriss--1 .slogan-bahn {
  max-width: 765px;
}

/* Reisewege je Anriss: der einsinnige Gesamtweg ist das Doppelte des frueheren halben
   E2-Laufs (155/152/116/108 px) - die Amplitude des Originals bleibt damit erhalten.
   Sie gelten in allen Breiten, deshalb ausserhalb der 1140er Medienabfrage. */
.anriss--1 {
  --reise: 310px;
}

.anriss--2 {
  --reise: 304px;
}

.anriss--3 {
  --reise: 232px;
}

.anriss--4 {
  --reise: 216px;
}

.anriss .lead-copy {
  order: 3;
  color: var(--c-sec);
  max-width: 810px;
  margin-bottom: 20px;
}

.anriss-knopf {
  order: 4;
  margin: 0;
}

.anriss--2 .anriss-text {
  text-align: end;
}

.anriss--2 .slogan-bahn,
.anriss--2 .anriss-titel,
.anriss--2 .lead-copy {
  margin-left: auto;
  margin-right: 0;
}

/* AN2.4 TIEFENANORDNUNG (Nutzer-Entscheid 2026-08-21): Text und Knoepfe stehen VOR den
   Bildern. Die Bildbuehne ist ab 1140 px absolut positioniert und wurde damit ueber den
   statischen Hero-Inhalt gemalt - gemessen am 2026-08-21 lag das Zweitbild des ersten
   Anrisses 56 px ueber dem Hero-CTA, der Klick fiel auf /260-grad/. Die Bilder bleiben
   sichtbar: der Hero traegt keinen eigenen Hintergrund. */
body[data-layout="start"] .hero .container {
  position: relative;
  z-index: 3;
}

body[data-layout="start"] .anriss-text {
  z-index: 2;
}

body[data-layout="start"] .anriss-buehne {
  z-index: 0;
}

@media (min-width: 1140px) {
  .anriss-buehne {
    position: absolute;
    inset-inline: 0;
    top: 0;
    height: 0;
    max-width: none;
    margin: 0;
    padding: 0;
  }

  .anriss-bild {
    position: absolute;
    top: var(--y);
    left: calc(50% - var(--container) / 2 + var(--x));
    width: var(--b);
    aspect-ratio: var(--ar);
    margin: 0;
  }

  /* Textspalte 42 px innerhalb des Containers - im Original bei 1440 px genau x = 216,
     Fliesstextbreite 810, Titelbreite 1008 (erster Anriss 765). */
  .anriss-text {
    padding: var(--textoben) 24px 20px 66px;
  }

  .anriss--2 .anriss-text {
    padding-left: 24px;
    padding-right: 66px;
  }

  .anriss--1 {
    --textoben: 749px;
    min-height: 1474px;
  }

  .anriss--2 {
    --textoben: 598px;
    min-height: 1173px;
    margin-top: 500px;
  }

  .anriss--3 {
    --textoben: 900px;
    min-height: 1480px;
    margin-top: 399px;
  }

  .anriss--4 {
    --textoben: 911px;
    min-height: 1404px;
    margin-top: 401px;
  }

  .anriss--1 .anriss-titel {
    max-width: 765px;
  }

  /* Der E1-Zoom laeuft um die MITTE DES 1140er RASTERS, nicht um die Bildmitte - am
     Original gemessen (AN1a, 2026-08-20): der Skalierungsmittelpunkt liegt bei allen
     vier Hauptbildern bei x = 712 bis 721, also auf der Spaltenmitte. Ohne diese Zeile
     saesse das erste Bild im Zoom 35 px, das vierte 178 px daneben. */
  .anriss-bild--haupt {
    transform-origin: calc(var(--container) / 2 - var(--x)) 50%;
  }

  .anriss--1 .anriss-bild--haupt {
    --x: 193px;
    --y: 182px;
    --b: 931px;
    --ar: 931 / 583;
  }

  .anriss--1 .anriss-bild--zweit {
    --x: -382px;
    --y: 300px;
    --b: 477px;
    --ar: 477 / 636;
  }

  .anriss--2 .anriss-bild--haupt {
    --x: 64px;
    --y: 62px;
    --b: 934px;
    --ar: 934 / 553;
  }

  .anriss--2 .anriss-bild--zweit {
    --x: 487px;
    --y: 312px;
    --b: 791px;
    --ar: 791 / 512;
  }

  .anriss--3 .anriss-bild--haupt {
    --x: 2px;
    --y: 62px;
    --b: 1138px;
    --ar: 1138 / 854;
  }

  .anriss--3 .anriss-bild--zweit {
    --x: -185px;
    --y: 120px;
    --b: 569px;
    --ar: 569 / 759;
  }

  .anriss--4 .anriss-bild--haupt {
    --x: 402px;
    --y: 62px;
    --b: 676px;
    --ar: 676 / 865;
  }

  .anriss--4 .anriss-bild--zweit {
    --x: -185px;
    --y: 121px;
    --b: 800px;
    --ar: 800 / 534;
  }
}

/* MOB1 (Nutzer-Entscheid 2026-08-21): Bis 767 px zeigt jeder Anriss nur noch EIN Bild -
   das verlinkte Hauptbild. Das Zweitbild verschwindet.
   Die Grenze ist gemessen, nicht gegriffen (2026-08-21, ausgelieferte Startseite bei
   390 / 767 / 900 / 1139 px): bis 767 px steht auf beiden Anriss-Bildern
   animation-name: none, ab 768 px laufen start-lauf auf beiden und start-zoom bzw.
   start-zoom-gross auf dem Hauptbild (Abschnitt 17). Genau dort, wo die Scroll-Effekte
   abgeschaltet sind, bleibt kuenftig nur ein Bild; zwischen 768 und 1139 px laufen die
   Effekte und beide Bilder bleiben stehen.
   Das Markup bleibt unangetastet - die feste 1140er Komposition und die Scroll-Effekte
   bleiben unberuehrt. display: none nimmt das Zweitbild samt seinem Rand (margin 0 0 40px)
   aus dem Fluss; es bleibt kein Leerraum stehen. */
@media (max-width: 767px) {
  .anriss-bild--zweit {
    display: none;
  }
}

/* --- start: Ausbau ST1-ST6 (Nutzer-Entscheid 2026-08-18) ---
 *
 * Referenz dieser Bausteine ist die ORIGINAL-Startseite (Wireframe-Luecke, DESIGN_OOW-
 * ONLINE Abschnitt 9); alle Masse sind dort gemessen: Collage margin-top 220, Padding 300,
 * 82-px-Keil; Innenband #FCFCFC, Spalten 50/50 bis 767 px; Grid randlos mit 20 px
 * Aussenrand, Kacheln 3:2, Luecken 35/30, Titel AGG 600. */

/* Nur fuer Vorleser und Bots - ersetzt keinen sichtbaren Inhalt. */
.visuell-versteckt {
  position: absolute;
  left: -9999px;
}

/* ST1 Projekt-Collage, seit H1 v2 (Nutzer-Entscheid 2026-08-19) aus ZEHN kuratierten
   Hero-Bildern auf festem Slot-Raster statt des einen Original-JPGs. Die Buehne ist
   FIXIERT, der Inhalt scrollt darueber; das clip-path der Sektion begrenzt die Buehne
   aufs eigene Feld (iOS-sicheres Muster, KEIN background-attachment: fixed) und
   schneidet zugleich die Schraegkante des Originals (82-px-Keil zur Mitte).
   Sektionshoehe bewusst flacher als das Original: 75svh, mindestens 640 px. */
.collage {
  position: relative;
  margin-top: 220px;
  height: 75vh; /* Rueckfall ohne svh */
  height: 75svh;
  min-height: 640px;
  display: grid;
  place-content: center;
  padding: 0 24px;
  text-align: center;
  clip-path: polygon(0 5px, 50% 82px, 100% 5px, 100% 100%, 0 100%);
}

.collage-buehne {
  position: fixed;
  inset: 0;
  z-index: -1;
  background: var(--c-bg);
}

/* Die zehn Slots: fixe Geometrie (Position, Groesse, Ueberlappung, z-Reihenfolge),
   der Original-Komposition nachempfunden. Jeder Slot schneidet sein Bild nach dem
   Bildschnitt-Standard; keine Transforms im Ruhezustand. */
.c-slot {
  position: absolute;
  overflow: clip;
}

.c-slot img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.c-slot-1 { left: 12%; top: 6%; width: 44%; aspect-ratio: 21 / 9; z-index: 2; }
.c-slot-2 { left: 52%; top: 4%; width: 34%; aspect-ratio: 4 / 3; z-index: 1; }
.c-slot-3 { left: 0; top: 26%; width: 24%; aspect-ratio: 3 / 4; z-index: 3; }
.c-slot-4 { left: 27%; top: 30%; width: 26%; aspect-ratio: 4 / 3; z-index: 4; }
.c-slot-5 { left: 57%; top: 34%; width: 16%; aspect-ratio: 3 / 4; z-index: 5; }
.c-slot-6 { left: 76%; top: 28%; width: 24%; aspect-ratio: 3 / 2; z-index: 2; }
.c-slot-7 { left: 6%; top: 60%; width: 26%; aspect-ratio: 3 / 2; z-index: 3; }
.c-slot-8 { left: 34%; top: 56%; width: 30%; aspect-ratio: 4 / 3; z-index: 2; }
.c-slot-9 { left: 60%; top: 62%; width: 40%; aspect-ratio: 21 / 9; z-index: 1; }
.c-slot-10 { left: 44%; top: 74%; width: 22%; aspect-ratio: 3 / 2; z-index: 6; }

/* Bewegungsempfindlich: die Buehne scrollt normal mit. */
@media (prefers-reduced-motion: reduce) {
  .collage-buehne {
    position: absolute;
  }
}

/* Mobil: gleiche zehn Slots, aber verdichtete Geometrie - mit den Desktop-Prozenten
   schrumpfen die Bilder staerker als die Flaeche und die Ueberlappung ginge verloren
   (gegengeprueft bei 390, Entscheid: 75svh bleibt, die Slots ruecken zusammen). */
@media (max-width: 767px) {
  .collage {
    margin-top: 90px;
  }
  .c-slot-1 { left: 8%; top: 4%; width: 70%; }
  .c-slot-2 { left: 55%; top: 12%; width: 45%; }
  .c-slot-3 { left: 0; top: 22%; width: 40%; }
  .c-slot-4 { left: 34%; top: 30%; width: 44%; }
  .c-slot-5 { left: 70%; top: 34%; width: 28%; }
  .c-slot-6 { left: 60%; top: 52%; width: 40%; }
  .c-slot-7 { left: 4%; top: 52%; width: 42%; }
  .c-slot-8 { left: 30%; top: 64%; width: 48%; }
  .c-slot-9 { left: 58%; top: 74%; width: 42%; }
  .c-slot-10 { left: 8%; top: 78%; width: 36%; }
}

/* ST2/ST3: der helle Block der Startseite (Innenband und Personen-Teaser). Eigene
   Text- und Linkfarben, weil die Seite selbst dunkel ist. Umbruch bei 767 px wie das
   Original (nicht bei 1024 wie split50). */
.innenband,
.personensplit {
  background: #fcfcfc;
  color: var(--c-ink);
  padding: 0;
}

/* AN3.1 KOMPRIMIERT (Nutzer-Entscheid 2026-08-21, Werte am Bildschirm festgelegt).
   Die frueheren Masse folgten dem Original (H2/H3, UHD1 2026-08-19: Band 85vh mit
   80 px Fuss, Diaschau 1000 px, Personenbilder 668/586 px, Splitabstand 10 %). Sie
   sind ABGELOEST: das Weiss stand nicht zwischen den Sektionen, sondern in ihnen -
   als Luft unter dem Bandtext, als Fuss am Band und als Vorlauf vor dem zweiten
   Personen-Block. Das Original ist fuer diese Masse kein Massstab mehr. */
.innenband {
  padding-bottom: 0;
  min-height: 48vh;
  min-height: 48svh;
}

.innen-zeile {
  display: grid;
  grid-template-columns: 1fr 1fr;
  align-items: stretch;
}

@media (max-width: 767px) {
  .innen-zeile {
    grid-template-columns: 1fr;
  }
}

.innen-text {
  padding: 40px 8% 8px;
}

.innenband .subline {
  display: block;
  color: var(--c-ink);
  margin-bottom: 22px;
}

.innenband h2 {
  font: 800 var(--fs-h1) / 1 var(--f-disp);
  color: var(--c-ink);
  margin-bottom: 26px;
}

.innenband .lead-copy {
  color: var(--c-ink);
}

/* Slideshow: gestapelte Bilder, reine CSS-Crossfade-Rotation. Der Takt ist am Original
   gemessen: 8 Bilder, 5 s je Bild, 0,5 s Blende - Zyklus 40 s, Sichtfenster 12,5 %.
   Aendert sich die Bildzahl im Frontmatter, muss der Takt hier nachziehen. */
.diaschau {
  position: relative;
  overflow: clip;
  /* Feste Hoehe, das Band folgt dieser Spalte. 560 px seit AN3.1 (2026-08-21),
     vorher 1000 px nach Original-Mass. */
  height: 560px;
}

.diaschau img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  opacity: 0;
  animation: diaschau-takt 40s linear infinite;
  animation-delay: calc(var(--n, 0) * 5s);
}

/* Ohne Animation (alte Browser) bleibt das erste Bild stehen. */
.diaschau img:first-child {
  opacity: 1;
}

@keyframes diaschau-takt {
  0% {
    opacity: 0;
  }
  1.25% {
    opacity: 1;
  }
  12.5% {
    opacity: 1;
  }
  13.75% {
    opacity: 0;
  }
  100% {
    opacity: 0;
  }
}

/* Bewegungsempfindlich: erstes Bild statisch, keine Rotation. Die opacity-Regeln sind
   noetig, weil die globale reduced-motion-Regel nur die Animation stoppt. */
@media (prefers-reduced-motion: reduce) {
  .diaschau img {
    animation: none;
    opacity: 0;
  }
  .diaschau img:first-child {
    opacity: 1;
  }
}

/* ST3 Personen-Teaser: Bild | Panel, alternierend gedreht. Name violett auf der
   H3-Stufe, Zitat im Fliesstextmass, Knopf als heller Rahmen-Pill (alles am Original
   gemessen). */
/* Abstand zwischen den Personen-Teasern: prozentual zur Breite, damit er bei UHD
   mitwaechst (ein fester Pixelwert lag dort 242 px zu niedrig, Sweep 2026-08-20).
   3 % seit AN3.1 (2026-08-21), vorher 10 % nach Original-Mass. */
.personensplit + .personensplit {
  padding-top: 3%;
}

.innen-zeile--gedreht > .personenbild {
  order: 2;
}

@media (max-width: 767px) {
  .innen-zeile--gedreht > .personenbild {
    order: 0;
  }
}

/* Feste Hoehen statt Ratios, je Breakpoint. Der Standardsatz ist seit AN3.1
   (2026-08-21) ein Nutzer-Entscheid und kein Original-Mass mehr: 550 / 470 px statt
   668 / 586 px. Der Widescreen-Satz ab 2400 px (545 / 504 px) bleibt unveraendert. */
.personenbild {
  height: 550px;
}

.personensplit + .personensplit .personenbild {
  height: 470px;
}

@media (min-width: 2400px) {
  .personenbild {
    height: 545px;
  }
  .personensplit + .personensplit .personenbild {
    height: 504px;
  }
}

@media (max-width: 767px) {
  .personenbild {
    height: auto;
    min-height: 420px;
  }
  .personensplit + .personensplit .personenbild {
    height: auto;
  }
}

.personenbild > img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.personentext {
  display: flex;
  flex-direction: column;
  justify-content: center;
  align-items: flex-start;
  padding: 50px 8%;
}

.personenname {
  font: 800 var(--fs-h3) / 1 var(--f-disp);
  color: var(--c-accent);
  margin-bottom: 26px;
}

/* AN3.2 (Nutzer-Entscheid 2026-08-21): die Namenszeile des Gruender-Blocks nennt ZWEI
   Personen und laeuft auf der H3-Stufe (3,5 rem) zweizeilig ueber die Nachbarbloecke
   hinaus. Kleinere Stufe, groessere Zeilenhoehe fuer den zweizeiligen Satz. Der Umbruch
   bleibt dem Browser ueberlassen - kein <br> im Text. */
.personensplit--gruender .personenname {
  font-size: 2.7rem;
  line-height: 1.15;
}

.personenzitat {
  font: 300 var(--fs-body) / 1.6 var(--f-disp);
  margin-bottom: 34px;
}

.btn-rahmen {
  display: inline-block;
  font: 300 14px/1 var(--f-mono);
  letter-spacing: 3.5px;
  text-transform: uppercase;
  color: var(--c-ink);
  background: var(--c-white);
  border: 2px solid #1e242d;
  border-radius: 50px;
  padding: 12px 22px;
  text-decoration: none;
  transition: background 0.25s, color 0.25s;
}

.btn-rahmen:hover {
  background: var(--c-ink);
  color: var(--c-white);
}

/* ST6 Projektgrid der Startseite. AN4.1 (Nutzer-Entscheid 2026-08-21, Werte am
   Bildschirm festgelegt): 220 px Aussenrand, Kacheln im Format 1,52 mit 8 px Fuge, der
   Titel als violettes Hover-Overlay IN der Kachel. ABGELOEST sind damit die am Original
   gemessenen Werte 20 px Rand, Fugen 35/30, Kachel 3:2 und der dauerhaft sichtbare Titel
   unter der Kachel (ST6, 2026-08-18).
   Kachel und Liste selbst stehen seit AN5 in Abschnitt 10 (.projektraster,
   .projektkachel) und gelten dort fuer alle Seiten - hier bleibt nur, was die Startseite
   von den uebrigen unterscheidet: der Aussenrand.
   Die untere Sektionspolsterung steht bewusst auf 0: den Abstand zum Fuss traegt dessen
   padding-top von 80 px. */
.startgrid {
  padding: 90px 220px 0;
  /* Den Rand traegt hier die Sektion, nicht das Raster - sonst kaeme er zweimal. */
  --raster-rand: 0;
}

.startgrid .bandtitel {
  font: 800 var(--fs-quote-h1) / 1 var(--f-disp);
  text-align: center;
  margin: 0 0 72px;
}

@media (max-width: 767px) {
  .startgrid {
    padding: 56px 15px 0;
  }
}

/* AN4.2 (Nutzer-Entscheid 2026-08-21): der CTA unter dem Raster misst 489x71 px statt
   331x51 und steht 92 px unter der letzten Kachelreihe statt 26. Gilt nur im Startgrid;
   der Standard-CTA aus Abschnitt 4 bleibt unveraendert. */
.startgrid .cta-row {
  text-align: center;
  padding: 92px 0 0;
  margin: 0;
}

.startgrid .btn-violet {
  font-size: 21px;
  padding: 25px 55px;
}

/* --- projekte --- */
.page-head {
  padding: 70px 0 34px;
  text-align: center;
}

.page-head h1 {
  font: 800 var(--fs-h3) / 1 var(--f-disp);
  color: var(--c-white);
}

.pfilters {
  list-style: none;
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  margin: 26px 0 34px;
}

.pfilters li {
  padding: 8px;
}

.pfilters button {
  background: none;
  border: 0;
  cursor: pointer;
  padding: 0;
  font: 300 var(--fs-filter) / 1.3 var(--f-disp);
  color: var(--c-accent);
  transition: color 0.2s;
}

.pfilters button:hover {
  color: #8b6bff;
}

.pfilters button[aria-pressed="true"] {
  color: var(--c-white);
}

/* --- ueber-uns --- */
.split50 {
  display: grid;
  grid-template-columns: 1fr 1fr;
  min-height: 78vh;
}

@media (max-width: 1024px) {
  .split50 {
    grid-template-columns: 1fr;
    min-height: 0;
  }
}

.hero-founders {
  background: var(--c-black);
  padding: 0;
}

.founder-photo,
.member-photo {
  position: relative;
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  align-items: center;
  text-align: center;
  padding: 0 24px 44px;
  min-height: 520px;
}

.member-photo {
  min-height: 480px;
  padding-bottom: 40px;
}

.founder-photo .ph,
.founder-photo .bildslot,
.member-photo .ph,
.member-photo .bildslot {
  position: absolute;
  inset: 0;
}

.founder-photo > *,
.member-photo > * {
  position: relative;
}

.overlay-quote {
  font: 800 var(--fs-quote) / 1.2 var(--f-disp);
  color: var(--c-white);
  max-width: 16ch;
  margin-bottom: 24px;
}

.mono-name {
  font: 500 15px/1.7 var(--f-mono);
  letter-spacing: 5.5px;
  text-transform: uppercase;
  color: var(--c-white);
  margin-top: 18px;
}

.panel-violet {
  background: var(--c-accent);
  display: flex;
  flex-direction: column;
  justify-content: center;
  padding: 80px 8%;
}

.panel-violet h1 {
  font: 800 var(--fs-h1) / 1 var(--f-disp);
  text-transform: uppercase;
  color: var(--c-white);
  margin-bottom: 34px;
}

.panel-violet p {
  font: 300 1.35rem/1.7 var(--f-disp);
  color: var(--c-white);
}

@media (max-width: 767px) {
  .panel-violet {
    padding: 56px 24px;
  }
  .panel-violet p {
    font-size: 1.05rem;
  }
}

.teaser-split {
  padding: 0;
}

.teaser-split .split50 {
  min-height: 66vh;
}

.teaser-split .panel-violet {
  justify-content: flex-start;
  padding-top: 90px;
}

.teaser-split .panel-violet h2 {
  font: 800 2.4rem/1.1 var(--f-disp);
  text-transform: uppercase;
  color: var(--c-white);
  margin-bottom: 26px;
}

@media (max-width: 767px) {
  .teaser-split .panel-violet h2 {
    font-size: 1.6rem;
  }
}

/* Unter 1024 px steht in den Wireframes das Foto ueber dem Panel, auch wenn die
   Reihenfolge im Markup umgekehrt ist. */
@media (max-width: 1024px) {
  .teaser-split .order-a {
    order: 2;
  }
}

/* --- interview --- */
.person-head {
  padding: 56px 0 20px;
  text-align: center;
}

.person-head .person-name {
  font: 300 var(--fs-name) / 1.2 var(--f-mono);
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--c-ink);
}

.contactrow {
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  gap: 24px;
  align-items: center;
  max-width: 1180px;
  margin: 34px auto 0;
  padding: 0 24px;
  font: 300 20px/1.5 var(--f-disp);
  letter-spacing: 1px;
}

.contactrow .tel {
  text-align: left;
}

.contactrow .role {
  text-align: center;
  color: var(--c-ink);
}

.contactrow .mail {
  text-align: right;
}

.contactrow a {
  color: var(--c-accent);
  text-decoration: none;
  text-transform: uppercase;
}

.contactrow a:hover {
  text-decoration: underline;
}

@media (max-width: 767px) {
  .contactrow {
    grid-template-columns: 1fr;
    text-align: center;
    gap: 10px;
    font-size: 15px;
  }
  .contactrow .tel,
  .contactrow .mail {
    text-align: center;
  }
}

.intro-copy {
  max-width: 820px;
  margin: 0 auto;
  padding: 0 24px 70px;
  text-align: center;
  color: var(--c-ink);
}

.interview {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 64px;
  max-width: 1180px;
  margin: 0 auto;
  padding: 0 24px 90px;
  align-items: start;
}

@media (max-width: 1024px) {
  .interview {
    grid-template-columns: 1fr;
    gap: 40px;
  }
}

.iv-left .ph,
.iv-left .bildslot {
  aspect-ratio: 4 / 3;
  margin-bottom: 40px;
}

/* Bilder der Interviewstrecke fuellen ihre Spalte ohne den 1080er-Zentrierrahmen der
   Inhaltsbilder; eine Bildunterschrift (rolle:bildtext) sitzt 14 px unter ihrem Bild,
   danach folgen 40 px - so steht es im Gruender-Wireframe. */
.interview .img-block {
  padding: 0;
  margin-bottom: 40px;
}

.interview .img-block:has(+ .bildtext) {
  margin-bottom: 14px;
}

.interview .bildtext {
  margin-bottom: 40px;
}

/* PULL-QUOTE-GROESSE NACH ZITATLAENGE (Nutzer-Anweisung 2026-08-21, Interviewseite
   /leda-kremmyda/). Eine feste Groesse passt nur kurzen Zitaten: bei 3.2 rem stehen
   45 Zeichen in drei Zeilen, 136 Zeichen dagegen in neun - der violette Block
   uebernimmt dann die ganze linke Spalte. Die Groesse haengt deshalb an der
   Zeichenzahl, die das Interview-Layout als --zeichen an den Block schreibt:
   bis 60 Zeichen volle --fs-pull, darueber umgekehrt proportional, sodass die
   Zeilenzahl gleich bleibt; --fs-pull-min ist die Untergrenze, damit sehr lange
   Zitate nicht zu Fliesstext schrumpfen. Ohne --zeichen (Vorlage ohne Wert) greift
   der Ruecksprung 60 und damit die volle Groesse. */
.pull {
  font: 800 var(--fs-pull) / 1.25 var(--f-disp);
  font-size: clamp(
    var(--fs-pull-min),
    calc(var(--fs-pull) * 60 / var(--zeichen, 60)),
    var(--fs-pull)
  );
  letter-spacing: 0.06em;
  color: var(--c-accent);
}

.pull--sub {
  font-size: calc(var(--fs-pull) * 0.55);
  font-weight: 500;
  letter-spacing: 0.04em;
  margin-top: 44px;
}

.iv-right .frage,
.iv-left .frage {
  font: 800 var(--fs-frage) / 1.4 var(--f-disp);
  letter-spacing: 1px;
  color: var(--c-ink);
  margin: 38px 0 16px;
}

.iv-right .frage:first-child {
  margin-top: 0;
}

.iv-right p,
.iv-left p.antwort {
  color: var(--c-ink);
  margin-bottom: 8px;
}

.antwort b {
  font-weight: 600;
}

/* Die Gruender-Variante setzt Fragen und Pull-Quotes gleich gross und gesperrt. */
.interview--gruender .pull {
  font: 800 var(--fs-frage) / 1.5 var(--f-disp);
  letter-spacing: 1.92px;
  margin-top: 8px;
}

.interview--gruender .frage {
  letter-spacing: 1.92px;
}

/* --- text / Rechtsseite --- */
.legal {
  max-width: 860px;
  margin: 0 auto;
  padding: 72px 24px 100px;
  color: var(--c-ink);
}

.legal h1 {
  font: 800 var(--fs-quote-h1) / 1.1 var(--f-disp);
  margin-bottom: 40px;
}

.legal h2 {
  font: 800 1.6rem/1.3 var(--f-disp);
  margin: 52px 0 18px;
}

.legal h3 {
  font: 800 1.2rem/1.4 var(--f-disp);
  letter-spacing: 0.5px;
  margin: 32px 0 12px;
}

.legal h4 {
  font: 600 1.02rem/1.5 var(--f-disp);
  margin: 22px 0 8px;
}

.legal p {
  margin-bottom: 16px;
}

.legal ul,
.legal ol {
  margin: 0 0 16px 22px;
}

.legal a {
  color: var(--c-accent);
  text-decoration: none;
}

.legal a:hover {
  text-decoration: underline;
}

/* Die Rechtsseite setzt Sektionstitel in ihrer eigenen, schlichten Stufe - nicht als
   Statement-Kopf. So steht es im Wireframe oow-wireframe-rechtsseite.html. */
.legal .statement {
  font: 800 1.6rem/1.3 var(--f-disp);
  color: var(--c-ink);
  max-width: none;
  margin: 52px 0 18px;
  text-align: left;
}

.legal .lead-copy {
  font: 300 16px/1.7 var(--f-disp);
}

.legal .seo-copy {
  padding: 0;
  max-width: none;
}

.legal .label,
.legal .kicker {
  color: var(--c-accent);
  margin-bottom: 18px;
}

.legal figure {
  margin: 32px 0;
}

.legal blockquote p {
  margin-bottom: 8px;
}

/* --- kontakt --- */
.formsec {
  max-width: 860px;
  margin: 0 auto;
  padding: 80px 24px 100px;
  text-align: center;
}

.formsec h2 {
  font: 800 calc(var(--fs-h2) * 0.72) / 1 var(--f-disp);
  color: var(--c-ink);
  margin: 14px 0 44px;
}

.kform {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 22px 24px;
  text-align: left;
}

.kform label {
  display: flex;
  flex-direction: column;
  gap: 8px;
  font: 500 13px/1 var(--f-mono);
  letter-spacing: 2px;
  text-transform: uppercase;
  color: var(--c-ink);
}

.kform .full {
  grid-column: 1 / -1;
}

.kform input,
.kform textarea {
  font: 300 16px/1.5 var(--f-disp);
  color: var(--c-ink);
  background: var(--c-white);
  border: 1px solid #d6d5d5;
  border-radius: 0;
  padding: 13px 14px;
  width: 100%;
}

.kform input:focus,
.kform textarea:focus {
  border-color: #706f6f;
}

.kform ::placeholder {
  color: #9da5ae;
}

.hinweis {
  font: 300 13px/1.6 var(--f-disp);
  letter-spacing: 0;
  text-transform: none;
  color: #6f6a66;
}

.hinweis a {
  color: var(--c-accent);
}

.full-c {
  grid-column: 1 / -1;
  justify-self: center;
}

/* Einwilligungszeile der Newsletter-Anmeldung (Auftrag NL1 Punkt 1, 2026-08-19).
   Der Block ist bewusst NICHT kleingedruckt: Kaestchen 20 px, Beschriftung in
   Fliesstextgroesse. Eine Einwilligung, die man uebersieht, ist keine. */
.einwilligung {
  margin-top: 6px;
}

.kform .wahl {
  display: flex;
  /* .kform label steht auf flex-direction column - fuer die Kaestchenzeile muss die
     Richtung ausdruecklich zurueckgedreht werden, sonst steht der Haken ueber dem Text. */
  flex-direction: row;
  align-items: flex-start;
  gap: 12px;
  font: 300 16px/1.5 var(--f-disp);
  letter-spacing: 0;
  text-transform: none;
  color: var(--c-ink);
  cursor: pointer;
}

.kform .wahl input[type="checkbox"] {
  appearance: none;
  -webkit-appearance: none;
  width: 20px;
  height: 20px;
  flex: 0 0 20px;
  margin: 2px 0 0;
  background: var(--c-white);
  border: 1px solid #706f6f;
  border-radius: 0;
  cursor: pointer;
}

.kform .wahl input[type="checkbox"]:checked {
  background: var(--c-accent);
  border-color: var(--c-accent);
}

.einwilligung .hinweis {
  margin-top: 12px;
}

/* Turnstile-Widget im Kontaktformular (2026-08-24). Cloudflare setzt seine eigene Groesse
   in einem iframe; hier steht nur, dass es die volle Spaltenbreite nicht sprengt - das
   Widget misst rund 300 px und wuerde auf schmalen Geraeten sonst ueberlaufen. */
.kform .cf-turnstile {
  min-height: 65px;
}

.kform .cf-turnstile iframe {
  max-width: 100%;
}

@media (max-width: 767px) {
  .kform {
    grid-template-columns: 1fr;
  }
}

/* Honigtopf: ausserhalb des Sichtfelds statt display:none - manche Automaten
   erkennen display:none und lassen das Feld dann leer. */
.honig {
  position: absolute;
  left: -9999px;
  top: auto;
}

/* ------------------------------------------------------------------ 11a. Bloecke des Spiegels
 *
 * Was teile/block.njk aus dem Textkoerper macht. Die Klassen kommen aus dem Spiegel, die
 * Werte aus den Wireframes: Statement-H2 wie .intro h2, Lead wie .intro .copy,
 * Namenszeile wie blockquote footer. */

.statement {
  font: 800 var(--fs-h2) / 1 var(--f-disp);
  color: var(--c-ink);
  max-width: 22ch;
  margin: 0 auto 22px;
}

.lead-copy {
  font: 300 var(--fs-body) / 1.6 var(--f-disp);
}

.quote-name {
  margin-top: 26px;
  margin-bottom: 22px;
  font: 500 15px/1.5 var(--f-disp);
  letter-spacing: 2px;
  text-transform: uppercase;
  color: var(--c-ink);
}

/* Zwischenueberschrift der SEO-Textstrecken: bewusst LEICHT statt fett
   (DESIGN_OOW-ONLINE Abschnitt 4, Rolle "H3-leicht"), links, wie .seo-copy h3
   im Wireframe oow-wireframe-kategorie-nativ.html. */
.unterzeile {
  font: 300 var(--fs-h3light) / 1.6 var(--f-disp);
  color: var(--c-ink);
  margin: 52px 0 20px;
  max-width: 1140px;
  padding: 0 24px;
}

.koerper--dunkel .unterzeile {
  color: var(--c-white);
}

.legal .unterzeile {
  padding: 0;
  max-width: none;
  margin: 32px 0 12px;
}

.seo-copy--seite {
  padding-bottom: 60px;
}

/* Fremdes Markup der beiden Werkzeug-Seiten: eingerahmt, damit seine festen Breiten
   nicht die Seite aufschieben. Gescrollt wird der Rahmen, nicht das Dokument. */
.rohblock {
  overflow-x: auto;
  max-width: 100%;
}

.rohblock img,
.rohblock table {
  max-width: 100%;
}

/* Der Inhaltsstrom der Projektseite steht im weissen Bereich zwischen Meta-Band und
   Zaehlerband. Fliesstext links, Statement-Koepfe zentriert.
   P1 (Nutzer-Entscheid 2026-08-18): der Langtext teilt sich mit Bildern und
   Bildunterschriften EINE linksbuendige Spalte im Original-Mass - gemessen 1100 px fix
   ab 1440 (auch bei 1880), darunter fluid mit Standardrand (1024: voller Rand 20).
   Das 900er-Lesemass des Wireframes gilt hier nicht. */
.intro .container {
  max-width: 1148px; /* 1100 px Inhalt + 2 x 24 px Randabstand */
}

.intro .seo-copy {
  max-width: none;
  margin: 0;
  padding: 0;
  text-align: left;
}

/* Bilder und Karussells exakt in Spaltenbreite, an derselben linken Kante. */
.intro .img-block,
.intro .carousel {
  max-width: none;
  padding: 0;
  margin-left: 0;
  margin-right: 0;
}

.intro .img-block:has(+ .bildtext) {
  margin-bottom: 14px;
}

.intro > .container > .bildtext {
  margin-bottom: 80px;
  text-align: left;
}

.intro .kicker,
.intro .mlabel,
.intro .quote-block,
.intro .quote-name,
.intro .cta-row {
  text-align: center;
}

.intro .img-block,
.intro .carousel {
  margin-top: 44px;
}

/* TYPOGRAFIE DES WEISSEN INHALTSBEREICHS DER PROJEKT-DETAILSEITEN (Auftrag PI1,
   Nutzer-Entscheid 2026-08-23). Zielwerte vom Nutzer per Regler-Screenshot festgeschrieben,
   Referenz ist der Spiegel-Wireframe von neu.oow.berlin/7047-concrete/ (2026-08-21,
   1600x1000). Vorher-Werte in den Kommentaren, live gemessen am 2026-08-21.

   TRAEGER IST body[data-layout="projekt"] (gesetzt in basis.njk) und nicht .intro allein:
   denselben weissen Inhaltsbereich benutzen auch /leistungen/, die Bereichsseiten und die
   Teamseiten. Ohne die Klammer wanderten die Werte dorthin mit - dort gelten sie nicht.
   Aus demselben Grund bleiben --fs-h2, --fs-body und --fs-quote unangetastet: sie sind die
   Stufen des Designsystems fuer ALLE Seitentypen (Abschnitt 4 der Doku), hier steht nur
   die Ausnahme der Projektseite. */
[data-layout="projekt"] .intro h2.statement {
  font-size: 69.2px; /* vorher var(--fs-h2), gemessen 62,4 px */
  margin: 0 auto 18px; /* vorher 0 auto */
}

[data-layout="projekt"] .intro .seo-copy p.lead-copy {
  font-size: 20px; /* vorher var(--fs-body), gemessen 25,6 px */
  line-height: 2; /* vorher 1.6 */
}

/* Der Normalabsatz behaelt seine 16 px und bekommt nur den weiteren Durchschuss. */
[data-layout="projekt"] .intro .seo-copy p:not(.lead-copy) {
  line-height: 2; /* vorher 1.7 */
}

[data-layout="projekt"] .intro .seo-copy p {
  margin-bottom: 16px; /* vorher 26px */
}

/* Zitat und Bildunterschrift stehen linksbuendig in der Inhaltsspalte, nicht zentriert.
   Beide erben die Mitte von .intro; hier wird sie zurueckgenommen. Fuer die
   Bildunterschrift gilt das jetzt UEBERALL im Inhaltsbereich - die Regel weiter oben traf
   nur die direkten Kinder des Containers, nicht die im Zitat-Split. */
[data-layout="projekt"] .intro blockquote {
  text-align: left; /* vorher zentriert, geerbt von .intro */
}

[data-layout="projekt"] .intro blockquote p {
  font-size: 16px; /* vorher var(--fs-quote), gemessen 22,4 px */
  line-height: 2; /* vorher 1.8 */
}

[data-layout="projekt"] .intro .bildtext {
  text-align: left; /* Groesse bleibt 15 px; vorher zentriert */
}

[data-layout="projekt"] .quote-split {
  gap: 20px; /* vorher 64px */
}

/* Die 20 px gelten fuer den ZWEISPALTIGEN Satz - dort sind sie der Abstand zwischen Zitat
   und Bild und wurden bei 1600x1000 festgeschrieben. Einspaltig ist derselbe Wert der
   Abstand UNTER dem Bild; dort bleibt es bei den 36 px von vorher. Die Zeile muss HINTER
   der Projektregel stehen: beide haben dieselbe Spezifitaet, also entscheidet die
   Reihenfolge - in der Media Query weiter oben bliebe sie wirkungslos. Ohne sie zoege PI1
   den Mobilabstand still mit, und das war nicht beauftragt. */
@media (max-width: 1024px) {
  [data-layout="projekt"] .quote-split {
    gap: 36px;
  }
}

/* ENTFALLEN am 2026-08-25 (Auftrag KTX Punkt 2, Nutzer-Entscheid). Hier stand die Regel
   aus KAR Punkt 4: unter 899 px brach das Karussell aus dem 24-px-Rand der Inhaltsspalte
   aus und holte sich jeden Pixel - bei 390 px Fenster 390 statt 342 px.
   Ihr einziger Grund war die SCHRIFT IM BILD: die Slides trugen Ueberschrift, Eckdaten
   und Bildunterschrift als Pixel, und die waren schmal nicht mehr zu lesen. Seit dem
   2026-08-25 sind die Slides textfrei - reine Fotos und Renderings. Damit haengt die
   Lesbarkeit an nichts mehr, und das Karussell haelt wieder den normalen Rand des
   Designsystems wie jeder andere Baustein.
   Mit der Regel entfaellt auch das Nachruecken der Scroll-Pfeile: sie standen nur nach
   innen, weil das ausgebrochene Karussell sie sonst aus dem Fenster geschoben haette. */

/* Arbeitsweise setzt alles mittig. */
.koerper-mitte .seo-copy {
  max-width: 940px;
  margin: 0 auto;
  padding: 0 24px 70px;
  text-align: center;
  font: 300 1.3rem/1.7 var(--f-disp);
}

.koerper-mitte .bildtext {
  max-width: 1180px;
  margin: 0 auto;
  padding: 0 24px 46px;
}

/* Dunkle Vorlagen: derselbe Strom, nur in der dunklen Palette. */
.koerper--dunkel .statement,
.koerper--dunkel .seo-copy h2,
.koerper--dunkel .seo-copy h3 {
  color: var(--c-white);
}

.koerper--dunkel .seo-copy,
.koerper--dunkel .kicker,
.koerper--dunkel .quote-name {
  color: var(--c-sec);
}

.koerper--dunkel .seo-copy {
  max-width: 760px;
  margin: 0 auto 26px;
  padding: 0;
  font: 300 var(--fs-body) / 1.6 var(--f-disp);
}

.koerper--dunkel .seo-copy a {
  color: var(--c-white);
  text-decoration: underline;
}

.koerper--dunkel .img-block,
.koerper--dunkel .carousel {
  margin-top: 48px;
}

.koerper--dunkel .ph {
  background: #2c2c2c;
  border-color: #4a4a4a;
}

/* ------------------------------------------------------------------ 12. FAQ-Akkordeon */

.faq {
  max-width: 1180px;
  margin: 0 auto;
  padding: 20px 24px 100px;
}

.faq h2 {
  font: 800 calc(var(--fs-h2) * 0.72) / 1 var(--f-disp);
  color: var(--c-ink);
  text-align: center;
  margin-bottom: 52px;
}

:root {
  interpolate-size: allow-keywords;
}

.acc-item {
  border: 1px solid #e2dcd7;
  border-bottom: 0;
  background: var(--c-white);
}

.acc-item:last-of-type {
  border-bottom: 1px solid #e2dcd7;
}

.acc-t {
  display: flex;
  align-items: center;
  gap: 16px;
  cursor: pointer;
  list-style: none;
  padding: 20px 22px;
  font: 800 clamp(16px, 1.5vw, 24px) / 1.3 var(--f-disp);
  letter-spacing: 1.92px;
  color: var(--c-ink);
  transition: color 0.2s;
}

.acc-t::-webkit-details-marker {
  display: none;
}

.acc-t::before {
  content: "+";
  font-weight: 300;
  font-size: 1.2em;
  line-height: 1;
  width: 0.9em;
  flex: 0 0 auto;
}

.acc-item[open] .acc-t::before {
  content: "\2212";
}

.acc-t:hover,
.acc-item[open] .acc-t {
  color: var(--c-accent);
}

.acc-item::details-content {
  block-size: 0;
  overflow: hidden;
  transition: block-size 0.4s ease, content-visibility 0.4s allow-discrete;
}

.acc-item[open]::details-content {
  block-size: auto;
}

.acc-inner {
  padding: 2px 22px 24px 60px;
  font: 300 16px/1.7 var(--f-disp);
  color: var(--c-ink);
}

/* ------------------------------------------------------------------ 13. Fuss */

.fuss {
  background: var(--c-bg);
  padding: 80px 0 36px;
  font: 300 18px/1.7 var(--f-mono);
  letter-spacing: 0.9px;
  color: var(--c-monotext);
}

/* Fusszeile vollbreit (ST7, Nutzer-Entscheid 2026-08-18, alle Seiten): der Fuss laeuft
   ohne den 1140er-Deckel mit 20 px Randabstand - am Original gemessen, Desktop wie
   mobil 20 px. Spaltenraster und Inhalte bleiben unveraendert. */
.fuss .container {
  max-width: none;
  padding: 0 20px;
}

/* AN4.3a (Nutzer-Auftrag 2026-08-21): die Marke der Fusszeile ist das Original-Asset -
   die weisse Wortmarke MIT Anspruchszeile im Bild, natuerlich 632x32. Sie ist ein
   ANDERES Asset als das Dreieck-Badge des Kopfes (Abschnitt 5, .badge) und nicht mit ihm
   austauschbar. Der frueher hier gesetzte Schrift-Nachbau (.f-brand .logo) und die
   separate Anspruchszeile (.f-brand span) sind entfallen - die Zeile steckt im Bild. Die
   Regeln .logo, .logo b und .logo i in Abschnitt 5 bleiben: der mobile Kopf nutzt sie
   weiter.
   Die Hoehe steht hier und nicht im Markup, weil die Originalmasse eine @2x-Fassung
   sind - wie bei den Social-Logos.

   MOB3 (Nutzer-Entscheid 2026-08-21): feste Anzeigehoehe, Breite automatisch, KEIN
   Schrumpfen in der Flexzeile. Ohne flex: none staucht die Flexzeile das Bild auf
   schmalen Fenstern in der Breite, waehrend die Hoehe stehen bleibt - genau die
   verzerrte Darstellung auf dem Telefon.
   HOEHEN: 40 px ab 768 px, 14 px bis 767 px. Die 14 px sind NICHT die im Briefing
   empfohlenen 32 px, sondern die Ueberlaufgrenze aus MOB3 Punkt 2: das Asset laeuft
   632:32, also 19,75:1. Bei 320 px Fenster stehen 320 - 2 x 20 = 280 px Textbreite zur
   Verfuegung, das erlaubt hoechstens 280 / 19,75 = 14,18 px Hoehe. 32 px waeren 632 px
   breit und wuerden den Fuss aufschieben. 14 px ergeben 276,5 px - der groesste Wert,
   der die Grenze haelt. */
.f-brand {
  display: flex;
  align-items: center;
  gap: 16px;
  margin-bottom: 54px;
}

.f-logo {
  height: 40px;
  width: auto;
  flex: none;
  display: block;
}

@media (max-width: 767px) {
  .f-logo {
    height: 14px;
  }
}

/* Zwischenband 768-831 px: bei 40 px Hoehe ist das Bild 790 px breit, dafuer braucht es
   790 + 2 x 20 = 830 px Fenster. Darunter greift die Grundregel img { max-width: 100% }
   und staucht das Bild in der BREITE, waehrend die feste Hoehe stehen bleibt - dieselbe
   Verzerrung, die MOB3 mobil abstellt, nur eine Fensterbreite hoeher. flex: none hilft
   dagegen nicht, max-width wirkt unabhaengig von der Flexverteilung. 36 px ergeben
   711 px und passen schon bei 768 px Fenster. Gemessen 2026-08-21. */
@media (min-width: 768px) and (max-width: 831px) {
  .f-logo {
    height: 36px;
  }
}

.f-cols {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
}

/* Der Wireframe setzt column-gap 0 - unter Lorem-Text faellt das nicht auf, unter den
   echten Namen und Nummern stossen die Spalten aneinander ("...811 - 11Arbeitsweise").
   Der Abstand kommt deshalb als Innenabstand der Spalte, das Raster bleibt bei 0. */
.f-cols > * {
  padding-right: 24px;
}

@media (max-width: 1024px) {
  .f-cols {
    grid-template-columns: repeat(2, 1fr);
    gap: 36px 24px;
  }
}

@media (max-width: 767px) {
  .f-cols {
    grid-template-columns: 1fr;
    gap: 32px;
  }
}

.f-cols ul {
  list-style: none;
}

/* width:max-content steht so im Wireframe, dort aber unter Lorem-Text. Der echte
   Bueroname ist laenger als ein 390er Fenster - ohne die Deckelung schiebt er die
   Seite waagerecht auf (bei 390 px gemessen: 55 px Ueberlauf). */
.f-cols a {
  color: var(--c-monotext);
  text-decoration: none;
  display: block;
  width: max-content;
  max-width: 100%;
  transition: color 0.2s;
}

.f-cols a:hover {
  color: var(--c-white);
}

/* AN4.3b (Nutzer-Auftrag 2026-08-21): der Kontaktblock traegt DREI Zeilen je Person -
   Name, Telefon, Mailzeile am Stueck - statt frueher fuenf. Zwischen den beiden Personen
   steht eine Leerzeile.
   HINWEIS zum Schnitt: Roboto Mono liegt nur in 300 und 500 (Entscheid F2,
   BRIEFING_DESIGN_UPDATE) - 500 ist das Maximum, kein synthetisches Fetten.
   .f-cols a { overflow-wrap: anywhere } in Abschnitt 2 bleibt und greift weiter fuer die
   Anschrift; .f-mail schlaegt es fuer die Mailzeile. */
.f-cols p {
  margin: 0;
}

.f-kontakt p + p {
  margin-top: 31px;
}

.f-name {
  font-weight: 500;
  color: var(--c-white);
}

.f-mail {
  white-space: nowrap;
}

/* Ohne diese Zeile bleibt der Block bei FUENF Zeilen je Person: .f-cols a setzt
   display: block (Abschnitt weiter oben, gegen den zu langen Bueronamen im 390er
   Fenster), und ein Block-Link im Absatz erzwingt eigene Zeilen - fuer die Telefon-
   nummer, fuer die Mailadresse und noch eine leere hinter dem <br>. Im Kontaktblock
   laufen die Links deshalb wieder inline; die Deckelung bleibt fuer die Anschrift und
   das Fussmenue bestehen, wo sie gebraucht wird. */
.f-kontakt a {
  display: inline;
  width: auto;
}

.socials {
  display: flex;
  gap: 14px;
  margin-top: 14px;
}

.socials a {
  width: 36px;
  height: 36px;
  border: 1.5px solid var(--c-monotext);
  border-radius: 8px;
  display: flex;
  align-items: center;
  justify-content: center;
  font: 500 12px/1 var(--f-mono);
  letter-spacing: 0;
}

.socials a:hover {
  border-color: var(--c-white);
}

/* Die Logos kommen als weisse PNG aus der Mediathek. Die Hoehe steht hier und nicht im
   Markup, weil die Originalmasse eine @2x-Fassung sind - das Bild soll auf Anzeigegroesse
   herunterskaliert werden, nicht in Originalgroesse den Rahmen sprengen. Feste Hoehe bei
   automatischer Breite haelt das Seitenverhaeltnis und verhindert einen Layoutsprung beim
   Nachladen. */
.socials img {
  height: 18px;
  width: auto;
}

/* Die SEO-Kategorienzeile (.f-seo) ist am 2026-08-21 ersatzlos entfallen (AN4.3c);
   navigation.bereiche bleibt als Quelle stehen, wird aber nicht mehr ausgespielt. Die
   sieben Landing Pages sind weiterhin aus drei bis fuenf anderen Dateien heraus
   verlinkt und verwaisen nicht. */

.f-credit {
  margin-top: 20px;
  text-align: right;
  font: 300 11px/1 var(--f-mono);
  letter-spacing: 3px;
  text-transform: uppercase;
  color: rgba(255, 255, 255, 0.22);
}

/* Derselbe Credit auf der Impressum-Seite. Eigene Klasse statt .f-credit, weil die
   Textseite HELL ist - weiss auf 22 Prozent waere dort unlesbar. Linksbuendig wie der
   uebrige Text der schmalen Spalte, mit Abstand als eigener Abbinder.
   Die Deckung ist nicht frei gewaehlt: 0.62 auf Weiss ergibt rund #767676 und damit die
   4.5:1, die kleiner Text nach WCAG AA braucht. Mit der Fuss-Deckung 0.22 waere der Satz
   auf hellem Grund praktisch unsichtbar, mit 0.45 kaeme er nur auf 2.7:1. */
.legal-credit {
  margin-top: 64px;
  font: 300 11px/1.6 var(--f-mono);
  letter-spacing: 3px;
  text-transform: uppercase;
  color: rgba(35, 35, 35, 0.62);
}

/* Sprachschalter: Chip unten rechts (DESIGN_OOW-ONLINE Abschnitt 6). */
.lang-chip {
  position: fixed;
  right: 14px;
  bottom: 14px;
  z-index: 900;
  background: #f2f2f2;
  color: #232323;
  padding: 9px 13px;
  font: 500 11px/1 var(--f-mono);
  border-radius: 2px;
  text-decoration: none;
}

/* ------------------------------------------------------------------ 14. Hell und Dunkel
 *
 * PFLICHTREGEL aus DESIGN_OOW-ONLINE Abschnitt 7: helle Seiten sperren den
 * Geraete-Darkmode dreifach ab - color-scheme, expliziter Hintergrund auf html UND body,
 * und die body::before-Ebene. Ohne diese drei Ebenen verdunkeln WebViews die Seite.
 * Das Meta-Tag dazu setzt basis.njk.
 */

/* Dunkel ist der Standard. */
html {
  background: var(--c-bg);
  color-scheme: dark;
}

body {
  background-color: var(--c-bg);
  color: var(--c-monotext);
}

body::before {
  content: "";
  position: fixed;
  inset: 0;
  z-index: -1;
  background: #232323;
}

/* Helle Seiten. Die Rolle steht an html UND body, damit keine der drei Ebenen von einem
   Selektor abhaengt, den ein aelterer Browser nicht kann. */
html[data-hell="ja"] {
  background: #fff;
  color-scheme: only light;
}

html[data-hell="ja"] body,
body[data-hell="ja"] {
  background-color: #fff;
  color: #232323;
}

html[data-hell="ja"] body::before,
body[data-hell="ja"]::before {
  background: #fff;
}

/* Und noch einmal ausdruecklich gegen den Geraete-Darkmode: manche WebViews werten
   color-scheme nicht aus und legen ihre eigene Verdunkelung darueber. */
@media (prefers-color-scheme: dark) {
  html[data-hell="ja"],
  html[data-hell="ja"] body {
    background: #fff;
    color: #232323;
  }
  html[data-hell="ja"] body::before {
    background: #fff;
  }
}

/* ------------------------------------------------------------------ 15. Mobile Zeilenhoehe
 *
 * Nutzer-Entscheid 2026-08-18 (Nachschaerfung 4-Seiten-Pruefung, M1): die grossen
 * AGG-800-Ueberschriften laufen auf dem Desktop mit line-height 1 (Marken-DNA), unter
 * 767 px aber mit 1.1 - mehrzeilige Umbrueche kleben sonst aneinander. Das Zitat-h1 der
 * Interviewseiten behaelt seine 1.15, der Bandtitel seine 1.15. Die Regel steht NACH den
 * font-Kurzformen der Bausteine, weil sie deren line-height bei gleicher Spezifitaet
 * sonst nicht ueberschreiben koennte. */

@media (max-width: 767px) {
  .display,
  .brandband h2,
  .panel-violet h1,
  .page-head h1,
  .intro h2,
  .anriss-titel,
  .statement,
  .facts h2,
  .formsec h2,
  .faq h2 {
    line-height: 1.1;
  }
}

/* ------------------------------------------------------------------ 16. Bewegung */

@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    transition: none !important;
    animation: none !important;
  }
  html {
    scroll-behavior: auto;
  }
  .car-scroll {
    scroll-behavior: auto;
  }
}

/* ------------------------------------------------------------------ 17. Scroll-Effekte Startseite
 *
 * Nutzer-Entscheid 2026-08-19, NUR Startseite (body[data-layout="start"]). Nativer
 * Nachbau der Elementor Motion FX des Originals - Inventar, Werte und Abweichungen
 * stehen in DESIGN_OOW-ONLINE Abschnitt 8, Unterabschnitt Bewegung. Alles in EINEM
 * @supports-Block: Firefox u. a. sehen die statische, voll sichtbare Seite; ausserhalb
 * gibt es keine Initialzustaende. reduced-motion schaltet ab. Animiert werden nur
 * translate/scale/opacity. --lauf ist der halbe Gesamtweg ueber die cover-Strecke:
 * positiv mitlaufend, negativ gegenlaeufig; fill both friert ausserhalb der Range ein
 * (wie das affectedRange des Originals). */

@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) {
    /* Seitlich darf nichts ueberstehen; senkrechtes Ueberlappen IST der Effekt.
       Das Clipping steht seit AN1 (2026-08-20) in Abschnitt 11a und gilt damit auch
       ohne Scroll-Effekte - hier steht es nicht noch einmal. */

    @keyframes start-lauf {
      from {
        translate: 0 calc(-1 * var(--lauf));
      }
      to {
        translate: 0 var(--lauf);
      }
    }

    /* E1-Zoom, Form korrigiert (AN1a, 2026-08-20). Das Original pulst NICHT
       (1 -> x -> 1), es zoomt EINSINNIG heraus: das Bild steht beim Eintritt gross und
       geht auf 1 zurueck, dort bleibt es. Am Original ueber den ganzen Scrollweg
       gemessen - Anriss 2 zum Beispiel 1,050 / 1,044 / 1,024 / 1,002 / 1,000, danach
       konstant 1. Ausserhalb der Sichtflaeche ist die view()-Timeline inaktiv; das
       Bild traegt dort keinen Transform (H5 bleibt gewahrt). */
    @keyframes start-zoom {
      from {
        scale: 1.05;
      }
      to {
        scale: 1;
      }
    }

    @keyframes start-zoom-gross {
      from {
        scale: 1.4;
      }
      to {
        scale: 1;
      }
    }

    @keyframes start-fade-outin {
      from {
        opacity: 1;
      }
      50% {
        opacity: 0;
      }
      to {
        opacity: 1;
      }
    }

    @keyframes start-einblenden {
      from {
        opacity: 0;
      }
      to {
        opacity: 1;
      }
    }

    /* E4 Bandtitel-Fades, alle Breiten. Ziele seit dem Ausbau ST1-ST7: Kicker und
       Statement des Innenbands; der Zahlen-Titel ist mit ST4 entfallen. */
    body[data-layout="start"] .innenband .subline,
    body[data-layout="start"] .innenband h2 {
      animation: start-fade-outin linear both;
      animation-timeline: view();
      animation-range: cover 3% cover 54%;
    }

    /* E5 Eintritte, alle Breiten; blenden beim Rueckwaertsscrollen wieder aus. */
    body[data-layout="start"] .hero,
    body[data-layout="start"] .helloow {
      animation: start-einblenden linear both;
      animation-timeline: view();
      animation-range: entry 0% entry 60%;
    }

    /* Parallax ab 768 px, wie die motion_fx_devices des Originals.
       KALIBRIERUNG v2 nach Faktormessung am Original (2026-08-18); die FAKTOREN sind
       unveraendert, nur die --lauf-Werte sind mit dem Anriss-Umbau AN1 (2026-08-20)
       neu gerechnet: lauf = (1 - Faktor) / 2 x (Viewporthoehe + Elementhoehe), und die
       Elementhoehen haben sich mit den Original-Bildmassen geaendert. Je Anriss ein
       Paar: --haupt = grosses verlinktes Teaser-Bild (mitlaufend, mit Zoom
       1 -> 1,2 -> 1 beim ersten, sonst 1 -> 1,05 -> 1), --zweit = Overlay-Bild
       (gegenlaeufig, teils weit ueber den eigenen Teaser hinaus - so das Original;
       senkrecht wird bewusst NICHT geclippt, seitlich sichert overflow-x: clip). */
    @media (min-width: 768px) {
      /* E1 grosse Teaser-Bilder, mitlaufend + Zoom (Original-Faktoren 0,57-0,74). */
      body[data-layout="start"] .anriss-bild--haupt {
        animation: start-lauf linear both, start-zoom linear both;
        animation-timeline: view(), view();
        /* Zoom-Range wie das Original: 19-49 % der Strecke ... */
        animation-range: normal, cover 19% cover 49%;
      }

      body[data-layout="start"] .anriss--1 .anriss-bild--haupt {
        --lauf: 177px;
        /* ... nur das erste Bild zoomt wie im Original staerker (1,2) und ueber 0-65 %. */
        animation-name: start-lauf, start-zoom-gross;
        animation-range: normal, cover 0% cover 65%;
      }

      body[data-layout="start"] .anriss--2 .anriss-bild--haupt {
        --lauf: 151px;
      }

      /* Anriss 3 und 4 nachjustiert (2026-08-20, zweiter Sweep): erst mit vorgeladenen
         Bildern liessen sich die Original-Faktoren dieser beiden Bilder ueberhaupt
         messen - 0,81 und 0,82. Mit den bis dahin uebernommenen Laeufen (99 / 64) lag
         der Nachbau bei 0,91 und 0,94 und riss die 10-Prozent-Toleranz. */
      body[data-layout="start"] .anriss--3 .anriss-bild--haupt {
        --lauf: 189px;
      }

      body[data-layout="start"] .anriss--4 .anriss-bild--haupt {
        --lauf: 173px;
      }

      /* E3 Overlay-Bilder, gegenlaeufig, je Element gemessen (Faktoren 1,26-2,66). */
      body[data-layout="start"] .anriss-bild--zweit {
        animation: start-lauf linear both;
        animation-timeline: view();
      }

      body[data-layout="start"] .anriss--1 .anriss-bild--zweit {
        --lauf: -204px;
      }

      body[data-layout="start"] .anriss--2 .anriss-bild--zweit {
        --lauf: -1210px;
      }

      body[data-layout="start"] .anriss--3 .anriss-bild--zweit {
        --lauf: -999px;
      }

      body[data-layout="start"] .anriss--4 .anriss-bild--zweit {
        --lauf: -1042px;
      }

      /* E1b Personen-Teaser-Bilder Meri/Leda (ST3), halbe Staerke - als Innen-Parallax
         im geclippten Spaltenslot. Der Anschnitt kommt aus der Geometrie (Ueberhoehe
         plus Versatz), NICHT aus einem statischen scale - H5-Auflage: kein Element
         traegt in Ruhe scale != 1. */
      body[data-layout="start"] .personenbild {
        position: relative;
        overflow: clip;
      }

      body[data-layout="start"] .personenbild > img {
        position: absolute;
        left: 0;
        top: -45px;
        height: calc(100% + 90px);
        --lauf: 45px;
        /* OHNE fill (H5): ausserhalb der Range traegt das Bild keinen Rest-Transform.
           Der Uebergang an der Range-Kante ist unsichtbar, weil das ueberhohe Bild im
           geclippten Slot sitzt - anders als bei den Anriss-Parallaxen, die ihren
           fill brauchen (sonst Sprung an der Sichtbarkeitskante). */
        animation: start-lauf linear;
        animation-timeline: view();
      }

      /* E2 steht seit AN2.2 (2026-08-21) als eigener Block unter diesem @supports -
         einsinnige Fahrt in reservierter Bahn, ohne 768er-Schwelle. */

      /* E6 Hero-Bild als Innen-Parallax: Anschnitt aus der Geometrie (Ueberhoehe plus
         Versatz) statt statischem scale (H5-Auflage), Lauf im geclippten Rahmen. */
      body[data-layout="start"] .hero .bildslot {
        overflow: clip;
      }

      body[data-layout="start"] .hero .bildslot img {
        position: absolute;
        left: 0;
        top: -24px;
        height: calc(100% + 48px);
        --lauf: 24px;
        /* OHNE fill (H5): kein Rest-Transform ausserhalb der Range - im Sweep
           2026-08-20 war genau hier ein Ruhe-Transform ('0px 24px') gemessen worden. */
        animation: start-lauf linear;
        animation-timeline: view();
      }
    }
  }
}

/* E2 SLOGAN-FAHRT v2 (AN2.2, Nutzer-Entscheid 2026-08-21) - ERSETZT den symmetrischen
 * start-lauf der Schlagzeilen (--lauf 155/152/116/108 px). Der war die Ursache des
 * Ueberfahrens: er lief von -155 bis +155 px um die Satzposition und schob die
 * Schlagzeile beim Eintritt 127 px (1440x950) bzw. 108 px (2560x1249) in den Kicker,
 * beim Austritt 87 px in den Fliesstext (gemessen 2026-08-21).
 *
 * Jetzt startet die Schlagzeile an ihrer Satzposition und faehrt EINSINNIG nach unten
 * bis an den Projektnamen - der Weg ist als padding-bottom der Bahn reserviert
 * (Abschnitt 11a), Projektname und Fliesstext ruecken um genau diesen Weg nach. Nach
 * oben ist bei translate 0 Schluss. Die Amplitude des Originals bleibt: der einsinnige
 * Gesamtweg ist das Doppelte des frueheren halben Laufs.
 *
 * Keyframes NUR auf translate (Auflage dieses Abschnitts, kein transform). Ohne
 * animation-timeline steht die Schlagzeile oben in ihrer Bahn - statisch und
 * vollstaendig sichtbar wie der Rest der @supports-Weiche. */
@keyframes slogan-fahrt {
  from {
    translate: 0 0;
  }
  to {
    translate: 0 var(--reise);
  }
}

@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) {
    body[data-layout="start"] .anriss-titel {
      animation: slogan-fahrt auto linear both;
      animation-timeline: view();
      animation-range: cover 15% cover 60%;
    }
  }
}

/* ==================================================================
   WORTMARKE OOW IM FLIESSTEXT (Nutzer-Auftrag KPB1 Punkt 3, 2026-08-25)

   OO fett, W kursiv aus einem duenneren Schnitt und etwas breiter. Gesetzt wird sie
   NICHT im Inhalt, sondern beim Bauen ueber die Ausgabe (eleventy.config.mjs,
   Transform "wortmarke") - sonst stuende die Auszeichnung in TXT/claude und wanderte
   bei jedem Export mit.

   Geladene AGG-Schnitte: 100-200 Extra Light, 300-400 Book, 500 Medium, 600 Demi,
   700-800 Bold. Die Kursive erzeugt der Browser; ein kursiver Schnitt ist nicht geladen.

   DER ABSTAND HAENGT AM W, nicht am OO. Als margin-left ist er ein ZUSCHLAG auf den
   Buchstabenabstand der Umgebung und ersetzt ihn nicht - deshalb stimmt er auch in den
   gesperrten Mono-Zeilen (5,5 px). Mass in em, damit er mit der Schriftgroesse waechst.

   DIE BREITE ist transform: scaleX() an einem inline-block. Der Kasten behaelt seine
   Breite, die Skalierung laeuft ueber seine Kanten hinaus - von der Mitte aus je zur
   Haelfte nach beiden Seiten. Genau diese Haelfte gleichen die Raender wieder aus, damit
   die Wortzwischenraeume stehen bleiben. --oow-wbreite ist die gemessene Laufweite des
   W in AGG: 0,90 em (bei H1 67 px also 61 px).
   ================================================================== */
:root{
  --oow-oo: 800;
  --oow-w: 400;
  --oow-kern: -0.18em;
  --oow-breite: 1.15;
  --oow-wbreite: 0.90em;
}
.oow b{ font-weight: var(--oow-oo); }
.oow i{
  font-style: italic;
  font-weight: var(--oow-w);
  display: inline-block;
  transform: scaleX(var(--oow-breite));
  transform-origin: 50% 50%;
  margin-left: calc(var(--oow-kern) + (var(--oow-breite) - 1) * var(--oow-wbreite) / 2);
  margin-right: calc((var(--oow-breite) - 1) * var(--oow-wbreite) / 2);
  letter-spacing: inherit;
}

/* ==================================================================
   KONTAKT-EINSTIEG /mit-oow-planen-und-bauen/
   (Nutzer-Auftrag KPB1, 2026-08-25)

   Uebernommen aus docs/wireframes/oow-wireframe-planen-und-bauen.html. Alles auf den
   Tokens des Designsystems - Farben, Schriften, Radien und Rhythmus kommen aus den
   Variablen; hier wird kein Mass erfunden, das es schon gibt.

   EINE ABWEICHUNG VOM WIREFRAME, bewusst: der fuehrt die Inhaltsbreite auf 940 px. Der
   Auftrag schreibt 1100 px vor - dieselbe wie Projekt-, Arbeitsweise- und Leistungsseite
   (live gemessen 2026-08-25: .intro .seo-copy 1100 px, .legal 860 px). Der Auftrag geht
   vor; die 940 px waren der Ausgangswert der Reglerleiste.
   ================================================================== */
:root{
  /* 1148 = 1100 px Inhalt + 2 x 24 px Randabstand. Genau die Rechnung von
     .intro .container, damit die Spalte exakt so breit steht wie auf Projekt-,
     Arbeitsweise- und Leistungsseite. 1100 als Kastenbreite waere 48 px zu schmal. */
  --ke-breite: 1148px;
  --ke-abstand: 90px;      /* Abstand zwischen den Abschnitten */
  --ke-kartengap: 48px;
  --ke-portrait: 0.80;     /* Hochformat 4:5 */
  --ke-name: 32px;
  --ke-zeile: 20px;
  --ke-nr: 64px;
  --ke-schrittgap: 40px;
  --ke-fpad: 18px;
  --ke-kartenbreite: 520px;
  --ke-ortgroesse: 13px;
  --ke-linie: 1.1px;
  --ke-punkt: 4.5px;
  --ke-herohoehe: 580px;
  --ke-herofokus: 47%;
}

.ke-breite{ max-width: var(--ke-breite); margin: 0 auto; padding: 0 24px; }
.ke-abschnitt{ padding: 0 0 var(--ke-abstand); }
.ke-kopf{ padding-top: 56px; }

/* --- Herobild, randlos. stil.css setzt global section{ padding: 90px 0 } - dieses Band
       laeuft dagegen bis an die Fensterkanten. --- */
.ke-heroband{ width: 100%; padding: 0; }
.ke-heroband .ke-hero img{
  display: block; width: 100%; height: var(--ke-herohoehe);
  object-fit: cover; object-position: 50% var(--ke-herofokus);
}

.ke-kopf h1{ font: 800 var(--fs-quote-h1)/1.1 var(--f-disp); color: var(--c-ink); margin: 0 0 28px; }
.ke-lead{ font: 300 20px/1.7 var(--f-disp); color: var(--c-ink); max-width: 62ch; margin: 0; }
.ke-h2{ font: 800 1.6rem/1.3 var(--f-disp); color: var(--c-ink); margin: 0 0 28px; }

/* --- Die beiden Gruenderkarten --- */
.ke-kartengrid{ display: grid; grid-template-columns: 1fr 1fr; gap: var(--ke-kartengap); }
.ke-karte{ min-width: 0; text-align: center; --ke-ls-rolle: 5.5px; }
.ke-portrait{ aspect-ratio: var(--ke-portrait); overflow: hidden; margin-bottom: 26px; background: #ececec; }
.ke-portrait img{ width: 100%; height: 100%; object-fit: cover; display: block; }
.ke-name{ font: 800 var(--ke-name)/1.1 var(--f-disp); color: var(--c-accent); margin: 0 0 10px; }

/* Eine gesperrte Zeile traegt ihren Buchstabenabstand auch HINTER dem letzten Zeichen.
   Zentriert schiebt das den Satz um genau diesen Betrag nach links - der negative rechte
   Rand gleicht ihn aus. Nur im mittigen Zustand noetig. */
.ke-rolle{
  font: 500 15px/1.7 var(--f-mono); letter-spacing: var(--ke-ls-rolle);
  text-transform: uppercase; color: var(--c-ink);
  margin: 0 0 18px; margin-right: calc(-1 * var(--ke-ls-rolle));
}
.ke-zeile{ font: 300 var(--ke-zeile)/1.5 var(--f-disp); letter-spacing: 1px; margin: 0 0 6px; }
.ke-zeile a{ color: var(--c-accent); text-decoration: none; text-transform: uppercase; overflow-wrap: anywhere; }
.ke-zeile a:hover{ text-decoration: underline; }
.ke-vcf{ margin: 14px 0 0; }
.ke-vcf a{
  display: inline-block; font: 300 13px/1 var(--f-mono); letter-spacing: 3px;
  text-transform: uppercase; color: var(--c-accent); text-decoration: none;
  border: 1px solid var(--c-accent); border-radius: 50px; padding: 12px 24px;
}
.ke-vcf a:hover{ background: var(--c-accent); color: var(--c-white); }
.ke-gleich{ font: 300 16px/1.7 var(--f-disp); color: var(--c-ink); margin: 34px auto 0; max-width: 62ch; text-align: center; }

/* --- In drei Schritten (wartet auf den Wortlaut) --- */
.ke-schritte{ list-style: none; display: grid; grid-template-columns: repeat(3,1fr); gap: var(--ke-schrittgap); margin: 0; padding: 0; }
.ke-schritte li{ min-width: 0; }
.ke-nr{ display: block; font: 800 var(--ke-nr)/1 var(--f-disp); color: var(--c-accent); margin-bottom: 14px; }
.ke-schritte h3{ font: 800 1.2rem/1.4 var(--f-disp); color: var(--c-ink); margin: 0 0 10px; }
.ke-schritte p{ font: 300 16px/1.7 var(--f-disp); color: var(--c-ink); margin: 0; }

/* --- Checkliste (wartet auf den Wortlaut) --- */
.ke-liste{ list-style: none; margin: 0; padding: 0; max-width: 62ch; }
.ke-liste li{ font: 300 16px/1.7 var(--f-disp); color: var(--c-ink); padding-left: 26px; position: relative; margin-bottom: 22px; }
.ke-liste li::before{ content: ""; position: absolute; left: 0; top: 13px; width: 14px; height: 1px; background: var(--c-accent); }
.ke-liste b{ display: block; font: 800 1.02rem/1.5 var(--f-disp); color: var(--c-ink); margin-bottom: 4px; }

/* --- Formular hinter einem Pillen-Knopf. Der Ausloeser ist die Pille des Designsystems,
       kein Akkordeon; Plus und Minus als Marker. --- */
.ke-details{ border: 0; background: transparent; text-align: center; }
.ke-formknopf{
  display: inline-flex; align-items: center; gap: 14px; cursor: pointer;
  list-style: none; max-width: 100%;
  font: 300 13px/1.6 var(--f-mono); letter-spacing: 3px; text-transform: uppercase;
  color: var(--c-accent); background: transparent;
  border: 1px solid var(--c-accent); border-radius: 50px;
  padding: var(--ke-fpad) 34px; transition: background .2s, color .2s;
}
.ke-formknopf::-webkit-details-marker{ display: none; }
.ke-formknopf::before{ content: "+"; font-size: 1.5em; line-height: 1; flex: 0 0 auto; }
.ke-details[open] .ke-formknopf::before{ content: "\2212"; }
.ke-formknopf:hover{ background: var(--c-accent); color: var(--c-white); }
.ke-forminner{ text-align: left; max-width: 640px; margin: 30px auto 0; padding: 0; }
.ke-forminner .kform .btn-violet{ justify-self: start; }

/* --- Buero und Anreise. Die Anschrift bestimmt die erste Spalte (max-content, damit der
       Bueroname einzeilig steht), die uebrige Luft teilen sich die beiden anderen. --- */
.ke-bueroraster{ display: grid; grid-template-columns: max-content 1fr 1.4fr; gap: 32px 40px; }
.ke-bueroraster > *{ min-width: 0; }
.ke-blabel{ font: 500 13px/1.6 var(--f-mono); letter-spacing: 3px; text-transform: uppercase; color: var(--c-accent); margin: 0 0 10px; }
.ke-bueroraster p{ font: 300 16px/1.7 var(--f-disp); color: var(--c-ink); margin: 0; }
.ke-bueroraster a{ color: var(--c-ink); text-decoration: none; }
.ke-bueroraster a:hover{ color: var(--c-accent); }

/* --- Wo arbeitet OOW: Liniengrafik DACH. Die Strichstaerke bleibt beim Skalieren gleich
       (non-scaling-stroke), die Beschriftung skaliert mit - deshalb unter 900 px eine
       groessere Einheit. Der weisse Textumriss haelt Ortsnamen ueber Grenzlinien
       lesbar. --- */
.ke-orteraster{ display: grid; grid-template-columns: var(--ke-kartenbreite) 1fr; gap: 48px; align-items: start; }
.ke-orteraster > *{ min-width: 0; }
.karte-dach{ width: 100%; height: auto; display: block; }
.k-land{ fill: none; stroke: var(--c-ink); stroke-width: var(--ke-linie); stroke-linejoin: round; vector-effect: non-scaling-stroke; }
.k-ort{ cursor: pointer; }
.k-ort circle{ fill: var(--c-accent); r: var(--ke-punkt); transition: r .15s; }
.k-ort text{
  font: 300 var(--ke-ortgroesse) / 1 var(--f-mono); letter-spacing: 1.5px;
  text-transform: uppercase; fill: var(--c-ink);
  paint-order: stroke fill; stroke: #fff; stroke-width: 4px; stroke-linejoin: round;
}
.k-ort:hover circle{ r: calc(var(--ke-punkt) * 1.6); }
.k-ort:hover text{ fill: var(--c-accent); }
.ke-ortetext p{ font: 300 16px/1.7 var(--f-disp); color: var(--c-ink); margin: 0 0 20px; }
.ke-ortetext a{ color: var(--c-accent); text-decoration: none; }
.ke-ortetext a:hover{ text-decoration: underline; }

/* --- Weiterlesen --- */
.ke-pillreihe{ display: flex; flex-wrap: wrap; gap: 14px; }
.ke-pill{
  display: inline-block; font: 300 13px/1 var(--f-mono); letter-spacing: 3px;
  text-transform: uppercase; color: var(--c-ink); border: 1px solid var(--c-ink);
  border-radius: 50px; padding: 15px 30px; text-decoration: none; transition: .2s;
}
.ke-pill:hover{ background: var(--c-ink); color: var(--c-white); }

/* Umbruch: unter 861 px steht alles einspaltig. */
@media (max-width: 900px){
  .ke-orteraster{ grid-template-columns: 1fr; gap: 30px; }
  .ke-kartenfeld{ max-width: 480px; margin: 0 auto; }
  .k-ort text{ --ke-ortgroesse: 20px; }
}
@media (max-width: 860px){
  .ke-kartengrid{ grid-template-columns: 1fr; }
  .ke-schritte{ grid-template-columns: 1fr; }
  .ke-bueroraster{ grid-template-columns: 1fr; }
}
