/* ==========================================================================
   REELR · Base-Styles (Phase 2: Tokens & Typografie)
   Voraussetzung: css/tokens.css ist VOR dieser Datei eingebunden.
   Interaktions-Muster nach MEDIAKIT §3 (drei Prinzipien, monochrom):
   1) Invertierung (Button-Pill) 2) Unterstreichung (Links) 3) Border-Aufhellung
   ========================================================================== */

/* ------------------------------------------------------------- @font-face
   Self-hosted woff2-Subsets (Basic Latin + DE), font-display: swap.
   Kein CDN (MEDIAKIT §4). */

@font-face {
  font-family: "Clash Display";
  src: url("../assets/fonts/ClashDisplay-Medium.woff2") format("woff2");
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}

@font-face {
  font-family: "Clash Display";
  src: url("../assets/fonts/ClashDisplay-Semibold.woff2") format("woff2");
  font-weight: 600;
  font-style: normal;
  font-display: swap;
}

@font-face {
  font-family: "Satoshi";
  src: url("../assets/fonts/Satoshi-Regular.woff2") format("woff2");
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}

@font-face {
  font-family: "Satoshi";
  src: url("../assets/fonts/Satoshi-Medium.woff2") format("woff2");
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}

@font-face {
  font-family: "JetBrains Mono";
  src: url("../assets/fonts/JetBrainsMono-Regular.woff2") format("woff2");
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}

/* ------------------------------------------------------------------ Reset */

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

html {
  color-scheme: dark;
  -webkit-text-size-adjust: 100%;
  text-size-adjust: 100%;
}

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

button,
input,
select,
textarea {
  font: inherit;
  color: inherit;
}

/* ------------------------------------------------------------------- Base */

body {
  background: var(--reelr-bg);
  color: var(--reelr-text-2);
  font-family: var(--reelr-font-body);
  font-size: var(--reelr-fluid-body);
  line-height: var(--reelr-leading-body);
  letter-spacing: var(--reelr-tracking-body);
  -webkit-font-smoothing: antialiased;
}

h1,
h2,
h3 {
  font-family: var(--reelr-font-display);
  font-weight: 500;
  letter-spacing: var(--reelr-tracking-display);
  line-height: var(--reelr-leading-display);
  color: var(--reelr-text);
  text-wrap: balance;
}

h1 {
  font-size: var(--reelr-fluid-display);
  font-weight: 600;
}

h2 {
  font-size: var(--reelr-fluid-h2);
}

h3 {
  font-size: var(--reelr-fluid-h3);
}

p {
  max-width: 65ch;
}

strong {
  font-weight: 500;
  color: var(--reelr-text);
}

::selection {
  background: var(--reelr-text);
  color: var(--reelr-bg);
}

/* Sichtbarer Fokus als Doppelring (Kit-Token), auf allem Interaktiven */
:focus-visible {
  outline: none;
  box-shadow: var(--reelr-focus-ring);
  border-radius: var(--reelr-radius-sm);
}

/* --------------------------------------------------- Prinzip 2 · Der Link
   Unterstreichung ist immer da, nie nur Farbe als Unterscheidung. */

a {
  color: var(--reelr-text);
  text-decoration-line: underline;
  text-decoration-thickness: 1px;
  text-underline-offset: 0.22em;
  text-decoration-color: var(--reelr-text-3);
  transition: text-decoration-color var(--reelr-dur-fast) var(--ease-reelr-mass);
}

/* Touch-Verhalten (P7, Befund 3): kein Doppeltipp-Zoom-Delay auf
   Interaktivem; das mobile Tap-Highlight ist transparent (monochrom,
   das Feedback liefern die drei Kit-Prinzipien selbst). */
a,
button,
.btn {
  touch-action: manipulation;
  -webkit-tap-highlight-color: transparent;
}

@media (hover: hover) and (pointer: fine) {
  a:hover {
    text-decoration-color: var(--reelr-text);
  }
}

/* ------------------------------------------- Prinzip 1 · Die Button-Pill
   Invertiert: weisse Flaeche, schwarzes Label. Hover: Dim-Stufe +
   Border-Aufhellung. Press: leichtes Scale (haptisches Feedback). */

.btn {
  display: inline-flex;
  align-items: center;
  gap: var(--reelr-space-2);
  background: var(--reelr-accent);
  color: var(--reelr-on-accent);
  font-family: var(--reelr-font-body);
  font-size: var(--reelr-fluid-small);
  font-weight: 500;
  line-height: 1;
  text-decoration: none;
  border: 1px solid var(--reelr-border);
  border-radius: var(--reelr-radius-pill);
  padding: var(--reelr-space-4) var(--reelr-space-6);
  cursor: pointer;
  transition:
    background-color var(--reelr-dur-fast) var(--ease-reelr-mass),
    border-color var(--reelr-dur-fast) var(--ease-reelr-mass),
    transform var(--reelr-dur-fast) var(--ease-reelr-mass);
}

@media (hover: hover) and (pointer: fine) {
  .btn:hover {
    background: var(--reelr-accent-dim);
    border-color: var(--reelr-border-hover);
  }
}

.btn:active {
  transform: scale(0.97);
}

.btn:focus-visible {
  border-radius: var(--reelr-radius-pill);
}

/* -------------------------------- Prinzip 3 · Die Double-Bezel-Karte
   Aussenschale surface-1 (Radius lg) + innerer Kern surface-2 (Radius md),
   Inset 4 px, Radien konzentrisch: innen = aussen minus Inset.
   Hover: Border-Aufhellung, sonst Ruhe. */

.karte {
  background: var(--reelr-surface-1);
  border: 1px solid var(--reelr-border);
  border-radius: var(--reelr-radius-lg);
  padding: var(--reelr-bezel-inset);
  transition: border-color var(--reelr-dur-base) var(--ease-reelr-mass);
}

@media (hover: hover) and (pointer: fine) {
  .karte:hover {
    border-color: var(--reelr-border-hover);
  }
}

.karte > .karte-kern {
  background: var(--reelr-surface-2);
  border-radius: var(--reelr-radius-md); /* konzentrisch: lg minus Inset */
  padding: var(--reelr-space-6);
}

/* ------------------------------------------------------------- Mono-Label
   Timecode, Eyebrows, Meta. IMMER Versalien, +0,14 em.
   text-3 nur auf bg/bg-deep; auf Surfaces text-2 verwenden (Kontrastregel). */

.mono-label {
  font-family: var(--reelr-font-mono);
  font-size: var(--reelr-fluid-label);
  font-weight: 400;
  line-height: var(--reelr-leading-mono);
  letter-spacing: var(--reelr-tracking-label);
  text-transform: uppercase;
  color: var(--reelr-text-3);
}

.mono-label--surface {
  color: var(--reelr-text-2); /* auf surface-1/-2 (text-3 faellt dort unter AA) */
}

/* -------------------------------------------------------------- Letterbox
   2.39:1 auf bg-deep, das primaere Markenmotiv. Mit Timecode-Zeile und
   REC-Punkt (Phase 2: statisch, kein Puls). */

.letterbox {
  position: relative;
  z-index: var(--z-stage);
  aspect-ratio: var(--reelr-ratio-cinema);
  background: var(--reelr-bg-deep);
  border: 1px solid var(--reelr-border);
  border-radius: var(--reelr-radius-md);
  overflow: hidden;
  display: flex;
  align-items: center;
  justify-content: center;
}

.letterbox-tc {
  position: absolute;
  left: var(--reelr-space-4);
  right: var(--reelr-space-4);
  bottom: var(--reelr-space-3);
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--reelr-space-4);
}

