/* ============================================================
   FIGHTING SPIRIT NECKARBISCHOFSHEIM e.V.
   Design system — "Rounds" concept.
   A gym journey told in rounds, like a bout: every section is a
   round, timed and counted, because that is how this sport
   measures effort.
   ============================================================ */

:root{
  /* --- Color tokens --- */
  --c-black: #0B0B0B;
  --c-black-soft: #141414;
  --c-card: #171716;
  --c-line: #2A2626;
  --c-white: #FFFFFF;
  --c-grey: #9A9490;
  --c-grey-dim: #807A77;
  --c-red: #C0392B;
  --c-red-deep: #7C2118;
  --c-red-bright: #E0503F;

  /* --- Type tokens --- */
  --f-display: 'Anton', 'Arial Narrow', sans-serif;
  --f-body: 'Manrope', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
  --f-mono: 'JetBrains Mono', ui-monospace, monospace;

  /* --- Layout tokens --- */
  --maxw: 1240px;
  --gutter: clamp(20px, 5vw, 64px);
  --radius: 2px;

  /* --- Spacing scale ---
     General-purpose steps for new/refactored components. Existing
     component-specific values (card padding, grid gaps etc.) were
     tuned by eye and are intentionally left as-is — only the two
     section-rhythm tokens below were wired in, since that vertical
     rhythm is what actually reads as "systematic" to a viewer. */
  --space-1: .5rem;   /* 8px */
  --space-2: .75rem;  /* 12px */
  --space-3: 1rem;    /* 16px */
  --space-4: 1.5rem;  /* 24px */
  --space-5: 2rem;    /* 32px */
  --space-6: 2.5rem;  /* 40px */
  --space-7: 3rem;    /* 48px */
  --space-8: 4rem;    /* 64px */
  --space-9: 6rem;    /* 96px */

  --space-section: clamp(4rem, 9vw, 7.5rem); /* vertical rhythm: standard <section> */
  --space-act: clamp(5rem, 10vw, 8rem);      /* vertical rhythm: full-height .act (homepage story rounds) */

  --ease: cubic-bezier(.16,.84,.32,1);
}

