/**
 * Genius Board — ad motion presets (Admin preview + Player).
 * Intensity via --fx-intensity (soft≈0.65 · normal=1 · strong≈1.35).
 * Duration via --ad-dur.
 */
/*
 * Do NOT set position:relative on .ad-fx — it loads after player.css and was
 * overriding position:absolute; inset:0. Relative + only abspos children
 * collapses .ad-fx to height:0 → blank ads pane (community still worked).
 * Admin preview keeps relative via .ad-fx-preview only.
 */
:is(.ad-fx, .ad-fx-preview) {
  --fx-intensity: 1;
  --ad-dur: 8s;
  overflow: hidden;
  isolation: isolate;
  contain: paint;
}
.ad-fx-preview {
  position: relative;
}

/* Admin preview: cover. Signage ads override below to Canva-style contain. */
:is(.ad-fx, .ad-fx-preview) :is(img, video) {
  width: 100%;
  height: 100%;
  max-width: none;
  max-height: none;
  object-fit: cover;
  object-position: center;
  transform-origin: center center;
  will-change: transform, opacity, filter;
}

/* Full creative visible — Signage ads only (img + video); never fill / never cover-crop */
body[data-gb-app="player"] :is(.ads, .ads-multi .ad-pane) .ad-fx .ad-media {
  object-fit: var(--gb-object-fit, contain) !important;
  object-position: center !important;
  visibility: visible !important;
  opacity: 1 !important;
}
.ads-multi .ad-fx .ad-media {
  opacity: 1 !important;
}
/* Entrance FX that animate opacity would paint black cells in multi layouts */
.ads-multi .ad-fx.fx-rise .ad-media,
.ads-multi .ad-fx.fx-punch .ad-media,
.ads-multi .ad-fx.fx-veil .ad-media,
.ads-multi .ad-fx.fx-alegre .ad-media,
.ads-multi .ad-fx.fx-anuncio .ad-media {
  animation: gbKenBurns var(--ad-dur, 8s) ease-in-out both !important;
  opacity: 1 !important;
}
/* Letterbox bars only on Admin preview — never on Signage multi cells */
body[data-gb-app="player"] .ads-multi .ad-fx.fx-cinematic::before,
body[data-gb-app="player"] .ads-multi .ad-fx.fx-cinematic::after {
  content: none !important;
  display: none !important;
  height: 0 !important;
}

/* Overlay layers (CSS-only; no JS loops) */
:is(.ad-fx, .ad-fx-preview)::before,
:is(.ad-fx, .ad-fx-preview)::after {
  content: none;
  pointer-events: none;
}

/* —— No motion (explicit still) —— */
:is(.ad-fx, .ad-fx-preview).fx-none :is(img, video) {
  animation: none !important;
  transform: none !important;
  filter: none !important;
}
:is(.ad-fx, .ad-fx-preview).fx-none::before,
:is(.ad-fx, .ad-fx-preview).fx-none::after {
  content: none !important;
  display: none !important;
}