.rec {
  display: inline-flex;
  align-items: center;
  gap: var(--reelr-space-2);
}

.rec::before {
  content: "";
  width: 8px;
  height: 8px;
  border-radius: var(--reelr-radius-pill);
  background: var(--reelr-accent); /* REC-Punkt ist reines Weiss (Kit §3) */
}

/* ==========================================================================
   Phase 3 · One-Pager (statisch) · 7 Sektionen = 7 Layout-Familien (v1.1
   Schritt 3: Studio-Sektion ersatzlos entfernt, der Schluss ist gestrafft)
   1 Hero (Full-Bleed, Copy links unten)  2 Marken-Streifen (eine Zeile)
   3 Markenbau (Sticky-Buehne, v1.1)      4 Zweiakter MARKE/BUEHNE (v1.1)
   5 Cases (horizontaler Streifen)        6 Prozess (Hairline-Grid)
   7 Finale (typografisch, bg-deep)
   ========================================================================== */

html {
  scroll-behavior: smooth; /* Fallback ohne JS; mit Lenis unten neutralisiert */
  /* Horizontal-Overscroll-Sperre (v1.1 Fix), Teil 1: mit clip auch auf
     html propagiert das body-clip NICHT mehr an den Viewport, sondern
     body clippt seinen Inhalt selbst (Regel unten). Nur auf body war das
     Dokument im Desktop-Pin-Modus ~1400 px programmatisch ueberscrollbar
     (Cases-Strip unclipped; Cmd+F/scrollIntoView schob die Seite dauerhaft
     nach rechts, ohne Weg zurueck). clip statt hidden: erzeugt keinen
     Scroll-Container, CSS-sticky (Hero, Markenbau) bleibt intakt. */
  overflow-x: clip;
}

/* Anker-Ziele (v1.1): die fixe Glass-Nav ist entfallen, es schwebt
   nichts mehr ueber der Seite - der Offset ist nur noch Atemluft fuer
   Deep-Links (reelr.de/#leistungen etc.), keine Kollisionsvermeidung. */
[id] {
  scroll-margin-top: 1.5rem;
}

/* Lenis-Handshake (P4a): Lenis setzt die Klassen selbst auf <html>.
   Natives smooth-Scrolling abgeben, sonst kaempfen zwei Scroller. */
html.lenis,
html.lenis body {
  height: auto;
}

html.lenis {
  scroll-behavior: auto; /* Lenis aktiv: native Smooth-Easing komplett aus */
}

.lenis.lenis-smooth {
  scroll-behavior: auto !important;
}

.lenis.lenis-stopped {
  overflow: hidden;
}

/* Horizontal-Overscroll-Sperre, Teil 2 (siehe html-Regel oben): body
   clippt den Cases-Strip u.a. an der eigenen Kante - das Dokument hat
   keinen horizontalen Scroll-Ueberhang mehr (scrollWidth == clientWidth),
   window.scrollTo(x > 0) laeuft ins Leere. */
body {
  overflow-x: clip;
}

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

/* Volle-Breite-Streifen (Logo-Wall, Cases): linke Kante buendig zum Container */
.marken-strip,
.cases-strip {
  padding-inline: calc(max(0px, 50vw - 45rem) + var(--reelr-gutter));
}

.skip-link {
  position: fixed;
  top: var(--reelr-space-2);
  left: var(--reelr-space-2);
  z-index: var(--z-overlay);
  transform: translateY(-250%);
  background: var(--reelr-accent);
  color: var(--reelr-on-accent);
  font-weight: 500;
  text-decoration: none;
  padding: var(--reelr-space-3) var(--reelr-space-4);
  border-radius: var(--reelr-radius-sm);
}

.skip-link:focus-visible {
  transform: none;
}

/* ------------------------------------------------------ Grain (statisch)
   Dezenter SVG-Noise, NUR auf Markenflaechen und Marken-Atmosphaeren
   (MEDIAKIT §6). Nie auf Kundenfootage: Case-Stages bleiben frei. */

.grain {
  position: relative;
}

.grain::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  pointer-events: none;
  border-radius: inherit;
  opacity: var(--reelr-grain-opacity);
  background-image: url("data:image/svg+xml,%3Csvg%20xmlns='http://www.w3.org/2000/svg'%20width='160'%20height='160'%3E%3Cfilter%20id='n'%3E%3CfeTurbulence%20type='fractalNoise'%20baseFrequency='0.9'%20numOctaves='2'%20stitchTiles='stitch'/%3E%3CfeColorMatrix%20type='saturate'%20values='0'/%3E%3C/filter%3E%3Crect%20width='160'%20height='160'%20filter='url(%23n)'/%3E%3C/svg%3E");
  background-size: 160px 160px;
}

/* ----------------------------------------------------- Media in Buehnen */

.letterbox picture {
  position: absolute;
  inset: 0;
}

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

.letterbox-tc {
  z-index: 3;
}

.stage-platzhalter {
  position: relative;
  z-index: 1;
  text-align: center;
  padding-inline: var(--reelr-space-4);
}

/* ------------------------------------------- Wortmarken-Link (Rechtsseiten)
   Die fixe Glass-Pill-Nav der Startseite ist mit v1.1 entfallen (Robert,
   2026-07-07); dort traegt .hero-marke die nackte Wortmarke auf der
   Hero-Buehne. Diese Regeln nutzen nur noch die Koepfe von
   impressum.html/datenschutz.html. */

.nav-marke {
  display: inline-flex;
  align-items: center;
  text-decoration: none;
  border-radius: var(--reelr-radius-sm);
}

.nav-marke img {
  width: 98px;
  height: auto;
}

/* ------------------------------------------ S1 · HERO · v1.1 Full-Bleed
   "Full-Bleed Monolith + Scroll-Zerfall" (Mockup freigegeben). Der
   Monolith fuellt den ersten Viewport randlos; die UI liegt als
   HUD-Schicht AUF der Szene (Copy oben links, Timecode unten links,
   Meta-Bezel unten rechts, Mikro-Zeile unten mittig). Die Sektion ist
   hoeher als der Viewport (Scroll-Runway fuer den Zerfall), die Buehne
   klebt per CSS-sticky - KEIN dritter GSAP-Pin (Pin-Budget v3.5).
   HUD-Rand = Container-Geometrie der Nav/Streifen (buendige Kanten). */

.hero {
  --hero-rand: calc(max(0px, 50vw - 45rem) + var(--reelr-gutter));
  position: relative;
}

/* Ohne-JS-Gate (v1.1 Fix): die Scroll-Runways gibt es NUR, wenn der
   Motion-Stack wirklich laeuft (main.js setzt html.js nach dem GSAP-Gate).
   Ohne JS bespielt niemand die sticky Buehnen - der Hero waere 100svh
   toter Scroll, das Markenbau-Totem bliebe hinter overflow:hidden
   unvollstaendig. Default (ohne .js) kollabieren beide Sektionen auf
   natuerliche Hoehe, alles steht statisch komplett im normalen Fluss. */
/* Runway 340svh (v1.2, Robert-Feedback: mehr Scrollweg, der Zerfall
   atmet - vorher 200svh; die Fragment-Mappings sind relativ und
   stretchen mit). */
.js .hero {
  height: 340svh;
}

.hero-buehne {
  position: sticky;
  top: 0;
  height: 100svh;
  overflow: hidden;
  background: #060606; /* Basis-Grund der Zerfall-Buehne (Prototyp 1:1) */
}

