/* ═══════════════════════════════════════
   branding-page-fx.css (v2)
   Animazioni dedicate — pagina Branding &
   Comunicazione Strategica.
   File separato da animations.css (condiviso
   con le altre pagine del sito): qui vivono
   solo gli effetti pensati per impressionare
   su questa landing — DESKTOP + MOBILE.
═══════════════════════════════════════ */

/* ─────────────────────────────────────────
   0. INTRO "WOW" — sipario all'ingresso
   Si vede su tutti i dispositivi, dura ~1s.
───────────────────────────────────────── */
#fxIntro {
  position: fixed;
  inset: 0;
  z-index: 20000;
  display: flex;
  pointer-events: none;
}
.fx-intro-panel {
  flex: 1;
  background: var(--nv-black, #0a0a0a);
  transition: transform 0.85s cubic-bezier(0.76, 0, 0.24, 1);
}
.fx-intro-panel--l { transform: translateX(0); }
.fx-intro-panel--r { transform: translateX(0); }
body.fx-intro-out .fx-intro-panel--l { transform: translateX(-101%); }
body.fx-intro-out .fx-intro-panel--r { transform: translateX(101%); }

.fx-intro-mark {
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%) scale(0.85);
  font-family: 'Montserrat', sans-serif;
  font-weight: 800;
  font-size: clamp(22px, 6vw, 34px);
  letter-spacing: 0.04em;
  color: var(--nv-green, #00ff00);
  opacity: 0;
  animation: fxIntroMarkIn 0.5s ease-out 0.15s forwards, fxIntroMarkOut 0.35s ease-in 0.65s forwards;
  white-space: nowrap;
}
@keyframes fxIntroMarkIn {
  to { opacity: 1; transform: translate(-50%, -50%) scale(1); }
}
@keyframes fxIntroMarkOut {
  to { opacity: 0; transform: translate(-50%, -50%) scale(1.06); }
}
body.fx-intro-done #fxIntro { display: none; }
body:not(.fx-intro-done) { overflow: hidden; }

@media (prefers-reduced-motion: reduce) {
  #fxIntro { display: none !important; }
  body:not(.fx-intro-done) { overflow: auto; }
}

/* ─────────────────────────────────────────
   1. Barra di progresso scroll
───────────────────────────────────────── */
#fxProgress {
  position: fixed;
  top: 0;
  left: 0;
  height: 3px;
  width: 0%;
  background: linear-gradient(90deg, var(--nv-green), #b8ffb8, var(--nv-green));
  background-size: 200% 100%;
  z-index: 10001;
  animation: fxProgressShine 3s linear infinite;
  transition: width 0.1s ease-out;
  pointer-events: none;
}
@keyframes fxProgressShine {
  to { background-position: -200% 0; }
}

/* ─────────────────────────────────────────
   2. Hero: orbs fluttuanti — ORA ANCHE MOBILE
───────────────────────────────────────── */
.fx-orb {
  position: absolute;
  border-radius: 50%;
  filter: blur(60px);
  pointer-events: none;
  z-index: 0;
  opacity: 0.55;
  will-change: transform;
}
.fx-orb-1 {
  width: 380px;
  height: 380px;
  background: radial-gradient(circle, rgba(0, 255, 0, 0.35), transparent 70%);
  top: 8%;
  right: 6%;
  animation: fxOrbDrift1 14s ease-in-out infinite;
}
.fx-orb-2 {
  width: 260px;
  height: 260px;
  background: radial-gradient(circle, rgba(0, 255, 0, 0.2), transparent 70%);
  bottom: 12%;
  left: 4%;
  animation: fxOrbDrift2 18s ease-in-out infinite;
}
@keyframes fxOrbDrift1 {
  0%, 100% { transform: translate(0, 0) scale(1); }
  50%      { transform: translate(-40px, 30px) scale(1.15); }
}
@keyframes fxOrbDrift2 {
  0%, 100% { transform: translate(0, 0) scale(1); }
  50%      { transform: translate(30px, -25px) scale(1.1); }
}
/* Su mobile: non più nascosti, solo più piccoli e meno "pesanti" per le performance */
@media (max-width: 767px) {
  .fx-orb {
    filter: blur(38px);
    opacity: 0.4;
  }
  .fx-orb-1 { width: 220px; height: 220px; top: 4%; right: -8%; }
  .fx-orb-2 { width: 160px; height: 160px; bottom: 6%; left: -10%; }
}

/* ─────────────────────────────────────────
   3. Hero: rete di nodi animata (canvas)
   Sostituisce le vecchie particelle DOM con
   un'unica rete "costellazione" disegnata su
   canvas — molto più scenica e più leggera,
   attiva anche su mobile con meno nodi.
───────────────────────────────────────── */
.fx-particles {
  position: absolute;
  inset: 0;
  overflow: hidden;
  pointer-events: none;
  z-index: 0;
}
#fxNetwork {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  opacity: 0.9;
}
@media (prefers-reduced-motion: reduce) {
  #fxNetwork { display: none; }
}