*,*::before,*::after{ box-sizing: border-box; }
html{ scroll-behavior: smooth; background: #000; }
@media (prefers-reduced-motion: reduce){
  html{ scroll-behavior: auto; }
  *,*::before,*::after{ animation-duration: .001ms !important; animation-iteration-count: 1 !important; transition-duration: .001ms !important; scroll-behavior: auto !important; }
}

body{
  margin:0;
  background: var(--c-black);
  color: var(--c-white);
  font-family: var(--f-body);
  font-size: 16px;
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
  overflow-x: hidden;
}

img{ max-width:100%; display:block; }
a{ color: inherit; text-decoration: none; }
ul{ margin:0; padding:0; list-style:none; }
button{ font-family: inherit; cursor:pointer; }
input,textarea,select{ font-family: inherit; }

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

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

.wrap{
  max-width: var(--maxw);
  margin: 0 auto;
  padding-left: var(--gutter);
  padding-right: var(--gutter);
}

/* ============================================================
   TYPOGRAPHY
   ============================================================ */

h1,h2,h3,h4{
  font-family: var(--f-display);
  font-weight: 400;
  text-transform: uppercase;
  letter-spacing: 0.01em;
  line-height: 1.08;
  margin: 0;
}

h1{ font-size: clamp(2.6rem, 7vw, 6.4rem); letter-spacing: -0.02em; }
h2{ font-size: clamp(2rem, 4.6vw, 3.6rem); letter-spacing: -0.01em; }
h3{ font-size: clamp(1.3rem, 2.4vw, 1.8rem); letter-spacing: 0; }
h4{ font-size: 1.05rem; letter-spacing: .04em; }

p{ margin: 0; color: var(--c-grey); }
.lede{ font-size: clamp(1.05rem, 1.6vw, 1.3rem); color: var(--c-grey); max-width: 46ch; }

.eyebrow{
  display:flex; align-items:center; gap:.7em;
  font-family: var(--f-mono);
  font-size: .78rem;
  letter-spacing: .18em;
  text-transform: uppercase;
  color: var(--c-red-bright);
  margin-bottom: 1.4rem;
}
.eyebrow::before{
  content:"";
  width: 26px; height: 2px;
  background: var(--c-red-bright);
}

.section-head{ margin-bottom: clamp(2.5rem, 6vw, 4.5rem); }
.section-head h2{ margin-top:.4rem; }

/* --- Price table --- */
.price-table-wrap{
  overflow-x:auto; border:1px solid var(--c-line); position:relative;
  background: linear-gradient(180deg, rgba(255,255,255,.015), transparent 20%);
}
.price-table{ width:100%; border-collapse:collapse; min-width:600px; }
.price-table th, .price-table td{ padding: 1.5rem 1.7rem; text-align:left; border-bottom:1px solid var(--c-line); transition: background .25s var(--ease); }
.price-table thead th{
  font-family: var(--f-mono); font-size:.72rem; letter-spacing:.1em; text-transform:uppercase;
  color: var(--c-grey-dim); font-weight:400; border-bottom:1px solid var(--c-line);
  padding-top:1.5rem; padding-bottom:1.3rem; vertical-align:bottom;
}
.price-table tbody th{
  font-family: var(--f-display); font-size:1.25rem; color: var(--c-white); font-weight:400; white-space:nowrap;
  position:relative; padding-left:1.9rem;
}
.price-table tbody th::before{
  content:""; position:absolute; left:0; top:50%; transform:translateY(-50%);
  width:3px; height:2.2rem; background: var(--c-red-deep);
}
.price-table tbody th span{ display:block; font-family: var(--f-mono); font-size:.68rem; color: var(--c-grey); text-transform:none; letter-spacing:0; margin-top:.3rem; }
.price-table td{ font-family: var(--f-display); font-size:2.1rem; color: var(--c-white); transition: color .25s var(--ease), transform .25s var(--ease); }
.price-table td span{ font-family: var(--f-mono); font-size:.6rem; color: var(--c-grey); margin-left:.2rem; }
.price-table tbody tr:last-child th, .price-table tbody tr:last-child td{ border-bottom:none; }
.price-table tbody tr:hover td{ color: var(--c-red-bright); transform: translateX(3px); }
.price-table tbody tr:hover th::before{ background: var(--c-red-bright); }
.price-table th:nth-child(2), .price-table td:nth-child(2){ background: rgba(224,80,63,.09); }
.price-table thead th:nth-child(2){ border-bottom:1px solid var(--c-red-bright); }
.badge-popular{
  display:inline-block; font-family: var(--f-mono); font-size:.6rem; letter-spacing:.08em; text-transform:uppercase;
  color: var(--c-black); background: var(--c-red-bright); padding:.3em .65em; border-radius: var(--radius);
  margin-bottom:.7rem; white-space:nowrap;
}
.price-table thead th:nth-child(2){ display:table-cell; }
.price-table thead th:nth-child(2) .badge-popular{ display:block; width:fit-content; }

/* ============================================================
   ROUND PROGRESS BAR — signature element
   Fixed strip at top of viewport that behaves like a boxing
   round clock: fills as the visitor moves through the page and
   labels the current section as a "round".
   ============================================================ */

.round-bar{
  position: fixed;
  top: 0; left: 0; right: 0;
  height: 3px;
  background: var(--c-line);
  z-index: 300;
}
.round-bar__fill{
  height: 100%;
  width: 0%;
  background: linear-gradient(90deg, var(--c-red-deep), var(--c-red-bright));
  transition: width .08s linear;
}
.round-tag{
  position: fixed;
  top: 92px; right: var(--gutter);
  z-index: 300;
  font-family: var(--f-mono);
  font-size: .72rem;
  letter-spacing: .14em;
  color: var(--c-grey);
  background: rgba(11,11,11,.7);
  border: 1px solid var(--c-line);
  padding: 6px 10px;
  backdrop-filter: blur(6px);
  display: none;
}
@media (min-width: 860px){ .round-tag{ display:flex; align-items:center; gap:8px; } }
.round-tag b{ color: var(--c-white); font-weight: 600; }
.round-tag .dot{ width:6px; height:6px; border-radius:50%; background: var(--c-red-bright); animation: pulse 1.6s ease-in-out infinite; }
@keyframes pulse{ 0%,100%{ opacity:1 } 50%{ opacity:.3 } }

/* ---------------------------------------------------------------
   Reduced transparency / higher contrast — the three glass surfaces
   on the site (header, round-tag, glass-panel cards) solidify instead
   of staying translucent; borders get louder under high contrast.
   --------------------------------------------------------------- */
@media (prefers-reduced-transparency: reduce){
  .site-header, .round-tag{ background: var(--c-black); backdrop-filter: none; }
  .glass-panel{ background: var(--c-card); backdrop-filter: none; }
}
@media (prefers-contrast: more){
  .card, .trainer-card{ border-color: var(--c-white); }
  .btn-ghost{ border-width: 2px; }
}

/* ============================================================
   HEADER / NAV
   ============================================================ */

.site-header{
  position: sticky; top: 0; z-index: 200;
  background: rgba(11,11,11,.82);
  backdrop-filter: blur(10px);
}
.site-header::after{
  content:"";
  position:absolute; left:0; right:0; bottom:-18px; height:18px;
  background: linear-gradient(to bottom, rgba(0,0,0,.4), transparent);
  opacity:0; transition: opacity .2s var(--ease); pointer-events:none;
}
.site-header.is-scrolled::after{ opacity:1; }
.site-header .wrap{
  display:flex; align-items:center; justify-content:space-between;
  height: 78px;
}
.logo{
  display:flex; align-items:center;
}
.logo-img{
  height: 66px; width:auto; display:block;
}
.logo-img--footer{ height: 108px; }
@media (max-width: 480px){ .logo-img{ height: 52px; } }

.nav-desktop{ display:none; }
@media (min-width: 980px){
  .nav-desktop{ display:flex; align-items:center; gap: 2.1rem; }
  .nav-desktop a{
    font-size: .86rem; letter-spacing:.04em; color: var(--c-grey);
    position: relative; padding: 6px 0; transition: color .2s var(--ease);
  }
  .nav-desktop a:hover, .nav-desktop a.active{ color: var(--c-white); }
  .nav-desktop a.active::after{
    content:""; position:absolute; left:0; right:0; bottom:0; height:2px; background: var(--c-red);
  }
}
.nav-cta{
  display:none;
}
@media (min-width: 980px){
  .nav-cta{ display:inline-flex; }
}

.nav-toggle{
  display:flex; flex-direction:column; gap:5px; background:none; border:none; padding:8px; z-index:210;
}
@media (min-width: 980px){ .nav-toggle{ display:none; } }
.nav-toggle span{ width:24px; height:2px; background: var(--c-white); transition: transform .25s var(--ease), opacity .25s var(--ease); }
.nav-toggle.open span:nth-child(1){ transform: translateY(7px) rotate(45deg); }
.nav-toggle.open span:nth-child(2){ opacity:0; }
.nav-toggle.open span:nth-child(3){ transform: translateY(-7px) rotate(-45deg); }

.nav-mobile{
  position: fixed; inset: 78px 0 0 0; z-index: 199;
  background: var(--c-black);
  display:flex; flex-direction:column; justify-content:space-between;
  padding: 2.4rem var(--gutter) 2.4rem;
  transform: translateY(-8px);
  opacity: 0; pointer-events:none;
  transition: opacity .25s var(--ease), transform .25s var(--ease);
}
.nav-mobile.open{ opacity:1; pointer-events:auto; transform: translateY(0); }
.nav-mobile ul{ display:flex; flex-direction:column; gap:0; }
.nav-mobile a{
  font-family: var(--f-display); text-transform:uppercase; font-size: 2rem;
  padding: .55rem 0; border-bottom: 1px solid var(--c-line); color: var(--c-white);
}
@media (min-width: 980px){ .nav-mobile{ display:none; } }

/* ============================================================
   BUTTONS
   ============================================================ */

.btn{
  display:inline-flex; align-items:center; justify-content:center; gap:.6em;
  font-family: var(--f-body); font-weight: 700; font-size: .92rem;
  letter-spacing: .02em;
  padding: 1rem 1.8rem;
  border-radius: var(--radius);
  border: 1px solid transparent;
  transition: transform .18s var(--ease), background .2s var(--ease), border-color .2s var(--ease), color .2s var(--ease);
  white-space: nowrap;
}
.btn-primary{ background: var(--c-red); color: var(--c-white); }
.btn-primary:hover{ background: var(--c-red-bright); transform: translateY(-2px); }
.btn-ghost{ border-color: var(--c-line); color: var(--c-white); background: transparent; }
.btn-ghost:hover{ border-color: var(--c-white); transform: translateY(-2px); }
.btn:active{ transform: scale(.97); transition-duration: .08s; }
.btn-block{ width:100%; }
.btn svg{ width:16px; height:16px; }

/* ============================================================
   HERO
   ============================================================ */

.hero{
  position:relative;
  min-height: 92vh;
  display:flex; align-items:flex-end;
  padding-top: 78px;
  overflow:hidden;
  background:
    radial-gradient(120% 90% at 50% 0%, rgba(192,57,43,.16), transparent 55%),
    var(--c-black);
}
.hero-ropes{
  position:absolute; inset:0; z-index:0; opacity:.5;
  background-image: repeating-linear-gradient(180deg, rgba(255,255,255,.035) 0px, rgba(255,255,255,.035) 1px, transparent 1px, transparent 64px);
}
.hero-grain{
  position:absolute; inset:0; z-index:0; pointer-events:none; opacity:.35; mix-blend-mode: overlay;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='120' height='120'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='2' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)' opacity='0.5'/%3E%3C/svg%3E");
}
.hero-content{ position:relative; z-index:1; padding-bottom: clamp(3rem, 8vw, 6rem); }
.hero-tag{
  font-family: var(--f-mono); font-size:.78rem; letter-spacing:.2em; color: var(--c-red-bright); text-transform:uppercase;
  margin-bottom: 1.6rem; display:flex; align-items:center; gap:.8em;
}
.hero-tag::before{ content:"●"; font-size:.6em; color: var(--c-red-bright); }
.hero h1{ max-width: 14ch; }
.hero h1 em{ font-style:normal; color: var(--c-red); }
.hero-sub{
  font-family: var(--f-display); text-transform:uppercase; font-size: clamp(1.1rem,2.4vw,1.5rem);
  color: var(--c-grey); margin-top: 1.1rem; letter-spacing:.02em;
}
.hero-text{ margin-top: 1.6rem; max-width: 52ch; }
.hero-ctas{ display:flex; flex-wrap:wrap; gap: 1rem; margin-top: 2.4rem; }
.hero-scroll{
  position:absolute; right: var(--gutter); bottom: 2.4rem; z-index:1;
  writing-mode: vertical-rl; font-family: var(--f-mono); font-size:.7rem; letter-spacing:.2em; color: var(--c-grey-dim);
  display:none; align-items:center; gap:10px;
}
@media(min-width:760px){ .hero-scroll{ display:flex; } }
.hero-scroll::after{ content:""; writing-mode: horizontal-tb; width:1px; height:44px; background: var(--c-grey-dim); }

/* Sub-page hero (shorter) */
.page-hero{
  padding: calc(78px + 4.5rem) 0 3.5rem;
  border-bottom: 1px solid var(--c-line);
  position:relative;
  background: radial-gradient(90% 120% at 100% 0%, rgba(192,57,43,.14), transparent 60%);
}
.page-hero .eyebrow{ margin-bottom: 1rem; }
.page-hero h1{ font-size: clamp(2.4rem, 6vw, 4.6rem); max-width: 18ch; }
.page-hero p{ margin-top:1.2rem; max-width: 60ch; }
.crumb{ font-family: var(--f-mono); font-size:.74rem; color: var(--c-grey-dim); letter-spacing:.08em; margin-bottom:1.4rem; }
.crumb a:hover{ color: var(--c-white); }

/* ============================================================
   STAT / NUMBERS ROW
   ============================================================ */

.stats{
  border-top: 1px solid var(--c-line); border-bottom: 1px solid var(--c-line);
  display:grid; grid-template-columns: repeat(2,1fr);
}
@media(min-width:760px){ .stats{ grid-template-columns: repeat(5,1fr); } }
.stat{
  padding: 2.2rem var(--gutter);
  border-right: 1px solid var(--c-line);
  border-bottom: 1px solid var(--c-line);
}
@media(min-width:760px){ .stat:nth-child(2n){ border-right:1px solid var(--c-line); } .stat{ border-bottom:none; } }
.stat:last-child{ border-right:none; }
.stat b{ display:block; font-family: var(--f-display); font-size: clamp(2rem,4vw,3rem); color: var(--c-white); transition: transform .3s var(--ease), color .3s var(--ease); }
.stat span{ font-family: var(--f-mono); font-size:.74rem; letter-spacing:.1em; text-transform:uppercase; color: var(--c-grey-dim); }
.stat:hover b{ transform: translateY(-4px); color: var(--c-red-bright); }

