/* kiro-motion.css · Kiro Bausteine v2 (Okt. 2026)
   Nur Technik, kein Look. Farben, Schriften, Radien kommen aus dem Projekt-CSS.
   Werte pro Projekt nur in :root überschreiben (im Projekt-CSS, nach dieser Datei).
   Doku: docs/kiro-bausteine.md, Abschnitt D. */

:root {
  --ease: cubic-bezier(0.65, 0, 0.35, 1);  /* die EINE Kurve des Projekts */
  --dur-ui: 240ms;
  --dur-reveal: 520ms;
  --dur-signature: 1000ms;
  --reveal-shift: 16px;
  --stagger: 90ms;
  --header-h: 4.5rem;
  --section-space: clamp(3rem, 7vw, 5.5rem);
}

/* Grundlagen: Fokus nie unter dem Header, Overflow an Sektionskanten, Fokusring */
html { scroll-padding-top: calc(var(--header-h) + 1rem); }
section { overflow-x: clip; } /* clip bricht position: sticky nicht, hidden schon */
.k-section { padding-block: var(--section-space); }
:focus-visible { outline: 2px solid var(--focus, currentColor); outline-offset: 3px; }

/* 1. Reveal: nur mit html.js (kiro-early.js) und ohne reduced motion versteckt */
@media (prefers-reduced-motion: no-preference) {
  html.js [data-reveal] {
    transition:
      opacity var(--dur-reveal) var(--ease),
      transform var(--dur-reveal) var(--ease);
    transition-delay: calc(var(--i, 0) * var(--stagger));
  }
  html.js [data-reveal]:not(.is-in) {
    opacity: 0;
    transform: translate3d(0, var(--reveal-shift), 0);
  }
  /* Modus "repeat" (Kiro-Portfolio): beim Hochscrollen kommt es von oben */
  html.js [data-reveal=""].from-top:not(.is-in) {
    transform: translate3d(0, calc(var(--reveal-shift) * -1), 0);
  }

  /* Variante: nur Fade */
  html.js [data-reveal="fade"]:not(.is-in) { transform: none; }

  /* Variante: Scale-Settle (Wrapper clippt, Bild 1.06 → 1) */
  html.js [data-reveal="scale"] { overflow: clip; }
  html.js [data-reveal="scale"]:not(.is-in) { transform: none; }
  html.js [data-reveal="scale"] > img { transition: transform var(--dur-signature) var(--ease); }
  html.js [data-reveal="scale"]:not(.is-in) > img { transform: scale(1.06); }

  /* Variante: Zeilen-Reveal für H2 (nie für die Hero-H1) */
  html.js [data-reveal="lines"]:not(.is-in) { opacity: 1; transform: none; }
  html.js [data-reveal="lines"] .line > span {
    transition: transform var(--dur-reveal) var(--ease);
    transition-delay: calc(var(--i, 0) * var(--stagger));
  }
  html.js [data-reveal="lines"]:not(.is-in) .line > span { transform: translate3d(0, 110%, 0); }

  /* Hero: nur transform, keine Opacity (LCP-sicher) */
  .hero-rise { animation: kiro-rise var(--dur-reveal) var(--ease) both; }
}
@keyframes kiro-rise { from { transform: translate3d(0, 12px, 0); } }

.line { display: block; overflow: clip; padding-bottom: 0.12em; margin-bottom: -0.12em; }
.line > span { display: block; }

/* 2. Hover-Lift (auf inneren Elementen, nie auf dem [data-reveal]-Element selbst) */
.lift { transition: transform var(--dur-ui) var(--ease); }
@media (hover: hover) and (prefers-reduced-motion: no-preference) {
  .lift:hover { transform: translate3d(0, -4px, 0); }
}

/* 3. Pinned Scene (stehende Szene) */
.scene { position: relative; --scene-length: calc(100svh + var(--scene-steps, 3) * 80svh); }
.scene__shots { position: relative; }
@media (max-width: 47.99em) {
  .scene { --scene-length: calc(100svh + var(--scene-steps, 3) * 60svh); }
}
@media (prefers-reduced-motion: no-preference) {
  html.js .scene { height: var(--scene-length); }
  html.js .scene__stage {
    position: sticky;
    top: 0;
    height: 100svh;
    overflow: clip;
    display: grid;
    align-items: center;
  }
  html.js .scene__shots { min-height: var(--shots-min, 12rem); }
  html.js .scene__shots > [data-shot] { position: absolute; inset: 0; }
  html.js .scene [data-shot] { opacity: 0; transition: opacity var(--dur-reveal) var(--ease); }
  html.js .scene [data-shot].is-current { opacity: 1; }
  /* Beispiel: Objekt folgt dem eased Fortschritt --pe (0 bis 1) */
  html.js .scene__device {
    transform:
      translate3d(0, calc((1 - var(--pe, 0)) * 40px), 0)
      scale(calc(0.94 + var(--pe, 0) * 0.06));
  }
}

