/* Text Animations V3 -- 5 effets spectaculaires */
/* D3RF v3 -- animations texte colonne droite */

/* ============================================================
   TOKENS ANIMATION (lus par text-animations-v3.js)
   ============================================================ */
:root {
  /* WE DREAM -- brume qui se condense */
  --dream-letter-duration: 900ms;
  --dream-letter-stagger: 80ms;

  /* WE DESIGN -- dessin blueprint */
  --design-letter-duration: 600ms;
  --design-letter-stagger: 70ms;

  /* WE DELIVER -- chute gravite + rebond */
  --deliver-letter-duration: 700ms;
  --deliver-letter-stagger: 60ms;
  --deliver-impact-duration: 300ms;

  /* WE REFINE -- typewriter puis polissage */
  --typewriter-char-speed: 80ms;
  --typewriter-pause: 300ms;
  --refine-polish-duration: 600ms;

  /* WE FINALIZE -- puzzle + verrou + point encre */
  --finalize-letter-duration: 800ms;
  --finalize-letter-stagger: 50ms;
  --finalize-period-delay: 200ms;
  --finalize-period-duration: 500ms;

  /* Colonne gauche */
  --left-text-animation-duration: 1.1s;
  --left-text-opacity-duration: 0.7s;
}

/* ============================================================
   COLONNE GAUCHE -- inchange
   ============================================================ */
.left-text-line {
  transform-origin: right center;
  transform: translateX(120%) translateY(15px) rotateY(-25deg);
  transition: transform var(--left-text-animation-duration) cubic-bezier(0.19, 1, 0.22, 1),
              opacity var(--left-text-opacity-duration) ease-out;
  justify-content: flex-end;
}

.left-text-line.visible {
  opacity: 1;
  transform: translateX(0%) translateY(0px) rotateY(0deg);
}

/* ============================================================
   COLONNE DROITE -- base commune
   ============================================================ */
.right-text-line {
  position: relative;
  width: 100%;
  height: 100%;
  justify-content: flex-start;
}

/* ============================================================
   EFFET 1: WE DREAM
   Concept: brume nebuleuse qui se condense en lettres solides
   Chaque lettre: blur 20px + scale 1.4 + translateY flottant -> net
   ============================================================ */
.right-text-line.effect-dream {
  opacity: 1;
}

.right-text-line.effect-dream span.char-dream {
  opacity: 0;
  display: inline-block;
  filter: blur(18px);
  transform: scale(1.4) translateY(-8px);
  will-change: filter, transform, opacity;
  -webkit-backface-visibility: hidden;
  backface-visibility: hidden;
}

.right-text-line.effect-dream.visible span.char-dream {
  animation: dreamCondense var(--dream-letter-duration) cubic-bezier(0.16, 1, 0.3, 1) forwards;
  animation-delay: calc(var(--dream-letter-stagger) * var(--i));
}

@keyframes dreamCondense {
  0% {
    opacity: 0;
    filter: blur(18px);
    transform: scale(1.4) translateY(-8px);
  }
  30% {
    opacity: 0.3;
    filter: blur(12px);
    transform: scale(1.25) translateY(-4px);
  }
  60% {
    opacity: 0.7;
    filter: blur(5px);
    transform: scale(1.08) translateY(-1px);
  }
  80% {
    opacity: 0.9;
    filter: blur(1.5px);
    transform: scale(1.02) translateY(0.5px);
  }
  100% {
    opacity: 1;
    filter: blur(0px);
    transform: scale(1) translateY(0px) translateZ(0);
  }
}

/* ============================================================
   EFFET 2: WE DESIGN
   Concept: tracé blueprint -- grille fugace puis lettres dessinées
   Chaque lettre: slide depuis la gauche avec effet "stylo technique"
   ============================================================ */
.right-text-line.effect-design {
  opacity: 1;
  position: relative;
}

/* Grille blueprint fugace en arrière-plan */
.right-text-line.effect-design::before {
  content: '';
  position: absolute;
  inset: -4px -8px;
  background-image:
    linear-gradient(rgba(10,10,10,0.06) 1px, transparent 1px),
    linear-gradient(90deg, rgba(10,10,10,0.06) 1px, transparent 1px);
  background-size: 8px 8px;
  opacity: 0;
  pointer-events: none;
  z-index: 0;
  transition: opacity 0.2s ease;
}

.right-text-line.effect-design.visible::before {
  animation: blueprintGrid 1.2s ease forwards;
}

@keyframes blueprintGrid {
  0% { opacity: 0; }
  20% { opacity: 1; }
  70% { opacity: 0.4; }
  100% { opacity: 0; }
}