/* ─────────────────────────────────────────
   3b. Burst iniziale — esplosione di particelle
   nell'istante in cui si apre il sipario.
   Effetto "wow" immediato, dura meno di un secondo.
───────────────────────────────────────── */
#fxBurst {
  position: fixed;
  inset: 0;
  z-index: 19999;
  pointer-events: none;
  overflow: hidden;
}
.fx-burst-particle {
  position: absolute;
  top: 50%;
  left: 50%;
  width: var(--fx-bsize, 6px);
  height: var(--fx-bsize, 6px);
  margin: calc(var(--fx-bsize, 6px) / -2) 0 0 calc(var(--fx-bsize, 6px) / -2);
  border-radius: 50%;
  background: var(--nv-green, #00ff00);
  box-shadow: 0 0 10px rgba(0, 255, 0, 0.8);
  opacity: 0;
  animation: fxBurstOut var(--fx-bdur, 0.8s) cubic-bezier(0.16, 1, 0.3, 1) forwards;
}
@keyframes fxBurstOut {
  0%   { transform: translate(0, 0) scale(1); opacity: 1; }
  100% { transform: translate(var(--fx-bx, 200px), var(--fx-by, 200px)) scale(0.2); opacity: 0; }
}
@media (prefers-reduced-motion: reduce) {
  #fxBurst { display: none; }
}

/* ─────────────────────────────────────────
   3c. Spotlight cursore — bagliore che segue
   il mouse su tutta la pagina (solo desktop).
───────────────────────────────────────── */
#fxSpotlight {
  position: fixed;
  top: 0;
  left: 0;
  width: 480px;
  height: 480px;
  margin: -240px 0 0 -240px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(0, 255, 0, 0.16), transparent 70%);
  mix-blend-mode: screen;
  pointer-events: none;
  z-index: 5;
  opacity: 0;
  transition: opacity 0.4s ease;
  will-change: transform;
}
#fxSpotlight.fx-active { opacity: 1; }
@media (max-width: 991px), (pointer: coarse) {
  #fxSpotlight { display: none; }
}
@media (prefers-reduced-motion: reduce) {
  #fxSpotlight { display: none; }
}

/* ─────────────────────────────────────────
   3d. Testo "decodifica" (scramble reveal)
   Usato per titoli ed eyebrow: appare a
   caratteri casuali e si risolve nel testo
   reale. Molto scenico, funziona anche su
   mobile (è puro JS + testo, niente hover).
───────────────────────────────────────── */
.fx-scramble-line {
  display: inline-block;
}
.fx-scramble-line[data-text] {
  opacity: 0;
  transition: opacity 0.25s ease;
}
.fx-scramble-line.fx-scrambling,
.fx-scramble-line.fx-done {
  opacity: 1;
}
@media (prefers-reduced-motion: reduce) {
  .fx-scramble-line[data-text] { opacity: 1; }
}

/* ─────────────────────────────────────────
   4. Hero title: reveal a righe (split)
───────────────────────────────────────── */
.fx-split-line {
  display: block;
  overflow: hidden;
}
.fx-split-line > span {
  display: inline-block;
  transform: translateY(110%) rotate(4deg);
  opacity: 0;
  animation: fxLineIn 0.9s var(--nv-ease) forwards;
}
.fx-split-line:nth-of-type(1) > span { animation-delay: 0.15s; }
.fx-split-line:nth-of-type(2) > span { animation-delay: 0.28s; }
.fx-split-line:nth-of-type(3) > span { animation-delay: 0.41s; }
.fx-split-line:nth-of-type(4) > span { animation-delay: 0.54s; }
/* Ritardo extra per allinearsi con l'intro overlay (parte dopo il sipario) */
body:not(.fx-intro-done) .fx-split-line > span { animation-play-state: paused; }
@keyframes fxLineIn {
  to { transform: translateY(0) rotate(0); opacity: 1; }
}