/* 4. Marquee: ruhig, pausierbar (WCAG 2.2.2), clippt */
.marquee { position: relative; overflow-x: clip; }
.marquee__track { display: flex; flex-wrap: wrap; gap: 2.5rem; list-style: none; margin: 0; padding: 0; }
.marquee__toggle { display: none; }
.marquee.is-running .marquee__toggle { display: inline-flex; align-items: center; min-block-size: 24px; }
@media (prefers-reduced-motion: no-preference) {
  .marquee.is-running .marquee__rail {
    display: flex;
    width: max-content;
    animation: kiro-marquee var(--marquee-dur, 45s) linear infinite; /* linear = zeitlose Kopplung, siehe D1 */
  }
  .marquee.is-running .marquee__track { flex-wrap: nowrap; padding-inline-end: 2.5rem; }
  .marquee:hover .marquee__rail,
  .marquee:focus-within .marquee__rail,
  .marquee.is-paused .marquee__rail,
  .marquee.is-offscreen .marquee__rail,
  html.is-hidden-tab .marquee__rail { animation-play-state: paused; }
}
@keyframes kiro-marquee { to { transform: translate3d(-50%, 0, 0); } }

/* Generisch: off-screen oder versteckter Tab pausiert CSS-Animationen */
[data-pause-offscreen].is-offscreen,
[data-pause-offscreen].is-offscreen *,
html.is-hidden-tab [data-pause-offscreen],
html.is-hidden-tab [data-pause-offscreen] * { animation-play-state: paused; }

/* 5a. Accordion nativ (<details name="…">), Animation nur wo unterstützt */
details > summary { cursor: pointer; list-style: none; }
details > summary::-webkit-details-marker { display: none; }
@media (prefers-reduced-motion: no-preference) {
  @supports (interpolate-size: allow-keywords) {
    :root { interpolate-size: allow-keywords; }
    details::details-content {
      block-size: 0;
      overflow: clip;
      transition:
        block-size var(--dur-ui) var(--ease),
        content-visibility var(--dur-ui) var(--ease) allow-discrete;
    }
    details[open]::details-content { block-size: auto; }
  }
}

/* 5b. Accordion mit Button + grid 0fr → 1fr (animiert in allen Browsern) */
html.js .acc__panel { display: grid; grid-template-rows: 0fr; }
html.js .acc__panel.is-open { grid-template-rows: 1fr; }
.acc__panel > div { overflow: hidden; min-height: 0; }
@media (prefers-reduced-motion: no-preference) {
  html.js .acc__panel { transition: grid-template-rows var(--dur-ui) var(--ease); }
}

/* 6. Header: Fläche blendet per Opacity ein. Kein backdrop-filter (ruckelt beim Scrollen). */
.site-header {
  position: fixed;
  inset: 0 0 auto;
  z-index: 50;
  height: var(--header-h);
  display: flex;
  align-items: center;
  isolation: isolate;
}
.site-header::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: -1;
  background: var(--surface, Canvas);
  box-shadow: 0 1px 0 var(--line, rgb(0 0 0 / 0.08));
  opacity: 0;
  transition: opacity var(--dur-ui) var(--ease);
}
.site-header.is-solid::before { opacity: 1; }
[data-header-sentinel] { position: absolute; top: 0; left: 0; width: 1px; height: 80px; pointer-events: none; }

/* 7. Mobil-Navigation */
html:not(.js) .nav-toggle { display: none; }
@media (min-width: 48em) { .nav-toggle { display: none; } }
@media (max-width: 47.99em) {
  html.js .nav-menu {
    position: fixed;
    inset: var(--header-h) 0 auto;
    background: var(--surface, Canvas);
    visibility: hidden;
    opacity: 0;
    transition: opacity var(--dur-ui) var(--ease), visibility 0s var(--dur-ui);
  }
  html.nav-open .nav-menu {
    visibility: visible;
    opacity: 1;
    transition: opacity var(--dur-ui) var(--ease), visibility 0s;
  }
}
@media (max-width: 47.99em) and (prefers-reduced-motion: no-preference) {
  html.js .nav-menu li {
    opacity: 0;
    transform: translate3d(0, 8px, 0);
    transition: opacity var(--dur-ui) var(--ease), transform var(--dur-ui) var(--ease);
  }
  html.nav-open .nav-menu li { opacity: 1; transform: none; transition-delay: calc(var(--i, 0) * 80ms); }
}

/* 8. Scroll-driven: nur Zusatz, nur in @supports, nur Desktop */
@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) and (min-width: 64em) {
    .parallax > img {
      animation: kiro-parallax linear both; /* Shorthand zuerst, sonst setzt sie die Timeline zurück */
      animation-timeline: view();
    }
  }
}
@keyframes kiro-parallax {
  from { transform: translate3d(0, -6%, 0) scale(1.12); }
  to   { transform: translate3d(0, 6%, 0) scale(1.12); }
}

/* 9. Reduced motion global (wie kiro-tokens.css): stoppt auch Pseudo-Elemente und Loops */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.001ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.001ms !important;
    scroll-behavior: auto !important;
  }
  .marquee__track[aria-hidden="true"] { display: none; }
}

/* 10. Druck: alles sichtbar */
@media print {
  [data-reveal], [data-reveal] *, .scene [data-shot] { opacity: 1 !important; transform: none !important; }
}