/* Stage mit Bleed: Maus-Parallax (Tiefe 0.4, max. ~7 px horizontal /
   ~4.4 px vertikal) UND die Schwebe-Rotation + das vertikale Treiben
   (v1.3 Fix B, +-3.8 Grad / +-9 px, main.js Block 3d) legen keine
   Kanten frei. Rotations-Geometrie unveraendert: der Ecken-Fehlbetrag
   einer um theta gedrehten Buehne ist ~(W/2)*sin(theta) vertikal bzw.
   (H/2)*sin(theta) horizontal - bei 3.8 Grad (sin 0.0663) also
   ~3.3 vw / ~3.3 svh, mit Rundungs-Reserve 3.6/3.6. Die Flach-Reserven
   (Parallax + ggf. Treiben) sind PRO ACHSE verschieden, weil Treiben
   nur vertikal wirkt: oben/unten braucht Parallax-Y (4.4 px) + Treiben
   (9 px) + Marge = 15 px; links/rechts braucht nur Parallax-X (7.2 px)
   + Marge = 8 px (unveraendert). */
.hero-stage {
  position: absolute;
  inset: calc(-3.6vw - 15px) calc(-3.6svh - 8px);
  z-index: 1;
  will-change: transform;
}

/* Statisches Fallback-Bild (LCP; ohne JS die ganze Buehne): Cover-
   Naeherung der Canvas-Regie (Fokus mittig-rechts, Zoom 1.12). Mit JS
   rahmt heroBildRahmen() das Bild exakt wie den Canvas (main.js). */
.hero-stage-bild {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  max-width: none;
  object-fit: cover;
  object-position: 0% 52%;
  transform: scale(1.12);
  transform-origin: 0% 54%;
}

@media (orientation: portrait) {
  .hero-stage-bild {
    object-position: 50% 52%;
    transform: scale(1.15);
    transform-origin: 50% 60%;
  }
}

.hero-stage-canvas {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
}

/* Weiche Licht-Scrims: keine Kaesten, nur Verlaeufe zum Setzen der UI */
.hero-scrim {
  position: absolute;
  z-index: 3;
  pointer-events: none;
}

.hero-scrim--oben {
  inset: 0 0 auto 0;
  height: 22vh;
  background: linear-gradient(to bottom, rgba(0, 0, 0, 0.42), rgba(0, 0, 0, 0));
}

.hero-scrim--unten {
  inset: auto 0 0 0;
  height: 20vh;
  background: linear-gradient(to top, rgba(0, 0, 0, 0.4), rgba(0, 0, 0, 0));
}

.hero-scrim--copy {
  left: 0;
  top: 0;
  width: 62vw;
  height: 66vh;
  background: radial-gradient(120% 100% at 10% 32%, rgba(0, 0, 0, 0.48), rgba(0, 0, 0, 0) 72%);
}

.hero-orbits {
  position: absolute;
  inset: 0;
  z-index: 4;
  width: 100%;
  height: 100%;
  pointer-events: none;
  will-change: transform;
}

/* Grain der Buehne liegt ueber ALLEN Hero-Ebenen (Prototyp: z 9) */
.hero-buehne.grain::after {
  z-index: 9;
}

/* ------------------------------------ S1 · HUD-Schicht (auf der Szene) */

/* Nackte Wortmarke oben links (v1.1, ersetzt die fixe Pill-Nav): ruhige
   Ebene AUF der Szene, ueber Scrims/Orbits, unter dem Grain (z 9). Sitzt
   in der sticky Buehne und scrollt mit dem Hero weg. Groesse und Abstand
   orientiert an der alten Logo-Position (98 px, oberer Saum); die linke
   Kante liegt auf dem HUD-Raster (buendig mit Copy und Timecode). */
.hero-marke {
  position: absolute;
  z-index: 8;
  left: var(--hero-rand);
  top: 1.9rem;
}

.hero-marke img {
  display: block;
  width: 98px;
  height: auto;
}

.hero-copy {
  position: absolute;
  z-index: 7;
  left: var(--hero-rand);
  top: clamp(6.5rem, 16svh, 10rem);
  max-width: min(760px, 58vw);
  will-change: opacity, transform;
}

.hero-headline {
  font-size: clamp(3.2rem, 6.6vw, 6.2rem);
  font-weight: 500;
  line-height: 1;
}

.hero-subline {
  margin-top: 1.75rem;
  font-size: 1.125rem;
  color: var(--reelr-text-2);
  max-width: 42ch;
}

.hero-cta {
  margin-top: 2.6rem;
  max-width: none;
}

/* CTA als unterstrichener Mono-Textlink (Prinzip 2: die Linie ist der Link) */
.hero-cta-link {
  display: inline-flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 2.5rem;
  min-width: 340px;
  font-family: var(--reelr-font-mono);
  font-size: 0.8125rem;
  letter-spacing: var(--reelr-tracking-label);
  text-transform: uppercase;
  color: var(--reelr-text);
  text-decoration: none;
  padding-bottom: 0.7rem;
  border-bottom: 1px solid rgba(250, 250, 250, 0.42);
  transition: border-bottom-color var(--reelr-dur-fast) var(--ease-reelr-mass);
}

@media (hover: hover) and (pointer: fine) {
  .hero-cta-link:hover {
    border-bottom-color: var(--reelr-accent);
  }
}

.hero-cta-pfeil {
  letter-spacing: 0;
}

.hero-hud {
  position: absolute;
  z-index: 7;
  left: var(--hero-rand);
  bottom: 1.9rem;
  color: rgba(250, 250, 250, 0.78);
  white-space: nowrap;
}

.hero-hud-sep {
  color: var(--reelr-text-3);
  margin-inline: 0.55em;
}

/* Meta-Bezel unten rechts: Mini-Double-Bezel (Kit-Prinzip 3) */
.hero-meta {
  position: absolute;
  z-index: 7;
  right: var(--hero-rand);
  bottom: 1.9rem;
  padding: var(--reelr-bezel-inset);
  background: rgba(18, 18, 18, 0.55);
  border: 1px solid var(--reelr-border);
  border-radius: var(--reelr-radius-lg);
  -webkit-backdrop-filter: blur(10px);
  backdrop-filter: blur(10px);
}

.hero-meta-kern {
  display: flex;
  align-items: stretch;
  background: rgba(26, 26, 26, 0.55);
  border-radius: var(--reelr-radius-md);
}

.hero-meta-zelle {
  display: flex;
  align-items: center;
  padding: 0.8rem 1.1rem;
  font-family: var(--reelr-font-mono);
  font-size: 0.6875rem;
  letter-spacing: var(--reelr-tracking-label);
  text-transform: uppercase;
  color: var(--reelr-text-2);
  white-space: nowrap;
}

.hero-meta-zelle + .hero-meta-zelle {
  border-left: 1px solid var(--reelr-border);
}

.hero-micro {
  position: absolute;
  z-index: 7;
  left: 50%;
  bottom: 2.1rem;
  transform: translateX(-50%);
  font-family: var(--reelr-font-mono);
  font-size: 0.6875rem;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  /* text-2 statt text-3 (v1.1 Fix): die Zeile liegt auf dem Bild-Dunst,
     nicht auf bg/bg-deep (Kit-Regel). Gemessen (CDP, hellster Pixel im
     Band): #A8A8A8 = 6,0:1 desktop / 5,3:1 mobil >= AA 4,5:1;
     #7C7C7C lag mit 3,4:1 darunter. */
  color: var(--reelr-text-2);
  white-space: nowrap;
}

