/* ==========================================================================
   ANIMATIONS: the living reactor, click feedback, Surge states, prestige
   collapse sequences, shop transitions, toasts, and interface motion.
   Reduced-motion handling lives in base.css and zeroes all of these out.
   ========================================================================== */

/* Reactor idle state: breathing halo, drifting internal energy, rotating
   rings. Higher power tiers spin faster — the reactor feels stronger. */
.core-halo {
  animation: breathe 3.5s ease-in-out infinite;
}

.core-inner {
  animation: corePulse 2.8s ease-in-out infinite;
}

.core-flicker {
  animation: flickerDrift 7s ease-in-out infinite alternate;
}

.core-ring {
  animation: ringRotate 8s linear infinite;
}

.core-ring::after {
  animation: ringRotate 5s linear infinite reverse;
}

.core-spark {
  animation: ringRotate 14s linear infinite reverse;
}

.core-orbit {
  animation: ringRotate 22s linear infinite;
}

body[data-core-tier="3"] .core-ring { animation-duration: 6s; }
body[data-core-tier="4"] .core-ring { animation-duration: 4.5s; }
body[data-core-tier="4"] .core-spark { animation-duration: 9s; }

body.singularity-ready .core-orbit,
body.horizon-ready .core-orbit {
  animation: ringRotate 10s linear infinite, orbitPulse 2.2s ease-in-out infinite;
}

/* Click feedback: compression plus an expanding pulse ring. */
.core-btn.clicked .core-inner {
  animation: coreHit 0.26s ease-out, corePulse 2.8s ease-in-out infinite;
}

.core-btn.crit-hit .core-inner {
  animation: critHit 0.34s ease-out, corePulse 2.8s ease-in-out infinite;
}

.core-pulse.pulse {
  animation: pulseRing 0.5s ease-out forwards;
}

.core-btn.crit-hit .core-pulse.pulse {
  border-color: var(--accent-3);
  animation: pulseRing 0.6s ease-out forwards;
}

/* Surge nearly charged / ready: ring quickens and the button pulses. */
body.surge-ready .core-ring {
  border-color: var(--accent-2);
  animation-duration: 4s;
}

body.surge-ready .surge-btn:not(:disabled) {
  animation: readyPulse 1.6s ease-in-out infinite;
}

@keyframes readyPulse {
  0%, 100% { box-shadow: 0 0 0 rgba(255, 45, 149, 0); }
  50% { box-shadow: var(--glow-pink); }
}

/* Surge active: hotter, faster reactor with a magenta cast. */
body.surge-active .core-inner {
  animation-duration: 1.1s;
  box-shadow:
    inset 0 0 52px var(--core-glow-inner),
    0 0 34px var(--accent-2),
    0 0 84px color-mix(in srgb, var(--accent-2) 55%, transparent),
    0 0 140px color-mix(in srgb, var(--core-color) 35%, transparent);
}

body.surge-active .core-ring {
  border-color: var(--accent-2);
  animation-duration: 2.5s;
}

body.surge-active .core-halo {
  background: radial-gradient(circle, color-mix(in srgb, var(--accent-2) 24%, transparent), transparent 65%);
  animation-duration: 1.4s;
}

/* Brief flash on the charge bar when a click extends an active Surge. */
.charge-shell.extended .charge-bar {
  animation: chargeFlash 0.3s ease-out;
}

@keyframes chargeFlash {
  0% { filter: brightness(1.9); }
  100% { filter: brightness(1); }
}

/* Singularity module shimmer. */
.singularity-module::after,
.horizon-module::after {
  animation: spin 18s linear infinite;
}

/* Floating numbers + particles. */
.float-num {
  animation: floatUp 1.18s ease-out forwards;
}

.particle {
  animation: particleBurst 0.78s ease-out forwards;
}

/* Shop motion: purchases pop, categories cross-fade. */
.upgrade.purchased {
  animation: purchasePop 0.4s ease-out;
}

.shop-panel.panel-switch {
  animation: panelSwitch 0.24s ease-out;
}

@keyframes panelSwitch {
  from { opacity: 0; transform: translateY(5px); }
  to { opacity: 1; transform: translateY(0); }
}

