/* ==========================================================================
   House Works · Bewegung
   Ein Prinzip für die ganze Seite: alles wird gezeichnet, nichts blinkt.
   Linien wachsen, Flächen wischen entlang der Flyer-Schräge, Text steigt auf.
   ========================================================================== */

/* --- Auftakt --------------------------------------------------------------
   Alles, was zunächst verborgen ist, hängt an .js. Ohne JavaScript steht die
   Seite vollständig und ohne Auftakt da. */

.intro {
  display: none;
}

.js .intro {
  position: fixed;
  inset: 0;
  z-index: 120;
  display: grid;
  place-items: center;
  background: var(--navy-deep);
  transition: transform 900ms var(--ease-in-out);
}

.intro[data-state="done"] {
  transform: translateY(-100%);
}

.intro__logo {
  position: relative;
  width: clamp(9rem, 22vw, 14rem);
  margin-inline: auto;
}

.intro__mark {
  display: block;
  width: 100%;
  color: var(--creme);
}

/* Die Wortmarke steht wie im Logo linksbündig im Haus und erscheint,
   sobald der Umriss fertig gezeichnet ist. */
.intro__letters {
  position: absolute;
  left: 11.5%;
  top: 58.7%;
  width: 55.7%;
  height: auto;
  opacity: 0;
  animation: einblenden 500ms var(--ease-out) 600ms forwards;
}

@keyframes einblenden {
  to {
    opacity: 1;
  }
}

.intro__mark path,
.intro__mark line {
  stroke-dasharray: var(--len, 400);
  stroke-dashoffset: var(--len, 400);
  animation: draw-line 800ms var(--ease-out) forwards;
}

.intro__word {
  overflow: hidden;
  margin-top: 1.25rem;
  text-align: center;
}

.intro__word span {
  display: block;
  font-size: var(--text-sm);
  font-weight: 600;
  color: var(--gold-lift);
  transform: translateY(110%);
  animation: rise 500ms var(--ease-out) 450ms forwards;
}

@keyframes draw-line {
  to {
    stroke-dashoffset: 0;
  }
}

@keyframes rise {
  to {
    transform: none;
  }
}

/* --- Auftritt der Person --------------------------------------------------
   Person und Bogen kommen nach dem Auftakt herein. Bewegt wird nur, was die
   Parallaxe nicht ohnehin schon steuert: also Maske und Deckkraft, nicht
   transform – sonst überschreiben sich Skript und Stylesheet gegenseitig. */

.js .hero__person {
  opacity: 0;
  clip-path: inset(14% 0 0 0);
  transition: opacity 900ms var(--ease-out) 240ms,
    clip-path 1200ms var(--ease-out) 240ms;
}

.js .hero-ready .hero__person,
.js .hero__person.is-in {
  opacity: 1;
  clip-path: inset(0 0 0 0);
}

.js .hero__glow {
  opacity: 0;
  transition: opacity 1400ms var(--ease-out) 200ms;
}

.js .hero-ready .hero__glow {
  opacity: 1;
}

.hero__arc circle {
  transition: stroke-dashoffset 1600ms var(--ease-out) 420ms;
}

.hero-ready .hero__arc circle {
  stroke-dashoffset: 0;
}

/* --- Einblendungen -------------------------------------------------------- */

.js [data-reveal] {
  opacity: 0;
  transform: translateY(1.75rem);
  transition: opacity 760ms var(--ease-out), transform 760ms var(--ease-out);
  transition-delay: calc(var(--i, 0) * 90ms);
}

.js [data-reveal].is-revealed {
  opacity: 1;
  transform: none;
}

/* Wortweise Maske für Schlagzeilen. */
/* Der Kasten wird oben und unten aufgeweitet, damit Umlautpunkte und
   Unterlängen nicht an der Maske abgeschnitten werden. Nach unten bleibt der
   verborgene Zustand trotzdem außer Sicht. */
.word {
  display: inline-block;
  overflow: hidden;
  padding-top: 0.22em;
  margin-top: -0.22em;
  padding-bottom: 0.12em;
  margin-bottom: -0.12em;
  vertical-align: bottom;
}

.js .word > span {
  display: inline-block;
  transform: translateY(135%);
  transition: transform 900ms var(--ease-out);
  transition-delay: calc(var(--i, 0) * 55ms);
}

.js .is-revealed .word > span {
  transform: none;
}

/* Bildplatten wischen entlang derselben Schräge wie im Flyer auf. */
.js .plate {
  clip-path: polygon(0 0, 0 0, 0 100%, 0 100%);
  transition: clip-path 1100ms var(--ease-out);
}

.js .is-revealed .plate,
.js .plate.is-revealed {
  clip-path: polygon(0 0, 118% 0, 100% 100%, 0 100%);
}

/* Fotos blenden erst auf, wenn sie wirklich geladen sind. */
.js .plate__photo {
  opacity: 0;
  transition: opacity 600ms var(--ease-out), transform var(--dur-slow) var(--ease-out);
}

.js .plate__photo.is-loaded {
  opacity: 1;
}

/* Sanfte Tiefenstaffelung im Hero. */
[data-parallax] {
  will-change: transform;
}

/* --- Rücksicht auf Bewegungsempfindlichkeit ------------------------------- */

@media (prefers-reduced-motion: reduce) {
  html {
    scroll-behavior: auto;
  }

  *,
  *::before,
  *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    transition-delay: 0ms !important;
  }

  .js [data-reveal] {
    opacity: 1;
    transform: none;
  }

  .js .word > span {
    transform: none;
  }

  .js .plate {
    clip-path: none;
  }

  .js .plate__photo {
    opacity: 1;
  }

  .js .intro {
    display: none;
  }

  .js .hero__person,
  .js .hero__glow {
    opacity: 1;
    clip-path: none;
  }

  .hero__arc circle {
    stroke-dashoffset: 0;
  }
}
