/* ========================= Mermaid Tail — styles ========================= */

* { box-sizing: border-box; -webkit-tap-highlight-color: transparent; }

/* The two racers are colors the emoji set doesn't have, so we dye them ourselves.
   Both appear in the score bar, on the cards, in the banner and on the die — see
   .as-mermaid / .as-goblin and the #die-who rules further down.
   Each one always has to be wrapped on its own, or the emoji standing next to it
   (🏰, 🎉, 😤, ✈️) gets dyed too.

   Note these dye a SHAPE, not a racer. Since the Snap button you can be either
   one, so nothing about the color is allowed to assume who's who. */
:root {
  /* 👺 is a red tengu mask; one spin round the wheel turns that red green. */
  --goblin-tint: hue-rotate(110deg) saturate(1.15);

  /* 🧜‍♀️ can't be done that way — her orange hair and green tail sit on opposite
     sides of the wheel, so no single spin makes both purple. Flatten her to one
     hue first, then dye that. Brightness survives it, so her tail still comes out
     deeper than her skin instead of one flat purple blob.
     The brightness step goes LAST and takes the finished purple down to a deep
     plum. It scales every channel by the same amount, so the light-and-dark of
     her still reads — she goes darker, not flatter. */
  --mermaid-tint: grayscale(1) sepia(1) hue-rotate(230deg) saturate(3) brightness(0.7);
}

.gob-emoji,
.mer-emoji { display: inline-block; }

.gob-emoji { filter: var(--goblin-tint); }
.mer-emoji { filter: var(--mermaid-tint); }

/* touch-action is the only thing that actually stops a phone zooming the page.
   The viewport meta says user-scalable=no, but iOS has ignored that for years.
   "manipulation" kills double-tap-to-zoom everywhere without killing panning,
   so the overlay cards can still be scrolled if they're taller than the screen —
   which is why this isn't the blunter touch-action: none the other games use. */
html, body {
  margin: 0;
  height: 100%;
  overflow: hidden;
  touch-action: manipulation;
  font-family: "Baloo 2", system-ui, "Segoe UI", sans-serif;
  user-select: none;
  -webkit-user-select: none;
}

#game {
  position: fixed;
  inset: 0;
  display: flex;
  flex-direction: column;
  background: radial-gradient(130% 90% at 50% 0%, #e2f8ff 0%, #a5e4f8 45%, #6cc4e8 100%);
  transition: background 0.5s ease;
}

/* Lets the portal ring animate smoothly between the ticks the clock writes.
   It has to inherit: the clock writes --p on the portal tile, but the ring that
   draws it is that tile's ::after. */
@property --p {
  syntax: "<number>";
  inherits: true;
  initial-value: 0;
}

/* ------------------------------- HUD -------------------------------- */

#hud {
  flex: 0 0 auto;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: clamp(8px, 2.8vw, 26px);
  padding: clamp(5px, 1.6vw, 12px) clamp(8px, 2vw, 16px);
  flex-wrap: wrap;
}

.hud-item { flex: 0 0 auto; text-align: center; }

.stat-label {
  font-size: clamp(12px, 3vw, 18px);
  font-weight: 700;
  color: #12506b;
  white-space: nowrap;
}

/* The two counts are colored by SHAPE, not by whose they are — snap and the
   purple number follows the mermaid across to the other side of the bar. */