/* Mobil (<768): kein Fragment-Canvas - sanftes Aufloesen traegt der
   Motion-Branch auf der Stage; der Runway ist kuerzer. */
@media (max-width: 767px) {
  .js .hero {
    height: 290svh; /* v1.2: vorher 170svh (Runway-Streckung, s.o.) */
  }
  /* v1.4.2: Canvas mobil SICHTBAR - der Zerfall laeuft als Light-Stufe
     (72 Fragmente, main.js); die alte Mobil-Sperre ist aufgehoben. */
}

/* reduced-motion: der Canvas malt nie - das gerahmte Standbild steht */
@media (prefers-reduced-motion: reduce) {
  .hero-stage-canvas {
    display: none;
  }
}

@media (max-width: 640px) {
  .hero-scrim--oben {
    height: 42vh;
    background: linear-gradient(to bottom, rgba(0, 0, 0, 0.68) 30%, rgba(0, 0, 0, 0));
  }

  .hero-scrim--copy {
    width: 100vw;
    height: 52vh;
    background: radial-gradient(130% 100% at 18% 26%, rgba(0, 0, 0, 0.55), rgba(0, 0, 0, 0) 74%);
  }

  .hero-copy {
    top: 5.8rem;
    max-width: calc(100vw - 2.5rem);
  }

  .hero-headline {
    font-size: clamp(2rem, 9vw, 2.9rem);
  }

  .hero-subline {
    margin-top: 1.2rem;
    font-size: 0.9375rem;
    max-width: 32ch;
    color: rgba(230, 230, 230, 0.92);
  }

  .hero-cta {
    margin-top: 1.9rem;
  }

  .hero-cta-link {
    min-width: 0;
    width: 100%;
    font-size: 0.75rem;
  }

  .hero-hud {
    bottom: 1.15rem;
    font-size: 0.5625rem;
  }

  .hero-hud-ratio {
    display: none;
  }

  .hero-meta {
    bottom: 0.9rem;
    padding: 3px;
  }

  .hero-meta-zelle {
    padding: 0.5rem 0.55rem;
    font-size: 0.5rem;
    letter-spacing: 0.1em;
  }

  .hero-micro {
    bottom: 3.6rem;
    font-size: 0.5625rem;
    letter-spacing: 0.16em;
  }
}

/* Mobil laeuft sanftes Aufloesen statt Zerfall (Motion-Branch 3a):
   "zum Zerlegen" wuerde etwas Falsches ankuendigen - unter 768px steht
   nur "Scrollen" (v1.1 Fix; Breakpoint = Fragment-Gate min-width 768). */
@media (max-width: 767px) {
  .hero-micro-voll {
    display: none;
  }
}

.eyebrow {
  margin-bottom: var(--reelr-space-3);
}

/* --------------------------------- S2 · LOGO-WALL · einzeiliger Streifen
   Naht 1 (Contract v3.3.1, Continuous Stage): keine Border, kein eigener
   Grund - die Naht im dunklen Akt ist unsichtbar. Desktop overlappt S2 den
   Hero-Ausklang (-15vh, z-2); der Inhalt bleibt per Padding-Ausgleich
   unterhalb der Hero-Copy (nur ~5vh frueherer Peek, keine Kollision). */

.marken {
  padding-block: clamp(3rem, 2rem + 3vw, 5rem);
}

@media (min-width: 1024px) {
  .marken {
    position: relative;
    z-index: 2;
    margin-top: -15vh;
    padding-top: calc(clamp(3rem, 2rem + 3vw, 5rem) + 10vh);
  }
}

.marken-intro {
  font-size: var(--reelr-text-base); /* 16px: Kit-Mindestgroesse fuer Fliesstext (v1.1 Fix, vorher fluid-small = 15px) */
  color: var(--reelr-text-3);
  margin-bottom: var(--reelr-space-6);
}