.upgrade.is-new {
  animation: unlockGlow 1.6s ease-out;
}

@keyframes unlockGlow {
  0% { border-color: var(--accent-3); box-shadow: var(--glow-gold); }
  100% { border-color: var(--border); box-shadow: none; }
}

.tab-dot {
  animation: dotPulse 1.8s ease-in-out infinite;
}

@keyframes dotPulse {
  0%, 100% { transform: scale(1); }
  50% { transform: scale(1.25); }
}

/* Toasts. */
.toast {
  animation: toastIn 0.28s ease-out;
}

.toast.toast-out {
  animation: toastOut 0.22s ease-in forwards;
}

.toast.toast-bump {
  animation: toastBump 0.3s ease-out;
}

/* Singularity collapse sequence: flare implodes, flashes, title appears. */
.singularity-overlay.active {
  animation: overlayFlash 2s ease-out forwards;
}

.singularity-overlay.active .singularity-flare {
  animation: flareCollapse 2s ease-out forwards;
}

.singularity-overlay.active .singularity-text {
  animation: singularityTitle 2s ease-out forwards;
}

/* Event Horizon collapse: deeper, violet, slightly longer. */
.singularity-overlay.variant-horizon .singularity-flare {
  background: radial-gradient(circle, #fff 0%, var(--horizon) 30%, #1a0533 60%, transparent 75%);
}

.singularity-overlay.variant-horizon .singularity-text {
  text-shadow: 0 0 24px var(--horizon), 0 0 60px var(--horizon);
}

.singularity-overlay.variant-horizon.active {
  animation: overlayFlashHorizon 2.6s ease-out forwards;
}

.singularity-overlay.variant-horizon.active .singularity-flare {
  animation: flareCollapseHorizon 2.6s ease-out forwards;
}

.singularity-overlay.variant-horizon.active .singularity-text {
  animation: singularityTitle 2.6s ease-out forwards;
}

/* Reduced-motion variants: a short gentle fade, no scaling or flashing. */
.singularity-overlay.active.reduced,
.singularity-overlay.active.reduced .singularity-flare,
.singularity-overlay.active.reduced .singularity-text {
  animation: none;
}

.singularity-overlay.active.reduced {
  opacity: 1;
  background: color-mix(in srgb, var(--bg) 78%, transparent);
}

.singularity-overlay.active.reduced .singularity-flare {
  opacity: 0.25;
}

.singularity-overlay.active.reduced .singularity-text {
  opacity: 1;
}

/* Interface motion. */
.sheet[open] {
  animation: sheetIn 0.26s ease-out;
}

@keyframes sheetIn {
  from { transform: translateX(28px); opacity: 0.4; }
  to { transform: translateX(0); opacity: 1; }
}

.modal[open] {
  animation: modalIn 0.22s ease-out;
}

@keyframes modalIn {
  from { transform: translateY(8px) scale(0.97); opacity: 0; }
  to { transform: translateY(0) scale(1); opacity: 1; }
}

.collapse-body:not([hidden]) {
  animation: collapseIn 0.22s ease-out;
}

@keyframes collapseIn {
  from { opacity: 0; transform: translateY(-4px); }
  to { opacity: 1; transform: translateY(0); }
}

/* Keyframes -------------------------------------------------------------- */
@keyframes breathe {
  0%, 100% { transform: scale(0.92); opacity: 0.65; }
  50% { transform: scale(1.06); opacity: 1; }
}

@keyframes corePulse {
  0%, 100% {
    box-shadow:
      inset 0 0 40px var(--core-glow-inner),
      0 0 26px var(--core-color),
      0 0 64px color-mix(in srgb, var(--core-color) 45%, transparent),
      0 0 110px color-mix(in srgb, var(--accent-2) 18%, transparent);
  }
  50% {
    box-shadow:
      inset 0 0 56px var(--core-glow-inner),
      0 0 38px var(--core-color),
      0 0 88px color-mix(in srgb, var(--core-color) 55%, transparent),
      0 0 135px color-mix(in srgb, var(--accent-2) 26%, transparent);
  }
}

@keyframes flickerDrift {
  0% { transform: rotate(0deg) scale(1); opacity: 0.75; }
  50% { transform: rotate(14deg) scale(1.05); opacity: 1; }
  100% { transform: rotate(-10deg) scale(0.97); opacity: 0.8; }
}

@keyframes orbitPulse {
  0%, 100% { opacity: 0.55; }
  50% { opacity: 1; }
}

@keyframes coreHit {
  0% { transform: scale(1); }
  45% { transform: scale(0.86); }
  100% { transform: scale(1); }
}

@keyframes critHit {
  0% { transform: scale(1); }
  35% { transform: scale(0.82); }
  70% { transform: scale(1.08); }
  100% { transform: scale(1); }
}

@keyframes pulseRing {
  0% { opacity: 0.8; transform: scale(1); }
  100% { opacity: 0; transform: scale(1.65); }
}

@keyframes ringRotate {
  to { transform: rotate(360deg); }
}

@keyframes spin {
  to { transform: rotate(360deg); }
}

@keyframes floatUp {
  0% { opacity: 0; transform: translate(-50%, 0) scale(0.65); }
  16% { opacity: 1; transform: translate(-50%, -10px) scale(1.22); }
  100% { opacity: 0; transform: translate(-50%, -120px) scale(0.88); }
}

@keyframes particleBurst {
  0% { opacity: 1; transform: translate(-50%, -50%) scale(1); }
  100% { opacity: 0; transform: translate(calc(-50% + var(--dx)), calc(-50% + var(--dy))) scale(0); }
}

@keyframes purchasePop {
  0% { transform: scale(1); }
  40% { transform: scale(1.025); border-color: var(--accent); box-shadow: var(--glow); }
  100% { transform: scale(1); }
}

@keyframes toastIn {
  from { opacity: 0; transform: translateX(14px) scale(0.97); }
  to { opacity: 1; transform: translateX(0) scale(1); }
}

@keyframes toastOut {
  to { opacity: 0; transform: translateY(-6px) scale(0.97); }
}

@keyframes toastBump {
  0% { transform: scale(1); }
  40% { transform: scale(1.04); }
  100% { transform: scale(1); }
}

@keyframes overlayFlash {
  0% { background: transparent; }
  18% { background: color-mix(in srgb, var(--bg) 88%, transparent); }
  30% { background: rgba(255, 255, 255, 0.55); }
  45%, 80% { background: color-mix(in srgb, var(--bg) 82%, transparent); }
  100% { background: transparent; opacity: 0; }
}

@keyframes flareCollapse {
  0% { opacity: 0; transform: scale(1.4); }
  20% { opacity: 1; transform: scale(0.6); }
  30% { opacity: 1; transform: scale(0.05); }
  36% { opacity: 1; transform: scale(1.8); filter: blur(2px); }
  60% { opacity: 0.5; transform: scale(2.4); }
  100% { opacity: 0; transform: scale(2.8); }
}

@keyframes overlayFlashHorizon {
  0% { background: transparent; }
  16% { background: color-mix(in srgb, #0a0118 90%, transparent); }
  32% { background: rgba(236, 222, 255, 0.6); }
  46%, 82% { background: color-mix(in srgb, #0a0118 86%, transparent); }
  100% { background: transparent; opacity: 0; }
}

@keyframes flareCollapseHorizon {
  0% { opacity: 0; transform: scale(1.6); }
  22% { opacity: 1; transform: scale(0.5); }
  34% { opacity: 1; transform: scale(0.03); }
  40% { opacity: 1; transform: scale(2.1); filter: blur(3px); }
  64% { opacity: 0.5; transform: scale(2.7) rotate(8deg); }
  100% { opacity: 0; transform: scale(3.1) rotate(12deg); }
}

@keyframes singularityTitle {
  0%, 30% { opacity: 0; transform: scale(0.85); letter-spacing: 0.5em; }
  45% { opacity: 1; transform: scale(1); letter-spacing: 0.3em; }
  85% { opacity: 1; }
  100% { opacity: 0; }
}