.right-text-line.effect-design span.char-design {
  opacity: 0;
  display: inline-block;
  position: relative;
  overflow: hidden;
  transform: translateX(-12px) scaleY(0.3);
  transform-origin: left bottom;
  will-change: transform, opacity;
}

/* Trait de "crayon" qui sweeps la lettre */
.right-text-line.effect-design span.char-design::after {
  content: '';
  position: absolute;
  top: 0;
  left: 0;
  width: 2px;
  height: 100%;
  background: var(--text-primary, #1A1A18);
  opacity: 0;
  transform: scaleY(0);
  transform-origin: top center;
}

.right-text-line.effect-design.visible span.char-design {
  animation: designDraw var(--design-letter-duration) cubic-bezier(0.77, 0, 0.175, 1) forwards;
  animation-delay: calc(var(--design-letter-stagger) * var(--i));
}

.right-text-line.effect-design.visible span.char-design::after {
  animation: designStroke var(--design-letter-duration) cubic-bezier(0.77, 0, 0.175, 1) forwards;
  animation-delay: calc(var(--design-letter-stagger) * var(--i));
}

@keyframes designDraw {
  0% {
    opacity: 0;
    transform: translateX(-12px) scaleY(0.3);
    filter: brightness(2);
  }
  35% {
    opacity: 0.6;
    transform: translateX(-4px) scaleY(0.85);
    filter: brightness(1.4);
  }
  70% {
    opacity: 0.9;
    transform: translateX(1px) scaleY(1.02);
    filter: brightness(1.1);
  }
  100% {
    opacity: 1;
    transform: translateX(0) scaleY(1);
    filter: brightness(1);
  }
}

@keyframes designStroke {
  0% {
    opacity: 1;
    transform: scaleY(0);
  }
  30% {
    opacity: 1;
    transform: scaleY(1.1);
  }
  60% {
    opacity: 0.5;
    transform: scaleY(1);
  }
  100% {
    opacity: 0;
    transform: scaleY(1);
  }
}

/* ============================================================
   EFFET 3: WE DELIVER
   Concept: chute physique depuis le haut + rebond + onde d'impact
   Chaque lettre tombe individuellement avec stagger
   ============================================================ */
.right-text-line.effect-deliver {
  opacity: 1;
  position: relative;
  overflow: visible;
}

.right-text-line.effect-deliver span.char-deliver {
  opacity: 0;
  display: inline-block;
  transform: translateY(-120px) scaleY(0.7);
  will-change: transform, opacity;
}

.right-text-line.effect-deliver.visible span.char-deliver {
  animation: deliverFall var(--deliver-letter-duration) cubic-bezier(0.55, 0, 0.85, 0.2) forwards;
  animation-delay: calc(var(--deliver-letter-stagger) * var(--i));
}

@keyframes deliverFall {
  0% {
    opacity: 0;
    transform: translateY(-120px) scaleY(0.7) scaleX(1.1);
  }
  10% {
    opacity: 1;
  }
  /* Impact au sol */
  72% {
    transform: translateY(0px) scaleY(0.82) scaleX(1.12);
    animation-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
  }
  /* Rebond 1 */
  84% {
    transform: translateY(-14px) scaleY(1.08) scaleX(0.96);
    animation-timing-function: cubic-bezier(0.755, 0.050, 0.855, 0.060);
  }
  /* Impact 2 */
  91% {
    transform: translateY(0px) scaleY(0.94) scaleX(1.04);
    animation-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
  }
  /* Rebond 2 petit */
  96% {
    transform: translateY(-4px) scaleY(1.02) scaleX(0.99);
  }
  100% {
    opacity: 1;
    transform: translateY(0px) scaleY(1) scaleX(1);
  }
}

/* Onde d'impact -- injectee par JS sur chaque lettre */
.deliver-impact-ring {
  position: absolute;
  bottom: -2px;
  left: 50%;
  transform: translateX(-50%) scale(0);
  width: 20px;
  height: 4px;
  border-radius: 50%;
  border: 1px solid rgba(10, 10, 10, 0.35);
  pointer-events: none;
  animation: deliverImpact var(--deliver-impact-duration) cubic-bezier(0.25, 0.46, 0.45, 0.94) forwards;
}

@keyframes deliverImpact {
  0% {
    transform: translateX(-50%) scale(0);
    opacity: 0.6;
  }
  100% {
    transform: translateX(-50%) scale(2.5);
    opacity: 0;
  }
}

/* ============================================================
   EFFET 4: WE REFINE (typewriter WE RETRY -> WE REFINE)
   Le typewriter reste, + effet de "polissage" après REFINE
   ============================================================ */
.right-text-line.effect-typewriter {
  opacity: 0;
  position: relative;
  white-space: nowrap;
}

.right-text-line.effect-typewriter.typing {
  opacity: 1;
}

/* Curseur clignotant pendant la frappe */
.right-text-line.effect-typewriter.typing::after {
  content: '|';
  display: inline-block;
  margin-left: 1px;
  animation: cursorBlink 0.7s step-end infinite;
  opacity: 0.8;
  font-weight: 300;
}

.right-text-line.effect-typewriter.refine-done::after {
  display: none;
}

@keyframes cursorBlink {
  0%, 100% { opacity: 0.8; }
  50% { opacity: 0; }
}

/* Lettres de REFINE: état "brut" avant polissage */
.right-text-line.effect-typewriter span.char-refine {
  display: inline-block;
  position: relative;
  will-change: transform, filter;
}

/* Phase "bruit" -- lettres avec micro-imperfections aléatoires */
.right-text-line.effect-typewriter span.char-refine.is-rough {
  animation: refineNoise 0.4s ease forwards;
  animation-delay: calc(var(--i) * 20ms);
}

@keyframes refineNoise {
  0% {
    transform: translate(
      calc(var(--noise-x, 0) * 1px),
      calc(var(--noise-y, 0) * 1px)
    ) rotate(calc(var(--noise-r, 0) * 1deg));
    opacity: 0.6;
    filter: blur(calc(var(--noise-blur, 0) * 1px));
  }
  100% {
    transform: translate(0, 0) rotate(0deg);
    opacity: 1;
    filter: blur(0px);
  }
}

/* ============================================================
   EFFET 5: WE FINALIZE
   Concept: puzzle + flash de verrouillage sur chaque lettre
   ============================================================ */
.right-text-line.effect-finalize {
  opacity: 1;
  perspective: 800px;
  transform-style: preserve-3d;
}

.right-text-line.effect-finalize span.char-finalize {
  opacity: 0;
  display: inline-block;
  transform: translate(calc(var(--random-x, 0) * 1px), calc(var(--random-y, 0) * 1px))
             scale(var(--random-s, 0.8))
             rotate(calc(var(--random-r, 0) * 1deg));
  filter: brightness(0.6);
  transition-property: opacity, transform, filter;
  transition-duration: var(--finalize-letter-duration);
  transition-timing-function: cubic-bezier(0.68, -0.55, 0.265, 1.55);
  will-change: transform, opacity, filter;
}

.right-text-line.effect-finalize.visible span.char-finalize {
  opacity: 1;
  transform: translate(0, 0) scale(1) rotate(0deg);
  filter: brightness(1);
}

/* Flash de verrouillage -- overlay blanc transitoire */
.char-lock-flash {
  position: absolute;
  inset: 0;
  background: rgba(255, 255, 255, 0.9);
  border-radius: 1px;
  pointer-events: none;
  animation: lockFlash 0.18s ease-out forwards;
}

@keyframes lockFlash {
  0%  { opacity: 0.85; }
  100% { opacity: 0; }
}

/* Micro-cercle d'impact de verrouillage */
.char-lock-ring {
  position: absolute;
  top: 50%;
  left: 50%;
  width: 6px;
  height: 6px;
  margin: -3px 0 0 -3px;
  border-radius: 50%;
  border: 1px solid rgba(10, 10, 10, 0.5);
  pointer-events: none;
  animation: lockRing 0.3s ease-out forwards;
}

@keyframes lockRing {
  0%   { transform: scale(0.2); opacity: 0.8; }
  100% { transform: scale(2.5); opacity: 0; }
}

/* Point final -- goutte d'encre qui tombe */
.finalize-period {
  display: inline-block;
  opacity: 0;
  transform: translateY(-60px) scale(0.2);
  transform-origin: center bottom;
}

.finalize-period.visible {
  animation: inkDrop var(--finalize-period-duration) cubic-bezier(0.36, 0.07, 0.19, 0.97) forwards;
}

@keyframes inkDrop {
  0% {
    opacity: 0;
    transform: translateY(-60px) scale(0.2);
  }
  50% {
    opacity: 1;
    transform: translateY(4px) scale(1.3);
  }
  70% {
    transform: translateY(-3px) scale(0.9);
  }
  85% {
    transform: translateY(1.5px) scale(1.05);
  }
  100% {
    opacity: 1;
    transform: translateY(0) scale(1);
  }
}