.marken-strip {
  display: flex;
  overflow-x: auto;
  overscroll-behavior-x: contain; /* P7, Befund 4: keine Browser-Back-Geste am Streifenende */
  padding-block: var(--reelr-space-4);
  scrollbar-width: thin;
  scrollbar-color: var(--reelr-border) transparent;
  -webkit-mask-image: linear-gradient(90deg, transparent, #000 1.5rem, #000 calc(100% - 1.5rem), transparent);
  mask-image: linear-gradient(90deg, transparent, #000 1.5rem, #000 calc(100% - 1.5rem), transparent);
}

/* Fokus-Ring vs. Kanten-Maske (P7, Befund 1): die mask-image-Rampe
   beschneidet ALLES, was das Element selbst zeichnet - auch box-shadow
   und outline. Bei Tastatur-Fokus faellt die Maske deshalb weg (der
   volle Streifen ist im Fokusmoment ohnehin die ehrlichere Ansicht),
   der Ring laeuft als outline mit Offset. */
.marken-strip:focus-visible {
  -webkit-mask-image: none;
  mask-image: none;
  box-shadow: none;
  outline: 2px solid var(--reelr-text);
  outline-offset: 2px;
}

.marken-strip::-webkit-scrollbar {
  height: 4px;
}

.marken-strip::-webkit-scrollbar-thumb {
  background: var(--reelr-border);
  border-radius: var(--reelr-radius-pill);
}

.marken-track {
  display: flex;
  align-items: baseline;
  gap: clamp(2.5rem, 5vw, 4.5rem);
}

.marken-track span {
  flex: 0 0 auto;
  white-space: nowrap;
  font-family: var(--reelr-font-body);
  font-weight: 500;
  font-size: var(--reelr-text-lg);
  color: var(--reelr-text-3);
}

/* Marquee-Modus (setzt NUR der Motion-Branch per Klasse): Loop statt Scroll.
   Der Track-Klon haengt als zweites Flex-Kind, beide laufen xPercent -100. */
.marken-strip.ist-marquee {
  overflow: hidden;
}

.marken-strip.ist-marquee .marken-track {
  padding-inline-end: clamp(2.5rem, 5vw, 4.5rem); /* Fugenmass = Item-Gap */
  will-change: transform;
}

/* ------------------------ S3 · MARKENBAU · v1.3 "Galaxie + Meteoriten"
   Konzept v3, Logik 1:1 aus dem freigegebenen Prototyp (mediakit/
   referenzen/website-umbau-v1.1/marke-mockup-v3/index.html): die Buehne
   IST der Viewport (full-bleed). Ebene 1 Galaxie-Backdrop (cover),
   Ebene 2 Totem-Cutout mittig (contain 72svh/86vw, Mitte 50%/47% -
   dieselbe Geometrie rechnet der Canvas); Szene-Ebenen (Galaxie, Totem,
   Canvas, Schleier, Boden-Scrim) liegen absolut; Text-Overlay und
   Spruch stehen im Fluss (flex space-between) - dadurch ist die
   Geometrie mit und ohne JS identisch, nur Hoehe und Sticky
   unterscheiden sich. Die Sektion traegt den Scroll-Runway, die Buehne
   klebt per CSS-sticky (Hero-Muster, KEIN GSAP-Pin). Ohne JS und mit
   reduced-motion: Galaxie + fertiges Totem-Cutout statisch, Text +
   Spruch sichtbar, natuerliche Hoehe (kein toter Scroll). */

/* Runway 560svh (v1.2, Robert-Feedback: mehr Scrollweg): Text-Aufloesung
   + Partikel-Assembly + Spruch + Ruhe-Beat + Saallicht-Curtain atmen in
   Ruhe (Mapping in main.js, Block 4; die Fenster sind relativ und
   stretchen mit). */
.markenbau {
  position: relative;
}

/* Runway + Sticky nur mit JS (Ohne-JS-Gate, siehe Hero): ohne .js steht
   die Buehne als EIN Viewport im normalen Fluss - kein toter Scroll. */
.js .markenbau {
  height: 560svh;
}

.js .markenbau-buehne {
  position: sticky;
  top: 0;
  height: 100svh;
}

.markenbau-buehne {
  position: relative;
  min-height: 100svh;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  overflow: hidden;
  background: var(--reelr-bg-deep);
}

/* Ebene 1 · Galaxie-Backdrop: zentriertes Cover = Cover-Mathe des
   Canvas-Atlas (main.js malt exakt dieselbe Geometrie darueber). */
.markenbau-galaxie {
  position: absolute;
  inset: 0;
  z-index: 1;
  width: 100%;
  height: 100%;
  object-fit: cover;
}

/* Ebene 2 · Totem-Cutout: contain-Formel des Prototyps als CSS -
   ts = min(0.72*H/natH, 0.86*W/natW) ist exakt max-height 72svh +
   max-width 86vw bei width/height:auto; Mitte 50%/47% (OBJ_CX/CY). */
.markenbau-totem {
  position: absolute;
  left: 50%;
  top: 47%;
  z-index: 1;
  transform: translate(-50%, -50%);
  width: auto;
  height: auto;
  max-width: 86vw;
  max-height: 72svh;
}

.markenbau-canvas {
  position: absolute;
  inset: 0;
  z-index: 2;
  width: 100%;
  height: 100%;
}

/* 42%-Ruheschleier (Prototyp v3 1:1, rgba(5,5,5,0.42)): Lesbarkeit des
   Text-Overlays auf dem Sternenfeld bei p=0; den Fade steuert NUR der
   Motion-Branch - ohne JS steht er, der Text liegt dauerhaft lesbar
   auf der kompletten Szene. */
.markenbau-schleier {
  position: absolute;
  inset: 0;
  z-index: 3;
  background: rgba(5, 5, 5, 0.42);
  pointer-events: none;
}

/* Boden-Scrim fuer den Spruch (Prototyp: Canvas-Gradient, hier DOM, weil
   der Spruch DOM ist); Einblendung setzt der Motion-Branch, ohne JS
   steht er unter dem sichtbaren Spruch. */
.markenbau-boden {
  position: absolute;
  inset: auto 0 0 0;
  z-index: 3;
  height: 42vh; /* Prototyp v3: Gradient ab 0.58 H, Ziel-Alpha 0.45 */
  background: linear-gradient(to bottom, rgba(0, 0, 0, 0), rgba(0, 0, 0, 0.45));
  pointer-events: none;
}

/* Text-Overlay (Sektions-Einstieg): loest sich im Motion-Branch auf
   (Opacity + Drift Richtung Buehne + Blur bis ~7px, main.js). */
.markenbau-overlay {
  position: relative;
  z-index: 4;
  padding-top: clamp(2.5rem, 4.5vw, 4rem);
  will-change: opacity, transform, filter;
}

.markenbau-wortmarke {
  padding-inline: var(--reelr-gutter);
}

.markenbau-wortmarke img {
  width: 100%;
  height: auto;
}

.markenbau-zeile {
  display: grid;
  grid-template-columns: minmax(0, 7fr) minmax(0, 3fr);
  align-items: end;
  gap: clamp(2rem, 6vw, 6rem);
  padding-inline: var(--reelr-gutter);
  margin-top: clamp(3.5rem, 6.5vw, 6rem);
}

.markenbau-statement {
  font-size: clamp(2.4rem, 5.4vw, 4.9rem);
  line-height: 1.04;
}

.markenbau-mono {
  font-family: var(--reelr-font-mono);
  font-size: 0.8125rem;
  line-height: 1.6;
  color: var(--reelr-text-2);
  display: flex;
  flex-direction: column;
  gap: 2.75rem;
  padding-bottom: 0.35em;
}

.markenbau-scrollhinweis {
  align-self: flex-start;
}

/* Abschluss-Spruch: ECHTES DOM-Element (SEO/A11y, nie Canvas-Text),
   Clash Display auf Papierweiss, unteres Drittel zentriert (Mockup-
   Referenz V2-4); die Einblendung setzt NUR der Motion-Branch - ohne
   JS und mit reduced-motion steht der Spruch sichtbar. */
.markenbau-spruch {
  position: relative;
  z-index: 4;
  margin-bottom: 11vh;
  padding-inline: var(--reelr-gutter);
  text-align: center;
  font-family: var(--reelr-font-display);
  font-weight: 500;
  font-size: clamp(3rem, 5.4vw, 5rem);
  line-height: 1.05;
  letter-spacing: -0.01em;
  color: var(--reelr-text);
  text-shadow: 0 2px 28px rgba(0, 0, 0, 0.55);
  will-change: opacity, transform;
}

@media (max-width: 720px) {
  .markenbau-zeile {
    grid-template-columns: 1fr;
    align-items: start;
    margin-top: 3rem;
    gap: 2.25rem;
  }

  .markenbau-mono {
    gap: 1.75rem;
    padding-bottom: 0;
  }

  .markenbau-spruch {
    margin-bottom: 14vh;
    font-size: clamp(2.1rem, 9vw, 3rem);
  }
}

/* Kuerzerer Runway mobil (Hero-Analogie; v1.2: vorher 290svh); das
   Meteoriten-Rig laeuft auch hier, nur mit groesserer Zellgroesse
   (40px statt 32px = weniger Fragmente, und ohne Tiefen-Blur -
   Performance, main.js). */
@media (max-width: 767px) {
  .js .markenbau {
    height: 480svh;
  }
}

/* Saallicht-Curtain (Naht Akt I/II, trionn-exakt uebersetzt): 5 leere
   Streifen, paper, transform-only. margin/padding-Trick gegen Subpixel-
   Fugen. v1.1 Schritt 3: wohnt auf der Markenbau-Buehne und wipet im
   letzten Runway-Siebtel (main.js, Block 4; Wipe ab 0.86); Volldeckung
   faellt exakt auf den Sticky-Release, Akt II schliesst im normalen
   Fluss an. Den
   Flex-Modus schaltet NUR der Motion-Branch - ohne JS, mit reduced-motion
   oder Save-Data bleibt der Vorhang display:none (harter Schnitt, v3.6). */
.saallicht-curtain {
  position: absolute;
  inset: 0;
  z-index: 30;
  display: none; /* nur der Motion-Branch schaltet auf flex */
  flex-direction: column;
  pointer-events: none;
}

.curtain-streifen {
  flex: 1;
  background: var(--reelr-paper);
  transform-origin: center bottom;
  will-change: transform;
  margin-top: -1px;
  padding-bottom: 1px;
}

/* ------------------- S4 · LEISTUNGEN · v1.1 Zweiakter MARKE/BUEHNE
   V2 "Das Buehnenbild" als Basis + V1-Lichtkorridor als full-bleed
   Szenenwechsel (Robert, 2026-07-07; Prototypen: mediakit/referenzen/
   website-umbau-v1.1/leistungen-mockup/v1.html + v2.html). Papier-Akt:
   alle Farben sind die remappten Kit-Token (.akt-papier). Die grossen
   Akt-Worte laufen auf der Hero-Skala (Kit-clamp); Hairline-Hierarchie:
   das Triptychon traegt Ink-Linien (Statement), das Programm die leise
   Paper-Hairline. Ersetzt das v1.0-Bento. */

.leistungen {
  padding-block: clamp(4.5rem, 3rem + 5vw, 8rem) 0;
}

.leistungen-kopf {
  position: relative;
  padding-bottom: clamp(4rem, 7vw, 7rem);
}

.leistungen-kopf h2 {
  font-size: clamp(2.75rem, 6.4vw, 5.5rem);
  font-weight: 600;
}

/* Zweite Zeile springt ein (produx-Geste, Prototyp 1:1) */
.leistungen-einzug {
  display: inline-block;
  padding-left: clamp(2rem, 12vw, 11rem);
}

.leistungen-kopf-meta {
  position: absolute;
  right: 0;
  top: 0.25rem;
  text-align: right;
}

/* Akt-Label: Mono-Zeile mit auslaufender Hairline */
.akt-label {
  display: flex;
  align-items: center;
  gap: var(--reelr-space-4);
}

.akt-label::after {
  content: "";
  flex: 1;
  height: 1px;
  background: var(--reelr-border);
}

.akt-zeile {
  display: flex;
  align-items: flex-end;
  justify-content: space-between;
  gap: var(--reelr-space-8);
  flex-wrap: wrap;
  padding-top: var(--reelr-space-3);
}

.akt-wort {
  font-family: var(--reelr-font-display);
  font-weight: 600;
  font-size: var(--reelr-fluid-hero);
  line-height: var(--reelr-leading-display);
  letter-spacing: var(--reelr-tracking-display);
  color: var(--reelr-text);
  max-width: none;
}

.akt-claim {
  font-size: var(--reelr-text-xl);
  line-height: 1.35;
  max-width: 24ch;
  padding-bottom: 0.6em;
}

/* ---- Akt I · MARKE · Triptychon mit Treppen-Staffelung */

.triptychon {
  list-style: none;
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: clamp(1.5rem, 3vw, 3rem);
  margin-top: clamp(3rem, 5vw, 4.5rem);
}

.stufe {
  border-top: 1px solid var(--reelr-text); /* Ink-Linie: die Marke ist das Statement */
  padding-top: var(--reelr-space-4);
}

/* Die Marke baut sich auf: Stufe fuer Stufe tiefer */
.stufe:nth-child(2) { margin-top: 4.5rem; }
.stufe:nth-child(3) { margin-top: 9rem; }

.stufe-idx {
  display: block;
  margin-bottom: clamp(1.25rem, 2.4vw, 2.25rem);
}

.stufe h3 {
  font-size: clamp(1.75rem, 2.6vw, 2.5rem);
  margin-bottom: var(--reelr-space-3);
}

/* ---- Szenenwechsel · Lichtkorridor (full-bleed, Kit-Kader 2.39:1) */

.szenenwechsel {
  position: relative;
  margin-top: clamp(4rem, 8vw, 7rem);
}

.szenenwechsel-kader {
  overflow: hidden; /* clippt den Parallax-Zoom des Motion-Branch */
  aspect-ratio: var(--reelr-ratio-cinema);
  background: var(--reelr-bg-deep);
}

.szenenwechsel-kader img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.szenenwechsel figcaption {
  position: absolute;
  left: calc(max(0px, 50vw - 45rem) + var(--reelr-gutter));
  bottom: 0;
  transform: translateY(50%);
  background: var(--reelr-paper);
  color: var(--reelr-text-3);
  padding: var(--reelr-space-1) var(--reelr-space-4);
  display: flex;
  align-items: center;
  gap: var(--reelr-space-3);
}

.szenenwechsel figcaption::before {
  content: "";
  width: 40px;
  height: 1px;
  background: var(--reelr-text-3);
}

/* ---- Akt II · BUEHNE · Split-Stage, das Akt-Wort ragt in die Stage */

.akt-buehne {
  margin-top: clamp(4.5rem, 8vw, 7.5rem);
  padding-bottom: clamp(6rem, 10vw, 9rem);
}

.buehne-kopf {
  position: relative;
  z-index: 2; /* das ueberhaengende Akt-Wort liegt AUF der Stage */
}

.akt-zeile--buehne .akt-wort {
  margin-bottom: -0.42em; /* Ueberhang in die Stage (Prototyp 1:1) */
}

.buehne-split {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 6fr);
  gap: clamp(2rem, 4.5vw, 4.5rem);
  align-items: start;
}

.buehne-stage {
  position: relative;
  grid-column: 2;
  grid-row: 1;
}

.buehne-stage img {
  width: 100%;
  aspect-ratio: var(--reelr-ratio-feed); /* 4:5, das Feed-Format als Buehne */
  object-fit: cover;
}

.buehne-stage figcaption {
  position: absolute;
  left: 0;
  bottom: 0;
  transform: translateY(50%);
  background: var(--reelr-paper);
  color: var(--reelr-text-3);
  padding: var(--reelr-space-1) var(--reelr-space-4) var(--reelr-space-1) 0;
  display: flex;
  align-items: center;
  gap: var(--reelr-space-3);
}

.buehne-stage figcaption::after {
  content: "";
  width: 40px;
  height: 1px;
  background: var(--reelr-text-3);
}

.programm {
  list-style: none;
  grid-column: 1;
  grid-row: 1;
  padding-top: clamp(3rem, 6vw, 6rem);
}

.programm li {
  border-top: 1px solid var(--reelr-border);
  padding-block: clamp(1.5rem, 2.6vw, 2.5rem);
  display: grid;
  grid-template-columns: 4.5rem 1fr;
  gap: var(--reelr-space-4);
}

.programm li:last-child {
  border-bottom: 1px solid var(--reelr-border);
}

.programm-idx {
  padding-top: 0.55em;
}

.programm h3 {
  font-size: clamp(1.5rem, 2.2vw, 2.125rem);
  margin-bottom: var(--reelr-space-2);
}

.programm p {
  max-width: 55ch;
}

@media (max-width: 767px) {
  .leistungen-kopf-meta {
    position: static;
    text-align: left;
    margin-top: var(--reelr-space-4);
  }

  .leistungen-einzug {
    padding-left: 1.25rem;
  }

  .akt-claim {
    font-size: 1.25rem;
    padding-bottom: 0;
  }

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

  .stufe:nth-child(2),
  .stufe:nth-child(3) {
    margin-top: 0;
  }

  .stufe:nth-child(2) { margin-left: 1.5rem; }
  .stufe:nth-child(3) { margin-left: 3rem; }

  .szenenwechsel-kader {
    aspect-ratio: 16 / 10; /* mobil hoeher kadriert (Prototyp) */
  }

  .akt-zeile--buehne .akt-wort {
    margin-bottom: -0.28em;
  }

  .buehne-split {
    grid-template-columns: 1fr;
    gap: 0;
  }

  .buehne-stage {
    grid-column: 1;
    grid-row: 1;
  }

  .programm {
    grid-column: 1;
    grid-row: 2;
    padding-top: 2.5rem;
  }

  .programm li {
    grid-template-columns: 3rem 1fr;
  }
}

/* ------------------------- S5 · CASES · horizontaler Streifen (P3 nativ) */

.cases {
  padding-block: clamp(3rem, 2rem + 3vw, 4rem);
}

.cases-strip {
  display: flex;
  gap: var(--reelr-space-6);
  overflow-x: auto;
  overscroll-behavior-x: contain; /* P7, Befund 4: keine Browser-Back-Geste am Streifenende */
  margin-top: var(--reelr-space-12);
  padding-block: var(--reelr-space-2) var(--reelr-space-6);
  scroll-snap-type: x proximity;
  /* Snap-Position = Container-Kante: sonst zieht der Initial-Snap
     das padding-inline weg und Panel 1 klebt am Viewport-Rand */
  scroll-padding-inline-start: calc(max(0px, 50vw - 45rem) + var(--reelr-gutter));
  scrollbar-width: thin;
  scrollbar-color: var(--reelr-border) transparent;
}

.cases-strip::-webkit-scrollbar {
  height: 4px;
}

.cases-strip::-webkit-scrollbar-thumb {
  background: var(--reelr-border);
  border-radius: var(--reelr-radius-pill);
}

.case-panel {
  flex: 0 0 auto;
  /* v1.4: echte Hochkant-Reels (9:16) statt Cinema-Platzhalter - schmalere
     Panels, damit Kopf + Buehne + Text in der gepinnten 100svh-Sektion
     Platz haben */
  width: min(58vw, 17.5rem);
  scroll-snap-align: start;
}

.case-stage {
  /* Reel-Format ueberschreibt die Cinema-Ratio der Letterbox */
  aspect-ratio: 9 / 16;
  margin-bottom: var(--reelr-space-6);
}

.case-video {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.case-metrik {
  margin-bottom: var(--reelr-space-2);
}

.case-panel h3 {
  margin-bottom: var(--reelr-space-2);
}

.case-panel > p:last-child {
  max-width: 42ch;
}

/* ------------------------------- S6 · PROZESS · CSS-Sticky-Stack
   Contract v3.3.5 + §6.7: 4 dunkle Double-Bezel-Karten stapeln sich per
   position:sticky (KEIN GSAP-Pin); die Scale-Staffel 0.04 legt der
   Motion-Branch als Scrub darueber. reduced-motion: static (unten, MQ). */

.prozess {
  padding-block: clamp(3rem, 2rem + 3vw, 4rem);
}

.prozess-stapel {
  list-style: none;
  display: flex;
  flex-direction: column;
  gap: clamp(5rem, 20svh, 11rem);
  margin-top: var(--reelr-space-12);
}

.prozess-karte {
  position: sticky;
  top: clamp(5.5rem, 13svh, 7.5rem);
}

/* Staffel-Versatz: jede Karte dockt eine Stufe tiefer an (Stapel-Peek) */
.prozess-karte:nth-child(2) { top: calc(clamp(5.5rem, 13svh, 7.5rem) + 0.875rem); }
.prozess-karte:nth-child(3) { top: calc(clamp(5.5rem, 13svh, 7.5rem) + 1.75rem); }
.prozess-karte:nth-child(4) { top: calc(clamp(5.5rem, 13svh, 7.5rem) + 2.625rem); }

.prozess-kern {
  min-height: clamp(14rem, 34svh, 20rem);
  display: flex;
  flex-direction: column;
  padding: var(--reelr-space-8);
}

.prozess-nr {
  font-size: var(--reelr-text-base);
  margin-bottom: var(--reelr-space-6);
}

.prozess-kern h3 {
  font-size: var(--reelr-text-xl);
  margin-bottom: var(--reelr-space-3);
}

/* --------------------------- S7 · FINALE · typografisch, auf bg-deep
   Contract v3.3.7: Full-Viewport-Abschluss (100dvh), Inhalt staggert im
   Motion-Branch beim Eintritt (reelrOut, 60 ms, reversibel). Zugleich
   Akt-III-Auftakt (v1.1 Schritt 3: Studio-Sektion ersatzlos entfernt) -
   Naht 6 davor ist DER SCHNITT. */

.finale {
  position: relative;
  overflow: hidden;
  background: var(--reelr-bg-deep);
  border-top: 1px solid var(--reelr-border);
  min-height: 100dvh;
  display: grid;
  align-content: center;
  padding-block: clamp(6rem, 5rem + 6vw, 10rem) clamp(4rem, 3rem + 4vw, 7rem);
}

/* P5 · Finale-Atmo: 21:9-Monolith-Ableitung als Hintergrund-Ebene
   (Contract v2.3, "dunkler und ruhiger"). Liegt unter Inhalt (z 1)
   und Grain (z 2).
   v1.3 Orbit-Schweben (main.js Block 7): NUR diese Bild-Ebene treibt
   wie durch den Orbit - Rotation +-2.5 Grad (~16 s) + Drift x +-10 px
   (~14 s) / y +-7 px (~10 s), phasenversetzt. Bleed nach dem
   Hero-Muster (Formel siehe .hero-stage): der Ecken-Fehlbetrag einer
   um theta gedrehten Ebene ist ~(W/2)*sin(theta) vertikal bzw.
   (H/2)*sin(theta) horizontal - bei 2.5 Grad (sin 0.0436) also
   ~2.2vw / ~2.2svh, mit Rundungs-Reserve 2.4/2.4. Flach-Reserven
   PRO ACHSE: oben/unten y-Drift 7 px + Marge = 12 px; links/rechts
   x-Drift 10 px + Marge = 16 px (die groessere Seitenreserve deckt
   zugleich Sektions-Ueberhoehen ueber 100svh ab, die svh nicht
   abbildet - Worst Case schmales, niedriges Fenster >=768). Der
   overflow:hidden der Sektion clippt den Bleed; ohne JS /
   reduced-motion / mobil steht die Ebene unbewegt, der leicht
   groessere Cover-Crop ist unsichtbar (Hero-Prinzip). */
.finale-atmo {
  position: absolute;
  inset: calc(-2.4vw - 12px) calc(-2.4svh - 16px);
  z-index: 0;
  pointer-events: none;
  will-change: transform;
}

.finale-atmo img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.finale > .container {
  position: relative;
  z-index: 1;
}

.finale h2 {
  font-size: clamp(2.5rem, 2rem + 2.5vw, 3.75rem);
  max-width: 16em;
  margin-bottom: var(--reelr-space-12);
}

.finale-aktion {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: var(--reelr-space-8);
}

.finale-mail {
  font-size: var(--reelr-fluid-body);
}

.finale-claim {
  font-family: var(--reelr-font-mono);
  font-size: clamp(1rem, 4.4vw, 3.6rem);
  line-height: var(--reelr-leading-mono);
  letter-spacing: 0.3em;
  color: var(--reelr-text);
  white-space: nowrap;
  max-width: none;
  margin-top: clamp(4rem, 3rem + 5vw, 8rem);
  overflow: hidden; /* Maske fuer den transform-only Mask-Reveal */
}

.finale-claim-lauf {
  display: inline-block; /* der Motion-Branch faehrt ihn per yPercent ein */
}

/* -------------------------------------------------------------- FOOTER */

.footer {
  background: var(--reelr-bg-deep);
  border-top: 1px solid var(--reelr-border);
  padding-block: var(--reelr-space-16) var(--reelr-space-8);
}

.footer-inner {
  display: flex;
  align-items: flex-end;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: var(--reelr-space-8);
}

.footer-marke {
  width: min(300px, 74vw);
  height: auto;
}

.footer-nav {
  display: flex;
  flex-wrap: wrap;
  gap: var(--reelr-space-6);
}

.footer-nav a {
  font-size: var(--reelr-fluid-small);
}

.footer-zeile {
  margin-top: var(--reelr-space-12);
  padding-top: var(--reelr-space-6);
  border-top: 1px solid var(--reelr-border);
}

/* ------------------------------------------------------------ Responsive */

@media (max-width: 640px) {
  .hero-marke img {
    width: 90px;
  }

  .footer-inner {
    align-items: flex-start;
    flex-direction: column;
  }
}

/* ==========================================================================
   P4b · Drei-Akt-System + Sektions-Choreografie (Contract v3.2 bis v3.7)
   Alle Farben sind Kit-Token (Monochrom-Gesetz); JS toggelt nur Attribute
   und Klassen, die Flaechen selbst leben hier im CSS.
   ========================================================================== */

/* ------------------------------------------------- Akte (statisches Geruest)
   Akt I und III: den Grund traegt der Body (bg); Sektionen dort haben keine
   eigenen Flaechen (Ausnahme: bg-deep-Momente S7/S8, Kino-Logik).
   Akt II remappt die Kit-Token aufs Invers-Schema (MEDIAKIT §3) - Regeln,
   die var() am Element auswerten (Headlines, Labels, Links, Borders),
   wechseln damit automatisch. */

.akt {
  position: relative;
}

.akt-papier {
  background: var(--reelr-paper);
  color: var(--reelr-text-2); /* neu ausgewertet = ink-2 (Vererbung vom Body traegt sonst den Dark-Wert) */
  /* Deckungs-Saum (v1.1 Schritt 3, CDP-Befund 1512x982): die Markenbau-
     Buehne endet auf einer fraktionalen Koordinate (560svh), das Anti-
     Aliasing der Clip-Kante liess 1px dunklen Akt-I-Grund zwischen
     Curtain-Unterkante und Akt-II-Oberkante durchschimmern. 2px Saum
     decken die AA-Fuge Paper-auf-Paper - das ist KEIN Scroll-Overlap
     (Lehre aus 68e73c9: keine tote Strecke, keine Beat-Rechnung). */
  margin-top: -2px;
  z-index: 20; /* eigene Ebene ueber dem dunklen Akt-I-Grund (v3.3.3; v1.1
                  Schritt 3: der Curtain-Overlap ist Geschichte - Akt II
                  schliesst im normalen Fluss an die Volldeckung an) */
  --reelr-text: var(--reelr-ink);
  --reelr-text-2: var(--reelr-ink-2);
  --reelr-text-3: var(--reelr-ink-3);
  --reelr-border: var(--reelr-line);
  --reelr-border-hover: #BFBFBF; /* Invers-Ableitung der Border-Aufhellung (Grauwert, monochrom) */
  --reelr-bg: var(--reelr-paper);
  --reelr-focus-ring: 0 0 0 2px var(--reelr-paper), 0 0 0 4px var(--reelr-ink);
}

.akt-papier ::selection {
  background: var(--reelr-ink);
  color: var(--reelr-paper);
}

/* Dunkle Inseln im Hell-Akt (Karten, Media-Stages) behalten das Dark-Schema.
   Werte = Kit-Token 1:1 (tokens.css), hier bewusst literal restauriert. */
.akt-papier :is(.karte, .letterbox) {
  color: #A8A8A8;
  --reelr-text: #FAFAFA;
  --reelr-text-2: #A8A8A8;
  --reelr-text-3: #7C7C7C;
  --reelr-border: #2A2A2A;
  --reelr-border-hover: #3D3D3D;
  --reelr-bg: #0A0A0A;
  --reelr-focus-ring: 0 0 0 2px #0A0A0A, 0 0 0 4px #FAFAFA;
}

/* Grain lauft nur in Akt I und III; im Hell-Akt aus (Galerie-Logik, v3.7) */
.akt-papier .grain::after {
  content: none;
}

/* Theme-Flip (data-theme, v3.3.3) ist mit der fixen Nav entfallen (v1.1):
   es gibt keine fixe UI-Ebene mehr, die auf den Akt-Wechsel reagieren
   muesste. Auch der z-Flip an der Curtain-Naht ist Geschichte (v1.1
   Schritt 3): Volldeckung = Sticky-Release, es gibt keinen Overlap mehr. */

/* ------------------------------------------ Naht-Marker (Straddle, v3.3.4)
   Hairline + Mono-Label auf der Sektionskante; desktop straddelt die Zeile
   die Grenze (translateY 50 %), mobil sitzt sie auf der Kante. Das
   Linien-Wachstum (scaleX) setzt nur der Motion-Branch. */

/* Anker-Pflicht: ohne eigenes position:relative wuerden die absoluten
   Naht-Marker an Akt II statt an ihrer Sektionskante haengen. */
.leistungen,
.cases,
.prozess {
  position: relative;
}

.naht {
  position: absolute;
  bottom: 0;
  inset-inline: calc(max(0px, 50vw - 45rem) + var(--reelr-gutter));
  display: flex;
  align-items: center;
  gap: var(--reelr-space-4);
  transform: translateY(50%);
  pointer-events: none;
  z-index: 3;
}

.naht-linie {
  flex: 1;
  height: 1px;
  background: var(--reelr-border);
  transform-origin: left center;
}

.naht-label {
  background: var(--reelr-paper); /* Chip-Grund: haelt das Label auch auf der hell/dunkel-Kante lesbar */
  color: var(--reelr-ink-3);
  padding: var(--reelr-space-1) var(--reelr-space-3);
  border-radius: var(--reelr-radius-sm);
}

@media (max-width: 1023px) {
  .naht {
    transform: translateY(0);
  }
}

/* --------------------------------------- S5 · Cases desktop (Pin Nr. 2)
   Desktop wird die Sektion Full-Viewport und gepinnt (JS); mobil bleibt
   der native Snap-Scroll aus P3 unveraendert. */

@media (min-width: 1024px) {
  .cases {
    min-height: 100svh;
    display: flex;
    flex-direction: column;
    justify-content: center;
  }

  /* Flex-Falle: margin-inline auto verhindert das stretch des Flex-Items,
     der Container wuerde auf fit-content schrumpfen - explizit voll breit. */
  .cases > .container {
    width: 100%;
  }
}

/* --------------------------------------------------------- Reduced Motion
   MEDIAKIT §7 + Contract v3.6: alle Dauern auf 0, Inhalte sofort da; das
   Feature act-transitions wird gar nicht erst gesetzt (JS-Gate). Der
   Sticky-Stack degradiert hier von selbst, der Marquee wird zum Grid. */

@media (prefers-reduced-motion: reduce) {
  :root {
    --reelr-dur-fast: 0ms;
    --reelr-dur-base: 0ms;
    --reelr-dur-slow: 0ms;
    --reelr-dur-reveal: 0ms;
  }

  *,
  *::before,
  *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }

  .marken-strip {
    overflow: visible;
    -webkit-mask-image: none;
    mask-image: none;
  }

  .marken-track {
    flex-wrap: wrap; /* statisches Grid statt Marquee (Contract §6.2) */
  }

  /* Markenbau: statisch komplett - der Runway kollabiert, die Buehne
     steht als EIN Viewport im normalen Fluss (Galaxie full-bleed +
     fertiges Totem-Cutout, Text-Overlay + Spruch sichtbar), der Canvas
     malt nie (die Fallback-Bilder zeigen die fertige Szene).
     Selektoren mit .js (v1.1 Fix): muessen
     die .js-gegateten Runway-Regeln oben schlagen - gleiche
     Spezifitaet, spaeter im Stylesheet gewinnt. Die Buehne faellt auf
     die Basis-Regel zurueck (min-height 100svh; sticky ohne Runway
     verhaelt sich wie relative). */
  .js .markenbau {
    height: auto;
  }

  .js .markenbau-buehne {
    height: auto;
  }

  .markenbau-canvas {
    display: none;
  }

  .prozess-karte {
    position: static; /* Karten scrollen normal (Contract v3.6) */
  }
}