/* ============================================================
   SECTIONS / GRID
   ============================================================ */

section{ padding: var(--space-section) 0; }
.section-alt{ background: var(--c-black-soft); border-top:1px solid var(--c-line); border-bottom:1px solid var(--c-line); }

.grid{ display:grid; gap: 1.5rem; }
.grid-2{ grid-template-columns: 1fr; }
.grid-3{ grid-template-columns: 1fr; }
.grid-4{ grid-template-columns: 1fr; }
@media(min-width:700px){ .grid-2{ grid-template-columns: 1fr 1fr; } .grid-4{ grid-template-columns: 1fr 1fr; } }
@media(min-width:960px){ .grid-3{ grid-template-columns: repeat(3,1fr); } .grid-4{ grid-template-columns: repeat(4,1fr); } }

/* ============================================================
   CARDS — Course "fight card" style
   ============================================================ */

.card{
  background: var(--c-card);
  border: 1px solid var(--c-line);
  padding: 2.1rem;
  position: relative;
  transition: border-color .25s var(--ease), transform .25s var(--ease);
}
.card:hover{ border-color: var(--c-red-deep); transform: translateY(-4px); }
.card-num{
  font-family: var(--f-mono); font-size:.76rem; color: var(--c-grey-dim); letter-spacing:.1em;
  display:flex; justify-content:space-between; gap:.6em; margin-bottom: 1.6rem;
}
.card-num span:first-child{ white-space:nowrap; }
.card-num .lvl{ color: var(--c-red-bright); }
.card-num .lvl:only-child{ margin-left:auto; }
.card h3{ margin-bottom: .8rem; }
.card p{ font-size:.95rem; }
.card-tags{ display:flex; flex-wrap:wrap; gap:.5rem; margin-top:1.4rem; }
.tag{
  font-family: var(--f-mono); font-size:.68rem; letter-spacing:.06em; text-transform:uppercase;
  border:1px solid var(--c-line); padding:.35em .7em; color: var(--c-grey);
}
.card-link{
  margin-top: 1.6rem; display:flex; align-items:center; gap:.5em;
  font-size:.86rem; font-weight:700; color: var(--c-white);
}
.card-link svg{ width:14px; height:14px; transition: transform .2s var(--ease); }
.card:hover .card-link svg{ transform: translateX(4px); }

.card-photo{ margin: -2.1rem -2.1rem 1.6rem; aspect-ratio: 4/3; overflow:hidden; }
.card-photo img{ width:100%; height:100%; object-fit:cover; display:block; }

/* Sponsor tile — white card so any sponsor's own logo colors stay legible */
.sponsor-tile{
  display:flex; align-items:center; justify-content:center;
  background:#FFFFFF; border:1px solid var(--c-line); padding:2rem;
  min-height:120px; transition: transform .25s var(--ease), box-shadow .25s var(--ease);
}
.sponsor-tile:hover{ transform: translateY(-4px); box-shadow: 0 8px 24px rgba(0,0,0,.35); }
.sponsor-tile img{ max-width:100%; max-height:60px; width:auto; height:auto; }

/* Trainer card */
.trainer-card{
  background: var(--c-card); border:1px solid var(--c-line);
  transition: border-color .25s var(--ease), transform .25s var(--ease);
}
.trainer-card:hover{ border-color: var(--c-red-deep); transform: translateY(-4px); }
.trainer-photo{
  aspect-ratio: 4/5; width:100%;
  background: linear-gradient(155deg, #201d1c, #0d0c0c);
  position: relative; overflow:hidden;
  display:flex; align-items:flex-end; justify-content:flex-start;
}
.trainer-photo:not(:has(img))::before{
  content:""; position:absolute; inset:0;
  background-image: repeating-linear-gradient(135deg, rgba(255,255,255,.025) 0 2px, transparent 2px 14px);
}
.trainer-initials{
  font-family: var(--f-display); font-size: 4.2rem; color: rgba(255,255,255,.08); padding: 1rem 1.2rem;
}
.trainer-body{ padding: 1.5rem 1.6rem 1.8rem; }
.trainer-body h3{ margin-bottom:.3rem; }
.trainer-role{ font-family: var(--f-mono); font-size:.72rem; letter-spacing:.1em; color: var(--c-red-bright); text-transform:uppercase; display:block; min-height:3.4rem; }

/* Compact variant: homepage "Die Ecke" shows all nine trainers, not a
   four-card teaser. Coverflow-style: the centred trainer steps forward
   (full size, sharp) while exactly one neighbour on each side recedes
   into the background — enough to read "swipe, there's more" without
   ever showing more than three at once. Position/scale/opacity are
   driven every frame by js/main.js (a small drag+spring engine), not by
   native scroll — see the coverflow IIFE there for the physics.
   Scoped to its own classes so trainer.html's full-size cards are untouched. */
.trainer-grid-compact{
  position:relative;
  overflow:hidden;
  width:100%; max-width:100%;
  height: calc(var(--cw, 200px) + 2.7rem);
  touch-action: pan-y;
  cursor: grab;
  -webkit-user-select:none; user-select:none;
}
.trainer-grid-compact.is-dragging{ cursor:grabbing; }
.trainer-grid-compact .trainer-spotlight{
  position:absolute; top:0; left:50%;
  width: var(--cw, 200px);
  margin-left: calc(var(--cw, 200px) / -2);
  will-change: transform, opacity;
}
.trainer-grid-compact .trainer-spotlight img{ -webkit-user-drag:none; user-drag:none; }

/* Explicit prev/next affordance — static photos alone don't read as
   "swipeable", and starting a drag directly on a photo used to be flaky
   (see js/main.js's dragstart guard), so these are the reliable, obvious
   way in for anyone, on any device, drag or no drag. Shared by every
   coverflow carousel on the site (trainers, Kinderkurse, Disziplinen). */
.carousel-nav{
  position:absolute; top:50%; transform:translateY(-50%);
  width:38px; height:38px; border-radius:50%;
  display:flex; align-items:center; justify-content:center;
  background: rgba(11,11,11,.55); backdrop-filter: blur(6px); -webkit-backdrop-filter: blur(6px);
  border:1px solid rgba(255,255,255,.2);
  color:#fff; font-size:1.4rem; line-height:1; font-family: var(--f-display, inherit);
  cursor:pointer; z-index:200; padding:0;
  transition: background .2s var(--ease), border-color .2s var(--ease), transform .15s var(--ease);
}
.carousel-nav:hover, .carousel-nav:focus-visible{
  background: var(--c-red-deep); border-color: var(--c-red-deep);
}
.carousel-nav:active{ transform: translateY(-50%) scale(.9); }
.carousel-nav--prev{ left:4px; }
.carousel-nav--next{ right:4px; }
@media(max-width:559px){
  .carousel-nav{ width:32px; height:32px; font-size:1.15rem; }
}
.trainer-card--compact{ background:none; border:none; }
.trainer-card--compact:hover{ transform:none; }
.trainer-card--compact .trainer-photo{ aspect-ratio: 1/1; border:1px solid var(--c-line); transition: border-color .25s var(--ease); }
.trainer-grid-compact .trainer-spotlight:hover .trainer-photo{ border-color: var(--c-red-deep); }
.trainer-card--compact .trainer-body{ padding: .9rem 0 0; text-align:center; }
.trainer-card--compact .trainer-body h3{ font-size: 1rem; margin-bottom:.1rem; }
.trainer-card--compact .trainer-role{ display:none; }
.trainer-body p{ margin-top: .9rem; font-size: .92rem; }

/* Kinderkurse carousel (Runde 04) — same coverflow physics/markup shape
   as the trainer carousel above, 4:3 photo instead of a square one. */
.kurs-grid-compact{
  position:relative;
  overflow:hidden;
  width:100%; max-width:100%;
  height: calc(var(--cw, 240px) * .75 + 2.7rem);
  touch-action: pan-y;
  cursor: grab;
  -webkit-user-select:none; user-select:none;
}
.kurs-grid-compact.is-dragging{ cursor:grabbing; }
.kurs-grid-compact .kurs-spotlight{
  position:absolute; top:0; left:50%;
  width: var(--cw, 240px);
  margin-left: calc(var(--cw, 240px) / -2);
  will-change: transform, opacity;
  transform: translateX(var(--x, 0px)) scale(var(--s, 1));
  opacity: var(--o, 1);
  transition: opacity .3s var(--ease);
}
.kurs-grid-compact .kurs-spotlight img{ -webkit-user-drag:none; user-drag:none; }
.kurs-card-compact{ display:block; }
.kurs-card-compact .kurs-photo-compact{
  aspect-ratio: 4/3; overflow:hidden; border:1px solid var(--c-line);
  transition: border-color .25s var(--ease);
}
.kurs-card-compact .kurs-photo-compact img{ width:100%; height:100%; object-fit:cover; display:block; }
.kurs-grid-compact .kurs-spotlight:hover .kurs-photo-compact{ border-color: var(--c-red-deep); }
.kurs-card-compact h3{ padding:.9rem 0 0; text-align:center; font-size:1rem; margin:0; }

/* Disziplinen (Runde 03) — static "wall" of three big cards, not a
   carousel: with only 3 items there's nothing hidden left to reveal, so
   filling the full row width reads as more substantial than a coverflow
   ever would. A large faint background word fills the extra card height
   — the discipline's own name, not a number (numbers read as a ranking:
   "01" next to K1/Muay Thai looked like it was crowned #1 over Ringen). */
.disziplin-card-big{
  min-height: 22rem;
  display:flex; flex-direction:column; justify-content:flex-end;
  padding: 2.6rem 2.2rem;
}
.disziplin-card-big .disziplin-num-bg{
  position:absolute; top:1.6rem; right:1.8rem; max-width: calc(100% - 3.6rem);
  font-family: var(--f-display); font-size:2.5rem; line-height:1;
  letter-spacing:.02em; white-space:nowrap; overflow:hidden;
  color: rgba(255,255,255,.07); pointer-events:none;
}
.disziplin-card-big h3{ font-size:1.7rem; margin-bottom:.7rem; }
.disziplin-card-big p{ font-size:1.05rem; }

/* ============================================================
   TESTIMONIALS
   ============================================================ */

.quote-card{
  border-left: 2px solid var(--c-red-bright); padding-left: 1.6rem;
}
.quote-card p{ font-family: var(--f-display); text-transform:none; font-size: clamp(1.1rem,2vw,1.4rem); color: var(--c-white); line-height:1.35; letter-spacing:.01em; }
.quote-by{ margin-top:1.2rem; font-family: var(--f-mono); font-size:.78rem; color: var(--c-grey-dim); letter-spacing:.06em; }
.quote-stars{ display:block; color: var(--c-red-bright); font-size:.92rem; letter-spacing:.15em; margin-bottom:.4rem; }

/* Runde 2 stands alone with a single quote, not a grid of them —
   give it more typographic room than the testimonial cards get. */
#act-emotion .quote-card p{ font-size: clamp(1.3rem, 2.6vw, 1.85rem); }
#act-emotion .quote-by{ font-size:.76rem; color: var(--c-grey); }

/* Faint light through high windows — felt after a few seconds, not
   seen outright. Specific to Runde 2; every round gets its own air. */
#act-emotion::before{
  content:"";
  position:absolute; inset:0; z-index:0; pointer-events:none;
  background:
    linear-gradient(112deg, transparent 40%, rgba(255,255,255,.05) 47%, rgba(255,255,255,.02) 50%, transparent 56%),
    linear-gradient(112deg, transparent 62%, rgba(255,255,255,.03) 68%, transparent 74%);
  mix-blend-mode: screen;
}