.stat-label b { font-size: 1.2em; color: #0a6f9c; }
.stat.as-mermaid .stat-label b { color: #6a2fb5; }
.stat.as-goblin .stat-label b { color: #3f7a24; }

.stat-label b.bump { display: inline-block; animation: bump 0.3s ease; }
@keyframes bump {
  0% { transform: scale(1); }
  50% { transform: scale(1.55); }
  100% { transform: scale(1); }
}

/* --- the Snap button --- */

/* Small and round and emoji-only on purpose. It shares the one wrapping row
   with four counts, and anything that pushes that row onto a second line steals
   height from the stage and makes the whole path re-fold itself.

   It lives ABOVE the overlay (60) rather than under it. The overlay is only
   45% opaque, so from underneath the button stayed in plain sight on the title
   screen while every tap went into the card in front of it — you could see the
   thing perfectly well and it simply refused to work. Now the very first thing
   you can do, before the race even starts, is decide who you'd rather be. */
.snap-btn {
  position: relative;
  z-index: 65;
  flex: 0 0 auto;
  display: flex;
  align-items: center;
  justify-content: center;
  width: clamp(38px, 9.5vw, 50px);
  height: clamp(38px, 9.5vw, 50px);
  padding: 0;
  font-size: clamp(17px, 4.6vw, 24px);
  line-height: 1;
  background: linear-gradient(180deg, #ffd97a, #f2a20c);
  border: 3px solid #fff;
  border-radius: 50%;
  cursor: pointer;
  box-shadow: 0 4px 0 #b9700a, 0 6px 12px rgba(0, 0, 0, 0.2);
  transition: transform 0.1s ease, box-shadow 0.1s ease;
  touch-action: manipulation;
}

.snap-btn:active {
  transform: translateY(3px);
  box-shadow: 0 1px 0 #b9700a, 0 3px 8px rgba(0, 0, 0, 0.2);
}

/* Out of the way while a card is asking you something. Being above the overlay
   is what makes it work on the title screen, but it would also leave it floating
   over the win card and over the three traps, where it has no business being. */
.snap-btn.away {
  opacity: 0;
  pointer-events: none;
}

.snap-btn.spin { animation: snapSpin 0.45s cubic-bezier(0.34, 1.5, 0.64, 1); }
@keyframes snapSpin {
  0% { transform: rotate(0deg) scale(1); }
  60% { transform: rotate(300deg) scale(1.25); }
  100% { transform: rotate(360deg) scale(1); }
}

/* ------------------------------ Stage -------------------------------- */

/* The portal is the one and only place you tap the BOARD instead of a button,
   and the game shouts at you to do it fast. Nothing here ever needs to be
   panned, pinched or double-tapped, so the whole stage refuses those outright —
   the overlay cards sit outside it and keep their scrolling. */
#stage {
  position: relative;
  flex: 1 1 auto;
  min-height: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  overflow: hidden;
  padding: 0;
  touch-action: none;
}

/* The wiggly path. JS sets --cols / --rows / --tile-px and the pixel size. */
#track {
  --gap: clamp(2px, 0.8vmin, 9px);
  --tile-px: 30px;
  position: relative;
  flex: 0 0 auto;
  display: grid;
  grid-template-columns: repeat(var(--cols, 9), 1fr);
  grid-template-rows: repeat(var(--rows, 9), 1fr);
  gap: var(--gap);
}

/* ------------------------------- Tiles -------------------------------- */

.tile {
  position: relative;
  display: flex;
  align-items: center;
  justify-content: center;
  line-height: 1;
  font-size: calc(var(--tile-px) * 0.5);
  border-radius: 30%;
  border: 2px solid rgba(255, 255, 255, 0.75);
  box-shadow: 0 2px 4px rgba(6, 60, 90, 0.16);
}

/* The mermaid's half of the ocean, and the goblin's swampy half. */
.side-m { background: linear-gradient(160deg, #d8f6ff, #a7e6fa); }
.side-g { background: linear-gradient(160deg, #e8f8d4, #c2e7a0); }
.side-c { background: linear-gradient(160deg, #fff3cf, #ffd98f); }

/* The little bars that join one tile to the next, so it reads as one ribbon. */
.link-r::before, .link-l::before, .link-d::before {
  content: "";
  position: absolute;
  background: rgba(255, 255, 255, 0.65);
}

.link-r::before, .link-l::before {
  top: 50%;
  height: 26%;
  width: calc(var(--gap) + 4px);
  transform: translateY(-50%);
}
.link-r::before { left: calc(100% - 2px); }
.link-l::before { right: calc(100% - 2px); }

.link-d::before {
  left: 50%;
  width: 26%;
  height: calc(var(--gap) + 4px);
  top: calc(100% - 2px);
  transform: translateX(-50%);
}

/* --- the two castles --- */

.castle {
  font-size: calc(var(--tile-px) * 0.82);
  border-width: 3px;
  z-index: 3;
  animation: castleGlow 2.4s ease-in-out infinite;
}

.castle-m {
  background: linear-gradient(160deg, #7b4fc4, #3d1a72);
  border-color: #b57bff;
}

.castle-g {
  background: linear-gradient(160deg, #e4ffc8, #a8dd6c);
  border-color: #5f9b30;
}

@keyframes castleGlow {
  0%, 100% { box-shadow: 0 0 0 0 rgba(255, 255, 255, 0.85), 0 2px 4px rgba(6, 60, 90, 0.2); }
  50% { box-shadow: 0 0 0 6px rgba(255, 255, 255, 0), 0 2px 4px rgba(6, 60, 90, 0.2); }
}

/* --- the start shell in the middle --- */

.start {
  border-color: #ffab2e;
  border-width: 3px;
  font-size: calc(var(--tile-px) * 0.7);
  z-index: 2;
}

/* --- the magic portals --- */

.portal {
  background: radial-gradient(circle at 50% 45%, #f6e8ff, #c58bff 70%, #9b4dff);
  border-color: #7b2ff7;
  color: #fff;
  font-size: calc(var(--tile-px) * 0.72);
  font-weight: 800;
  text-shadow: 0 0 6px rgba(255, 255, 255, 0.9);
  z-index: 3;
  animation: portalSwirl 2.6s linear infinite;
}

@keyframes portalSwirl {
  0%, 100% { box-shadow: 0 0 0 0 rgba(155, 77, 255, 0.55), 0 2px 4px rgba(6, 60, 90, 0.2); }
  50% { box-shadow: 0 0 0 7px rgba(155, 77, 255, 0), 0 2px 4px rgba(6, 60, 90, 0.2); }
}

/* A portal that's already been used up — it goes quiet. */
.portal.used {
  background: linear-gradient(160deg, #e6e2ee, #c3bcd0);
  border-color: #9a92ab;
  color: #7a7189;
  text-shadow: none;
  animation: none;
}

/* You just landed on it — one big attention-grabbing ping. */
.tile.ping { animation: portalPing 0.7s ease-out; }
@keyframes portalPing {
  0% { transform: scale(1); }
  35% { transform: scale(1.5); }
  100% { transform: scale(1); }
}

/* --- the ten-second ring --- */

.tile.counting {
  z-index: 8;
  --ring-c: #37e0a0;
  transform: scale(1.25);
}

.tile.counting::after {
  content: "";
  position: absolute;
  inset: -22%;
  border-radius: 50%;
  transition: --p 0.1s linear;
  background: conic-gradient(from -90deg, var(--ring-c) calc(var(--p, 0) * 360deg), rgba(255, 255, 255, 0.3) 0);
  -webkit-mask: radial-gradient(closest-side, transparent 68%, #000 70%);
          mask: radial-gradient(closest-side, transparent 68%, #000 70%);
  filter: drop-shadow(0 0 4px rgba(0, 0, 0, 0.3));
}

.tile.counting.hurry {
  --ring-c: #ff2d63;
  animation: portalShake 0.28s linear infinite;
}

@keyframes portalShake {
  0%, 100% { transform: scale(1.25) translate(0, 0); }
  25% { transform: scale(1.3) translate(-2px, 1px); }
  75% { transform: scale(1.3) translate(2px, -1px); }
}

/* The real tap target — much bigger than the tile, because fingers. */
.portal-hit {
  position: absolute;
  border-radius: 50%;
  z-index: 20;
  cursor: pointer;
  touch-action: manipulation;
}

/* ------------------------------ Racers -------------------------------- */

/* The outer element only ever slides; the inner one only ever wiggles. */
.token {
  position: absolute;
  left: 0;
  top: 0;
  width: 0;
  height: 0;
  z-index: 10;
  pointer-events: none;
  will-change: transform;
}

.token--player { z-index: 11; }

.tok-inner {
  position: absolute;
  left: 0;
  top: 0;
  display: block;
  white-space: nowrap;
  line-height: 1;
  font-size: calc(var(--tile-px) * 0.95);
  filter: var(--tint, none) drop-shadow(0 3px 3px rgba(0, 40, 60, 0.4));
  transform: translate(calc(-50% + var(--nudge)), -50%);
}

.token.sad .tok-inner { filter: var(--tint, none) grayscale(0.7) drop-shadow(0 3px 3px rgba(0, 40, 60, 0.4)); }

/* The tokens on the board — dyed the same way as every other copy of the two.
   Which class a token wears is decided by the game, not by which racer it is,
   so a snap moves the purple across the board along with the mermaid. */
.token.as-mermaid { --tint: var(--mermaid-tint); }
.token.as-goblin  { --tint: var(--goblin-tint); }

/* Held by something — swallowed by the baby, or sitting on a plane that hasn't
   taken off. It's a plane or a bottle standing on the tile now, not a racer, so
   the tint comes off and it gets a nervous little jiggle instead. */
.token.stuck .tok-inner {
  filter: drop-shadow(0 3px 3px rgba(0, 40, 60, 0.4));
  animation: stuckJiggle 0.9s ease-in-out infinite;
}

@keyframes stuckJiggle {
  0%, 100% { transform: translate(calc(-50% + var(--nudge)), -50%) rotate(-4deg); }
  50% { transform: translate(calc(-50% + var(--nudge)), -50%) rotate(4deg); }
}

@keyframes hop {
  0%, 100% { transform: translate(calc(-50% + var(--nudge)), -50%) scale(1); }
  45% { transform: translate(calc(-50% + var(--nudge)), -100%) scale(1.1, 0.9); }
}

@keyframes warpOut {
  0% { transform: translate(calc(-50% + var(--nudge)), -50%) scale(1) rotate(0deg); opacity: 1; }
  100% { transform: translate(calc(-50% + var(--nudge)), -50%) scale(0.05) rotate(540deg); opacity: 0.15; }
}

@keyframes warpIn {
  0% { transform: translate(calc(-50% + var(--nudge)), -50%) scale(0.05) rotate(-540deg); opacity: 0.15; }
  100% { transform: translate(calc(-50% + var(--nudge)), -50%) scale(1) rotate(0deg); opacity: 1; }
}

/* ------------------------------- Traps -------------------------------- */

/* His half starts salted and yours starts clean — everything that ever turns up
   in your water was dropped there by a wild.

   These are the one thing on the path you actually have to SPOT, and they used
   to be the quietest thing on it: a small flat emoji on a flat tile, while the
   portals swirled and the castles glowed right next to them. So a trap is now
   the biggest emoji on the board, it sits above its neighbors, it's ringed in
   its own color, and it breathes. You can pick one out from across the room. */
.trap {
  font-size: calc(var(--tile-px) * 0.82);
  border-width: 3px;
  border-color: #d24a2f;
  background: linear-gradient(160deg, #ffe3d2, #ffb08c);
  color: #fff;
  text-shadow: 0 1px 2px rgba(0, 0, 0, 0.35);
  z-index: 4;
  animation: trapWarn 2.2s ease-in-out infinite;
}

/* The same trick the portals use: a ring pushed outward and faded away, so the
   tile pulses without ever changing size and shoving the grid around. */
@keyframes trapWarn {
  0%, 100% { box-shadow: 0 0 0 0 rgba(210, 74, 47, 0.5), 0 2px 4px rgba(6, 60, 90, 0.2); }
  50% { box-shadow: 0 0 0 6px rgba(210, 74, 47, 0), 0 2px 4px rgba(6, 60, 90, 0.2); }
}

.trap--airplane {
  background: linear-gradient(160deg, #eaf4ff, #8fbdf0);
  border-color: #2f6fc4;
  animation-name: trapWarnPlane;
}
@keyframes trapWarnPlane {
  0%, 100% { box-shadow: 0 0 0 0 rgba(47, 111, 196, 0.55), 0 2px 4px rgba(6, 60, 90, 0.2); }
  50% { box-shadow: 0 0 0 6px rgba(47, 111, 196, 0), 0 2px 4px rgba(6, 60, 90, 0.2); }
}

.trap--baby {
  background: linear-gradient(160deg, #ffeaf4, #ffa6ca);
  border-color: #e0509a;
  animation-name: trapWarnBaby;
}
@keyframes trapWarnBaby {
  0%, 100% { box-shadow: 0 0 0 0 rgba(224, 80, 154, 0.55), 0 2px 4px rgba(6, 60, 90, 0.2); }
  50% { box-shadow: 0 0 0 6px rgba(224, 80, 154, 0), 0 2px 4px rgba(6, 60, 90, 0.2); }
}

/* 🕳️ is a black disc, so the one thing this tile mustn't be is dark — the hole
   would vanish into its own square. Pale sandy ground, dark rim, and the black
   of the hole does all the work. */
.trap--hole {
  background: linear-gradient(160deg, #fff0cf, #e2c489);
  border-color: #6b563a;
  animation-name: trapWarnHole;
}
@keyframes trapWarnHole {
  0%, 100% { box-shadow: 0 0 0 0 rgba(107, 86, 58, 0.55), 0 2px 4px rgba(6, 60, 90, 0.2); }
  50% { box-shadow: 0 0 0 6px rgba(107, 86, 58, 0), 0 2px 4px rgba(6, 60, 90, 0.2); }
}

/* Sprung: it's had its fun and goes limp. The pulse stops with it — a dead trap
   that carried on flashing would keep pulling your eye to the one tile on the
   board that can't hurt anybody any more. */
.trap.used {
  background: linear-gradient(160deg, #ece8ea, #cfc7cb);
  border-color: #a89ea3;
  filter: grayscale(1);
  opacity: 0.6;
  animation: none;
  box-shadow: 0 2px 4px rgba(6, 60, 90, 0.16);
  z-index: 2;
}

.tile.sprung {
  animation: trapSpring 0.55s cubic-bezier(0.36, 1.5, 0.6, 1);
  z-index: 7;
}

@keyframes trapSpring {
  0% { transform: scale(1) rotate(0deg); }
  30% { transform: scale(1.45) rotate(-14deg); }
  60% { transform: scale(1.2) rotate(12deg); }
  100% { transform: scale(1) rotate(0deg); }
}

/* A wild's present, thumping down onto a tile that was bare a second ago. */
.tile.dropped {
  animation: trapDrop 0.6s cubic-bezier(0.36, 1.5, 0.6, 1);
  z-index: 7;
}

@keyframes trapDrop {
  0% { transform: translateY(-260%) scale(1.6); opacity: 0; }
  55% { transform: translateY(0) scale(1.35); opacity: 1; }
  75% { transform: translateY(0) scale(0.88); }
  100% { transform: translateY(0) scale(1); }
}

/* ---------------------------- Say banner ------------------------------ */

#say {
  flex: 0 0 auto;
  align-self: center;
  z-index: 30;
  display: flex;
  align-items: center;
  gap: 0;   /* the countdown digit brings its own margin — see #say-count */
  max-width: 94%;
  margin-bottom: clamp(3px, 1vw, 8px);
  padding: clamp(5px, 1.4vw, 10px) clamp(12px, 3vw, 22px);
  font-size: clamp(14px, 3.4vw, 21px);
  font-weight: 800;
  color: #0d4a66;
  background: rgba(255, 255, 255, 0.92);
  border: 3px solid #7fd7f2;
  border-radius: 99px;
  box-shadow: 0 5px 0 rgba(10, 90, 130, 0.18), 0 8px 16px rgba(0, 0, 0, 0.14);
  pointer-events: none;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

#say.pop { animation: sayPop 0.4s cubic-bezier(0.34, 1.6, 0.64, 1); }
@keyframes sayPop {
  0% { transform: scale(0.7); }
  60% { transform: scale(1.08); }
  100% { transform: scale(1); }
}

#say.urgent {
  color: #b0004a;
  border-color: #ff2d63;
  animation: sayUrgent 0.5s ease-in-out infinite;
}

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

/* The digit is half again the size of the banner text, so letting it pop into
   the flow and out again changes how tall #say is. #say is one row of the #game
   column, so every change steals height from #stage or hands it back — and the
   ResizeObserver watching #stage answers by re-folding and re-scaling the whole
   board. Twice per portal, at the exact moment you're staring at it.
   So the tall line is held open always and only the width collapses. */
#say-count {
  font-size: 1.5em;
  line-height: 1;
  min-height: 1em;   /* 1em of ITS OWN size: the tall line, reserved for good */
  font-weight: 800;
  color: #0a8f5f;
  min-width: 1.2em;
  text-align: center;
}

#say-count:empty { min-width: 0; }
#say-count:not(:empty) { margin-left: 10px; }

#say-count.hurry { color: #ff2d63; }

/* ------------------------------- The d20 ------------------------------- */

#dock {
  flex: 0 0 auto;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: clamp(6px, 1.6vw, 14px) 10px calc(clamp(8px, 2vw, 16px) + env(safe-area-inset-bottom));
}

#die-btn {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 0;
  width: clamp(84px, 22vw, 122px);
  height: clamp(70px, 18vw, 100px);
  font-family: inherit;
  color: #fff;
  background: linear-gradient(180deg, #a86ce8, #6a2fb5);
  border: 4px solid #fff;
  border-radius: 26px;
  cursor: pointer;
  box-shadow: 0 8px 0 #45197d, 0 12px 20px rgba(0, 0, 0, 0.25);
  transition: transform 0.1s ease, box-shadow 0.1s ease, filter 0.25s ease;
  touch-action: manipulation;
}

#die-btn:active:not(:disabled) {
  transform: translateY(5px);
  box-shadow: 0 3px 0 #45197d, 0 6px 12px rgba(0, 0, 0, 0.25);
}

#die-btn.off {
  filter: saturate(0.4) brightness(0.92);
  cursor: default;
}

/* When it's the other one's roll the die goes green — his turn, not yours. This
   is about WHOSE turn it is, so it stays green whichever shape you're wearing.
   The face sitting on it is a separate question, handled just below. */
#die-btn.their-roll {
  background: linear-gradient(180deg, #a5d96a, #5f9b30);
  box-shadow: 0 8px 0 #3d6c18, 0 12px 20px rgba(0, 0, 0, 0.25);
}

#die-who {
  font-size: clamp(13px, 3.2vw, 18px);
  line-height: 1.1;
}

/* The little face above the number is whoever's rolling, dyed to match — by the
   shape they're currently wearing, which is why it can't hang off .their-roll. */
#die-who.as-mermaid { filter: var(--mermaid-tint); }
#die-who.as-goblin  { filter: var(--goblin-tint); }

/* A natural 20. The die turns gold and the star sits there glowing until the
   next roll clears it — right through the card where you pick what to drop. */
#die-btn.wild {
  background: linear-gradient(180deg, #ffd970, #e89a00);
  box-shadow: 0 8px 0 #a86b00, 0 12px 20px rgba(0, 0, 0, 0.25);
}

#die-btn.wild #die-face {
  animation: wildGlow 0.9s ease-in-out infinite;
  text-shadow: 0 0 10px rgba(255, 255, 255, 0.95), 0 2px 0 rgba(0, 0, 0, 0.22);
}

@keyframes wildGlow {
  0%, 100% { transform: scale(1) rotate(-5deg); }
  50% { transform: scale(1.15) rotate(5deg); }
}

#die-face {
  font-size: clamp(28px, 8vw, 44px);
  font-weight: 800;
  line-height: 1.05;
  text-shadow: 0 2px 0 rgba(0, 0, 0, 0.22);
}

#die-btn.rolling { animation: dieRoll 0.22s linear infinite; }
@keyframes dieRoll {
  0%, 100% { transform: rotate(-3deg) translateY(0); }
  50% { transform: rotate(3deg) translateY(-4px); }
}

#die-btn.landed #die-face { animation: dieLand 0.3s cubic-bezier(0.34, 1.7, 0.64, 1); }
@keyframes dieLand {
  0% { transform: scale(1.9); }
  100% { transform: scale(1); }
}

/* --------------------------- FX canvas ------------------------------ */

#fx {
  position: fixed;
  inset: 0;
  width: 100%;
  height: 100%;
  pointer-events: none;
  /* Above the overlays (60), so the win card's fireworks burst over the card and
     not behind it. It never swallows taps — pointer-events is off. */
  z-index: 70;
}

/* ---------------------------- Overlays ------------------------------ */

.overlay {
  position: fixed;
  inset: 0;
  z-index: 60;
  display: none;
  align-items: center;
  justify-content: center;
  padding: 20px;
  background: rgba(10, 60, 90, 0.45);
  backdrop-filter: blur(3px);
  overflow-y: auto;
}

.overlay.show { display: flex; }
.overlay.lose { background: rgba(35, 60, 20, 0.55); }
.overlay.win { background: rgba(46, 26, 82, 0.5); }
.overlay.pick { background: rgba(90, 60, 0, 0.5); }

.card-box {
  background: #fff;
  border-radius: 28px;
  border: 6px solid #7fd7f2;
  box-shadow: 0 16px 0 rgba(10, 90, 130, 0.25), 0 24px 40px rgba(0, 0, 0, 0.3);
  padding: clamp(20px, 5vw, 40px);
  max-width: 460px;
  width: 100%;
  text-align: center;
  animation: cardIn 0.4s cubic-bezier(0.34, 1.56, 0.64, 1);
}

@keyframes cardIn {
  from { transform: scale(0.6) translateY(30px); opacity: 0; }
}

.overlay.win .card-box { border-color: #a86ce8; }
.overlay.lose .card-box { border-color: #a8dd6c; }

.card-emoji {
  font-size: clamp(42px, 11vw, 66px);
  line-height: 1;
  margin-bottom: 6px;
}

/* The 🎉 on the win card rattles harder and harder on its fuse, then blows itself
   clean off the card. Keep this in step with popperFuseMs in the config — the
   real fireworks are fired the instant it vanishes. */
.overlay.win .popper {
  display: inline-block;
  animation: popperFuse 0.9s ease-in forwards;
}

@keyframes popperFuse {
  0%   { transform: rotate(0deg) scale(1); }
  20%  { transform: rotate(-6deg) scale(1.04); }
  35%  { transform: rotate(7deg) scale(1.06); }
  50%  { transform: rotate(-10deg) scale(1.1); }
  62%  { transform: rotate(11deg) scale(1.14); }
  74%  { transform: rotate(-13deg) scale(1.2); }
  84%  { transform: rotate(14deg) scale(1.26); }
  93%  { transform: rotate(-9deg) scale(1.4); opacity: 1; }
  100% { transform: rotate(6deg) scale(2.1); opacity: 0; }
}

.card-box h1 {
  margin: 6px 0 12px;
  font-size: clamp(27px, 7.4vw, 44px);
  font-weight: 800;
  color: #0a8ac0;
  letter-spacing: 1px;
}

.overlay.win .card-box h1 { color: #7b3fd0; }
.overlay.lose .card-box h1 { color: #4c7f21; }

.card-box p {
  margin: 8px 0;
  font-size: clamp(15px, 3.6vw, 19px);
  font-weight: 500;
  color: #24506a;
}

.card-box p.small { font-size: clamp(13px, 3vw, 16px); color: #6b8a9a; }

.card-box .new-best {
  font-weight: 800;
  color: #ff8a00;
  font-size: clamp(17px, 4.2vw, 22px);
}

.big-btn {
  margin-top: 18px;
  font-family: inherit;
  font-size: clamp(20px, 5vw, 28px);
  font-weight: 800;
  color: #fff;
  background: linear-gradient(180deg, #a86ce8, #6a2fb5);
  border: none;
  border-radius: 99px;
  padding: 14px 34px;
  cursor: pointer;
  box-shadow: 0 6px 0 #45197d, 0 10px 18px rgba(0, 0, 0, 0.25);
  transition: transform 0.1s ease, box-shadow 0.1s ease;
  touch-action: manipulation;
}

.big-btn:active {
  transform: translateY(4px);
  box-shadow: 0 2px 0 #45197d, 0 4px 10px rgba(0, 0, 0, 0.25);
}

/* ------------------------- The wild's three gifts ------------------------- */

/* Rows rather than a row of three: at 320px three side by side would be too
   narrow to read and too narrow to hit. Stacked, each one is a full-width
   target with room for its emoji, its name and a line saying what it does. */
.overlay.pick .card-box { border-color: #f2a20c; }
.overlay.pick .card-box h1 { color: #d98800; }

.pick-row {
  display: flex;
  flex-direction: column;
  gap: 10px;
  margin-top: 16px;
}

.pick-btn {
  display: flex;
  align-items: center;
  gap: 12px;
  width: 100%;
  padding: 10px 14px;
  font-family: inherit;
  text-align: left;
  background: linear-gradient(160deg, #fffdf4, #ffeec8);
  border: 4px solid #ffc247;
  border-radius: 20px;
  cursor: pointer;
  box-shadow: 0 5px 0 rgba(185, 112, 10, 0.4);
  transition: transform 0.1s ease, box-shadow 0.1s ease;
  touch-action: manipulation;
}

.pick-btn:active {
  transform: translateY(4px);
  box-shadow: 0 1px 0 rgba(185, 112, 10, 0.4);
}

.pick-emoji {
  flex: 0 0 auto;
  font-size: clamp(30px, 8vw, 42px);
  line-height: 1;
}

.pick-body { display: flex; flex-direction: column; min-width: 0; }

.pick-name {
  font-size: clamp(16px, 4vw, 20px);
  font-weight: 800;
  color: #24506a;
}

.pick-what {
  font-size: clamp(12px, 3vw, 15px);
  font-weight: 500;
  color: #6b8a9a;
}