/* ─────────────────────────────────────────
   5. Testo "shine" animato
───────────────────────────────────────── */
.fx-shine {
  background: linear-gradient(100deg, var(--nv-green) 30%, #d4ffd4 45%, var(--nv-green) 60%);
  background-size: 250% 100%;
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
  animation: fxShineMove 4.5s ease-in-out infinite;
}
@keyframes fxShineMove {
  0%   { background-position: 0% 0; }
  50%  { background-position: 100% 0; }
  100% { background-position: 0% 0; }
}

/* ─────────────────────────────────────────
   6. Scroll cue — freccina che invita a scendere
   (nuovo, visibile anche su mobile)
───────────────────────────────────────── */
.fx-scrollcue {
  position: absolute;
  left: 50%;
  bottom: 18px;
  transform: translateX(-50%);
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 6px;
  z-index: 1;
  opacity: 0.75;
  transition: opacity 0.4s ease;
}
.fx-scrollcue span {
  font-size: 10px;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--nv-green, #00ff00);
}
.fx-scrollcue i {
  font-size: 16px;
  color: var(--nv-green, #00ff00);
  animation: fxScrollBounce 1.6s ease-in-out infinite;
}
@keyframes fxScrollBounce {
  0%, 100% { transform: translateY(0); opacity: 0.6; }
  50%      { transform: translateY(6px); opacity: 1; }
}
.fx-scrollcue.fx-hide { opacity: 0; }
@media (prefers-reduced-motion: reduce) {
  .fx-scrollcue i { animation: none; }
}

/* ─────────────────────────────────────────
   7. Ticker: leggero rimbalzo ad onda
───────────────────────────────────────── */
.nv-ticker-inner .nv-ticker-item {
  display: inline-block;
  animation: fxTickerWave 2.4s ease-in-out infinite;
}
.nv-ticker-inner .nv-ticker-item:nth-child(4n+1) { animation-delay: 0s; }
.nv-ticker-inner .nv-ticker-item:nth-child(4n+2) { animation-delay: 0.15s; }
.nv-ticker-inner .nv-ticker-item:nth-child(4n+3) { animation-delay: 0.3s; }
.nv-ticker-inner .nv-ticker-item:nth-child(4n+4) { animation-delay: 0.45s; }
@keyframes fxTickerWave {
  0%, 100% { transform: translateY(0); }
  50%      { transform: translateY(-4px); }
}
.nv-ticker:hover .nv-ticker-inner { animation-play-state: paused; }

/* ─────────────────────────────────────────
   8. Quote: il titolo ora si "decodifica" a
   caratteri casuali (vedi .fx-scramble-line
   sopra) invece di un semplice wipe — stessa
   entrata scenica ma garantita da mostrare.
───────────────────────────────────────── */
.fx-wipe {
  position: relative;
}

.fx-accent-line {
  width: 0;
  height: 2px;
  background: var(--nv-green);
  margin: 0 auto 32px;
  transition: width 0.9s var(--nv-ease) 0.2s;
}
.fx-accent-line.fx-in { width: 64px; }

/* ─────────────────────────────────────────
   9. Timeline: la linea si riempie con lo scroll
───────────────────────────────────────── */
.lp-timeline.fx-line-wrap {
  --fx-fill: 0%;
}
.lp-timeline.fx-line-wrap::before {
  background: rgba(0, 255, 0, 0.15);
}
.lp-timeline.fx-line-wrap::after {
  content: '';
  position: absolute;
  left: 27px;
  top: 8px;
  width: 1px;
  height: var(--fx-fill);
  background: var(--nv-green);
  box-shadow: 0 0 8px rgba(0, 255, 0, 0.6);
  transition: height 0.3s linear;
}
@media (max-width: 767px) {
  .lp-timeline.fx-line-wrap::after { left: 23px; }
}

.fx-num {
  transition: transform 0.5s var(--nv-ease), box-shadow 0.5s ease, background 0.5s ease, color 0.5s ease;
}
.lp-timeline-item:hover .fx-num,
.lp-timeline-item.fx-active .fx-num {
  transform: scale(1.12) rotate(-6deg);
  box-shadow: 0 0 22px rgba(0, 255, 0, 0.55);
  background: var(--nv-green);
  color: var(--nv-black);
}

/* ─────────────────────────────────────────
   10. Servizi: riga con highlight scorrevole
   Su mobile l'hover non esiste: aggiungiamo
   una classe .fx-active gestita via JS su
   tap/intersezione, con la stessa resa visiva.
───────────────────────────────────────── */
.fx-row {
  position: relative;
  overflow: hidden;
  transition: padding-left 0.4s var(--nv-ease);
}
.fx-row::before {
  content: '';
  position: absolute;
  inset: 0;
  background: linear-gradient(90deg, rgba(0, 255, 0, 0.08), transparent);
  transform: translateX(-100%);
  transition: transform 0.5s var(--nv-ease);
  z-index: 0;
}
.fx-row:hover::before,
.fx-row.fx-active::before { transform: translateX(0); }
.fx-row:hover,
.fx-row.fx-active { padding-left: 14px; }
.fx-row > * { position: relative; z-index: 1; }

.fx-row-arrow {
  opacity: 0;
  transform: translateX(-8px);
  transition: opacity 0.35s ease, transform 0.35s ease;
  color: var(--nv-green);
  margin-left: 10px;
  display: inline-block;
}
.fx-row:hover .fx-row-arrow,
.fx-row.fx-active .fx-row-arrow {
  opacity: 1;
  transform: translateX(0);
}

/* Reveal alternato sinistra/destra per riga */
.fx-row.reveal { transform: translateX(-24px); }
.fx-row.reveal:nth-of-type(even) { transform: translateX(24px); }
.fx-row.reveal.visible { transform: translateX(0); }
@media (max-width: 767px) {
  /* su mobile lo swipe laterale è più contenuto per non "sforare" i margini */
  .fx-row.reveal,
  .fx-row.reveal:nth-of-type(even) { transform: translateY(18px); }
  .fx-row.reveal.visible { transform: translateY(0); }
}

/* ─────────────────────────────────────────
   11. Perché Not Visual: check con rimbalzo elastico
───────────────────────────────────────── */
.fx-check {
  display: inline-flex;
  transform: scale(0);
  transition: transform 0.55s cubic-bezier(0.34, 1.56, 0.64, 1);
}
.fx-check.fx-in { transform: scale(1); }

.lp-why-row {
  position: relative;
}
.lp-why-row::after {
  content: '';
  position: absolute;
  bottom: 0;
  left: 0;
  width: 0;
  height: 1px;
  background: var(--nv-green);
  transition: width 0.4s var(--nv-ease);
}
.lp-why-row:hover::after,
.lp-why-row.fx-active::after { width: 100%; }

/* ─────────────────────────────────────────
   12. CTA finale: cornice luminosa rotante
   + pulsazione "respiro" continua (visibile
   anche su mobile, dove non c'è hover)
───────────────────────────────────────── */
.fx-cta {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  animation: fxCtaBreath 3.2s ease-in-out infinite;
}
.fx-cta::before {
  content: '';
  position: absolute;
  top: 50%;
  left: 50%;
  width: 200%;
  aspect-ratio: 1;
  background: conic-gradient(from 0deg, transparent 0deg, rgba(0, 255, 0, 0.9) 40deg, transparent 100deg, transparent 360deg);
  transform: translate(-50%, -50%);
  animation: fxSpin 5s linear infinite;
  z-index: 0;
  opacity: 0.55;
}
.fx-cta::after {
  content: '';
  position: absolute;
  inset: 1px;
  background: var(--nv-black);
  border-radius: 11px;
  z-index: 0;
}
.fx-cta > * { position: relative; z-index: 1; }
@keyframes fxSpin {
  to { transform: translate(-50%, -50%) rotate(360deg); }
}
@keyframes fxCtaBreath {
  0%, 100% { box-shadow: 0 0 0 rgba(0, 255, 0, 0); }
  50%      { box-shadow: 0 0 32px rgba(0, 255, 0, 0.22); }
}

/* ─────────────────────────────────────────
   13. Pulsanti: effetto magnetico + ripple
   + pulsazione "invito al click" (utile su
   mobile dove non c'è mousemove magnetico)
───────────────────────────────────────── */
.fx-magnetic {
  position: relative;
  overflow: hidden;
  will-change: transform;
}
.fx-ripple {
  position: absolute;
  border-radius: 50%;
  background: rgba(255, 255, 255, 0.5);
  transform: scale(0);
  animation: fxRippleOut 0.65s ease-out forwards;
  pointer-events: none;
}
@keyframes fxRippleOut {
  to { transform: scale(2.6); opacity: 0; }
}
@media (max-width: 767px) {
  .nv-btn-primary.fx-magnetic {
    animation: fxBtnPulse 2.6s ease-in-out infinite;
  }
  @keyframes fxBtnPulse {
    0%, 100% { box-shadow: 0 0 0 rgba(0, 255, 0, 0.35); }
    50%      { box-shadow: 0 0 0 10px rgba(0, 255, 0, 0); }
  }
}

/* ─────────────────────────────────────────
   14. Rispetto per chi preferisce animazioni ridotte
───────────────────────────────────────── */
@media (prefers-reduced-motion: reduce) {
  #fxProgress,
  .fx-orb,
  .fx-split-line > span,
  .fx-shine,
  .nv-ticker-inner .nv-ticker-item,
  .fx-accent-line,
  .lp-timeline.fx-line-wrap::after,
  .fx-num,
  .fx-row::before,
  .fx-row-arrow,
  .fx-check,
  .fx-cta,
  .fx-cta::before,
  .nv-btn-primary.fx-magnetic {
    animation: none !important;
    transition: none !important;
  }
  .fx-split-line > span { transform: none; opacity: 1; }
  .fx-check { transform: scale(1); }
  .fx-row.reveal,
  .fx-row.reveal:nth-of-type(even) { transform: none; }
}