/* ============================================================
   RUNDE 8 — NÄCHSTES EVENT: content lives in the database, edited by
   Denis via /admin, not hardcoded — reuses .card so it always looks
   right no matter what he types in (see js/main.js for the fetch/fill
   logic and server.js for the /api/next-event + /admin/next-event
   routes). ============================================================ */
.card--event{
  max-width: 640px;
  background: rgba(224,80,63,.07);
  border-color: var(--c-red-deep);
}
.card--event .card-num{ color: var(--c-red-bright); }

/* ============================================================
   GALLERY
   ============================================================ */

.gallery-grid{ display:grid; grid-template-columns: repeat(2,1fr); gap: .8rem; }
@media(min-width:700px){ .gallery-grid{ grid-template-columns: repeat(4,1fr); } }
.gallery-item{
  aspect-ratio: 1/1; position:relative; overflow:hidden; cursor:pointer;
  background: linear-gradient(160deg, #1c1a19, #0a0a0a);
  transition: transform .4s var(--ease), box-shadow .4s var(--ease);
}
.gallery-item:not(:has(img))::before{ content:""; position:absolute; inset:0; background-image: repeating-linear-gradient(45deg, rgba(255,255,255,.03) 0 2px, transparent 2px 16px); }
.gallery-item span{
  position:absolute; left:.9rem; bottom:.9rem; font-family: var(--f-mono); font-size:.68rem; letter-spacing:.08em; color: var(--c-grey);
  text-transform:uppercase; z-index:1;
}
.gallery-item::after{ content:""; position:absolute; inset:0; background: linear-gradient(0deg, rgba(0,0,0,.55), transparent 55%); }
/* Every tile is the same size at rest — "big" is now something a tile
   becomes on hover/tap, not a fixed property some photos have and others
   don't (see main.js for the tap-to-expand toggle touch devices need,
   since :hover alone never fires there). */
.gallery-grid .gallery-item:hover, .gallery-grid .gallery-item.is-expanded{
  outline: 1px solid var(--c-red-deep); outline-offset:-1px;
  transform: scale(1.18);
  z-index: 5;
  box-shadow: 0 24px 48px -16px rgba(0,0,0,.65);
}
@media (prefers-reduced-motion: reduce){
  .gallery-item{ transition: none; }
}

/* ============================================================
   CTA BAND
   ============================================================ */

.cta-band{
  position:relative; overflow:hidden;
  background: linear-gradient(120deg, var(--c-red-deep), #4a140f 70%);
  padding: clamp(3.5rem, 8vw, 6rem) 0;
  text-align:center;
}
.cta-band h2{ max-width: 18ch; margin: 0 auto; }
.cta-band p{ color: rgba(255,255,255,.75); margin: 1.2rem auto 0; max-width: 50ch; }
.cta-band .hero-ctas{ justify-content:center; }
.cta-band .btn-ghost{ border-color: rgba(255,255,255,.35); }

/* ============================================================
   FORMS
   ============================================================ */

.form-field{ margin-bottom: 1.4rem; }
.form-field label{
  display:block; font-family: var(--f-mono); font-size:.72rem; letter-spacing:.1em; text-transform:uppercase;
  color: var(--c-grey); margin-bottom:.6rem;
}
.form-field input, .form-field select, .form-field textarea{
  width:100%; background: var(--c-black-soft); border: 1px solid var(--c-line); color: var(--c-white);
  padding: .9rem 1rem; font-size: .96rem; border-radius: var(--radius);
  transition: border-color .2s var(--ease);
}
.form-field input:focus, .form-field select:focus, .form-field textarea:focus{ border-color: var(--c-red); outline:none; }
.form-field textarea{ min-height: 120px; resize: vertical; }
.form-check{ display:flex; align-items:flex-start; gap:.7em; font-size:.85rem; color: var(--c-grey); }
.form-check input{ margin-top:.25em; width:auto; }
.form-note{ font-size:.82rem; color: var(--c-grey-dim); margin-top:1rem; }
.form-success{
  display:none; border:1px solid var(--c-red-deep); background: rgba(192,57,43,.08); padding: 1.4rem; margin-top:1.4rem;
  font-family: var(--f-mono); font-size:.88rem;
}
.form-success.show{ display:block; }

/* ============================================================
   FOOTER
   ============================================================ */

footer{ border-top: 1px solid var(--c-line); padding: 3.5rem 0 2rem; background: var(--c-black-soft); }
.footer-grid{ display:grid; gap: 2.4rem; grid-template-columns: 1fr; margin-bottom: 2.6rem; }
@media(min-width:760px){ .footer-grid{ grid-template-columns: 1.4fr 1fr 1fr 1fr; } }
.footer-col .footer-heading{
  font-family: var(--f-display); font-weight:400; text-transform:uppercase;
  font-size: 1.05rem; letter-spacing: .04em; line-height:1.08;
  color: var(--c-white); margin: 0 0 1.1rem;
}
.footer-col ul li{ margin-bottom: .6rem; }
.footer-col a{ color: var(--c-grey); font-size:.9rem; transition: color .2s; }
.footer-col a:hover{ color: var(--c-white); }
.footer-brand p{ margin-top:1rem; max-width: 32ch; font-size:.9rem; }
.footer-social{ display:flex; gap:.8rem; margin-top:1.4rem; }
.footer-social a{ width:36px; height:36px; border:1px solid var(--c-line); display:flex; align-items:center; justify-content:center; transition: border-color .2s, color .2s; }
.footer-social a:hover{ border-color: var(--c-red); color: var(--c-red-bright); }
.footer-bottom{
  border-top: 1px solid var(--c-line); padding-top: 1.6rem;
  display:flex; flex-direction:column; gap:.9rem; font-size:.8rem; color: var(--c-grey-dim);
}
@media(min-width:700px){ .footer-bottom{ flex-direction:row; justify-content:space-between; align-items:center; } }
.footer-bottom nav{ display:flex; gap:1.4rem; }
.footer-bottom a:hover{ color: var(--c-white); }

/* ============================================================
   REVEAL ON SCROLL
   ============================================================ */

.reveal{ opacity:0; transform: translateY(28px); transition: opacity .7s var(--ease), transform .7s var(--ease); }
.reveal.in{ opacity:1; transform:none; }
.reveal-stagger > *{ transition-delay: calc(var(--i,0) * 70ms); }

/* ============================================================
   UTILITIES
   ============================================================ */

.center{ text-align:center; }
.mt-1{ margin-top:1rem; } .mt-2{ margin-top:2rem; } .mt-3{ margin-top:3rem; }
.mb-3{ margin-bottom:3rem; }
.text-red{ color: var(--c-red-bright); }
.divider{ height:1px; background: var(--c-line); border:none; margin: 0; }

/* Legal pages */
.legal{ max-width: 76ch; }
.legal h2{ text-transform:none; font-family:var(--f-body); font-weight:800; font-size:1.4rem; margin-top:2.6rem; margin-bottom:.9rem; }
.legal h2:first-child{ margin-top:0; }
.legal p, .legal li{ font-size:.96rem; margin-bottom:.9rem; color: var(--c-grey); }
.legal a{ color: var(--c-red-bright); text-decoration: underline; text-underline-offset:3px; }
.legal ul{ list-style: disc; padding-left: 1.4rem; }
.legal strong{ color: var(--c-white); }

/* ============================================================
   CINEMATIC LAYER
   A visual language for the one-take story on the homepage:
   smoke-born headlines, red light-lines stitching acts together,
   a mouse-reactive ember field, magnetic controls, and cards with
   real spatial depth. Purely visual — no autoplay audio.
   Everything here is inert / hidden until .js-cinematic is added
   to <html> by cinematic.js, and everything is skipped outright
   under prefers-reduced-motion or on touch/small screens.
   ============================================================ */

/* --- Ambient ember / particle field --- */
.ember-field{
  position: fixed; inset:0; z-index:1; pointer-events:none;
  opacity:0; transition: opacity 1.2s var(--ease);
}
.ember-field.ready{ opacity:1; }

/* --- Red light-line stitch: draws itself between chapters as you scroll in --- */
.act-stitch{ width:2px; height:54px; margin:0 auto 2.2rem; }
.act-stitch svg{ width:100%; height:100%; overflow:visible; display:block; }
.act-stitch path{
  stroke: var(--c-red-bright); stroke-width:1.5; fill:none;
  filter: drop-shadow(0 0 6px rgba(224,80,63,.65));
  stroke-dasharray: 1 1;
  stroke-dashoffset: 1;
  vector-effect: non-scaling-stroke;
  transition: stroke-dashoffset 1.4s var(--ease);
}
.act-stitch path.drawn{ stroke-dashoffset: 0; }

/* --- Acts (cinematic sections) --- */
.act{
  position: relative;
  min-height: 100vh;
  display:flex; flex-direction:column; justify-content:center;
  padding: var(--space-act) 0;
  overflow: clip;
}
/* .act is a column flex container, so .act-inner is a flex item — flex
   items default to min-width:auto, refusing to shrink below their
   content's intrinsic width. A wide-content descendant (the trainer
   carousel's fixed-width, non-shrinking cards) bubbles its full
   unscrolled width up through that and inflates the whole section — only
   masked, not fixed, by .act's own overflow:clip. min-width:0 alone
   wasn't enough to stop it; an explicit width pins it for real. */
.act-inner{ position:relative; z-index:2; min-width:0; width:100%; }

/* Runde 03/04/05 carry noticeably less content than the other acts (a
   short lede + a single row of cards, no long-form copy) — forcing them
   to the same full-viewport min-height as the rest left ~170px of pure
   black margin above AND below the content on a typical desktop window,
   which read as "empty" rather than "cinematic". Letting height follow
   content here (padding/rhythm from .act is untouched) fixes that
   without changing how the longer acts breathe. */
#act-sportarten, #act-kinder, #act-trainer{ min-height:auto; }
.act-num{
  font-family: var(--f-mono); font-size:.76rem; letter-spacing:.22em; color: var(--c-red-bright);
  text-transform:uppercase; margin-bottom:1.6rem; display:flex; align-items:center; gap:.9em;
}
.act-num::before{ content:""; width:34px; height:1px; background: var(--c-red-bright); }
.act-glow{
  position:absolute; z-index:0; border-radius:50%; pointer-events:none; filter: blur(80px);
  background: radial-gradient(circle, rgba(192,57,43,.35), transparent 70%);
  width: 46vw; height: 46vw; opacity:.55;
}
.act-glow.left{ left:-14vw; top:14%; }
.act-glow.right{ right:-14vw; bottom:8%; }

/* Parallax depth layers inside an act, moved subtly by scroll via JS (translateY) */
.depth-l1{ will-change: transform; }
.depth-l2{ will-change: transform; }

/* --- Smoke-born headline reveal --- */
.smoke-text{ position: relative; display:inline-block; user-select:none; }
.smoke-text .word{
  display:inline-block; opacity:0; filter: blur(18px); transform: translateY(18px) scale(1.04);
  transition: opacity 1s var(--ease), filter 1.1s var(--ease), transform 1.1s var(--ease);
  transition-delay: calc(var(--w,0) * 90ms);
}
.smoke-text.in .word{ opacity:1; filter: blur(0); transform:none; }
.smoke-puff{
  position:absolute; border-radius:50%; pointer-events:none;
  background: radial-gradient(circle, rgba(255,255,255,.08), transparent 70%);
  filter: blur(22px); opacity:0; transform: scale(.6);
  transition: opacity 1.4s var(--ease), transform 1.6s var(--ease);
}
.smoke-text.in .smoke-puff{ opacity:1; transform: scale(1.4); transition-delay:.05s; }

/* --- Magnetic controls ---
   No transition while the cursor is inside — JS sets transform on every
   mousemove and must track it 1:1, or the CSS transition fights each
   update and the button lags behind the cursor. The transition only
   applies on the snap-back once the cursor leaves. */
.magnetic{ position:relative; }
.magnetic:not(:hover){ transition: transform .35s cubic-bezier(.2,.9,.25,1); }
.magnetic .btn{ display:inline-flex; }

/* --- Depth cards: real spatial layering, not just shadow --- */
.depth-card{
  display:block; position:relative; transform-style: preserve-3d; perspective: 900px;
  transition: transform .12s linear;
}
/* .card/.trainer-card carry a transform transition for their own hover
   lift (see base rule above) — but cinematic.js drives this same
   transform 1:1 on every mousemove for the tilt effect, and that
   transition would lag the tilt behind the cursor. Suppress it while
   actively hovered; it comes back for the release snap-back. */
.depth-card:hover .card, .depth-card:hover .trainer-card{ transition: border-color .25s var(--ease); }
.depth-card .card, .depth-card .trainer-card{
  transform: translateZ(0);
  box-shadow: 0 30px 60px -30px rgba(0,0,0,.7), 0 2px 0 rgba(255,255,255,.02) inset;
}
.depth-card .card-num, .depth-card h3{ transform: translateZ(28px); }
.depth-card::before{
  content:""; position:absolute; inset:6px -1px -18px 6px; z-index:-1;
  background: linear-gradient(160deg, rgba(192,57,43,.16), transparent 60%);
  border:1px solid var(--c-line);
  transform: translateZ(-26px);
}

/* --- Story progress dots (right-hand act navigator, desktop) --- */
.story-nav{
  position: fixed; right: 28px; top:50%; transform: translateY(-50%); z-index: 250;
  display:none; flex-direction:column; gap: 14px;
}
@media(min-width:1080px){ .js-cinematic .story-nav{ display:flex; } }
.story-nav a{
  width:9px; height:9px; border-radius:50%; background: var(--c-line); border:1px solid transparent;
  transition: background .25s, transform .25s, border-color .25s;
  position: relative;
}
.story-nav a::after{
  content: attr(data-label);
  position:absolute; right:22px; top:50%; transform: translateY(-50%);
  font-family: var(--f-mono); font-size:.68rem; letter-spacing:.08em; color: var(--c-grey);
  white-space:nowrap; opacity:0; transition: opacity .2s var(--ease);
  background: rgba(11,11,11,.85); padding:4px 8px; border:1px solid var(--c-line);
}
.story-nav a:hover::after{ opacity:1; }
.story-nav a.active{ background: var(--c-red-bright); transform: scale(1.3); border-color: rgba(224,80,63,.5); }

/* --- Reduced motion / non-cinematic fallback ---
   Without .js-cinematic (JS disabled, reduced-motion, or old browser)
   acts behave like plain sections and .reveal handles the fade-in. */
html:not(.js-cinematic) .smoke-text .word{ opacity:1; filter:none; transform:none; transition:none; }
html:not(.js-cinematic) .light-line path{ display:none; }
html:not(.js-cinematic) .ember-field{ display:none; }
html:not(.js-cinematic) body{ cursor:auto; }

/* --- Mobile: flatten depth + shrink acts, keep it fast --- */
@media (max-width: 760px){
  .act{ min-height: auto; padding: 4rem 0; }
  .act-glow{ width:70vw; height:70vw; filter: blur(60px); opacity:.35; }
  .depth-card{ perspective:none; }
  .depth-card .card, .depth-card .trainer-card{ transform:none !important; }
  .depth-card::before{ display:none; }
}
@media (prefers-reduced-motion: reduce){
  .smoke-text .word{ opacity:1 !important; filter:none !important; transform:none !important; }
  .smoke-puff{ display:none; }
  .act-glow{ opacity:.25; }
}

/* ============================================================
   IDENTITY LAYER — "Spirit Mode"
   The site doesn't just sit in dark mode: energy accumulates as
   you move through the story. --spirit runs 0 → 1 across the
   page (set by cinematic.js from scroll position) and a handful
   of elements listen to it — glow, grain, pulse. Subtle by design;
   this is a feeling, not a strobe.
   ============================================================ */

:root{ --spirit: 0.15; }

.act-glow{ opacity: calc(0.28 + var(--spirit) * 0.4); }
.round-tag .dot{ animation-duration: calc(1.9s - var(--spirit) * 1.1s); }
.ember-field{ filter: saturate(calc(1 + var(--spirit) * 0.35)); }

/* Ambient structure — faint steel-beam banding shared by every act,
   the visual throughline that stands in for "walking through one hall". */
.act::before{
  content:"";
  position:absolute; inset:0; z-index:0; pointer-events:none;
  background-image: repeating-linear-gradient(90deg, rgba(255,255,255,.025) 0px, rgba(255,255,255,.025) 1px, transparent 1px, transparent 120px);
  opacity: .5;
}
.act::after{
  content:""; position:absolute; left:0; right:0; bottom:0; height:40%; z-index:0; pointer-events:none;
  background: linear-gradient(0deg, rgba(0,0,0,.5), transparent);
}

/* ============================================================
   BOOT SEQUENCE — precise logo wipe + single light sweep
   Runs once per session on the homepage only. Skippable, and
   skipped outright under reduced motion or on repeat visits.
   ============================================================ */

#boot{
  position: fixed; inset:0; z-index: 900;
  background: #000;
  display:flex; align-items:center; justify-content:center;
  transition: opacity 1s var(--ease), visibility 1s var(--ease);
}
#boot.boot-hide{ opacity:0; visibility:hidden; pointer-events:none; }
.boot-copy{
  position:relative; z-index:1; text-align:center;
}
.sr-only{
  position:absolute; width:1px; height:1px; padding:0; margin:-1px;
  overflow:hidden; clip:rect(0,0,0,0); white-space:nowrap; border:0;
}

/* The emblem arrives as two halves and meets at the centre — contact
   is the trigger, not a decoration on top of it. Mirrors the site's
   own theme: two things becoming one. */
.boot-emblem{
  position:relative; width: clamp(220px, 34vw, 340px); aspect-ratio: 1000/1002;
  margin:0 auto;
}
.boot-emblem-half{
  position:absolute; inset:0;
  opacity:.5; filter: brightness(.55) saturate(.7);
  transition:
    transform .85s cubic-bezier(.5,0,.75,0) .2s,
    opacity .4s ease-out 1.2s,
    filter .4s ease-out 1.2s;
}
.boot-emblem-half img{ width:100%; height:100%; display:block; }
.boot-emblem-half--l{ clip-path: inset(0 50% 0 0); transform: translateX(-55%) rotate(-4deg); }
.boot-emblem-half--r{ clip-path: inset(0 0 0 50%); transform: translateX(55%) rotate(4deg); }
.boot-emblem.reveal-run .boot-emblem-half{ opacity:1; filter: brightness(1) saturate(1); }
.boot-emblem.reveal-run .boot-emblem-half--l,
.boot-emblem.reveal-run .boot-emblem-half--r{ transform: translateX(0) rotate(0deg); }

.boot-emblem-shine{
  position:absolute; inset:0; pointer-events:none;
  -webkit-mask-image: url('../images/logo.png'); mask-image: url('../images/logo.png');
  -webkit-mask-size: contain; mask-size: contain;
  -webkit-mask-repeat: no-repeat; mask-repeat: no-repeat;
  -webkit-mask-position: center; mask-position: center;
  background: linear-gradient(115deg, transparent 40%, rgba(255,255,255,.9) 50%, transparent 60%);
  background-size: 300% 300%;
  opacity:0;
}
.boot-emblem.reveal-run .boot-emblem-shine{
  animation: bootShine .8s cubic-bezier(.4,0,.2,1) 1.7s forwards;
}
@keyframes bootShine{
  0%{ background-position: 150% 0%; opacity:0; }
  12%{ opacity:1; }
  80%{ opacity:1; }
  100%{ background-position: -60% 0%; opacity:0; }
}
.boot-headline{
  font-size: clamp(1.6rem, 4.4vw, 3.4rem); color: var(--c-white); margin-top:2rem;
  max-width: 18ch; margin-inline:auto;
}
.boot-headline .boot-part{ display:block; }
.boot-headline .boot-twist{ color: var(--c-red-bright); margin-top:.3em; }
.boot-part .word{ display:inline-block; }
.boot-part .ch{
  display:inline-block; opacity:0; filter:blur(5px); transform:translateY(4px);
  transition: opacity .32s var(--ease), filter .32s var(--ease), transform .32s var(--ease);
}
.boot-copy.show .boot-part .ch{ opacity:1; filter:blur(0); transform:none; }
.boot-skip{
  position:absolute; z-index:2; right: 24px; bottom: 24px;
  font-family: var(--f-mono); font-size:.72rem; letter-spacing:.1em; text-transform:uppercase;
  color: var(--c-grey-dim); background:none; border:1px solid var(--c-line); padding:.6em 1em;
  transition: color .2s, border-color .2s;
}
.boot-skip:hover{ color: var(--c-white); border-color: var(--c-grey); }

/* ============================================================
   GLASS PANELS — sport cards float instead of sitting flat
   ============================================================ */
.glass-panel{
  position: relative;
  background: linear-gradient(160deg, rgba(255,255,255,.05), rgba(255,255,255,.015));
  border: 1px solid rgba(255,255,255,.08);
  backdrop-filter: blur(14px) saturate(1.2);
  -webkit-backdrop-filter: blur(14px) saturate(1.2);
  overflow: hidden;
}
.glass-panel::before{
  content:"";
  position:absolute; inset:-40%;
  background: radial-gradient(280px circle at var(--mx,50%) var(--my,50%), rgba(224,80,63,.22), transparent 60%);
  opacity:0; transition: opacity .4s var(--ease);
  pointer-events:none;
}
.glass-panel:hover::before{ opacity:1; }
.glass-panel::after{
  content:""; position:absolute; inset:0; pointer-events:none;
  background: linear-gradient(120deg, transparent 30%, rgba(255,255,255,.06) 48%, transparent 60%);
  transform: translateX(-120%);
  transition: transform .8s var(--ease);
}
.glass-panel:hover::after{ transform: translateX(120%); }

/* ============================================================
   TRAINERS — stepping out of darkness
   ============================================================ */
.trainer-spotlight{
  filter: brightness(.22) saturate(.7);
  transform: translateY(26px) scale(.96);
  opacity: .55;
  transition: filter 1.1s var(--ease), transform 1.1s var(--ease), opacity 1.1s var(--ease);
  cursor: pointer;
  overflow:hidden;
}
.trainer-spotlight::before{
  content:"";
  position:absolute; inset:-20% -20% auto -20%; height:60%;
  background: radial-gradient(circle at 50% 0%, rgba(224,80,63,.35), transparent 70%);
  opacity:0; transition: opacity 1.2s var(--ease); pointer-events:none; z-index:0;
}
.trainer-spotlight.lit{
  filter: brightness(1) saturate(1);
  transform: none;
  opacity: 1;
}
.trainer-spotlight.lit::before{ opacity:1; }
.trainer-spotlight .trainer-card{ position:relative; z-index:1; }

/* Karussell (Runde 05): position/scale come from --x/--s, set every frame
   by the coverflow engine in main.js — this needs to out-specificity the
   reveal system above (.trainer-spotlight{transform:...} / .lit{transform:none})
   without fighting it, and opacity has to multiply the reveal's own
   .55→1 fade with the coverflow's distance falloff (--o) since only one
   `opacity` can win per element. No transition on transform: a spring
   already drives it smoothly every frame, and a CSS transition on top
   would just lag behind the pointer during a drag. */
.trainer-grid-compact .trainer-spotlight{
  transform: translateX(var(--x, 0px)) scale(var(--s, 1));
  transition: filter 1.1s var(--ease), opacity .3s var(--ease);
  opacity: calc(.55 * var(--o, 1));
}
.trainer-grid-compact .trainer-spotlight.lit{
  opacity: var(--o, 1);
}
.trainer-grid-compact .trainer-spotlight.is-active .trainer-photo{ border-color: var(--c-red-deep); }
@media (prefers-reduced-motion: reduce){
  .trainer-grid-compact .trainer-spotlight{ transition: opacity .2s linear; }
}

/* ============================================================
   TRAINER PROFILE SECTIONS — used on individual trainer pages
   ============================================================ */
.profile-section{ margin-top:1.4rem; }
.profile-section h3{ color: var(--c-red-bright); margin-bottom:.5rem; font-size:1.05rem; letter-spacing:.04em; }
.profile-section p{ font-size:.95rem; }

/* ============================================================
   KINDERBEREICH — deliberately warmer, lighter, softer
   Same brand family (red), shifted warm + brighter so parents
   read "welcoming" at a glance, without breaking the identity.
   ============================================================ */
#act-kinder{
  --c-black: #17130F;
  --c-black-soft: #1E1811;
  --c-red: #D9773F;
  --c-red-bright: #F0A15C;
  --c-red-deep: #8C4A22;
}
#act-kinder .act-glow{ opacity: calc(0.4 + var(--spirit) * 0.35); filter: blur(100px); }
#act-kinder::after{ background: linear-gradient(0deg, rgba(23,19,15,.35), transparent); }