/* —— Basic / classic —— */
:is(.ad-fx, .ad-fx-preview).fx-kenburns :is(img, video) {
  animation: gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbKenBurns {
  from { transform: scale(calc(1.02 + 0.03 * var(--fx-intensity, 1))) translate3d(calc(-1.5% * var(--fx-intensity, 1)), 0, 0); }
  to { transform: scale(calc(1.08 + 0.1 * var(--fx-intensity, 1))) translate3d(calc(2% * var(--fx-intensity, 1)), calc(-1.5% * var(--fx-intensity, 1)), 0); }
}

:is(.ad-fx, .ad-fx-preview).fx-drift :is(img, video) {
  animation: gbDrift var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbDrift {
  from { transform: scale(1.12) translate3d(calc(-3% * var(--fx-intensity, 1)), 1%, 0); }
  to { transform: scale(1.12) translate3d(calc(3% * var(--fx-intensity, 1)), -1%, 0); }
}

:is(.ad-fx, .ad-fx-preview).fx-rise :is(img, video) {
  animation: gbRise 1.1s cubic-bezier(.2,.8,.2,1) both,
             gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbRise {
  from { opacity: 0; transform: translate3d(0, calc(8% * var(--fx-intensity, 1)), 0) scale(1.08); }
  to { opacity: 1; transform: translate3d(0, 0, 0) scale(1.08); }
}

:is(.ad-fx, .ad-fx-preview).fx-punch :is(img, video) {
  animation: gbPunch .85s cubic-bezier(.2,.9,.2,1) both,
             gbDrift var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbPunch {
  0% { opacity: 0; transform: scale(calc(1.15 + 0.13 * var(--fx-intensity, 1))); filter: brightness(1.15); }
  55% { opacity: 1; transform: scale(1.04); }
  100% { transform: scale(1.08); filter: brightness(1); }
}

:is(.ad-fx, .ad-fx-preview).fx-veil :is(img, video) {
  animation: gbVeil 1.2s ease both,
             gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbVeil {
  from { opacity: 0; filter: blur(calc(10px * var(--fx-intensity, 1))) brightness(.85); transform: scale(1.1); }
  to { opacity: 1; filter: blur(0) brightness(1); transform: scale(1.1); }
}

:is(.ad-fx, .ad-fx-preview).fx-split {
  --split: 50%;
}
:is(.ad-fx, .ad-fx-preview).fx-split .ad-split-mask {
  display: block;
  position: absolute;
  inset: 0;
  background:
    linear-gradient(90deg, #05090c 0, #05090c calc(var(--split) - 1px), transparent calc(var(--split) - 1px), transparent calc(var(--split) + 1px), #05090c calc(var(--split) + 1px), #05090c);
  animation: gbSplit 1.05s cubic-bezier(.2,.8,.2,1) both;
  z-index: 2;
}
:is(.ad-fx, .ad-fx-preview).fx-split :is(img, video) {
  animation: gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbSplit {
  from { clip-path: inset(0 0 0 0); opacity: 1; }
  to { clip-path: inset(0 50% 0 50%); opacity: 0; }
}

:is(.ad-fx, .ad-fx-preview).fx-orbit :is(img, video) {
  animation: gbOrbit var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbOrbit {
  0% { transform: scale(1.1) rotate(calc(-1.2deg * var(--fx-intensity, 1))) translate3d(calc(-1% * var(--fx-intensity, 1)), 0, 0); filter: brightness(.95); }
  50% { transform: scale(1.16) rotate(calc(0.6deg * var(--fx-intensity, 1))) translate3d(calc(1% * var(--fx-intensity, 1)), -1%, 0); filter: brightness(1.05); }
  100% { transform: scale(1.12) rotate(calc(-0.4deg * var(--fx-intensity, 1))) translate3d(0, 0.5%, 0); filter: brightness(1); }
}

:is(.ad-fx, .ad-fx-preview).fx-pulse :is(img, video) {
  animation: gbPulse var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbPulse {
  0%, 100% { transform: scale(1.06); }
  50% { transform: scale(calc(1.06 + 0.08 * var(--fx-intensity, 1))); }
}

/* —— Creative (Intermedia+) —— */

/* Barrido de luz cinematográfico */
:is(.ad-fx, .ad-fx-preview).fx-shine :is(img, video) {
  animation: gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
:is(.ad-fx, .ad-fx-preview).fx-shine::before {
  content: "";
  position: absolute;
  inset: -20%;
  z-index: 2;
  background: linear-gradient(
    105deg,
    transparent 35%,
    rgba(255, 248, 220, calc(0.08 * var(--fx-intensity, 1))) 45%,
    rgba(255, 236, 180, calc(0.42 * var(--fx-intensity, 1))) 50%,
    rgba(255, 248, 220, calc(0.08 * var(--fx-intensity, 1))) 55%,
    transparent 65%
  );
  transform: translate3d(-60%, 0, 0) skewX(-12deg);
  animation: gbShineSweep calc(var(--ad-dur, 8s) * 0.85) ease-in-out both;
  mix-blend-mode: soft-light;
}
@keyframes gbShineSweep {
  0% { transform: translate3d(-70%, 0, 0) skewX(-12deg); opacity: 0; }
  12% { opacity: 1; }
  55% { opacity: 1; }
  100% { transform: translate3d(70%, 0, 0) skewX(-12deg); opacity: 0; }
}

/* Parallax suave (eje mixto, no solo lateral) */
:is(.ad-fx, .ad-fx-preview).fx-parallax :is(img, video) {
  animation: gbParallax var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbParallax {
  0% {
    transform:
      scale(calc(1.14 + 0.04 * var(--fx-intensity, 1)))
      translate3d(calc(-2.5% * var(--fx-intensity, 1)), calc(1.8% * var(--fx-intensity, 1)), 0)
      rotate(calc(-0.35deg * var(--fx-intensity, 1)));
  }
  50% {
    transform:
      scale(calc(1.2 + 0.06 * var(--fx-intensity, 1)))
      translate3d(calc(1.5% * var(--fx-intensity, 1)), calc(-2.2% * var(--fx-intensity, 1)), 0)
      rotate(calc(0.25deg * var(--fx-intensity, 1)));
  }
  100% {
    transform:
      scale(calc(1.16 + 0.05 * var(--fx-intensity, 1)))
      translate3d(calc(2.2% * var(--fx-intensity, 1)), calc(0.6% * var(--fx-intensity, 1)), 0)
      rotate(calc(-0.15deg * var(--fx-intensity, 1)));
  }
}

/* Grano + viñeta (mood cine) */
:is(.ad-fx, .ad-fx-preview).fx-filmMood :is(img, video) {
  animation: gbFilmGrade var(--ad-dur, 8s) ease-in-out both,
             gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbFilmGrade {
  0%, 100% { filter: contrast(1.08) saturate(0.92) brightness(0.96); }
  50% { filter: contrast(calc(1.08 + 0.06 * var(--fx-intensity, 1))) saturate(0.88) brightness(0.94); }
}
:is(.ad-fx, .ad-fx-preview).fx-filmMood::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  opacity: calc(0.18 * var(--fx-intensity, 1));
  background-image:
    repeating-radial-gradient(circle at 20% 30%, rgba(255,255,255,.35) 0 0.6px, transparent 0.8px 3px),
    repeating-radial-gradient(circle at 70% 60%, rgba(0,0,0,.4) 0 0.5px, transparent 0.7px 2.5px);
  background-size: 120px 120px, 90px 90px;
  animation: gbGrainDrift calc(var(--ad-dur, 8s) * 0.5) steps(6) infinite;
  mix-blend-mode: overlay;
}
:is(.ad-fx, .ad-fx-preview).fx-filmMood::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background: radial-gradient(ellipse 75% 70% at 50% 45%, transparent 40%, rgba(5, 9, 12, calc(0.55 * var(--fx-intensity, 1))) 100%);
  animation: gbVignettePulse var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbGrainDrift {
  0% { transform: translate3d(0, 0, 0); }
  25% { transform: translate3d(-2%, 1%, 0); }
  50% { transform: translate3d(1%, -2%, 0); }
  75% { transform: translate3d(-1%, -1%, 0); }
  100% { transform: translate3d(0, 0, 0); }
}
@keyframes gbVignettePulse {
  0%, 100% { opacity: 0.85; }
  50% { opacity: 1; }
}

/* Borde cromático sutil (no glitch agresivo) */
:is(.ad-fx, .ad-fx-preview).fx-chroma :is(img, video) {
  animation: gbChroma var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbChroma {
  0%, 100% {
    transform: scale(1.1);
    filter:
      contrast(1.04)
      drop-shadow(calc(-1.2px * var(--fx-intensity, 1)) 0 0 rgba(180, 70, 50, 0.35))
      drop-shadow(calc(1.2px * var(--fx-intensity, 1)) 0 0 rgba(40, 120, 140, 0.35));
  }
  40% {
    transform: scale(1.14) translate3d(calc(0.4% * var(--fx-intensity, 1)), 0, 0);
    filter:
      contrast(1.08)
      drop-shadow(calc(-2px * var(--fx-intensity, 1)) 0 0 rgba(180, 70, 50, 0.4))
      drop-shadow(calc(2px * var(--fx-intensity, 1)) 0 0 rgba(40, 120, 140, 0.4));
  }
  70% {
    transform: scale(1.12) translate3d(calc(-0.3% * var(--fx-intensity, 1)), 0.2%, 0);
    filter:
      contrast(1.05)
      drop-shadow(calc(-1px * var(--fx-intensity, 1)) 0 0 rgba(180, 70, 50, 0.28))
      drop-shadow(calc(1.5px * var(--fx-intensity, 1)) 0 0 rgba(40, 120, 140, 0.32));
  }
}
:is(.ad-fx, .ad-fx-preview).fx-chroma::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  box-shadow: inset 0 0 calc(28px * var(--fx-intensity, 1)) rgba(232, 196, 122, calc(0.18 * var(--fx-intensity, 1)));
  animation: gbRimGlow var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbRimGlow {
  0%, 100% { opacity: 0.55; }
  50% { opacity: 1; }
}

/* Cristal clima (lluvia / escarcha) */
:is(.ad-fx, .ad-fx-preview).fx-glassWeather :is(img, video) {
  animation: gbGlassMedia var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbGlassMedia {
  from { transform: scale(1.12); filter: brightness(0.92) saturate(0.95); }
  to { transform: scale(1.18) translate3d(0, calc(-1% * var(--fx-intensity, 1)), 0); filter: brightness(0.96) saturate(1); }
}
:is(.ad-fx, .ad-fx-preview).fx-glassWeather::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background-image:
    linear-gradient(165deg, transparent 40%, rgba(180, 210, 230, calc(0.07 * var(--fx-intensity, 1))) 50%, transparent 60%),
    repeating-linear-gradient(
      100deg,
      transparent 0 14px,
      rgba(200, 220, 235, calc(0.14 * var(--fx-intensity, 1))) 14px 15px,
      transparent 15px 28px
    ),
    radial-gradient(circle at 18% 22%, rgba(255,255,255,calc(0.35 * var(--fx-intensity, 1))) 0 1.2px, transparent 1.8px),
    radial-gradient(circle at 62% 48%, rgba(255,255,255,calc(0.28 * var(--fx-intensity, 1))) 0 1px, transparent 1.6px),
    radial-gradient(circle at 78% 18%, rgba(255,255,255,calc(0.32 * var(--fx-intensity, 1))) 0 1.4px, transparent 2px),
    radial-gradient(circle at 40% 72%, rgba(255,255,255,calc(0.22 * var(--fx-intensity, 1))) 0 1px, transparent 1.5px);
  background-size: 100% 100%, 100% 180%, 100% 100%, 100% 100%, 100% 100%, 100% 100%;
  animation: gbGlassRain calc(2.8s / max(var(--fx-intensity, 1), 0.5)) linear infinite;
  mix-blend-mode: screen;
  opacity: 0.85;
}
:is(.ad-fx, .ad-fx-preview).fx-glassWeather::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background: linear-gradient(180deg, rgba(120, 150, 170, 0.12), transparent 35%, rgba(8, 14, 20, 0.2));
  backdrop-filter: blur(0.3px);
}
@keyframes gbGlassRain {
  from { background-position: 0 0, 0 -40%, 0 0, 0 0, 0 0, 0 0; }
  to { background-position: 0 0, 0 140%, 0 0, 0 0, 0 0, 0 0; }
}

/* Color grade cálido */
:is(.ad-fx, .ad-fx-preview).fx-gradeWarm :is(img, video) {
  animation: gbGradeWarm var(--ad-dur, 8s) ease-in-out both,
             gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbGradeWarm {
  0%, 100% {
    filter: sepia(calc(0.22 * var(--fx-intensity, 1))) saturate(calc(1.1 + 0.15 * var(--fx-intensity, 1))) brightness(1.04) hue-rotate(-6deg);
  }
  50% {
    filter: sepia(calc(0.32 * var(--fx-intensity, 1))) saturate(calc(1.2 + 0.2 * var(--fx-intensity, 1))) brightness(1.08) hue-rotate(-10deg);
  }
}
:is(.ad-fx, .ad-fx-preview).fx-gradeWarm::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background: radial-gradient(ellipse 80% 60% at 70% 10%, rgba(255, 180, 90, calc(0.18 * var(--fx-intensity, 1))), transparent 55%);
  mix-blend-mode: soft-light;
  animation: gbWarmWash var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbWarmWash {
  0%, 100% { opacity: 0.7; }
  50% { opacity: 1; }
}

/* Color grade frío */
:is(.ad-fx, .ad-fx-preview).fx-gradeCool :is(img, video) {
  animation: gbGradeCool var(--ad-dur, 8s) ease-in-out both,
             gbDrift var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbGradeCool {
  0%, 100% {
    filter: saturate(calc(0.9 + 0.05 * var(--fx-intensity, 1))) brightness(1.02) hue-rotate(calc(12deg * var(--fx-intensity, 1))) contrast(1.05);
  }
  50% {
    filter: saturate(calc(0.95 + 0.08 * var(--fx-intensity, 1))) brightness(1.05) hue-rotate(calc(18deg * var(--fx-intensity, 1))) contrast(1.08);
  }
}
:is(.ad-fx, .ad-fx-preview).fx-gradeCool::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background: radial-gradient(ellipse 70% 55% at 30% 0%, rgba(90, 160, 190, calc(0.2 * var(--fx-intensity, 1))), transparent 55%);
  mix-blend-mode: soft-light;
  animation: gbWarmWash var(--ad-dur, 8s) ease-in-out both;
}

/* Polvo / destellos (CSS particles) */
:is(.ad-fx, .ad-fx-preview).fx-sparkle :is(img, video) {
  animation: gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
:is(.ad-fx, .ad-fx-preview).fx-sparkle::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background-image:
    radial-gradient(circle at 12% 28%, rgba(255, 236, 190, calc(0.85 * var(--fx-intensity, 1))) 0 1.2px, transparent 2px),
    radial-gradient(circle at 38% 62%, rgba(255, 255, 255, calc(0.7 * var(--fx-intensity, 1))) 0 1px, transparent 1.8px),
    radial-gradient(circle at 72% 22%, rgba(232, 196, 122, calc(0.8 * var(--fx-intensity, 1))) 0 1.4px, transparent 2.2px),
    radial-gradient(circle at 84% 68%, rgba(255, 255, 255, calc(0.55 * var(--fx-intensity, 1))) 0 0.9px, transparent 1.6px),
    radial-gradient(circle at 55% 40%, rgba(255, 220, 160, calc(0.65 * var(--fx-intensity, 1))) 0 1.1px, transparent 2px),
    radial-gradient(circle at 22% 78%, rgba(255, 255, 255, calc(0.5 * var(--fx-intensity, 1))) 0 0.8px, transparent 1.4px),
    radial-gradient(circle at 48% 12%, rgba(232, 196, 122, calc(0.75 * var(--fx-intensity, 1))) 0 1px, transparent 1.8px);
  animation: gbSparkleFloat var(--ad-dur, 8s) ease-in-out both;
  mix-blend-mode: plus-lighter;
}
@keyframes gbSparkleFloat {
  0% { opacity: 0; transform: translate3d(0, 4%, 0) scale(0.96); }
  15% { opacity: 1; }
  50% { opacity: calc(0.75 + 0.2 * var(--fx-intensity, 1)); transform: translate3d(1%, -2%, 0) scale(1.02); }
  85% { opacity: 1; }
  100% { opacity: 0.4; transform: translate3d(-1%, -5%, 0) scale(1.04); }
}

/* Cortina que se abre */
:is(.ad-fx, .ad-fx-preview).fx-curtain :is(img, video) {
  animation: gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
:is(.ad-fx, .ad-fx-preview).fx-curtain::before,
:is(.ad-fx, .ad-fx-preview).fx-curtain::after {
  content: "";
  position: absolute;
  top: 0;
  bottom: 0;
  width: 52%;
  z-index: 3;
  background:
    linear-gradient(180deg, #1a1410, #0c1014 55%, #080c10);
  box-shadow: inset 0 0 40px rgba(0, 0, 0, 0.45);
}
:is(.ad-fx, .ad-fx-preview).fx-curtain::before {
  left: 0;
  border-right: 1px solid rgba(232, 196, 122, 0.18);
  animation: gbCurtainLeft calc(1.15s / max(var(--fx-intensity, 1) * 0.7, 0.55)) cubic-bezier(.2,.8,.2,1) both;
  transform-origin: left center;
}
:is(.ad-fx, .ad-fx-preview).fx-curtain::after {
  right: 0;
  border-left: 1px solid rgba(232, 196, 122, 0.18);
  animation: gbCurtainRight calc(1.15s / max(var(--fx-intensity, 1) * 0.7, 0.55)) cubic-bezier(.2,.8,.2,1) both;
  transform-origin: right center;
}
@keyframes gbCurtainLeft {
  from { transform: translate3d(0, 0, 0) scaleX(1); opacity: 1; }
  to { transform: translate3d(calc(-100% * var(--fx-intensity, 1) * 0.15 - 100%), 0, 0) scaleX(0.85); opacity: 0; }
}
@keyframes gbCurtainRight {
  from { transform: translate3d(0, 0, 0) scaleX(1); opacity: 1; }
  to { transform: translate3d(calc(100% * var(--fx-intensity, 1) * 0.15 + 100%), 0, 0) scaleX(0.85); opacity: 0; }
}

/* Shimmer holográfico (ámbar / teal de marca, no púrpura) */
:is(.ad-fx, .ad-fx-preview).fx-holo :is(img, video) {
  animation: gbHoloMedia var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbHoloMedia {
  0%, 100% {
    transform: scale(1.1);
    filter: saturate(calc(1.05 + 0.1 * var(--fx-intensity, 1))) brightness(1.02) contrast(1.04);
  }
  50% {
    transform: scale(calc(1.14 + 0.04 * var(--fx-intensity, 1))) translate3d(0.5%, -0.5%, 0);
    filter: saturate(calc(1.15 + 0.15 * var(--fx-intensity, 1))) brightness(1.06) contrast(1.06);
  }
}
:is(.ad-fx, .ad-fx-preview).fx-holo::before {
  content: "";
  position: absolute;
  inset: -10%;
  z-index: 2;
  background: linear-gradient(
    120deg,
    transparent 20%,
    rgba(90, 168, 196, calc(0.22 * var(--fx-intensity, 1))) 35%,
    rgba(232, 196, 122, calc(0.28 * var(--fx-intensity, 1))) 48%,
    rgba(122, 184, 154, calc(0.2 * var(--fx-intensity, 1))) 62%,
    transparent 78%
  );
  background-size: 220% 220%;
  animation: gbHoloShimmer var(--ad-dur, 8s) ease-in-out both;
  mix-blend-mode: color-dodge;
  opacity: 0.55;
}
@keyframes gbHoloShimmer {
  0% { background-position: 0% 40%; opacity: 0.25; }
  40% { opacity: calc(0.45 + 0.25 * var(--fx-intensity, 1)); }
  100% { background-position: 100% 60%; opacity: 0.2; }
}

/* —— Named creative: Tornado / Sacudida / Alegre / Anuncio / Urgente / Fiesta / Cinemático —— */

/* Tornado — slow spiral + wind debris (TV-safe) */
:is(.ad-fx, .ad-fx-preview).fx-tornado :is(img, video) {
  animation: gbTornado var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbTornado {
  0% {
    transform: scale(1.18) rotate(calc(-2.2deg * var(--fx-intensity, 1))) translate3d(calc(-1.5% * var(--fx-intensity, 1)), 1%, 0);
    filter: brightness(0.96) contrast(1.04);
  }
  35% {
    transform: scale(1.22) rotate(calc(1.4deg * var(--fx-intensity, 1))) translate3d(calc(1.2% * var(--fx-intensity, 1)), -1.5%, 0);
  }
  70% {
    transform: scale(1.2) rotate(calc(-1.1deg * var(--fx-intensity, 1))) translate3d(calc(-0.8% * var(--fx-intensity, 1)), 0.5%, 0);
  }
  100% {
    transform: scale(1.16) rotate(calc(0.6deg * var(--fx-intensity, 1))) translate3d(0.5%, -0.5%, 0);
    filter: brightness(1) contrast(1);
  }
}
:is(.ad-fx, .ad-fx-preview).fx-tornado::before {
  content: "";
  position: absolute;
  inset: -15%;
  z-index: 2;
  background:
    conic-gradient(from 0deg at 50% 55%, transparent 0 70%, rgba(200, 210, 220, calc(0.08 * var(--fx-intensity, 1))) 78%, transparent 90%),
    radial-gradient(ellipse 40% 70% at 50% 55%, rgba(180, 195, 210, calc(0.12 * var(--fx-intensity, 1))), transparent 70%);
  animation: gbTornadoWind calc(var(--ad-dur, 8s) * 0.9) linear both;
  mix-blend-mode: soft-light;
  opacity: 0.7;
}
:is(.ad-fx, .ad-fx-preview).fx-tornado::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background-image:
    radial-gradient(circle at 30% 40%, rgba(255,255,255,calc(0.35 * var(--fx-intensity, 1))) 0 1px, transparent 1.6px),
    radial-gradient(circle at 60% 55%, rgba(220,230,240,calc(0.3 * var(--fx-intensity, 1))) 0 1.2px, transparent 2px),
    radial-gradient(circle at 45% 70%, rgba(255,255,255,calc(0.25 * var(--fx-intensity, 1))) 0 0.9px, transparent 1.5px),
    radial-gradient(circle at 70% 35%, rgba(200,210,220,calc(0.28 * var(--fx-intensity, 1))) 0 1px, transparent 1.8px);
  animation: gbTornadoDebris var(--ad-dur, 8s) ease-in-out both;
  mix-blend-mode: screen;
}
@keyframes gbTornadoWind {
  from { transform: rotate(0deg) scale(1); }
  to { transform: rotate(calc(28deg * var(--fx-intensity, 1))) scale(1.08); }
}
@keyframes gbTornadoDebris {
  0% { transform: rotate(0deg) translate3d(0, 2%, 0); opacity: 0.3; }
  40% { opacity: 0.85; }
  100% { transform: rotate(calc(40deg * var(--fx-intensity, 1))) translate3d(-2%, -4%, 0); opacity: 0.2; }
}

/* Sacudida — short tremor, then settle (not seizure-inducing) */
:is(.ad-fx, .ad-fx-preview).fx-shake :is(img, video) {
  animation:
    gbShakeIn 0.7s cubic-bezier(.36,.07,.19,.97) both,
    gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbShakeIn {
  0% { transform: scale(1.12) translate3d(0, 0, 0); }
  12% { transform: scale(1.12) translate3d(calc(-1.1% * var(--fx-intensity, 1)), calc(0.4% * var(--fx-intensity, 1)), 0); }
  24% { transform: scale(1.12) translate3d(calc(1% * var(--fx-intensity, 1)), calc(-0.5% * var(--fx-intensity, 1)), 0); }
  36% { transform: scale(1.12) translate3d(calc(-0.7% * var(--fx-intensity, 1)), calc(0.3% * var(--fx-intensity, 1)), 0); }
  48% { transform: scale(1.12) translate3d(calc(0.6% * var(--fx-intensity, 1)), calc(-0.2% * var(--fx-intensity, 1)), 0); }
  60% { transform: scale(1.12) translate3d(calc(-0.35% * var(--fx-intensity, 1)), 0.1%, 0); }
  100% { transform: scale(1.1) translate3d(0, 0, 0); }
}

/* Alegre — bounce + confetti dots */
:is(.ad-fx, .ad-fx-preview).fx-alegre :is(img, video) {
  animation: gbAlegreBounce var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbAlegreBounce {
  0% {
    transform: scale(1.05) translate3d(0, 3%, 0);
    filter: saturate(1.05) brightness(1.02);
  }
  18% {
    transform: scale(calc(1.12 + 0.04 * var(--fx-intensity, 1))) translate3d(0, calc(-1.5% * var(--fx-intensity, 1)), 0);
    filter: saturate(calc(1.15 + 0.1 * var(--fx-intensity, 1))) brightness(1.08);
  }
  32% { transform: scale(1.1) translate3d(0, 0.8%, 0); }
  48% {
    transform: scale(calc(1.14 + 0.03 * var(--fx-intensity, 1))) translate3d(0, calc(-1% * var(--fx-intensity, 1)), 0);
  }
  100% {
    transform: scale(1.12) translate3d(0, 0, 0);
    filter: saturate(1.12) brightness(1.04);
  }
}
:is(.ad-fx, .ad-fx-preview).fx-alegre::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background-image:
    radial-gradient(circle at 15% 20%, rgba(232, 196, 122, calc(0.9 * var(--fx-intensity, 1))) 0 2.5px, transparent 3px),
    radial-gradient(circle at 78% 28%, rgba(90, 168, 196, calc(0.85 * var(--fx-intensity, 1))) 0 2px, transparent 2.6px),
    radial-gradient(circle at 40% 70%, rgba(224, 122, 74, calc(0.8 * var(--fx-intensity, 1))) 0 2.2px, transparent 2.8px),
    radial-gradient(circle at 62% 55%, rgba(122, 184, 154, calc(0.85 * var(--fx-intensity, 1))) 0 1.8px, transparent 2.4px),
    radial-gradient(circle at 88% 72%, rgba(232, 196, 122, calc(0.75 * var(--fx-intensity, 1))) 0 2px, transparent 2.6px),
    radial-gradient(circle at 28% 48%, rgba(90, 168, 196, calc(0.7 * var(--fx-intensity, 1))) 0 1.6px, transparent 2.2px);
  animation: gbConfettiFall var(--ad-dur, 8s) ease-out both;
  mix-blend-mode: plus-lighter;
}
@keyframes gbConfettiFall {
  0% { opacity: 0; transform: translate3d(0, -8%, 0); }
  15% { opacity: 1; }
  100% { opacity: 0.35; transform: translate3d(0, 12%, 0); }
}

/* Anuncio — promo sting + badge flash strip */
:is(.ad-fx, .ad-fx-preview).fx-anuncio :is(img, video) {
  animation:
    gbAnuncioSting 0.9s cubic-bezier(.2,.9,.2,1) both,
    gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbAnuncioSting {
  0% { opacity: 0; transform: scale(1.22); filter: brightness(1.25) contrast(1.1); }
  35% { opacity: 1; transform: scale(1.06); filter: brightness(1.08); }
  100% { transform: scale(1.1); filter: brightness(1); }
}
:is(.ad-fx, .ad-fx-preview).fx-anuncio::before {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: 22%;
  z-index: 3;
  background: linear-gradient(90deg, rgba(232, 196, 122, calc(0.85 * var(--fx-intensity, 1))), rgba(196, 160, 80, calc(0.55 * var(--fx-intensity, 1))), transparent 85%);
  clip-path: polygon(0 30%, 100% 0, 100% 100%, 0 100%);
  animation: gbAnuncioBar 1.1s cubic-bezier(.2,.8,.2,1) both;
  mix-blend-mode: soft-light;
}
:is(.ad-fx, .ad-fx-preview).fx-anuncio::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background: linear-gradient(105deg, transparent 40%, rgba(255, 248, 220, calc(0.35 * var(--fx-intensity, 1))) 50%, transparent 60%);
  animation: gbAnuncioFlash 1.2s ease-out both;
  mix-blend-mode: overlay;
}
@keyframes gbAnuncioBar {
  from { transform: translate3d(-8%, 40%, 0); opacity: 0; }
  to { transform: translate3d(0, 0, 0); opacity: 1; }
}
@keyframes gbAnuncioFlash {
  0% { opacity: 0; transform: translate3d(-30%, 0, 0); }
  30% { opacity: 1; }
  100% { opacity: 0; transform: translate3d(40%, 0, 0); }
}

/* Urgente — alert rim pulse */
:is(.ad-fx, .ad-fx-preview).fx-urgent :is(img, video) {
  animation: gbUrgentPulse var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbUrgentPulse {
  0%, 100% {
    transform: scale(1.1);
    filter: brightness(1) saturate(1.05);
  }
  25%, 75% {
    transform: scale(calc(1.12 + 0.03 * var(--fx-intensity, 1)));
    filter: brightness(calc(1.06 + 0.06 * var(--fx-intensity, 1))) saturate(1.12);
  }
  50% {
    transform: scale(1.1);
    filter: brightness(1.02) saturate(1.08);
  }
}
:is(.ad-fx, .ad-fx-preview).fx-urgent::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  box-shadow:
    inset 0 0 0 calc(3px * var(--fx-intensity, 1)) rgba(224, 122, 74, calc(0.55 * var(--fx-intensity, 1))),
    inset 0 0 calc(40px * var(--fx-intensity, 1)) rgba(224, 122, 74, calc(0.25 * var(--fx-intensity, 1)));
  animation: gbUrgentRim 1.4s ease-in-out infinite;
}
@keyframes gbUrgentRim {
  0%, 100% { opacity: 0.45; }
  50% { opacity: 1; }
}

/* Fiesta — celebration shimmer + warm saturate */
:is(.ad-fx, .ad-fx-preview).fx-fiesta :is(img, video) {
  animation: gbFiesta var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbFiesta {
  0%, 100% {
    transform: scale(1.1);
    filter: saturate(calc(1.15 + 0.1 * var(--fx-intensity, 1))) brightness(1.04) hue-rotate(-4deg);
  }
  50% {
    transform: scale(calc(1.15 + 0.04 * var(--fx-intensity, 1)));
    filter: saturate(calc(1.3 + 0.15 * var(--fx-intensity, 1))) brightness(1.1) hue-rotate(6deg);
  }
}
:is(.ad-fx, .ad-fx-preview).fx-fiesta::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background-image:
    radial-gradient(circle at 20% 30%, rgba(255, 220, 140, calc(0.7 * var(--fx-intensity, 1))) 0 1.5px, transparent 2.2px),
    radial-gradient(circle at 70% 20%, rgba(255, 255, 255, calc(0.65 * var(--fx-intensity, 1))) 0 1.2px, transparent 2px),
    radial-gradient(circle at 55% 65%, rgba(232, 196, 122, calc(0.7 * var(--fx-intensity, 1))) 0 1.8px, transparent 2.5px),
    radial-gradient(circle at 35% 80%, rgba(90, 168, 196, calc(0.55 * var(--fx-intensity, 1))) 0 1.3px, transparent 2px);
  animation: gbSparkleFloat var(--ad-dur, 8s) ease-in-out both;
  mix-blend-mode: plus-lighter;
}

/* Cinemático — letterbox bars + dramatic zoom */
:is(.ad-fx, .ad-fx-preview).fx-cinematic :is(img, video) {
  animation: gbCinematicZoom var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbCinematicZoom {
  from {
    transform: scale(1.05);
    filter: contrast(1.08) saturate(0.95) brightness(0.92);
  }
  to {
    transform: scale(calc(1.14 + 0.06 * var(--fx-intensity, 1))) translate3d(calc(1% * var(--fx-intensity, 1)), calc(-0.8% * var(--fx-intensity, 1)), 0);
    filter: contrast(1.12) saturate(1) brightness(1);
  }
}
:is(.ad-fx, .ad-fx-preview).fx-cinematic::before,
:is(.ad-fx, .ad-fx-preview).fx-cinematic::after {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  z-index: 3;
  height: calc(9% * var(--fx-intensity, 1) + 4%);
  background: #05090c;
  animation: gbLetterbox 1s ease both;
}
:is(.ad-fx, .ad-fx-preview).fx-cinematic::before { top: 0; }
:is(.ad-fx, .ad-fx-preview).fx-cinematic::after { bottom: 0; }
@keyframes gbLetterbox {
  from { transform: scaleY(0); opacity: 0; }
  to { transform: scaleY(1); opacity: 1; }
}

/* Tormenta — lightning + dark mood */
:is(.ad-fx, .ad-fx-preview).fx-thunder :is(img, video) {
  animation: gbThunderMood var(--ad-dur, 8s) ease-in-out both,
             gbKenBurns var(--ad-dur, 8s) ease-in-out both;
}
@keyframes gbThunderMood {
  0%, 100% { filter: brightness(0.8) contrast(1.1); }
  45%, 47%, 51% { filter: brightness(1.8) contrast(1.4) saturate(0.5); }
  46%, 49% { filter: brightness(0.9) contrast(1.1); }
}
:is(.ad-fx, .ad-fx-preview).fx-thunder::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background: rgba(0, 10, 30, 0.2);
  animation: gbThunderFlash var(--ad-dur, 8s) step-end both;
}
@keyframes gbThunderFlash {
  0%, 44%, 53%, 100% { opacity: 0; }
  45%, 47%, 51% { opacity: 0.4; background: #fff; }
}

/* Confeti PRO — dense explosion */
:is(.ad-fx, .ad-fx-preview).fx-confettiPro :is(img, video) {
  animation: gbPulse var(--ad-dur, 8s) ease-in-out both;
}
:is(.ad-fx, .ad-fx-preview).fx-confettiPro::before,
:is(.ad-fx, .ad-fx-preview).fx-confettiPro::after {
  content: "";
  position: absolute;
  inset: -100% 0 0;
  z-index: 3;
  background-image:
    radial-gradient(circle at 10% 10%, #ffeb3b 3px, transparent 4px),
    radial-gradient(circle at 30% 20%, #ff5722 2px, transparent 3px),
    radial-gradient(circle at 50% 15%, #4caf50 4px, transparent 5px),
    radial-gradient(circle at 70% 25%, #2196f3 3px, transparent 4px),
    radial-gradient(circle at 90% 10%, #e91e63 2px, transparent 3px),
    radial-gradient(circle at 20% 40%, #ffeb3b 3px, transparent 4px),
    radial-gradient(circle at 40% 50%, #ff5722 2px, transparent 3px),
    radial-gradient(circle at 60% 45%, #4caf50 4px, transparent 5px),
    radial-gradient(circle at 80% 55%, #2196f3 3px, transparent 4px);
  background-size: 200px 400px;
  animation: gbConfettiPro 3s linear infinite;
}
:is(.ad-fx, .ad-fx-preview).fx-confettiPro::after {
  animation-delay: 1.5s;
  background-position: 100px 200px;
  opacity: 0.7;
}
@keyframes gbConfettiPro {
  0% { transform: translateY(0) rotate(0deg); }
  100% { transform: translateY(100%) rotate(10deg); }
}

/* Vuelo de Avión — sky passage */
:is(.ad-fx, .ad-fx-preview).fx-flight :is(img, video) {
  animation: gbFlight var(--ad-dur, 8s) linear both;
}
@keyframes gbFlight {
  0% { transform: scale(1.1) translate3d(-2%, 1%, 0) rotate(-0.5deg); }
  50% { transform: scale(1.1) translate3d(0, -1%, 0) rotate(0.2deg); }
  100% { transform: scale(1.1) translate3d(2%, 1%, 0) rotate(-0.3deg); }
}
:is(.ad-fx, .ad-fx-preview).fx-flight::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 2;
  background: linear-gradient(90deg, transparent, rgba(255,255,255,0.15), transparent);
  transform: translateX(-100%) skewX(-20deg);
  animation: gbFlightClouds 4s linear infinite;
}
@keyframes gbFlightClouds {
  0% { transform: translateX(-100%) skewX(-20deg); opacity: 0; }
  50% { opacity: 0.4; }
  100% { transform: translateX(200%) skewX(-20deg); opacity: 0; }
}

/* —— Reduced motion: quieter variants —— */
@media (prefers-reduced-motion: reduce) {
  :is(.ad-fx, .ad-fx-preview).fx-kenburns :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-drift :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-orbit :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-pulse :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-parallax :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-shine :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-sparkle :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-curtain :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-gradeWarm :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-gradeCool :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-filmMood :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-chroma :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-glassWeather :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-holo :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-tornado :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-shake :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-alegre :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-anuncio :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-urgent :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-fiesta :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-cinematic :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-rise :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-punch :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-veil :is(img, video),
  :is(.ad-fx, .ad-fx-preview).fx-split :is(img, video) {
    animation: gbSoftHold var(--ad-dur, 8s) ease-in-out both !important;
  }
  :is(.ad-fx, .ad-fx-preview)::before,
  :is(.ad-fx, .ad-fx-preview)::after,
  :is(.ad-fx, .ad-fx-preview).fx-split .ad-split-mask {
    animation: none !important;
    opacity: 0.35;
  }
  :is(.ad-fx, .ad-fx-preview).fx-curtain::before,
  :is(.ad-fx, .ad-fx-preview).fx-curtain::after {
    opacity: 0 !important;
  }
  :is(.ad-fx, .ad-fx-preview).fx-glassWeather::before {
    animation: none !important;
    opacity: 0.25;
  }
  :is(.ad-fx, .ad-fx-preview).fx-shine::before,
  :is(.ad-fx, .ad-fx-preview).fx-sparkle::before,
  :is(.ad-fx, .ad-fx-preview).fx-holo::before,
  :is(.ad-fx, .ad-fx-preview).fx-alegre::before,
  :is(.ad-fx, .ad-fx-preview).fx-fiesta::before,
  :is(.ad-fx, .ad-fx-preview).fx-tornado::before,
  :is(.ad-fx, .ad-fx-preview).fx-tornado::after,
  :is(.ad-fx, .ad-fx-preview).fx-anuncio::before,
  :is(.ad-fx, .ad-fx-preview).fx-anuncio::after,
  :is(.ad-fx, .ad-fx-preview).fx-urgent::before {
    opacity: 0.12 !important;
  }
  :is(.ad-fx, .ad-fx-preview).fx-cinematic::before,
  :is(.ad-fx, .ad-fx-preview).fx-cinematic::after {
    opacity: 0.5 !important;
  }
}
@keyframes gbSoftHold {
  from { transform: scale(1.04); filter: none; }
  to { transform: scale(1.06); filter: none; }
}
