/* ---------- opening: the gacha ritual ----------
 * Four beats: idle -> charge (aura builds, box shakes) -> burst -> reveal.
 * Duration and colour come from the prize rarity: JS sets stage.dataset.tier
 * and --shake-ms, so a long charge always means something better than common.
 */

.opening {
  text-align: center;
  min-height: calc(100dvh - 190px);
  display: flex;
  flex-direction: column;
  justify-content: center;
}

.opening .counter {
  font-size: var(--t-sm);
  color: var(--text-dim);
  letter-spacing: .06em;
  text-transform: uppercase;
  font-weight: 600;
  margin-bottom: var(--s2);
}

/* box and prize card share one grid cell — no display:none swap mid-animation */
/* box and prize card occupy the same cell, so the card grows out of the flash */
.stage-wrap { display: grid; justify-items: center; align-items: center; }
.stage-wrap > * { grid-area: 1 / 1; width: 100%; }
.stage-wrap > [data-slot]:empty { display: none; }
.stage-wrap.spent .box-stage { visibility: hidden; }

.box-stage {
  position: relative;
  width: min(82vw, 420px);
  aspect-ratio: 1;
  margin: 0 auto;
  display: grid;
  place-items: center;
  overflow: clip;
  border: 0;
  background: none;
  padding: 0;
  cursor: pointer;
  touch-action: manipulation;
}

.box-art {
  width: 78%;
  filter: drop-shadow(0 18px 40px var(--glow));
  animation: idle-float 3.2s ease-in-out infinite;
  transition: transform .2s ease;
  will-change: transform;
}
@keyframes idle-float {
  0%, 100% { transform: translateY(0) rotate(-1deg); }
  50% { transform: translateY(-10px) rotate(1deg); }
}

/* aura: grows through the whole charge phase, tinted by rarity */
.aura {
  position: absolute;
  inset: 8%;
  border-radius: 50%;
  background: radial-gradient(circle, color-mix(in srgb, var(--r, var(--accent)) 55%, transparent) 0%, transparent 68%);
  opacity: 0;
  transform: scale(.6);
  pointer-events: none;
}
.box-stage.charging .aura {
  animation: aura-grow var(--shake-ms, 420ms) ease-in forwards;
}
@keyframes aura-grow {
  from { opacity: 0; transform: scale(.6); }
  to { opacity: .75; transform: scale(1.15); }
}

.box-stage.charging .box-art {
  animation: shake var(--shake-step, .34s) cubic-bezier(.36,.07,.19,.97) infinite;
}
@keyframes shake {
  10%, 90% { transform: translateX(-4px) rotate(-3deg); }
  20%, 80% { transform: translateX(6px) rotate(4deg); }
  30%, 50%, 70% { transform: translateX(-9px) rotate(-6deg) scale(1.03); }
  40%, 60% { transform: translateX(9px) rotate(6deg) scale(1.05); }
  100% { transform: none; }
}

.box-stage.bursting .box-art { animation: burst var(--burst-ms, 320ms) ease-in both; }
@keyframes burst {
  0% { transform: scale(1); opacity: 1; }
  55% { transform: scale(1.14); opacity: 1; }
  100% { transform: scale(1.8); opacity: 0; }
}

.flash {
  position: absolute;
  inset: 0;
  border-radius: 50%;
  background: radial-gradient(circle, #fff 0%, var(--r, var(--accent)) 35%, transparent 68%);
  opacity: 0;
  pointer-events: none;
}
.box-stage.bursting .flash { animation: flash var(--burst-ms, 320ms) ease-out both; }
@keyframes flash {
  0% { opacity: 0; transform: scale(.3); }
  40% { opacity: .9; transform: scale(1.1); }
  100% { opacity: 0; transform: scale(1.5); }
}

.stage-wrap.spent .box-stage { opacity: 0; transform: scale(1.6); pointer-events: none; transition: opacity .3s ease, transform .3s ease; }

.tap-hint { font-size: var(--t-md); color: var(--text-dim); animation: pulse 1.8s ease-in-out infinite; }
@keyframes pulse { 0%,100% { opacity: .55 } 50% { opacity: 1 } }

/* ---------- prize reveal ---------- */

.reveal { animation: reveal-in .42s cubic-bezier(.2,.9,.3,1.2) both; }
@keyframes reveal-in {
  from { opacity: 0; transform: scale(.72); }
  to { opacity: 1; transform: scale(1); }
}

.prize-card {
  position: relative;
  transform-origin: center;
  border-radius: var(--radius);
  border: 1.5px solid color-mix(in srgb, var(--r, var(--common)) 55%, transparent);
  background: var(--bg-card);
  overflow: hidden;
  text-align: left;
  box-shadow: 0 16px 44px color-mix(in srgb, var(--r, var(--common)) 22%, transparent);
}
.prize-card img { width: 100%; aspect-ratio: 1; object-fit: cover; display: block; background: var(--bg-soft); }
.prize-card .glow {
  position: absolute; inset: 0;
  background: linear-gradient(to top, color-mix(in srgb, var(--r) 26%, transparent), transparent 55%);
  pointer-events: none;
}
.prize-card .body { padding: var(--s4); }
.prize-card .title { font-size: var(--t-xl); font-weight: 800; margin: var(--s2) 0 var(--s1); letter-spacing: -.02em; }
.prize-card .title:focus-visible { outline-offset: 4px; }
.prize-card .price { font-size: var(--t-sm); color: var(--text-dim); }
.prize-card .text { font-size: var(--t-sm); margin-top: var(--s2); white-space: pre-line; }
.prize-card .text a { color: var(--accent); word-break: break-all; }
.prize-card .note-line { font-size: var(--t-xs); color: var(--text-dim); margin-top: var(--s2); }
.prize-card .dup {
  margin-top: var(--s3);
  font-size: var(--t-sm);
  color: var(--text);
  background: color-mix(in srgb, var(--accent) 8%, var(--bg-soft));
  border: 1px solid var(--border);
  border-radius: var(--radius-xs);
  padding: var(--s3);
}
.prize-card .dup b { display: block; margin-bottom: 2px; }

.legendary-rays {
  position: absolute; inset: -30%;
  background: conic-gradient(from 0deg, transparent 0 8%, color-mix(in srgb, var(--legendary) 40%, transparent) 9% 11%, transparent 12% 20%);
  animation: spin 12s linear infinite;
  opacity: .3;
  pointer-events: none;
}

#confetti { position: fixed; inset: 0; pointer-events: none; z-index: 5; }

@media (prefers-reduced-motion: reduce) {
  .box-art, .legendary-rays, .tap-hint, .aura { animation: none !important; }
  .flash { opacity: 0 !important; }
  .reveal, .screen { animation-duration: .01ms !important; }
}