/* ============================================================
   FINALE — the lit door
   Corners only, not a closed box — a ring is implied, not drawn.
   ============================================================ */

/* The hall itself, dimmed well behind the frame — before this, the
   round was just text floating on nothing. Sits as the section's own
   background, so it paints behind .act-glow/::before/::after/.act-inner
   without touching their z-index stack. */
#act-probetraining{
  background-image: linear-gradient(180deg, rgba(11,11,11,.86), rgba(11,11,11,.72) 45%, rgba(11,11,11,.94)), url('../images/halle.webp');
  background-size: cover;
  background-position: center 65%;
}

/* Overhead spotlight: repurposes the section's existing glow element
   into a soft cone falling on the frame, instead of a corner blob. */
#act-probetraining .act-glow.right{
  right:auto; left:50%; top:-10%; bottom:auto;
  width:70vw; height:60vw; max-width:900px; max-height:760px;
  transform:translateX(-50%);
  background: radial-gradient(ellipse 45% 60% at 50% 0%, rgba(255,220,210,.09), transparent 72%);
  opacity:.8; filter: blur(70px);
}
/* Film grain, layered into the section's existing bottom-fade so
   nothing about the base .act treatment is lost, just enriched. */
#act-probetraining::after{
  background:
    url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='140' height='140'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.85' numOctaves='2' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)' opacity='0.05'/%3E%3C/svg%3E"),
    linear-gradient(0deg, rgba(0,0,0,.5), transparent);
}

.door-frame{
  --corner: 26px; --corner-t: 1.5px; --corner-c: rgba(224,80,63,.55);
  position:relative; max-width: 620px; margin: 2.6rem auto 0;
  border: none;
  padding: clamp(2.8rem,6vw,4.2rem) clamp(1.8rem,4.5vw,2.6rem);
  text-align:center;
  transform: scale(.94);
  opacity: .75;
  transition: transform 1.2s var(--ease), opacity 1.2s var(--ease), filter .5s var(--ease), box-shadow 1.4s var(--ease);
  box-shadow: 0 30px 70px -30px rgba(224,80,63,.22), inset 0 0 60px -18px rgba(224,80,63,.1);
  background-repeat: no-repeat;
  background-image:
    linear-gradient(var(--corner-c), var(--corner-c)), linear-gradient(var(--corner-c), var(--corner-c)),
    linear-gradient(var(--corner-c), var(--corner-c)), linear-gradient(var(--corner-c), var(--corner-c)),
    linear-gradient(var(--corner-c), var(--corner-c)), linear-gradient(var(--corner-c), var(--corner-c)),
    linear-gradient(var(--corner-c), var(--corner-c)), linear-gradient(var(--corner-c), var(--corner-c));
  background-position:
    top left, top left, top right, top right,
    bottom left, bottom left, bottom right, bottom right;
  background-size:
    var(--corner) var(--corner-t), var(--corner-t) var(--corner),
    var(--corner) var(--corner-t), var(--corner-t) var(--corner),
    var(--corner) var(--corner-t), var(--corner-t) var(--corner),
    var(--corner) var(--corner-t), var(--corner-t) var(--corner);
}
.door-frame.approach{
  transform: scale(1); opacity:1;
  box-shadow: 0 30px 80px -25px rgba(224,80,63,.32), inset 0 0 70px -14px rgba(224,80,63,.14);
  animation: doorFlash 1.8s var(--ease);
}
.door-frame:hover{ filter: brightness(1.12); }
@keyframes doorFlash{
  0%{ filter: brightness(1); }
  32%{ filter: brightness(1.4); }
  100%{ filter: brightness(1); }
}
.door-frame .door-line1{ font-family: var(--f-display); text-transform:uppercase; font-size: clamp(1.4rem,3.4vw,2.1rem); }
.door-frame .door-line2{ font-family: var(--f-mono); font-size:.85rem; letter-spacing:.08em; color: var(--c-grey); margin-top:.8rem; }
.door-frame .hero-ctas{ margin-top: 2.6rem; }
#act-probetraining .btn-primary{
  box-shadow: 0 10px 26px -8px rgba(224,80,63,.55);
  transition: transform .4s var(--ease), box-shadow .4s var(--ease), background .3s var(--ease);
}
#act-probetraining .btn-primary:hover{
  box-shadow: 0 14px 36px -8px rgba(224,80,63,.7);
  transform: translateY(-3px);
}
@media (prefers-reduced-motion: reduce){
  .door-frame.approach{ animation:none; }
}

@media (max-width: 760px){
  .act::before{ background-size: 60px; opacity:.3; }
  .trainer-spotlight{ filter: brightness(.4); transform: translateY(14px) scale(.98); }
  .glass-panel{ backdrop-filter: blur(6px); }
}
@media (prefers-reduced-motion: reduce){
  #boot{ display:none; }
  .trainer-spotlight{ filter:none; transform:none; opacity:1; }
  .door-frame{ transform:none; opacity:1; }
}

/* ============================================================
   THE WALL — words become people
   A stack of big, blunt values; each one crossfades into a real
   member's (placeholder) portrait and one-line story as it
   reaches the center of the screen. Not a gallery grid — a wall
   you walk past.
   ============================================================ */

.wall{ margin-top: clamp(2rem,5vw,3.5rem); }
.wall-item{
  position: relative;
  height: 56vh; min-height: 320px;
  display:flex; align-items:center; justify-content:center;
  border-top: 1px solid var(--c-line);
}
.wall-item:last-child{ border-bottom: 1px solid var(--c-line); }
.wall-word, .wall-photo{
  position:absolute; inset:0;
  display:flex; align-items:center; justify-content:center; flex-direction:column;
  transition: opacity .9s var(--ease), transform .9s var(--ease), filter .9s var(--ease);
}
.wall-word{
  font-family: var(--f-display); text-transform:uppercase;
  font-size: clamp(2.6rem, 8vw, 6rem); color: var(--c-white);
  letter-spacing:.01em;
  opacity: .9; transform: scale(1);
}
.wall-photo{
  opacity:0; transform: scale(.94);
  pointer-events:none;
}
.wall-photo .frame{
  width: clamp(260px,34vw,400px); aspect-ratio:4/5;
  background: linear-gradient(155deg,#201d1c,#0d0c0c);
  border: 1px solid var(--c-line);
  display:flex; align-items:center; justify-content:center;
  position:relative; overflow:hidden;
}
.wall-photo .frame:not(:has(img))::before{
  content:""; position:absolute; inset:0;
  background-image: repeating-linear-gradient(135deg, rgba(255,255,255,.03) 0 2px, transparent 2px 14px);
}
.wall-photo .frame span{ font-family: var(--f-display); font-size:2.6rem; color: rgba(255,255,255,.12); }
.wall-photo .wall-caption{
  margin-top: 1.1rem; text-align:center; font-family: var(--f-mono); font-size:.8rem; color: var(--c-grey);
  letter-spacing:.04em; max-width: 34ch;
}
.wall-item.active .wall-word{ opacity:0; transform: scale(1.08); filter: blur(6px); }
.wall-item.active .wall-photo{ opacity:1; transform: scale(1); pointer-events:auto; }
.wall-item .act-glow{ opacity: calc(0.16 + var(--spirit) * 0.2); }

@media(max-width:760px){
  .wall-item{ height:auto; min-height:280px; padding: 3rem 0; }
}

/* ============================================================
   OUTRO — the coda beyond the last act
   Black. One red light. Two lines, one breath apart. A button.
   ============================================================ */

.outro{
  position:relative; min-height: 70vh;
  display:flex; flex-direction:column; align-items:center; justify-content:center;
  text-align:center; overflow:clip;
  background: #000;
  padding: 4rem var(--gutter);
}
.outro-round-tag{
  position:absolute; top:2.4rem; left:50%; transform:translateX(-50%);
  font-family: var(--f-mono); font-size:.72rem; letter-spacing:.22em; color: var(--c-red-bright);
  text-transform:uppercase; opacity:.7;
}
.outro-dot{
  width:8px; height:8px; border-radius:50%; background: var(--c-red-bright);
  box-shadow: 0 0 24px 6px rgba(224,80,63,.55);
  margin-bottom: 2.6rem;
  animation: outro-pulse 2.6s ease-in-out infinite;
}
@keyframes outro-pulse{ 0%,100%{ opacity:.55; transform:scale(1); } 50%{ opacity:1; transform:scale(1.3); } }
.outro-line{
  font-family: var(--f-display); text-transform:uppercase;
  font-size: clamp(1.3rem, 3.6vw, 2.3rem);
  max-width: 20ch; line-height:1.25;
  opacity:0; transform: translateY(14px); filter: blur(6px);
  transition: opacity 1.1s var(--ease), transform 1.1s var(--ease), filter 1.1s var(--ease);
}
.outro-line + .outro-line{ margin-top:.9rem; color: var(--c-grey); font-size: clamp(1.1rem,2.8vw,1.7rem); }
.outro.in .outro-line:nth-child(3){ transition-delay: .15s; }
.outro.in .outro-line:nth-child(4){ transition-delay: 1.35s; }
.outro.in .outro-line{ opacity:1; transform:none; filter:none; }
.outro .btn{ margin-top: 2.8rem; }
.outro.in .btn-wrap{ opacity:1; transform:none; }
.outro .btn-wrap{ opacity:0; transform: translateY(10px); transition: opacity 1s var(--ease) 2.3s, transform 1s var(--ease) 2.3s; }

@media (prefers-reduced-motion: reduce){
  .wall-item .wall-word{ transition:none; }
  .wall-item.active .wall-word{ opacity:.15; transform:none; filter:none; }
  .outro-line, .outro .btn-wrap{ opacity:1 !important; transform:none !important; filter:none !important; transition:none !important; }
}

/* ============================================================
   HERO VIDEO — optional background film
   Drop a file at media/hero.mp4 (+ media/hero.webm and
   media/hero-poster.jpg) and it plays behind the opening act.
   No file yet? The <video> simply never loads and the existing
   gradient/ember hero underneath shows exactly as before —
   nothing to configure, nothing that can break.
   ============================================================ */
.hero-video{
  position:absolute; inset:0; z-index:0;
  width:100%; height:100%; object-fit:cover;
  opacity:0; transition: opacity 1.2s var(--ease);
}
.hero-video.ready{ opacity: 1; }
.act#act-erwachen.has-video .act-glow{ opacity: .35; mix-blend-mode: multiply; }
.act#act-erwachen.has-video::after{
  /* Bottom edge stays near-opaque for a stretch (not just the exact 0%
     point) — the loop has moments where the bright ring canvas sits right
     at the bottom of frame, and a lighter footage-dependent seam showed
     through there once the fade thinned out too early. */
  background: linear-gradient(0deg, rgba(0,0,0,.95) 0%, rgba(0,0,0,.85) 12%, rgba(0,0,0,.35) 45%, rgba(0,0,0,.55) 100%);
  height:100%;
}

/* Large, persistent logo on the hero itself — not just the intro */
.hero-logo{
  width: clamp(140px, 18vw, 220px);
  height: auto;
  margin-bottom: 1.8rem;
}
@media (max-width: 640px){
  .hero-logo{ width: clamp(110px, 30vw, 160px); margin-bottom: 1.4rem; }
}

/* ============================================================
   TEAM PHOTO BAND — the real proof behind "Not just a gym. A family."
   Sits as a direct child of its .act (which has no max-width),
   so it reaches the true edges of the viewport without any
   negative-margin full-bleed trickery.
   ============================================================ */
.team-photo-band{
  position: relative;
  width: 100%;
  margin-top: clamp(2.2rem, 5vw, 3.6rem);
  overflow: hidden;
  line-height: 0;
}
.team-photo-band img{
  width: 100%;
  height: auto;
  display: block;
  filter: saturate(1.05) contrast(1.03);
}
.team-photo-band::after{
  content:"";
  position:absolute; inset:0;
  background: linear-gradient(0deg, rgba(0,0,0,.78) 0%, rgba(0,0,0,.22) 38%, transparent 62%);
  pointer-events:none;
}
.team-photo-band figcaption{
  position:absolute; left:0; right:0; bottom:0; z-index:2;
  padding: clamp(1.4rem,4vw,3rem) var(--gutter) clamp(1.6rem,4vw,2.4rem);
  display:flex; flex-direction:column; gap:.5rem;
  line-height: 1.3;
}
.team-photo-quote{
  font-family: var(--f-display); text-transform:uppercase;
  font-size: clamp(1.3rem,3.4vw,2.4rem); color:var(--c-white);
}
.team-photo-sub{
  font-family: var(--f-mono); font-size:.72rem; letter-spacing:.08em; color: var(--c-grey);
  text-transform:uppercase;
}
@media (max-width: 760px){
  .team-photo-band{ height: 56vh; min-height: 320px; }
  .team-photo-band img{ height:100%; width:100%; object-fit:cover; object-position: center 28%; }
}

/* Cinematic photo moment for Runde 02 — a real competition photo. Two
   people's heads sit close to the top of the frame, so it stays at its
   native 16/9 crop at every breakpoint (a narrower/taller aspect would
   crop into a face — already happened once, don't repeat).
   Mobile-first: caption and quote render as plain stacked blocks below
   the photo (first attempt overlaid them on the image at every width,
   and on a 16/9 frame scaled down to phone width there isn't enough
   pixel height for a full headline — it swallowed the photo). From
   760px up they lift onto the photo as an overlay + a floating card
   pulled over the bottom-right corner via negative margin. */
/* Plain photo band, no text overlay — an earlier version overlaid the
   headline on the image with a dark gradient for legibility, but the
   two real people in this photo sit at different heights in frame
   (one near the top, one near the bottom), so any gradient strong
   enough for text contrast ended up dimming or crossing someone's
   face. Keeping text and photo fully separate avoids that entirely. */
.moment-band{ position:relative; }
.moment-frame{
  position: relative; width:100%; aspect-ratio: 16/9;
  overflow:hidden;
}
.moment-frame img{ width:100%; height:100%; object-fit:cover; display:block; filter:saturate(1.03); }
.moment-frame::after{
  content:""; position:absolute; inset:0; pointer-events:none;
  box-shadow: inset 0 0 70px 20px var(--c-black);
}
