/* Story type, bundled so it works offline (SIL Open Font License) */
@font-face { font-family: 'Cormorant Garamond'; font-style: italic; font-weight: 500; font-display: swap; src: url(../fonts/cormorant-garamond.woff2) format('woff2'); }
@font-face { font-family: 'Cinzel'; font-weight: 600; font-display: swap; src: url(../fonts/cinzel.woff2) format('woff2'); }

:root {
  --serif: 'Cormorant Garamond', Georgia, serif;
  --display: 'Cinzel', Georgia, serif;
  --body: 'Exo 2', system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
  --bg: #07040f;
  --bg-2: #0e0b22;
  --card: #161a3a;
  --card-2: #20264f;
  --line: #2a2f63;
  --text: #eef0ff;
  --muted: #8f97cf;
  --gold: #ffd27a;
  --gold-dark: #3a2a05;
  --violet: #b9b3ff;
  --violet-dark: #1b1550;
  --cyan: #5ce1c6;
  --cyan-dark: #0d3a32;
  --pink: #ff7aa8;
  --radius: 16px;
}

/* First-run AURA cinematic. The captions stay DOM text for accessibility while WebGL carries the
   extinction, vacuum and surviving-information imagery behind them. The image's focus lives in the
   upper third and the captions in the lower third, so on a phone the words never cover the action. */
.cinematic-intro {
  position: fixed; inset: 0; z-index: 1000; overflow: hidden;
  background: #000; color: #f5f4ff; isolation: isolate;
  font-family: 'Exo 2', system-ui, sans-serif;
}
.cinematic-intro[hidden] { display: none; }
.cinematic-intro::before, .cinematic-intro::after {
  content: ''; position: absolute; z-index: 5; left: 0; right: 0; height: clamp(12px, 3.2vh, 34px);
  background: #000; pointer-events: none;
}
.cinematic-intro::before { top: 0; box-shadow: 0 12px 38px rgba(0,0,0,.85); }
.cinematic-intro::after { bottom: 0; box-shadow: 0 -12px 38px rgba(0,0,0,.85); }
.cinematic-intro canvas {
  position: absolute; inset: 0; width: 100%; height: 100%; opacity: 0;
  transition: opacity 1.35s cubic-bezier(.2,.65,.2,1);
}
.cinematic-intro.arming canvas, .cinematic-intro.playing canvas, .cinematic-intro.preview canvas { opacity: 1; }
.cinematic-vignette {
  position: absolute; z-index: 2; inset: 0; pointer-events: none;
  background:
    linear-gradient(180deg, rgba(0,0,0,.38), transparent 22%, transparent 76%, rgba(0,0,0,.55)),
    radial-gradient(ellipse at 50% 45%, transparent 7%, rgba(0,0,0,.1) 48%, rgba(0,0,0,.88) 100%);
  box-shadow: inset 0 0 150px rgba(0,0,0,.72);
}
.cinematic-start {
  position: absolute; z-index: 10; inset: 0; display: grid; place-content: center; justify-items: center; gap: 22px;
  text-align: center; background: #000; transition: opacity .8s ease;
}
.cinematic-start.receding { opacity: 0; pointer-events: none; }
.cinematic-start[hidden] { display: none; }
.cinematic-start > span { font-family: Cinzel, serif; font-size: clamp(16px, 3vw, 24px); letter-spacing: .36em; color: #aaa6cf; }
.cinematic-start button {
  min-width: 180px; padding: 13px 26px; border: 1px solid rgba(197,139,255,.7); border-radius: 999px;
  color: #fff; background: rgba(77,43,130,.25); font: 600 13px/1 'Exo 2', sans-serif; letter-spacing: .22em;
  box-shadow: 0 0 35px rgba(119,76,210,.18); cursor: pointer;
}
.cinematic-start button:hover { background: rgba(116,69,194,.38); box-shadow: 0 0 40px rgba(119,76,210,.3); }
.cinematic-start small { color: #77738f; font-size: 11px; letter-spacing: .08em; }
.cinematic-copy {
  position: absolute; z-index: 4; left: 50%; top: 72%; width: min(960px, calc(100% - 64px));
  transform: translate3d(-50%, -50%, 0); text-align: center; text-wrap: balance; contain: layout paint;
  padding: clamp(16px, 3vw, 34px); font-family: 'Cormorant Garamond', Georgia, serif;
  font-size: clamp(25px, 4.5vw, 50px); line-height: 1.24; letter-spacing: .025em;
  text-shadow: 0 3px 16px #000, 0 0 38px #000, 0 0 64px rgba(70,85,190,.34); pointer-events: none;
  transition: opacity .55s ease, transform .55s ease;
}
.cinematic-line {
  display: flex; min-height: 1.24em; align-items: baseline; justify-content: center;
  flex-wrap: wrap; column-gap: .24em; row-gap: .08em;
}
.cinematic-line + .cinematic-line { margin-top: .14em; }
.cinematic-word {
  display: inline-block; opacity: 0; color: rgba(245,244,255,.18);
  transform: translate3d(0, 8px, 0) scale(.99);
  text-shadow: 0 0 18px rgba(180,195,255,0);
  transition: opacity .4s ease, color .48s ease, text-shadow .55s ease, transform .4s cubic-bezier(.16,.75,.2,1);
}
.cinematic-word.revealed {
  opacity: 1; color: inherit; transform: none;
  text-shadow: 0 0 18px rgba(180,195,255,.16);
}
.cinematic-word.aura-name.revealed { color: #f5cf82; font-family: Cinzel, serif; letter-spacing: .12em; }
.cinematic-copy small {
  display: block; margin-top: 26px; color: #9d99c9; font: 500 clamp(9px, 1.5vw, 13px)/1.5 'Exo 2', sans-serif;
  letter-spacing: .28em; animation: cinematic-sub .9s .5s both;
}
.cinematic-copy.departing { opacity: 0; transform: translate3d(-50%, -54%, 0); }
.cinematic-copy.metrics {
  top: 72%; width: min(660px, calc(100% - 54px)); color: #d7d6ed;
  font-family: 'Exo 2', sans-serif; font-size: clamp(17px, 3.2vw, 31px); line-height: 1.65; letter-spacing: .14em;
}
.cinematic-copy.metrics .cinematic-line {
  justify-content: space-between; min-height: 1.65em; padding: .08em .5em;
  border-bottom: 1px solid rgba(126,133,190,.16);
}
.cinematic-copy.metrics .cinematic-line:first-child:last-child { justify-content: center; }
.cinematic-copy.identity .cinematic-line:last-of-type {
  margin-top: .55em; color: #aaa6cf; font-family: 'Exo 2', sans-serif;
  font-size: .48em; line-height: 1.45; letter-spacing: .14em; text-transform: uppercase;
  text-shadow: 0 3px 18px #000;
}
.cinematic-copy.survived { color: #b9d8ff; }
.cinematic-copy.you {
  color: #ffe0a0; font-size: clamp(32px, 5.6vw, 62px); letter-spacing: .05em;
  text-shadow: 0 0 22px rgba(255,186,77,.3), 0 3px 20px #000, 0 0 60px #000;
}
.cinematic-skip {
  position: absolute; z-index: 8; top: max(24px, env(safe-area-inset-top)); right: max(22px, env(safe-area-inset-right));
  padding: 9px 12px; border: 0; color: #77758c; background: transparent; font: 600 10px/1 'Exo 2', sans-serif;
  letter-spacing: .16em; cursor: pointer;
}
.cinematic-skip:hover { color: #ddd9ff; }
.cinematic-progress { position: absolute; z-index: 8; bottom: max(26px, env(safe-area-inset-bottom)); left: 50%; display: flex; gap: 9px; transform: translateX(-50%); }
.cinematic-progress i { width: 28px; height: 2px; background: #2c2b38; transition: background .7s, box-shadow .7s, width .7s; }
.cinematic-progress i.on { width: 46px; background: #bd9dff; box-shadow: 0 0 13px #8255dc; }
.cinematic-progress i.done { background: #67627a; }
.cinematic-intro.leaving { animation: cinematic-out .9s ease forwards; }
@keyframes cinematic-sub { from { opacity: 0; transform: translateY(7px); } to { opacity: 1; transform: none; } }
@keyframes cinematic-out { to { opacity: 0; visibility: hidden; } }
@media (max-width: 520px) {
  .cinematic-copy { top: 70%; width: calc(100% - 24px); padding: 12px; font-size: clamp(24px, 8.2vw, 38px); }
  .cinematic-line { column-gap: .2em; }
  .cinematic-copy.metrics { width: calc(100% - 34px); font-size: 15px; letter-spacing: .09em; }
  .cinematic-copy.identity .cinematic-line:last-of-type { letter-spacing: .18em; }
}
@media (prefers-reduced-motion: reduce) {
  .cinematic-word, .cinematic-copy small, .cinematic-intro.leaving { animation-duration: .01ms !important; animation-delay: 0ms !important; transition-duration: .01ms !important; }
}

* { box-sizing: border-box; }
[hidden] { display: none !important; }
svg { display: block; width: 100%; height: 100%; }

html, body {
  margin: 0;
  height: 100%;
  background: var(--bg);
  color: var(--text);
  font-family: var(--body);
  letter-spacing: .01em;
  -webkit-tap-highlight-color: transparent;
  user-select: none;
  overscroll-behavior: none;
}

button { font: inherit; color: inherit; cursor: pointer; touch-action: manipulation; }

/* The universe fills the whole screen; everything else floats on top of it. */
#app {
  position: relative;
  max-width: 480px;
  margin: 0 auto;
  height: 100dvh;
  overflow: hidden;
  --top: max(10px, env(safe-area-inset-top));
  --bottom: max(10px, env(safe-area-inset-bottom));
  --dock-h: 62px;
}

#stage { position: absolute; inset: 0; overflow: hidden; touch-action: none; cursor: pointer; }
#universe-bg, #universe, #void { position: absolute; inset: 0; width: 100%; height: 100%; display: block; }

/* Screens: the Void (tap to farm), the Universe (navigate space), the Inventory (manage).
   Canvases are hidden with visibility, not display, so they keep their size. */
#app:not([data-screen="void"]) #void, #app[data-screen="void"] :is(#universe, #universe-bg) { visibility: hidden; }
#app[data-screen="void"] :is(.era-label, .scales, .focus-card, .inside-exit, .boosts) { display: none !important; }
#app[data-screen="inventory"] :is(.era-label, .scales, .inside-exit, .tap-hint, .event) { display: none !important; }

/* The clicker's own upgrade: a slim pill under the counter, leaving the Void free for cutting */
/* Just the level and the button to raise it: what each level gives is told by its card. */
.tap-card {
  position: absolute; left: 12px; top: calc(var(--top) + 62px); z-index: 6;
  display: flex; gap: 6px; align-items: center; padding: 3px 3px 3px 5px;
  border-radius: 99px; background: rgba(12,9,30,.62); border: 1px solid rgba(255,210,122,.22); backdrop-filter: blur(8px);
  box-shadow: inset 0 1px 0 rgba(255,255,255,.06), 0 4px 14px rgba(0,0,0,.35);
}
.tap-card .sub { display: none; }
.tap-card .ico { width: 24px; height: 24px; padding: 2px; flex-shrink: 0; }
.tap-card .mid { display: flex; align-items: baseline; gap: 6px; }
.tap-card .top .name { display: none; }
.tap-card .top .badge { font-size: 12.5px; font-weight: 800; letter-spacing: .02em; color: #ffe2a0; background: none; padding: 0 2px; text-shadow: 0 0 8px rgba(255,190,90,.45); }
.tap-card .sub { font-size: 12px; color: var(--muted); white-space: nowrap; }
.tap-card .buy { min-height: 28px; width: auto; padding: 2px 11px 2px 9px; border-radius: 99px; box-shadow: inset 0 1px 0 rgba(255,255,255,.65), 0 2px 0 #c9962f, 0 0 12px rgba(255,190,90,.3); }
.tap-card .buy:disabled { box-shadow: inset 0 1px 0 rgba(255,255,255,.08), 0 2px 0 #141838; }
.tap-card .buy .cost { font-size: 13px; }
.tap-card .buy .cur { width: 13px; height: 13px; }
.tap-card .buy .qty { display: none; }
.tap-card.pop { animation: bump .25s ease-out; }
/* The pill by level (data-tier: 0 under 5, 1 from 5, 2 from 10, 3 from 20, 4 from 35): its rim and its
   number shine more, and at the top a slow sheen crosses it. */
.tap-card { overflow: hidden; }
.tap-card[data-tier="1"] { border-color: rgba(255,210,122,.45); box-shadow: inset 0 1px 0 rgba(255,255,255,.08), 0 0 12px rgba(255,190,90,.18), 0 4px 14px rgba(0,0,0,.35); }
.tap-card[data-tier="2"] { border-color: rgba(255,210,122,.7); box-shadow: inset 0 1px 0 rgba(255,255,255,.1), 0 0 18px rgba(255,180,70,.32), 0 4px 14px rgba(0,0,0,.35); }
.tap-card[data-tier="2"] .ico, .tap-card[data-tier="3"] .ico, .tap-card[data-tier="4"] .ico { filter: drop-shadow(0 0 5px rgba(255,200,110,.8)); }
.tap-card:is([data-tier="2"], [data-tier="3"], [data-tier="4"]) .top .badge { color: #fff1cc; text-shadow: 0 0 4px rgba(255,214,130,.9), 0 0 12px rgba(255,160,40,.6); }
.tap-card[data-tier="3"] { border-color: rgba(255,190,240,.7); background: linear-gradient(90deg, rgba(40,20,60,.7), rgba(20,14,50,.7)); box-shadow: inset 0 1px 0 rgba(255,255,255,.12), 0 0 20px rgba(220,120,255,.3), 0 4px 14px rgba(0,0,0,.35); }
.tap-card[data-tier="4"] { border-color: rgba(140,230,255,.8); background: linear-gradient(90deg, rgba(20,30,70,.72), rgba(40,18,70,.72)); box-shadow: inset 0 1px 0 rgba(255,255,255,.14), 0 0 22px rgba(120,200,255,.35), 0 4px 14px rgba(0,0,0,.35); }
.tap-card:is([data-tier="3"], [data-tier="4"])::after {
  content: ''; position: absolute; inset: 0; pointer-events: none; border-radius: inherit;
  background: linear-gradient(105deg, transparent 38%, rgba(255,245,220,.22) 50%, transparent 62%);
  transform: translateX(-100%); animation: streak-sheen 5s ease-in-out infinite;
}
@media (prefers-reduced-motion: reduce) { .tap-card::after { animation: none !important; } }

/* HUD */
.hud {
  position: absolute; left: 0; right: 0; top: 0; z-index: 5; pointer-events: none;
  display: flex; justify-content: space-between; align-items: center;
  padding: var(--top) 12px 18px;
  background: linear-gradient(rgba(7,4,15,.75), rgba(7,4,15,0));
}
.hud button { pointer-events: auto; }
.hud-right { display: flex; align-items: center; gap: 10px; }
.res { display: flex; align-items: center; gap: 8px; }
.res-icon { width: 30px; height: 30px; flex-shrink: 0; }
.amount { font-size: 26px; font-weight: 800; color: var(--gold); font-variant-numeric: tabular-nums; line-height: 1.1; text-shadow: 0 1px 8px rgba(0,0,0,.6); }
/* The energy counter by magnitude (data-tier: 0 under a thousand, 1 K, 2 M, 3 B, 4 T, 5 beyond). Each
   step is a little richer than the last; only the top ones move, and slowly. */
.res[data-tier] #stardust { transition: filter .4s; }
.res[data-tier="1"] #stardust { color: #ffe08f; text-shadow: 0 0 3px rgba(255,214,130,.6), 0 0 14px rgba(255,170,60,.45), 0 1px 6px rgba(0,0,0,.6); }
.res[data-tier="1"] .res-icon { filter: drop-shadow(0 0 5px rgba(255,200,110,.6)); }
.res:is([data-tier="2"], [data-tier="3"], [data-tier="4"], [data-tier="5"]) #stardust {
  color: transparent; -webkit-background-clip: text; background-clip: text; text-shadow: none;
  background-image: linear-gradient(100deg, #ffd27a 0%, #ffd27a 38%, #fffaf0 50%, #ffd27a 62%, #ffb347 100%);
  background-size: 260% 100%; background-position: 100% 0;
  filter: drop-shadow(0 0 2px rgba(255,214,130,.9)) drop-shadow(0 0 12px rgba(255,160,40,.55));
  animation: amount-sheen 4.5s ease-in-out infinite;
}
.res:is([data-tier="2"], [data-tier="3"], [data-tier="4"], [data-tier="5"]) .res-icon { filter: drop-shadow(0 0 7px rgba(255,190,90,.8)); }
/* Billions: the gold turns iridescent, with a violet halo. */
.res[data-tier="3"] #stardust {
  background-image: linear-gradient(100deg, #ffd27a 0%, #ffb3e6 30%, #fffaf0 50%, #b9b3ff 70%, #ffd27a 100%);
  filter: drop-shadow(0 0 2px rgba(255,220,180,.9)) drop-shadow(0 0 14px rgba(190,120,255,.6));
}
/* Trillions and beyond: cosmic, cyan through violet to gold, and the icon breathes. */
.res:is([data-tier="4"], [data-tier="5"]) #stardust {
  background-image: linear-gradient(100deg, #7ff0ff 0%, #b9b3ff 25%, #fffaf0 50%, #ffd27a 75%, #ff8ad8 100%);
  filter: drop-shadow(0 0 2px rgba(220,230,255,.9)) drop-shadow(0 0 16px rgba(120,180,255,.6));
  animation-duration: 3s;
}
.res:is([data-tier="4"], [data-tier="5"]) .res-icon { animation: icon-breathe 2.4s ease-in-out infinite; }
@keyframes amount-sheen { 0%, 55% { background-position: 100% 0; } 100% { background-position: 0% 0; } }
@keyframes icon-breathe { 50% { transform: scale(1.12); filter: drop-shadow(0 0 10px rgba(160,200,255,.9)); } }
/* Crossing into a new magnitude: the counter flares once. */
.res.tier-up #stardust { animation: tier-up .9s ease-out, amount-sheen 4.5s ease-in-out .9s infinite; }
.res.tier-up .res-icon { animation: tier-icon .9s ease-out; }
@keyframes tier-up { 0% { transform: scale(1); } 25% { transform: scale(1.25); filter: brightness(2) drop-shadow(0 0 16px rgba(255,220,150,1)); } 100% { transform: scale(1); } }
@keyframes tier-icon { 30% { transform: scale(1.5) rotate(45deg); filter: drop-shadow(0 0 14px rgba(255,230,170,1)); } }
#stardust { display: inline-block; transform-origin: left center; }
@media (prefers-reduced-motion: reduce) { .res #stardust, .res .res-icon { animation: none !important; } }
.rate { font-size: 13px; color: var(--muted); font-variant-numeric: tabular-nums; }
.dm { text-align: right; }
.dm .amount { font-size: 20px; color: var(--violet); }
/* Phase pill: where the whole game is headed, always in view */
.phase-pill {
  display: flex; flex-direction: column; gap: 4px; padding: 6px 10px 7px; border-radius: 14px; min-width: 112px;
  background: rgba(14,11,34,.75); border: 1px solid rgba(255,210,122,.4); color: var(--text); text-align: left;
}
.pp-top { display: flex; align-items: center; gap: 6px; font-size: 12px; font-weight: 700; white-space: nowrap; }
.pp-icon { width: 16px; height: 16px; flex-shrink: 0; }
.pp-bar { height: 4px; border-radius: 4px; background: var(--bg-2); overflow: hidden; }
.pp-bar i { display: block; height: 100%; width: 0; background: linear-gradient(90deg, #ffb347, var(--gold)); transition: width .4s; }
.hud-right { gap: 8px; }

/* Phase map */
.phases-wrap {
  position: fixed; inset: 0; z-index: 36; display: grid; place-items: center; padding: 16px;
  background: rgba(5,3,14,.78); backdrop-filter: blur(3px); animation: fade-in .2s ease-out;
}
.phases-box {
  position: relative; width: min(400px, 100%); max-height: calc(100dvh - 32px); overflow-y: auto;
  padding: 18px 14px 14px; border-radius: 22px; background: var(--bg-2); border: 1px solid var(--line);
  box-shadow: 0 16px 40px rgba(0,0,0,.6); animation: card-pop .25s cubic-bezier(.2,.9,.3,1.2);
}
.phases-box h2 { margin: 0 0 12px 4px; font-family: var(--display); font-size: 20px; color: var(--gold); letter-spacing: .04em; }
.phases-x { position: absolute; top: 10px; right: 8px; }
#phases-list { display: flex; flex-direction: column; gap: 10px; }
.phase { display: flex; gap: 12px; padding: 12px; border-radius: 16px; background: var(--card); border: 1px solid var(--line); }
.phase.current { border-color: var(--gold); box-shadow: 0 0 18px rgba(255,210,122,.15); }
.phase.locked { opacity: .55; }
.phase .ph-icon { width: 46px; height: 46px; flex-shrink: 0; }
.phase.locked .ph-icon { filter: grayscale(1); }
.phase .ph-body { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 6px; }
.ph-head { display: flex; justify-content: space-between; gap: 8px; align-items: baseline; }
.ph-head small { font-size: 11px; color: var(--muted); text-transform: uppercase; letter-spacing: .08em; }
.ph-head b { font-size: 16px; }
.ph-tag { font-size: 11px; font-weight: 700; color: var(--muted); white-space: nowrap; }
.phase.current .ph-tag { color: var(--gold); }
.ph-d { margin: 0; font-size: 12.5px; line-height: 1.4; color: var(--muted); }
.ph-bar { height: 5px; border-radius: 5px; background: var(--bg-2); overflow: hidden; }
.ph-bar i { display: block; height: 100%; background: linear-gradient(90deg, #ffb347, var(--gold)); }
.ph-steps { display: flex; flex-wrap: wrap; gap: 5px; }
.ph-steps span { font-size: 11px; padding: 3px 8px; border-radius: 99px; background: var(--bg-2); color: var(--muted); border: 1px solid var(--line); }
.ph-steps span.done { color: var(--gold-dark); background: var(--gold); border-color: var(--gold); }
.ph-steps span.now { color: var(--gold); border-color: var(--gold); }
.ph-deliver { display: flex; flex-direction: column; gap: 6px; padding-top: 4px; border-top: 1px solid var(--line); }
.ph-deliver small { font-size: 12px; color: var(--muted); }
.ph-need { display: flex; gap: 8px; flex-wrap: wrap; }
.ph-need span { display: flex; align-items: center; gap: 5px; font-size: 13px; font-weight: 700; padding: 4px 8px; border-radius: 10px; background: var(--bg-2); }
.ph-need span i { display: block; width: 20px; height: 20px; }
.ph-need span.ok { color: var(--cyan); }
.ph-light { min-height: 46px; }

.icon-btn {
  width: 40px; height: 40px; padding: 9px; border-radius: 50%; color: var(--muted);
  background: rgba(14,11,34,.7); border: 1px solid var(--line);
}
/* Settings: a glass tile the height of the phase pill, its gear in violet neon that turns a little when
   pressed. */
#settings-btn {
  width: 40px; height: 40px; padding: 8px; border-radius: 14px; color: #c9b8ff;
  background: radial-gradient(circle at 50% 40%, #8a6cff26, rgba(14,11,34,.8) 70%);
  border: 1px solid #b7a2ee55; box-shadow: inset 0 0 10px #a489ef1f, 0 0 10px #8a6cff1a;
  transition: border-color .2s, box-shadow .2s;
}
#settings-btn svg { width: 100%; height: 100%; display: block; filter: drop-shadow(0 0 3px #a98bffaa); transition: transform .35s ease; }
#settings-btn:hover, #settings-btn:focus-visible { border-color: #c9b8ffaa; box-shadow: inset 0 0 12px #a489ef33, 0 0 14px #8a6cff40; }
#settings-btn:active svg, #settings-btn:hover svg { transform: rotate(45deg); }
@media (prefers-reduced-motion: reduce) { #settings-btn svg { transition: none; } }

.era-label {
  position: absolute; left: 14px; top: calc(var(--top) + 60px); pointer-events: none;
  display: flex; flex-direction: column; font-size: 13px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase;
}
.era-label small { font-size: 12px; font-weight: 500; color: var(--muted); letter-spacing: 0; text-transform: none; }
.scales {
  position: absolute; left: 0; right: 0; top: calc(var(--top) + 100px); display: flex; gap: 5px;
  padding: 0 12px; overflow-x: auto; scrollbar-width: none;
}
.scale {
  flex-shrink: 0; font-size: 11.5px; padding: 5px 9px; border-radius: 99px; border: 1px solid rgba(255,255,255,.15);
  background: rgba(7,4,15,.55); color: var(--muted); backdrop-filter: blur(4px);
}
.scale.active { color: var(--bg); background: var(--text); border-color: var(--text); font-weight: 700; }
.boosts { position: absolute; right: 12px; top: calc(var(--top) + 60px); display: flex; flex-direction: column; gap: 6px; align-items: flex-end; pointer-events: none; }
.chip { font-size: 12px; font-weight: 700; padding: 4px 9px; border-radius: 99px; background: rgba(255,210,122,.15); color: var(--gold); border: 1px solid rgba(255,210,122,.4); }
.tap-hint {
  position: absolute; left: 24px; right: 24px; bottom: calc(var(--bottom) + var(--dock-h) + 90px); text-align: center; pointer-events: none;
  font-size: 14px; line-height: 1.4; color: var(--muted); text-shadow: 0 1px 4px #000; animation: card-in .4s ease-out;
}
@keyframes pulse { 50% { opacity: .3; } }
.float {
  position: absolute; pointer-events: none; font-weight: 800; font-size: 17px; color: #ffe2a0;
  animation: rise .9s ease-out forwards;
  /* A dark edge first, so it reads even over a gold flash; then its own glow. */
  text-shadow: 0 0 2px rgba(30,10,0,.95), 0 1px 3px rgba(0,0,0,.9), 0 0 10px rgba(255,170,60,.6);
}
@keyframes rise { to { transform: translateY(-60px) scale(1.15); opacity: 0; } }

/* Scale-themed events */
.event {
  position: absolute; z-index: 4; width: 56px; height: 56px; padding: 7px; border-radius: 50%;
  border: 2px solid var(--gold); background: rgba(255,210,122,.15);
  animation: drift 12s linear forwards, glow 1s ease-in-out infinite;
}
.event.tunnel { border-color: #5bf08d; background: rgba(91,240,141,.15); animation: tunnel 3s steps(1) infinite, glow-green 1s ease-in-out infinite; }
.event.neutrino { border-color: #fff; background: rgba(255,255,255,.1); animation: dash 12s linear forwards, glow 1s ease-in-out infinite; }
.event.photon { animation: wave 12s linear forwards, glow 1s ease-in-out infinite; }
.event.supernova { border-color: #ff7aa8; animation: drift 12s linear forwards, glow-pink .8s ease-in-out infinite; }
@keyframes drift { to { transform: translate(-60px, 40px) rotate(-20deg); } }
@keyframes tunnel { 0% { transform: none; opacity: 1; } 30% { transform: translate(70px, 0); } 60% { transform: translate(-50px, 30px); } 90% { opacity: .2; } }
@keyframes dash { to { transform: translate(120px, -60px); } }
@keyframes wave { 25% { transform: translate(30px, -18px); } 50% { transform: translate(60px, 0); } 75% { transform: translate(90px, -18px); } 100% { transform: translate(120px, 0); } }
@keyframes glow { 50% { box-shadow: 0 0 24px rgba(255,210,122,.85); } }
@keyframes glow-green { 50% { box-shadow: 0 0 24px rgba(91,240,141,.85); } }
@keyframes glow-pink { 50% { box-shadow: 0 0 28px rgba(255,122,168,.9); } }

/* Floating cards above the dock: what you're zoomed into, or the next thing to buy */
.focus-card, .quick {
  position: absolute; left: 10px; right: 10px; bottom: calc(var(--bottom) + var(--dock-h) + 10px); z-index: 6;
  display: flex; gap: 10px; align-items: center;
  border-radius: 18px; background: rgba(14,11,34,.88); border: 1px solid var(--line);
  backdrop-filter: blur(8px); animation: card-in .25s ease-out;
}
.focus-card { padding: 10px 8px 10px 12px; }
.quick { padding: 6px; touch-action: pan-y; }
.quick.snap { transition: transform .2s ease-out; }
.quick.from-left { animation: from-left .22s ease-out; }
.quick.from-right { animation: from-right .22s ease-out; }
@keyframes from-left { from { transform: translateX(-40px); opacity: .3; } }
@keyframes from-right { from { transform: translateX(40px); opacity: .3; } }
/* Which of the unlocked things the shortcut is on; swipe to move along */
.quick-dots { position: absolute; left: 0; right: 0; top: -13px; display: flex; justify-content: center; gap: 5px; pointer-events: none; }
.quick-dots i { width: 5px; height: 5px; border-radius: 50%; background: rgba(255,255,255,.25); transition: background .2s, transform .2s; }
.quick-dots i.on { background: var(--gold); transform: scale(1.3); }
.quick .ico { width: 44px; height: 44px; border-radius: 12px; }
.quick .buy { min-height: 44px; width: 86px; }
@keyframes card-in { from { transform: translateY(12px); opacity: 0; } }
.fc-icon { width: 40px; height: 40px; flex-shrink: 0; }
.fc-body { flex: 1; min-width: 0; }
.fc-title { display: block; font-size: 15px; color: var(--gold); }
.fc-text { margin: 2px 0 0; font-size: 12.5px; line-height: 1.4; color: var(--text); opacity: .85; }
.fc-enter {
  margin-top: 7px; padding: 5px 12px; border-radius: 99px; font-size: 12.5px; font-weight: 700;
  color: var(--gold-dark); background: var(--gold); border: 0;
}
/* Back out of an atom or proton that was entered */
.inside-exit {
  position: absolute; left: 12px; top: calc(var(--top) + 100px); z-index: 6; padding: 6px 12px; border-radius: 99px;
  font-size: 12.5px; font-weight: 700; color: var(--text); background: rgba(14,11,34,.8); border: 1px solid var(--gold);
}
.x-btn { align-self: flex-start; background: none; border: 0; color: var(--muted); font-size: 24px; line-height: 1; padding: 0 6px; }

/* Dock */
.dock {
  position: absolute; left: 50%; bottom: var(--bottom); transform: translateX(-50%); z-index: 20;
  display: flex; gap: 4px; padding: 5px; height: var(--dock-h);
  border-radius: 22px; background: rgba(14,11,34,.9); border: 1px solid var(--line); backdrop-filter: blur(8px);
}
.dock button {
  position: relative; width: 78px; background: none; border: 0; border-radius: 17px;
  display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 2px; font-size: 11.5px; color: var(--muted);
}
.dock button > span:first-child { width: 30px; height: 30px; margin-top: -2px; transition: filter .25s, transform .25s; }
/* Not chosen: the icon rests, dim and nearly gray. Chosen: it lights up in its colors with a halo. */
.dock button:not(.active) > span:first-child { filter: saturate(.35) brightness(.75); }
.dock button.active > span:first-child { transform: scale(1.08); filter: drop-shadow(0 0 5px rgba(160,120,255,.7)); }
/* A hop and a glow: "the dust is over here", when someone taps the Universe for it */
.dock button.nudge { animation: nudge .9s ease-out; }
@keyframes nudge {
  0%, 100% { transform: none; box-shadow: none; }
  20% { transform: translateY(-9px) scale(1.08); box-shadow: 0 0 18px rgba(255,210,122,.8); color: var(--gold); }
  40% { transform: translateY(0) scale(1); }
  60% { transform: translateY(-4px); box-shadow: 0 0 12px rgba(255,210,122,.5); color: var(--gold); }
}
.dock button.active {
  color: #ffe2a0; background: linear-gradient(180deg, rgba(60,50,130,.55), rgba(30,24,80,.55));
  box-shadow: inset 0 1px 0 rgba(255,255,255,.08), inset 0 -2px 0 rgba(255,210,122,.55), 0 0 14px rgba(140,100,255,.25);
  text-shadow: 0 0 8px rgba(255,190,90,.45);
}
.dock .dot { position: absolute; top: 6px; right: 18px; width: 8px; height: 8px; border-radius: 50%; background: var(--gold); box-shadow: 0 0 6px var(--gold); display: none; }
.dock .dot.on { display: block; }

/* Bottom sheet with the panels */
.sheet {
  position: absolute; left: 0; right: 0; bottom: 0; z-index: 15; height: 64dvh;
  display: flex; flex-direction: column;
  background: rgba(14,11,34,.96); border: 1px solid var(--line); border-bottom: 0; border-radius: 24px 24px 0 0;
  backdrop-filter: blur(10px); box-shadow: 0 -10px 30px rgba(0,0,0,.5);
  transform: translateY(105%); transition: transform .28s cubic-bezier(.2,.8,.2,1);
}
.sheet.open { transform: translateY(var(--drag, 0px)); }
/* The Inventory: the sheet fills the screen under the counters, with its sections as tabs */
.sheet.full { height: auto; top: calc(var(--top) + 58px); }
.sheet.full .grab, .sheet.full #sheet-close, .sheet.full h2 { display: none; }
.sheet.full .sheet-head { padding-top: 10px; cursor: default; }
.subtabs { display: none; flex: 1; gap: 6px; }
.sheet.full .subtabs { display: flex; }
.subtabs button {
  position: relative; flex: 1; padding: 8px 6px; border-radius: 12px; font-size: 13px; font-weight: 700;
  color: var(--muted); background: var(--bg-2); border: 1px solid var(--line);
}
.subtabs button.active { color: var(--gold-dark); background: var(--gold); border-color: var(--gold); }
.subtabs .dot { position: absolute; top: 5px; right: 7px; width: 7px; height: 7px; border-radius: 50%; background: var(--gold); box-shadow: 0 0 6px var(--gold); display: none; }
.subtabs .dot.on { display: block; }
.sheet.dragging { transition: none; }
.sheet-head { position: relative; display: flex; align-items: center; padding: 16px 12px 6px 16px; touch-action: none; cursor: grab; }
.sheet-head .grab { position: absolute; top: 6px; left: 50%; width: 40px; height: 4px; margin-left: -20px; border-radius: 4px; background: var(--line); }
.sheet-head h2 { flex: 1; margin: 0; font-size: 17px; }
.sheet-head .x-btn { align-self: center; }
#app.sheet-open .quick, #app.sheet-open .focus-card, #app.sheet-open .tap-hint { display: none; }
/* Settings covers the game: nothing to go to or build peeks over it. */
#app.settings-open .dock, #app.settings-open #build-btn { display: none; }

/* Panel */
#panel { flex: 1; overflow-y: auto; padding: 4px 10px calc(var(--bottom) + var(--dock-h) + 16px); }
.tab-panel { display: flex; flex-direction: column; gap: 8px; }
.era { display: flex; flex-direction: column; gap: 8px; }
.era-head {
  display: flex; align-items: baseline; gap: 8px; margin: 6px 4px 0;
  font-size: 13px; letter-spacing: .06em; text-transform: uppercase; color: var(--era, var(--muted));
}
.era-head small { font-size: 12px; color: var(--muted); letter-spacing: 0; text-transform: none; }
.era-head[data-info] { cursor: help; }

.buybar { display: flex; gap: 6px; justify-content: flex-end; }
.buybar button { background: var(--card); border: 1px solid var(--line); border-radius: 99px; padding: 4px 12px; font-size: 13px; color: var(--muted); }
.buybar button.active { color: var(--gold-dark); background: var(--gold); border-color: var(--gold); font-weight: 700; }

/* Rows */
.row {
  display: flex; gap: 10px; align-items: center;
  background: var(--card); border: 1px solid var(--line); border-radius: var(--radius); padding: 8px 8px 8px 8px;
}
.row.pop { animation: bump .25s ease-out; }
@keyframes bump { 40% { transform: scale(1.025); border-color: var(--gold); } }
.ico {
  width: 52px; height: 52px; flex-shrink: 0; padding: 4px; border: 0; border-radius: 14px;
  background: var(--bg-2);
}
.mid { flex: 1; min-width: 0; }
.top { display: flex; align-items: baseline; gap: 6px; }
.name { font-weight: 700; font-size: 15px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.badge { color: var(--gold); font-weight: 800; font-size: 14px; font-variant-numeric: tabular-nums; white-space: nowrap; flex-shrink: 0; }
.top .pause {
  margin-left: auto; flex-shrink: 0; width: 26px; height: 22px; border-radius: 8px; font-size: 11px; line-height: 1;
  background: var(--bg-2); color: var(--muted); border: 1px solid var(--line);
}
.top .pause.on { color: var(--pink); border-color: var(--pink); }
.sub .a.short { color: var(--pink); }
.fac-intro { margin: 2px 4px 4px; font-size: 13px; color: var(--muted); line-height: 1.4; }
.bar { height: 5px; border-radius: 5px; background: var(--bg-2); margin: 5px 0 4px; overflow: hidden; }
.bar i { display: block; height: 100%; width: 0; background: linear-gradient(90deg, #ffb347, var(--gold)); border-radius: 5px; transition: width .2s; }
.sub { display: flex; justify-content: space-between; gap: 8px; font-size: 12px; color: var(--muted); font-variant-numeric: tabular-nums; }
.sub .a { color: #9ad7ff; }
.sub .b.short { color: var(--pink); }
.nobar .bar { display: none; }
.nobar .sub { margin-top: 3px; }

.buy {
  flex-shrink: 0; width: 92px; min-height: 52px; border: 0; border-radius: 14px; padding: 6px;
  /* Gold with a little depth: lighter on top, a bright rim of light, a soft glow under it. */
  background: linear-gradient(180deg, #ffe3a3 0%, #ffd27a 45%, #f2b955 100%); color: var(--gold-dark);
  display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 1px;
  box-shadow: inset 0 1px 0 rgba(255,255,255,.65), 0 3px 0 #c9962f, 0 6px 16px rgba(255,190,90,.22);
  transition: transform .05s;
}
.buy:active:not(:disabled) { transform: translateY(2px); box-shadow: inset 0 1px 0 rgba(255,255,255,.5), 0 1px 0 #c9962f, 0 2px 8px rgba(255,190,90,.2); }
.buy .cost { display: flex; align-items: center; gap: 4px; font-weight: 800; font-size: 15px; font-variant-numeric: tabular-nums; }
.buy .cur { width: 18px; height: 18px; }
.buy .qty { font-size: 11px; font-weight: 700; opacity: .7; }
.buy:disabled { background: linear-gradient(180deg, #252a58, #1c2048); color: var(--muted); box-shadow: inset 0 1px 0 rgba(255,255,255,.08), 0 3px 0 #141838; cursor: default; }
.buy:disabled .cur { opacity: .5; }
/* On a gold button the gold star would vanish: draw it dark with a gold heart. */
.buy:not(:disabled):not(.violet, .green, .danger) .cur path { fill: var(--gold-dark); }
.buy:not(:disabled):not(.violet, .green, .danger) .cur circle { fill: var(--gold); }
.buy.violet { background: var(--violet); color: var(--violet-dark); box-shadow: 0 3px 0 #7f77d6; }
.buy.green { background: var(--cyan); color: var(--cyan-dark); box-shadow: 0 3px 0 #2fa891; }
.buy.violet:disabled, .buy.green:disabled { background: var(--card-2); color: var(--muted); box-shadow: 0 3px 0 #141838; }

.row.locked { background: transparent; border-style: dashed; }
.row.locked .name, .row.locked .ico { opacity: .6; }
.row.locked .sub .a { color: var(--muted); }
.row.soon { opacity: .45; }

.foot { margin-top: 10px; display: flex; flex-direction: column; gap: 10px; }
.settings-note { margin: 0 4px; font-size: 12.5px; color: var(--muted); line-height: 1.5; }
.stats { font-size: 13px; color: var(--muted); display: grid; grid-template-columns: 1fr auto; gap: 4px 12px; padding: 0 4px; }
.stats b { color: var(--text); text-align: right; }
.links { display: flex; gap: 8px; justify-content: space-between; align-items: center; font-size: 13px; }
.links button, .links a { background: none; border: 1px solid var(--line); border-radius: 99px; padding: 6px 12px; color: var(--muted); text-decoration: none; }
.links .danger { color: var(--pink); border-color: rgba(255,122,168,.35); }

/* Toast pill and tooltip bubble */
.toast {
  position: fixed; left: 50%; bottom: calc(max(10px, env(safe-area-inset-bottom)) + 62px + 78px); z-index: 40;
  transform: translateX(-50%); width: max-content; max-width: min(400px, calc(100vw - 32px));
  padding: 8px 14px; border-radius: 99px; text-align: center;
  font-size: 13px; font-weight: 600; line-height: 1.35; color: var(--text);
  background: rgba(14,11,34,.92); border: 1px solid rgba(255,210,122,.35); box-shadow: 0 6px 20px rgba(0,0,0,.45);
  pointer-events: none;
}
.toast.in { animation: toast-in .22s ease-out; }
@keyframes toast-in { from { transform: translate(-50%, 8px); opacity: 0; } }
.bubble {
  position: absolute; z-index: 30; padding: 10px 12px; border-radius: 14px;
  font-size: 13px; line-height: 1.45; color: var(--text);
  background: #20264f; border: 1px solid var(--line); box-shadow: 0 8px 24px rgba(0,0,0,.5);
  animation: card-in .18s ease-out;
}

/* Force cards */
.card-wrap {
  position: absolute; inset: 0; z-index: 35; display: grid; place-items: center; padding: 16px;
  background: rgba(5,3,14,.72); backdrop-filter: blur(3px); animation: fade-in .2s ease-out;
}
@keyframes fade-in { from { opacity: 0; } }
.card-box {
  position: relative; width: min(380px, 100%); max-height: calc(100dvh - 32px); overflow-y: auto;
  border-radius: 22px; background: var(--bg-2); border: 1px solid var(--line); box-shadow: 0 16px 40px rgba(0,0,0,.6);
  animation: card-pop .25s cubic-bezier(.2,.9,.3,1.2);
}
.card-box.pop { animation: bump .3s ease-out; }
@keyframes card-pop { from { transform: scale(.92); opacity: 0; } }
#card-canvas { display: block; width: 100%; height: 190px; background: radial-gradient(circle at 50% 50%, #161a3a, #07040f 70%); border-radius: 22px 22px 0 0; }
/* Cards redrawn in WebGL play on this one, laid over the 2D canvas. */
#card-gl { position: absolute; top: 0; left: 0; width: 100%; height: 190px; border-radius: 22px 22px 0 0; pointer-events: none; }
#card-gl[hidden] { display: none; }
.card-x { position: absolute; top: 8px; right: 8px; width: 34px; height: 34px; border-radius: 50%; background: rgba(7,4,15,.6); }
.card-info { padding: 14px 16px 16px; display: flex; flex-direction: column; gap: 10px; }
.card-head { display: flex; gap: 10px; align-items: center; }
/* Popped up by itself because it was just unlocked */
.card-info { position: relative; }
.card-new {
  position: absolute; top: -12px; left: 14px; padding: 3px 10px; border-radius: 99px; font-size: 11px; font-weight: 800;
  letter-spacing: .04em; text-transform: uppercase; color: #1a1030; background: var(--gold); box-shadow: 0 0 14px rgba(255,210,122,.7);
  animation: pulse 1.2s ease-in-out infinite;
}
.card-wrap.unlocked .card-box { animation: card-in .35s ease-out, bump .5s ease-out .35s; }
.card-icon { width: 44px; height: 44px; flex-shrink: 0; padding: 4px; border-radius: 12px; background: var(--card); }
.card-head h2 { margin: 0; font-size: 18px; }
.card-what { margin: 0; font-size: 14px; line-height: 1.5; color: var(--text); }
.card-what:empty { display: none; }
.card-fact { margin: 0; font-size: 12.5px; line-height: 1.45; color: var(--muted); padding-left: 10px; border-left: 2px solid var(--violet); }
.card-gain {
  display: flex; align-items: baseline; justify-content: space-between; gap: 10px; padding: 8px 12px; border-radius: 14px;
  background: var(--card); border: 1px solid var(--line);
}
.card-gain span { font-size: 11.5px; color: var(--muted); text-transform: uppercase; letter-spacing: .05em; }
.card-gain b { font-size: 16px; color: var(--gold); font-variant-numeric: tabular-nums; }
.card-buy { width: 100%; min-height: 52px; flex-direction: row; gap: 10px; }
.card-buy .qty { font-size: 13px; }
.row[data-card] { cursor: pointer; }

/* Narration: one line of the story at a time. Tapping it moves on. */
.story {
  position: absolute; left: 50%; top: calc(var(--top) + 150px); z-index: 7;
  width: max-content; max-width: min(340px, calc(100% - 32px)); transform: translateX(-50%);
  padding: 10px 18px 11px; border-radius: 16px; text-align: center;
  font-family: var(--serif); font-style: italic; font-weight: 500; font-size: 20px; line-height: 1.35; color: #f6efe0;
  background: radial-gradient(ellipse at center, rgba(7,4,15,.78), rgba(7,4,15,.5) 70%, rgba(7,4,15,0));
  text-shadow: 0 0 18px rgba(255,210,122,.25), 0 1px 3px #000;
  animation: story var(--ms, 4s) ease-in-out forwards;
}
.story .w { display: inline-block; white-space: pre; animation: word .7s ease-out backwards; }
@keyframes word { from { opacity: 0; filter: blur(6px); transform: translateY(4px); } }
/* The opening lines: big, warm white, a soft halo of light. Each word lights up as it arrives (a brief
   flash that settles), and the key word glows gold, the same gold as the chapter title. Only opacity,
   transform and filter are animated, so it stays smooth on phones. */
.story.intro {
  top: 34%; font-size: min(30px, 7.6vw); line-height: 1.28; max-width: min(340px, calc(100% - 36px)); background: none;
  color: #fff8ec; letter-spacing: .01em;
  text-shadow: 0 0 2px rgba(255,248,236,.35), 0 0 16px rgba(190,170,255,.35), 0 1px 2px #000;
}
.story.intro .w { animation: ignite 1.3s cubic-bezier(.2,.7,.2,1) backwards; }
.story .w.em {
  color: #ffe2a0;
  text-shadow: 0 0 3px rgba(255,214,130,.8), 0 0 14px rgba(255,176,60,.55), 0 0 34px rgba(255,140,30,.3);
}
@keyframes ignite {
  0% { opacity: 0; filter: blur(8px) brightness(2.2); transform: translateY(6px) scale(.98); }
  45% { opacity: 1; filter: blur(0) brightness(1.6); }
  100% { opacity: 1; filter: none; transform: none; }
}
.story.tip { font-size: 18px; }
/* A chapter title: gold neon. The glow is a drop-shadow on the title, and one sweep of light runs
   across its letters once, after it has settled. */
.story.chapter {
  display: flex; flex-direction: column; align-items: center; gap: 8px; padding: 14px 26px; background: none;
  font-family: var(--display); font-style: normal; color: var(--gold); text-shadow: none;
}
.story.chapter small {
  font-size: 11.5px; letter-spacing: .5em; margin-right: -.5em; text-transform: uppercase; color: #c9c3ff;
  text-shadow: 0 0 10px rgba(170,150,255,.6); animation: chapter-sub 1.6s ease-out backwards;
}
.story.chapter b {
  font-size: min(28px, 7vw); font-weight: 600; letter-spacing: .08em; white-space: nowrap;
  color: transparent; -webkit-background-clip: text; background-clip: text;
  background-image: linear-gradient(100deg, #ffd27a 0%, #ffd27a 40%, #fffaf0 50%, #ffd27a 60%, #ffd27a 100%);
  background-size: 300% 100%; background-position: 100% 0;
  filter: blur(0) drop-shadow(0 0 2px rgba(255,214,130,.9)) drop-shadow(0 0 14px rgba(255,165,50,.55));
  animation: chapter 1.4s ease-out backwards, shine 1.5s ease-in-out 1.3s backwards;
}
.story.chapter::before, .story.chapter::after {
  content: ''; width: 170px; height: 1px;
  background: linear-gradient(90deg, transparent, rgba(255,210,122,.9), transparent);
  box-shadow: 0 0 8px rgba(255,190,90,.6);
  animation: line 1.2s ease-out backwards;
}
@keyframes chapter-sub { from { opacity: 0; letter-spacing: .5em; filter: blur(4px); } }
@keyframes shine { from { background-position: 100% 0; } to { background-position: 0% 0; } }
@media (prefers-reduced-motion: reduce) {
  .story .w, .story.chapter b, .story.chapter small, .story.chapter::before, .story.chapter::after { animation: none !important; }
}
/* Only opacity, blur and scale: animating the spacing would reflow the title mid-entrance. */
@keyframes chapter { from { opacity: 0; transform: scale(1.12); filter: blur(5px) drop-shadow(0 0 2px rgba(255,214,130,0)) drop-shadow(0 0 14px rgba(255,165,50,0)); } }
@keyframes line { from { transform: scaleX(0); opacity: 0; } }
@keyframes story { 0% { opacity: 0; } 6%, 92% { opacity: 1; } 100% { opacity: 0; } }


/* Stardust flying from a tap to the counter */
.mote {
  position: absolute; z-index: 6; width: 8px; height: 8px; border-radius: 50%; pointer-events: none;
  background: #fff6dc; box-shadow: 0 0 10px 3px rgba(255,210,122,.8);
}
.hud .res { border-radius: 14px; }
.hud .res.bump .res-icon { animation: dust-in .3s ease-out; }
@keyframes dust-in { 40% { transform: scale(1.3); filter: drop-shadow(0 0 8px var(--gold)); } }
.hud .res.glow { animation: dust-glow 1.3s ease-in-out infinite !important; box-shadow: none !important; }
@keyframes dust-glow { 50% { filter: drop-shadow(0 0 10px rgba(255,210,122,.9)); } }

/* Something the current goal wants you to touch */
.glow { animation: point 1.3s ease-in-out infinite !important; }
/* An even, soft halo that follows the rounded corners: no solid ring and no offset, and both ends of the
   breath are spelled out so it never blends from the element's own (offset) shadow. */
@keyframes point {
  0%, 100% { box-shadow: 0 0 8px rgba(255,210,122,.25), inset 0 0 10px rgba(255,210,122,.1); border-color: rgba(255,210,122,.6); }
  50% { box-shadow: 0 0 22px rgba(255,210,122,.6), inset 0 0 18px rgba(255,210,122,.25); border-color: var(--gold); }
}
.tray-item.glow { background: radial-gradient(circle at 50% 50%, #816b3833, #101527 75%); }
/* Under a count goal: what reaching it opens, with a lock and its icon. */
/* The milestone bar: slim, gold filling a faint track, easing as it grows; a small ⓘ beside it tells
   the milestone in a few words. */
.hint-row { display: flex; align-items: center; justify-content: center; gap: 8px; margin-top: 6px; }
.hint-left { flex-shrink: 0; font-size: 12.5px; font-weight: 700; color: var(--gold); }
.hint-left:empty { display: none; }
.hint-info { pointer-events: auto; width: 20px; height: 20px; flex-shrink: 0; border-radius: 50%; padding: 0;
  font: italic 700 12px/18px Georgia, serif; color: var(--gold); background: rgba(14,11,34,.7); border: 1px solid rgba(255,210,122,.45); }
.hint-bar { display: block; width: min(220px, 70%); height: 5px; margin: 0; border-radius: 99px; overflow: hidden;
  background: rgba(255,255,255,.1); box-shadow: inset 0 0 0 1px rgba(255,210,122,.15); }
.hint-bar i { display: block; height: 100%; width: 0; border-radius: inherit; background: linear-gradient(90deg, #ffb347, var(--gold));
  box-shadow: 0 0 8px rgba(255,210,122,.6); transition: width .6s cubic-bezier(.2,.8,.2,1); }
.hint-unlock { display: flex; align-items: center; justify-content: center; gap: 6px; margin-top: 4px; font-size: 12.5px; font-weight: 700; color: var(--gold); }
.hint-unlock > svg { width: 14px; height: 14px; }
.hint-unlock i { width: 20px; height: 20px; display: inline-block; }
.hint-unlock i svg { width: 100%; height: 100%; display: block; }
 /* The coach: a bubble of light, not a box. A soft glass pill (no point, no dark fill) next to what the guide
   wants touched; a short trail of gold dots, brightest at the pill and fading out, leads the eye to it. */
.coach {
  position: absolute; z-index: 25; max-width: min(260px, calc(100% - 20px)); padding: 10px 18px; border-radius: 999px;
  pointer-events: none; font-size: 13.5px; font-weight: 600; line-height: 1.35; color: #fff4dc; text-align: center;
  text-shadow: 0 1px 6px rgba(7,4,15,.6);
  background: rgba(40,30,85,.72); -webkit-backdrop-filter: blur(8px); backdrop-filter: blur(8px);
  border: 1px solid rgba(255,210,122,.28);
  box-shadow: 0 0 24px rgba(185,179,255,.18), 0 4px 16px rgba(7,4,15,.35);
  animation: coach-bob 2.2s ease-in-out infinite;
}
.coach::after {
  content: ''; position: absolute; left: var(--arrow, 50%); top: 100%; width: 8px; height: 26px; margin: 5px 0 0 -4px;
  background:
    radial-gradient(circle, rgba(255,210,122,.95) 2.5px, transparent 3px) 50% 0 / 8px 8px no-repeat,
    radial-gradient(circle, rgba(255,210,122,.6) 2px, transparent 2.5px) 50% 9px / 8px 8px no-repeat,
    radial-gradient(circle, rgba(255,210,122,.32) 1.5px, transparent 2px) 50% 18px / 8px 8px no-repeat;
  filter: drop-shadow(0 0 3px rgba(255,210,122,.7));
}
.coach.below::after { top: auto; bottom: 100%; margin: 0 0 5px -4px; transform: scaleY(-1); }
.coach[hidden] { display: none; }
@keyframes coach-bob { 50% { transform: translateY(-2px); } }
.coach.below { animation-name: coach-bob-down; }
@keyframes coach-bob-down { 50% { transform: translateY(2px); } }
@media (prefers-reduced-motion: reduce) { .coach { animation: none; } }
.tap-hint.coached { visibility: hidden; }
.tap-hint.glow { box-shadow: none !important; animation: pulse 1.3s ease-in-out infinite !important; color: var(--gold); }
.dock button.new::after {
  content: ''; position: absolute; inset: 2px; border-radius: 15px; border: 1.5px solid var(--gold); animation: pulse 1.2s ease-in-out infinite;
}
#app.no-dock { --dock-h: 0px; }

.modal-wrap { position: fixed; inset: 0; z-index: 40; background: rgba(5,3,14,.78); display: grid; place-items: center; padding: 16px; }
.modal { width: min(380px, 100%); background: var(--card); border: 1px solid var(--line); border-radius: 20px; padding: 20px; }
.modal h2 { margin: 0 0 8px; font-size: 20px; color: var(--gold); }
.modal p { margin: 0 0 16px; color: var(--muted); line-height: 1.5; }
.modal-actions { display: flex; gap: 8px; justify-content: flex-end; flex-wrap: wrap; }
.btn { border: 0; border-radius: 12px; padding: 10px 16px; font-weight: 700; background: var(--gold); color: var(--gold-dark); }
.btn.ghost { background: transparent; color: var(--muted); border: 1px solid var(--line); }
.btn.violet { background: var(--violet); color: var(--violet-dark); }
.btn.danger { background: transparent; color: var(--pink); border: 1px solid rgba(255,122,168,.4); }

.buy.danger { background: transparent; color: var(--pink); border: 1px solid rgba(255,122,168,.45); box-shadow: none; }
.quick.pop { animation: bump .25s ease-out; }
/* Story lines stay readable over the Inventory list */
#app[data-screen="inventory"] .story { z-index: 16; pointer-events: none; }

/* What was just made, flying from the mini card into the Universe */
.seed {
  position: absolute; z-index: 30; width: 14px; height: 14px; border-radius: 50%; pointer-events: none;
  background: radial-gradient(circle, #fff 0 20%, rgba(var(--rgb), 1) 45%, rgba(var(--rgb), 0) 72%);
  box-shadow: 0 0 18px rgba(var(--rgb), .9);
}

/* The fingertip that shows how to swipe the mini card */
.swipe-finger {
  position: absolute; left: 0; top: 50%; width: 34px; height: 34px; margin-top: -17px; border-radius: 50%;
  pointer-events: none; opacity: 0; z-index: 2;
  background: radial-gradient(circle, rgba(255,255,255,.95) 0 30%, rgba(255,255,255,.35) 55%, rgba(255,255,255,0) 72%);
  box-shadow: 0 0 16px rgba(255,255,255,.5);
}

/* A recipe in a card: ingredient pieces, an arrow and what it makes, and how many can be made */
.card-recipe { display: flex; flex-direction: column; align-items: center; gap: 6px; padding: 10px 8px; border-radius: 14px; background: var(--card); border: 1px solid var(--line); }
.ings { display: flex; align-items: center; justify-content: center; gap: 6px; flex-wrap: wrap; }
.ing { position: relative; display: flex; flex-direction: column; align-items: center; min-width: 44px; padding: 4px 4px 3px; border-radius: 12px; background: var(--bg-2); border: 1px solid var(--line); }
.ing i { width: 30px; height: 30px; display: block; }
.ing i svg { width: 100%; height: 100%; display: block; }
.ing b { position: absolute; top: -7px; right: -6px; padding: 1px 5px; border-radius: 99px; font-size: 11px; background: var(--gold); color: #1a1030; font-variant-numeric: tabular-nums; }
.ing b:empty { display: none; }
.ing small { font-size: 11px; font-weight: 700; font-variant-numeric: tabular-nums; }
.ing.ok small { color: #5bf08d; }
.ing.short { border-color: rgba(255,122,168,.6); }
.ing.short small { color: var(--pink); }
.ing.out { border-color: rgba(255,210,122,.6); box-shadow: 0 0 12px rgba(255,210,122,.25); }
.ings .plus, .ings .arrow { color: var(--muted); font-weight: 800; font-size: 16px; }
.ings .arrow { color: var(--gold); font-size: 18px; }
.card-recipe em { font-style: normal; font-size: 12px; font-weight: 700; padding: 2px 10px; border-radius: 99px; color: var(--muted); background: var(--bg-2); }
.card-recipe em.ok { color: #5bf08d; }
.card-recipe em.short { color: var(--pink); }

/* Energy in the Factories section: what comes in, what the factories use */
.energy { padding: 10px 12px; border-radius: 14px; background: var(--card); border: 1px solid var(--line); display: flex; flex-direction: column; gap: 6px; }
.en-top { display: flex; justify-content: space-between; align-items: baseline; gap: 8px; font-size: 13px; }
.en-top b { color: var(--gold); }
.en-line { font-size: 12px; color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.en-bar { height: 6px; border-radius: 6px; background: var(--bg-2); overflow: hidden; }
.en-bar i { display: block; height: 100%; width: 0; background: linear-gradient(90deg, #5ce1c6, var(--gold), var(--pink)); transition: width .3s; }
.en-warn { color: var(--pink); font-size: 12px; line-height: 1.35; }
.top .pause { width: auto; min-width: 40px; padding: 0 6px; font-weight: 800; }
/* A factory's production setting in its card */
/* Label and value on top, the slider full width underneath, so it fits on any phone */
.card-throttle { display: flex; flex-wrap: wrap; align-items: baseline; justify-content: space-between; gap: 4px 10px; padding: 8px 12px; border-radius: 14px; background: var(--card); border: 1px solid var(--line); font-size: 12px; color: var(--muted); }
.card-throttle input { order: 3; flex: 1 0 100%; margin: 4px 0 0; accent-color: var(--gold); }
.card-throttle b { color: var(--gold); font-variant-numeric: tabular-nums; white-space: nowrap; }

/* How-to-play cards: just the animation, a line and a button that moves on through the deck */
.card-wrap.how :is(#card-level, .card-gain, .card-recipe, .card-throttle, .card-buy .cost) { display: none !important; }
.card-wrap.how .card-buy .qty { font-size: 20px; }
.card-box.from-left { animation: from-left .22s ease-out; }
.card-box.from-right { animation: from-right .22s ease-out; }
.card-dots { display: flex; justify-content: center; gap: 6px; }
.card-dots:empty { display: none; }
.card-dots i { width: 6px; height: 6px; border-radius: 50%; background: rgba(255,255,255,.22); }
.card-dots i.on { background: var(--gold); }
.deck-btn {
  display: flex; align-items: center; gap: 8px; width: 100%; margin: 0 0 12px; padding: 8px 12px; border-radius: 14px;
  background: var(--card); border: 1px solid var(--line); color: var(--gold); font-weight: 700; font-size: 14px;
}
.deck-btn[hidden] { display: none; }
.deck-btn span:first-child { width: 26px; height: 26px; }
/* The catalog of cards, in the modal: a grid per kind, locked tiles for what's still to come. */
#modal-body.catalog { max-height: 62vh; overflow-y: auto; margin-right: -6px; padding-right: 6px; }
.cat-group h3 { margin: 12px 0 8px; font-size: 13px; color: var(--gold); letter-spacing: .04em; }
.cat-group h3 small { color: var(--muted); font-weight: 600; margin-left: 4px; }
.cat-group:first-child h3 { margin-top: 0; }
.cat-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(72px, 1fr)); gap: 8px; }
.cat-tile { display: flex; flex-direction: column; align-items: center; gap: 4px; padding: 8px 4px; border-radius: 14px;
  background: radial-gradient(circle at 50% 35%, #a489ef1c, #10172b 75%); border: 1px solid #b7a2ee40; color: var(--text); }
.cat-tile > span { width: 34px; height: 34px; }
.cat-tile > span svg { width: 100%; height: 100%; display: block; }
.cat-tile small { font-size: 10.5px; line-height: 1.2; text-align: center; color: #d8d4f4; overflow-wrap: anywhere; }
.cat-tile.locked { opacity: .35; justify-content: center; min-height: 64px; border-style: dashed; }
.cat-tile.locked > span { width: 22px; height: 22px; }

/* The board's build mode: a hammer to start, a tray of what can be built in this scale */
.build-btn {
  position: absolute; right: 12px; bottom: calc(var(--bottom) + var(--dock-h) + 84px); z-index: 7;
  width: 52px; height: 52px; padding: 9px; border-radius: 16px;
  background: rgba(14,11,34,.88); border: 1px solid var(--gold); box-shadow: 0 0 16px rgba(255,210,122,.25);
}
.build-btn[hidden], .tray[hidden], .flow-bar[hidden] { display: none; }
#app:not([data-screen="space"]) :is(.build-btn, .tray, .flow-bar) { display: none !important; }
#app.building :is(.quick, .quick-open, .focus-card, .tap-hint) { display: none !important; }
.tray {
  position: absolute; left: 10px; right: 10px; bottom: calc(var(--bottom) + var(--dock-h) + 10px); z-index: 7;
  display: flex; align-items: center; gap: 6px; padding: 6px; border-radius: 18px;
  background: rgba(14,11,34,.9); border: 1px solid var(--gold); backdrop-filter: blur(8px); animation: card-in .25s ease-out;
}
.tray-list { flex: 1; display: flex; gap: 6px; overflow-x: auto; scrollbar-width: none; }
.tray-item {
  position: relative; flex-shrink: 0; width: 64px; padding: 6px 4px 4px; border-radius: 14px;
  display: flex; flex-direction: column; align-items: center; gap: 2px;
  background: var(--card); border: 1px solid var(--line);
}
.tray-item.on { border-color: var(--gold); box-shadow: 0 0 12px rgba(255,210,122,.45); background: var(--card-2); }
.tray-item[data-poor] { opacity: .5; }
.tray-item.pop { animation: bump .25s ease-out; }
.ti-ico { width: 32px; height: 32px; }
.ti-n { position: absolute; top: 3px; right: 5px; font-size: 11px; font-weight: 800; color: var(--muted); }
.ti-cost { display: flex; align-items: center; gap: 2px; font-size: 11px; font-weight: 700; color: var(--gold); }
.ti-cost svg { width: 11px; height: 11px; }
.tray-empty { width: 40px; height: 40px; opacity: .5; }
.tray-grp { flex-shrink: 0; display: flex; flex-direction: column; gap: 3px; }
.tray-grp + .tray-grp { padding-left: 6px; border-left: 1px solid var(--line); }
.tg-label { padding-left: 2px; font-size: 9px; font-weight: 800; letter-spacing: .08em; text-transform: uppercase; color: var(--muted); }
.tg-power .tg-label { color: rgb(120,230,255); }
.tg-items { display: flex; gap: 6px; }
.tray-name {
  position: absolute; bottom: calc(100% + 6px); left: 0; transform: translate(-50%, 4px); z-index: 2;
  max-width: 220px; padding: 5px 10px; border-radius: 10px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  font-size: 13px; font-weight: 700; color: var(--gold); background: rgba(14,11,34,.95); border: 1px solid var(--gold);
  pointer-events: none; opacity: 0; transition: opacity .2s, transform .2s;
}
.tray-name.show { opacity: 1; transform: translate(-50%, 0); }

/* What the scale on screen makes and takes per minute */
.flow-bar {
  position: absolute; left: 8px; right: 8px; top: calc(var(--top) + 134px); z-index: 5; pointer-events: none;
  display: flex; flex-wrap: wrap; justify-content: center; gap: 4px;
}
.flow-bar .fl, .flow-bar .fl-unit {
  display: flex; align-items: center; gap: 3px; padding: 2px 7px 2px 3px; border-radius: 99px;
  background: rgba(14,11,34,.78); border: 1px solid var(--line); font-size: 11.5px; font-variant-numeric: tabular-nums;
}
.flow-bar .fl-unit { padding: 2px 7px; color: var(--muted); font-size: 10.5px; }
.flow-bar .fl i { width: 18px; height: 18px; }
.flow-bar .fl b.up { color: #9bf0b0; }
.flow-bar .fl b.down { color: var(--pink, #ff7aa8); }
.flow-bar .fl small { color: var(--muted); font-size: 10.5px; }
.flow-bar .fl.en { padding-left: 7px; }
.flow-bar .fl.en.up { color: #9bf0b0; }
.flow-bar .fl.en.down { color: var(--gold); }
.card-move { margin-left: auto; width: 38px; height: 38px; border-radius: 12px; background: var(--card); border: 1px solid var(--line); font-size: 18px; color: var(--gold); }
.card-move[hidden] { display: none; }

/* A card that just popped up: locked for a moment, its button filling up until it can be pressed */
.card-wrap.locked .card-x { opacity: 0; pointer-events: none; }
/* While it waits, the button is dark and fills with gold from the left like a charge, a bright edge
   leading the way. Only a transform animates. When it can be pressed, a sweep of light runs across it
   once. */
.card-buy { position: relative; overflow: hidden; isolation: isolate; }
.card-buy > * { position: relative; z-index: 1; }
.card-wrap.locked .card-buy { pointer-events: none; background: #1a1d40; color: #fff6e0; text-shadow: 0 1px 3px rgba(30,15,0,.55); box-shadow: 0 3px 0 #10132e, inset 0 0 0 1px rgba(255,210,122,.25); }
.card-wrap.locked .card-buy::before {
  content: ''; position: absolute; inset: 0; z-index: 0;
  background: linear-gradient(90deg, rgba(201,150,47,.55), rgba(255,210,122,.9) calc(100% - 16px), #fff6dc calc(100% - 3px), rgba(255,246,220,0));
  box-shadow: 8px 0 18px rgba(255,200,100,.45);
  transform: translateX(-100%); animation: lock-fill var(--lock, 3s) cubic-bezier(.4,.1,.6,1) forwards;
}
@keyframes lock-fill { to { transform: translateX(0); } }
.card-wrap.ready .card-buy::after {
  content: ''; position: absolute; inset: 0; z-index: 2; pointer-events: none;
  background: linear-gradient(105deg, transparent 35%, rgba(255,255,255,.75) 50%, transparent 65%);
  transform: translateX(-100%); animation: ready-shine .7s ease-out forwards;
}
.card-wrap.ready .card-buy { animation: ready-pop .45s ease-out; }
@keyframes ready-shine { to { transform: translateX(100%); } }
@keyframes ready-pop { 40% { transform: scale(1.03); box-shadow: 0 3px 0 #c9962f, 0 0 22px rgba(255,210,122,.6); } }
@media (prefers-reduced-motion: reduce) { .card-wrap.locked .card-buy::before { animation-timing-function: steps(3); } .card-wrap.ready .card-buy, .card-wrap.ready .card-buy::after { animation: none; } }
.card-x { transition: opacity .3s; }

/* A popped-up deck with cards still to see: no way out yet, the button only moves on */
.card-wrap.unfinished .card-x { opacity: 0; pointer-events: none; }
.card-buy.next .cost { display: none; }
.card-buy.next .qty { font-size: 20px; }
.card-dots i.seen { background: rgba(255,210,122,.45); }

/* Cards that only tell: the button just says got it */
.card-buy.info .cost { display: none; }
.card-buy.info .qty { font-size: 20px; }

/* The Void's cuts: bigger numbers for big and golden pairs, a popping count for combos */
.float.big { font-size: 21px; }
.float.gold { font-size: 26px; color: #fff3c4; text-shadow: 0 0 2px rgba(30,10,0,.95), 0 1px 3px #000, 0 0 14px rgba(255,190,90,.9); }
/* A combo count: gold neon letters (white-hot in the middle), bigger and warmer with each one. */
.float.combo {
  font-family: var(--display); font-weight: 600; color: transparent; -webkit-background-clip: text; background-clip: text;
  background-image: linear-gradient(180deg, #fffaf0 15%, #ffe2a0 50%, #ffb347 100%); text-shadow: none;
  filter: drop-shadow(0 0 1.5px rgba(30,10,0,1)) drop-shadow(0 1px 3px rgba(0,0,0,.85)) drop-shadow(0 0 12px rgba(255,160,40,.6));
  animation: combo-pop .8s cubic-bezier(.2,1.4,.4,1) forwards;
}
.float.combo.c2 { font-size: 24px; }
.float.combo.c3 { font-size: 32px; }
.float.combo.c4 { font-size: 40px; }
.float.combo.c5 { font-size: 48px; background-image: linear-gradient(180deg, #fffaf0 10%, #ffd06a 45%, #ff7a2a 100%); filter: drop-shadow(0 0 1.5px rgba(30,10,0,1)) drop-shadow(0 1px 3px rgba(0,0,0,.85)) drop-shadow(0 0 18px rgba(255,120,30,.7)); }
@keyframes combo-pop {
  0% { transform: scale(.3) rotate(-8deg); opacity: 0; }
  25% { transform: scale(1.25) rotate(3deg); opacity: 1; }
  45% { transform: scale(1) rotate(0); }
  100% { transform: translateY(-36px) scale(1); opacity: 0; }
}
/* The streak: how much it multiplies, by the counter */
/* The streak multiplier: a small glass badge with the number in gold neon. Past ten in a row it runs
   hot: warmer, brighter, and a slow sheen crosses it. */
.streak {
  position: absolute; left: 50%; top: calc(var(--top) + 124px); transform: translateX(-50%); z-index: 6; pointer-events: none;
  display: flex; align-items: center; gap: 5px; padding: 4px 13px 4px 8px; border-radius: 99px; overflow: hidden;
  background: rgba(12,9,30,.55); border: 1px solid rgba(255,210,122,.45); backdrop-filter: blur(6px);
  box-shadow: inset 0 1px 0 rgba(255,255,255,.08), 0 0 16px rgba(255,190,90,.25); animation: card-in .2s ease-out;
}
.streak[hidden] { display: none; }
/* A rare pair's effect while it lasts, with its seconds left (under the streak). */
.rare-chip {
  position: absolute; left: 50%; top: calc(var(--top) + 158px); transform: translateX(-50%); z-index: 6; pointer-events: none;
  padding: 4px 12px; border-radius: 99px; font-size: 12.5px; font-weight: 700; color: #e6f8ff; white-space: nowrap;
  background: rgba(12,9,30,.55); border: 1px solid rgba(160,230,255,.5); backdrop-filter: blur(6px);
  box-shadow: 0 0 16px rgba(120,200,255,.3); font-variant-numeric: tabular-nums;
}
.rare-chip[hidden] { display: none; }
.rare-chip[data-kind="resonant"] { color: #dcfbff; border-color: rgba(0,235,255,.55); box-shadow: 0 0 16px rgba(0,220,255,.35); }
.rare-chip[data-kind="tide"] { color: #f0e2ff; border-color: rgba(205,120,255,.6); box-shadow: 0 0 16px rgba(180,110,255,.4); }
.rare-chip[data-kind="flare"] { color: #fff3d6; border-color: rgba(255,214,140,.7); box-shadow: 0 0 18px rgba(255,210,130,.45); }
.streak span { width: 16px; height: 16px; filter: drop-shadow(0 0 4px rgba(255,200,110,.8)); }
.streak b {
  font-family: var(--display); font-weight: 600; font-size: 16px; letter-spacing: .03em; font-variant-numeric: tabular-nums;
  color: #ffe2a0; text-shadow: 0 0 3px rgba(255,214,130,.8), 0 0 12px rgba(255,160,40,.5);
}
.streak.hot { border-color: rgba(255,170,70,.9); box-shadow: inset 0 1px 0 rgba(255,255,255,.1), 0 0 24px rgba(255,150,50,.55); }
.streak.hot b { color: #fff3d6; text-shadow: 0 0 4px rgba(255,220,150,1), 0 0 16px rgba(255,130,30,.8); }
.streak.hot::after {
  content: ''; position: absolute; inset: 0; pointer-events: none;
  background: linear-gradient(105deg, transparent 35%, rgba(255,240,200,.35) 50%, transparent 65%);
  transform: translateX(-100%); animation: streak-sheen 2.2s ease-in-out infinite;
}
@keyframes streak-sheen { 60%, 100% { transform: translateX(100%); } }
@media (prefers-reduced-motion: reduce) { .streak.hot::after { animation: none; } }
.streak.bump { animation: bump .35s ease-out; }
#app:not([data-screen="void"]) .streak { display: none !important; }

/* Force generators in the build tray */
.tray-item.force { border-color: rgba(120,230,255,.45); }
.tray-item.force.on { border-color: var(--gold); }

/* Cumuli in the build tray, and the mini card when what it makes is full */
.tray-item.store { border-style: dashed; }
.tray-item.store.on { border-style: solid; }
.quick.full .sub .a { color: var(--gold); }
#card-enter + .card-move { margin-left: 6px; }

/* Tunnels: tray pieces with their cost in matter and energy, and the upgrade rows on a piece's card */
.tray-item.piece { width: auto; min-width: 64px; padding: 6px 6px 4px; }
.tray-item.piece .ti-cost { gap: 3px; flex-wrap: nowrap; }
.ing.sm { flex-direction: row; min-width: 0; padding: 0; gap: 1px; background: none; border: 0; }
.ing.sm i { width: 12px; height: 12px; }
.ing.sm b { position: static; padding: 0; background: none; color: var(--gold); font-size: 10px; }
.ing.sm.short b { color: var(--pink); }
.ups { display: flex; flex-direction: column; gap: 8px; }
.up-row { display: flex; align-items: center; gap: 8px; }
.up-row.pop { animation: bump .25s ease-out; }
.up-l { min-width: 40px; font-weight: 800; color: #9ad7ff; }
.up-c { flex: 1; display: flex; gap: 10px; flex-wrap: wrap; }
.up-c .ing { min-width: 38px; }
.up-c .ing i { width: 22px; height: 22px; }
.up-b { width: 40px; height: 36px; border-radius: 12px; background: var(--gold); color: #1a1030; font-size: 18px; font-weight: 800; }
.up-b:disabled { opacity: .35; }
.tg-tunnel .tg-label { color: #9ad7ff; }
#card-move + .card-move { margin-left: 6px; }

/* Turning the picked tunnel piece before placing it */
.tray-rot { flex-shrink: 0; align-self: center; width: 40px; height: 40px; border-radius: 12px; background: var(--card); border: 1px solid var(--gold); color: var(--gold); font-size: 20px; }
.tray-item.piece .ti-ico { transition: transform .15s; }

/* Removing a tunnel piece: a bin, pink, that needs a second tap */
.card-trash { color: var(--pink); border-color: rgba(255,122,168,.4); padding: 8px; }
.card-trash svg { width: 100%; height: 100%; display: block; }
.card-trash.armed { background: var(--pink); color: #1a1030; animation: bin-shake .35s ease-in-out; }
@keyframes bin-shake { 0%, 100% { transform: rotate(0); } 25% { transform: rotate(-12deg); } 75% { transform: rotate(12deg); } }

/* A tunnel's entry and exit buttons */
.card-svg { padding: 8px; }
.card-svg svg { width: 100%; height: 100%; display: block; }

/* A picked tunnel piece's controls, in place of the tray's items */
.pick-bar { display: flex; flex-direction: column; gap: 8px; align-items: center; width: 100%; min-width: 0; padding: 2px; }
.pick-bar button { flex-shrink: 0; width: 52px; height: 52px; padding: 12px; border-radius: 14px; background: var(--card); border: 1px solid var(--line); color: var(--gold); font-size: 22px; }
.pick-bar button svg { width: 100%; height: 100%; display: block; }
.pick-bar .pk-bin { color: var(--pink); border-color: rgba(255,122,168,.4); }
.pick-bar .pk-bin.armed { background: var(--pink); color: #1a1030; animation: bin-shake .35s ease-in-out; }
.pick-bar .pk-done { background: var(--gold); color: #1a1030; }

/* A bridge port's choice of material */
.pick-bar .pk-mat { padding: 8px; }
.pick-bar .pk-mat.on { border-color: var(--gold); box-shadow: 0 0 12px rgba(255,210,122,.45); }
.pick-bar .pk-mat:disabled { opacity: .25; }

.pick-bar .pk-in { border-color: rgba(91,240,141,.5); }
.pick-bar .pk-out { border-color: rgba(255,210,122,.5); }
/* Editing controls wrap; primary actions stay above the tray on the right. */
.tray.editing .tray-list { min-width: 0; overflow: visible; }
.tray.editing #tray-close { display: none; }
.pick-rotations { display: flex; flex-wrap: wrap; justify-content: center; gap: 8px; max-width: 100%; }
.pick-rotations:empty { display: none; }
.pick-actions { position: absolute; right: 0; bottom: calc(100% + 12px); display: flex; flex-direction: column; align-items: center; gap: 8px; padding: 6px; border-radius: 18px; background: rgba(14,11,34,.94); border: 1px solid var(--line); }
.pick-actions .pk-info { width: 44px; height: 44px; padding: 8px; font-size: 20px; color: var(--muted); }
.pick-actions .pk-done { box-shadow: 0 0 12px rgba(255,210,122,.25); }
.pick-bar .pd-cost { flex-wrap: wrap; justify-content: center; }
@media (max-height: 480px) {
  .pick-actions { flex-direction: row; }
}

.pick-bar .pd-cost { display: flex; gap: 4px; align-items: center; padding: 0 4px; }
.pick-bar button:disabled { opacity: .35; }

.pick-bar .pk-mat svg { width: 50%; height: 50%; display: inline-block; vertical-align: middle; }
.pick-bar .pk-in.pk-mat { display: flex; align-items: center; justify-content: center; padding: 4px; gap: 0; }

/* The make-by-hand shortcut, folded into a round button on the right, and its fold button */
.quick-min { position: absolute; top: -12px; right: 10px; width: 26px; height: 26px; border-radius: 50%; z-index: 1;
  background: var(--card); border: 1px solid var(--line); color: var(--muted); font-size: 16px; line-height: 1; }
.quick-min[hidden], .quick-open[hidden] { display: none; }
.quick-open { position: absolute; right: 12px; bottom: calc(var(--bottom) + var(--dock-h) + 14px); z-index: 6; width: 52px; height: 52px;
  padding: 8px; border-radius: 50%; background: rgba(14,11,34,.88); border: 1px solid var(--gold); box-shadow: 0 0 14px rgba(255,210,122,.25);
  animation: card-in .25s ease-out; }
.quick-open svg { width: 100%; height: 100%; display: block; }
#app:not([data-screen="space"]) .quick-open, #app.sheet-open .quick-open { display: none !important; }

/* Which way out a splitter's turn button is for */
.pick-bar .pk-in, .pick-bar .pk-out { position: relative; }
.pick-bar .pk-in b, .pick-bar .pk-out b { position: absolute; right: 4px; bottom: 2px; font-size: 12px; font-weight: 900; color: var(--gold); }

/* The build tray's categories: an icon each, the open one unfolding its pieces beside it */
.tray-grp { flex-direction: row; align-items: center; gap: 6px; }
.tray-grp .tg-label { display: none; }
.tray-cat { flex-shrink: 0; width: 52px; height: 52px; padding: 9px; border-radius: 14px; display: flex; align-items: center; justify-content: center;
  background: var(--card-2); border: 1px solid var(--line); color: var(--muted); }
.tray-cat .ti-ico { width: 32px; height: 32px; }
.tray-grp + .tray-grp { padding-left: 0; border-left: 0; }
.tray-cat.on { border-color: var(--gold); color: var(--gold); box-shadow: 0 0 10px rgba(255,210,122,.35); }
.tray-grp.open .tg-items { animation: card-in .2s ease-out; }

.pick-bar .pk-in b { color: #5bf08d; }

/* Level and tier upgrades stay visible even on pieces without rotation controls. */
.pick-upgrade { display: flex; flex-wrap: wrap; justify-content: center; align-items: center; gap: 10px; width: 100%; color: var(--muted); font-size: 12px; }
.pick-bar .pk-upgrade { display: flex; flex-wrap: wrap; align-items: center; justify-content: center; gap: 8px; width: auto; max-width: 100%; height: auto; min-height: 44px; padding: 8px 12px; border-color: var(--gold); font-size: 13px; font-weight: 700; }

/* Cosmic fabrication console: lightweight surfaces and shared SVGs, no extra renderer. */
.build-btn {
  border-radius: 50% 42% 50% 44%; border-color: rgba(151,191,255,.55);
  background: radial-gradient(ellipse at 35% 20%, #37315a, #0c1027 72%);
  box-shadow: inset 0 1px 8px #af9aff22, 0 0 18px #8065d32b;
}
.build-btn span { display: block; width: 34px; height: 34px; }
.tray {
  border-radius: 24px; border-color: #a397e84d;
  background: radial-gradient(ellipse at 15% 0%, #333052b3, transparent 65%), #0d1023f5;
  box-shadow: inset 0 1px 0 #d5ceff1a, 0 12px 32px #02030b80;
}
.tray-grp { --console-accent: #aab9ff; }
.tg-store { --console-accent: #bda0ff; }
.tg-power { --console-accent: #80e2ed; }
.tg-make { --console-accent: #ffdb97; }
.tg-tunnel { --console-accent: #83d8bc; }
.tray-cat {
  width: 66px; height: 66px; padding: 7px 3px; gap: 4px; flex-direction: column;
  border-radius: 20px; color: var(--console-accent); border-color: #a7b9f023;
  background: linear-gradient(150deg, #bcc5ff0d, #080d1d66);
}
.tc-label { font-size: 9px; line-height: 1.1; max-width: 100%; overflow: hidden; text-overflow: ellipsis; }
.tray-cat.on { border-color: var(--console-accent); color: var(--console-accent); box-shadow: inset 0 0 15px #aaaaff0d, 0 0 10px #8973ff20; }
.tray-item {
  border-radius: 18px; background: linear-gradient(160deg, #7786bd1c, #0a1023);
  border-color: #9ab8ef33; box-shadow: inset 0 1px 0 #c0d7ff12;
}
.tray-item.on { background: radial-gradient(ellipse at top, #816b382e, #101527); border-color: #f2cd83; }
.tray-item.store { border-style: solid; border-color: #ad90ef55; }
.tray-item.store .ti-ico { border-radius: 46% 54% 43% 57%; background: radial-gradient(ellipse, #ad86ed33, #ad86ed00 72%); box-shadow: inset 0 0 0 1px #b19be966; }
.tray-item .ti-n { background: #151c37; color: #c3cced; border: 1px solid #a7b9f033; }
.ti-cost { font-variant-numeric: tabular-nums; }
.pick-bar { gap: 10px; padding: 4px; }
.pick-identity { display: flex; align-items: center; justify-content: center; gap: 9px; max-width: 100%; }
.pick-identity > span { width: 34px; height: 34px; flex-shrink: 0; }
.pick-identity svg { width: 100%; height: 100%; }
.pick-identity strong { color: #e0def8; font-size: 13px; font-weight: 500; overflow-wrap: anywhere; }
.pick-actions {
  position: static; flex-direction: row; flex-wrap: wrap; justify-content: center;
  width: 100%; box-sizing: border-box; border: 0; border-top: 1px solid #ac9ae52b;
  border-radius: 0; padding: 10px 0 0; background: transparent; gap: 8px;
}
.pick-bar button, .card-head .card-move {
  border-radius: 17px; background: linear-gradient(145deg, #a4b5e91c, #10172b);
  box-shadow: inset 0 1px 0 #c7d7ff1c; transition: border-color .15s, background .15s;
}
.pick-actions .pk-info, .pick-actions .pk-move { width: 46px; height: 46px; padding: 10px; color: #b8d7f4; border-color: #92b6e74d; }
.pick-actions .pk-done { width: 58px; height: 46px; padding: 7px 14px; background: linear-gradient(140deg, #f6df9e, #c6a35f); color: #24213c; border-color: #ffe8b4; box-shadow: 0 0 12px #ffd27a16; }
.pick-actions .pk-bin { width: 44px; height: 46px; padding: 11px; }
/* Its turns share the actions row, at the same size. */
.pick-actions .pk-in, .pick-actions .pk-out { width: 46px; height: 46px; padding: 10px; }
.pick-actions .pk-in.pk-mat { padding: 4px; }
.pick-upgrade > span { border: 1px solid #b7a2ee3b; background: #a489ef12; border-radius: 99px; padding: 6px 10px; color: #c6b4f2; }
.pick-bar .pk-upgrade { border-color: #e4c27d80; background: linear-gradient(120deg, #85663030, #14182b); border-radius: 16px; }
.upgrade-target { display: inline-flex; align-items: center; gap: 5px; }
.pick-bar .upgrade-target svg { width: 24px; height: 24px; }
.card-box { border-color: #a89be34d; background: #0d1023; box-shadow: 0 18px 60px #02030ba6, inset 0 1px 0 #cac0ff14; }
.card-info { background: radial-gradient(ellipse at top left, #64518724, transparent 70%); }
.card-head { flex-wrap: wrap; }
.card-icon { border-radius: 50%; background: radial-gradient(ellipse, #ac8cf32b, transparent 72%); }
.card-head .card-move { color: #b5cee9; border-color: #93afe53d; }
.card-move > span { display: block; width: 24px; height: 24px; }
.card-move > span > svg { width: 100%; height: 100%; }
.card-gain { background: linear-gradient(110deg, #6ebcd514, #ad8bda0c); border-color: #89c9de33; border-radius: 17px; }
.card-gain b { color: #d1f2f3; }
.card-throttle { border-radius: 17px; background: #7082c00c; border-color: #9ca9de2e; }
.card-throttle input { accent-color: #8edbe7; }
.tray button:focus-visible, .card-head button:focus-visible, .build-btn:focus-visible { outline: 2px solid #b3ecff; outline-offset: 3px; }
@media (hover: hover) { .tray button:not(:disabled):hover, .card-head .card-move:hover { border-color: #c2dbff; } }
@media (max-width: 380px) { .tray-cat { width: 56px; } .tc-label { font-size: 8px; } .pick-actions { gap: 6px; } }
@media (prefers-reduced-motion: reduce) { .tray-grp.open .tg-items { animation: none; } .tray button, .card-head .card-move { transition: none; } }
.card-head .card-trash { color: var(--pink); border-color: #ff7aa84d; }

/* Build mode: a category is a menu (name + ▸/◂, opens its pieces); a piece shows its cost; the picked one is
   lifted with a check, and a bar over the tray says what's being placed. */
.tray-cat { position: relative; border-style: dashed; }
.tray-cat.on { border-style: solid; background: linear-gradient(150deg, color-mix(in srgb, var(--console-accent) 22%, transparent), #080d1d99); }
.tc-chev { font-style: normal; margin-left: 3px; opacity: .8; font-size: 9px; }
.tray-grp.open { padding: 4px 6px 4px 4px; border-radius: 24px; background: color-mix(in srgb, var(--console-accent) 9%, transparent);
  box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--console-accent) 35%, transparent); }
.tray-grp.open .tg-items { display: flex; gap: 6px; padding-left: 6px; border-left: 2px solid color-mix(in srgb, var(--console-accent) 55%, transparent); }
.tray.has-open .tray-grp:not(.open) .tray-cat { width: 46px; height: 46px; opacity: .55; }
.tray.has-open .tray-grp:not(.open) .tc-label { opacity: 0; max-height: 0; }
/* The menu moves instead of snapping: categories shrink and fade, labels fold away, an opened category's
   pieces slide out from it, and a tick pops onto what's picked. */
.tray-cat { transition: width .25s cubic-bezier(.2,.8,.2,1), height .25s cubic-bezier(.2,.8,.2,1), opacity .25s ease, border-color .2s ease, background .2s ease, box-shadow .2s ease; }
.tc-label { max-height: 2.4em; transition: opacity .2s ease, max-height .25s ease; }
.tray-grp.open .tg-items { animation: tray-unfold .26s cubic-bezier(.2,.8,.2,1); }
@keyframes tray-unfold { from { opacity: 0; transform: translateX(-12px); } }
.tray-grp.open .tg-items > * { animation: tray-piece-in .3s cubic-bezier(.2,.8,.2,1) backwards; }
.tray-grp.open .tg-items > :nth-child(2) { animation-delay: .04s; }
.tray-grp.open .tg-items > :nth-child(3) { animation-delay: .08s; }
.tray-grp.open .tg-items > :nth-child(4) { animation-delay: .12s; }
.tray-grp.open .tg-items > :nth-child(n+5) { animation-delay: .16s; }
@keyframes tray-piece-in { from { opacity: 0; transform: translateY(6px) scale(.94); } }
.tray-item.piece .ti-ico { transition: transform .25s cubic-bezier(.2,.8,.2,1); }
@media (prefers-reduced-motion: reduce) { .tray-cat, .tc-label, .tray-grp.open .tg-items, .tray-grp.open .tg-items > * { transition: none; animation: none; } }
.tray-item { position: relative; transition: transform .22s cubic-bezier(.2,.8,.2,1), box-shadow .22s ease, border-color .22s ease, background .22s ease; touch-action: pan-x; }
.tray-item.on { transform: translateY(-4px) scale(1.03); border-color: #ffd27a; box-shadow: inset 0 0 0 1px #ffd27a, 0 0 0 3px #ffd27a26, 0 8px 18px #ffd27a33; }
.tray-item.on::after { content: '✓'; position: absolute; top: -7px; right: -7px; width: 18px; height: 18px; border-radius: 50%;
  background: #ffd27a; color: #1b1830; font-size: 12px; font-weight: 700; line-height: 18px; text-align: center; }
.tray-sel { flex-shrink: 0; display: flex; align-items: center; gap: 8px; padding: 6px 6px 6px 10px; margin-right: 6px; border-radius: 18px;
  border: 1px solid #ffd27a88; background: linear-gradient(120deg, #85663040, #14182b); color: #f4e2b8; animation: card-in .2s ease-out; }
.tray-sel .ts-ico { width: 30px; height: 30px; flex-shrink: 0; }
.tray-sel .ts-ico svg { width: 100%; height: 100%; }
.tray-sel .ts-txt { display: flex; flex-direction: column; max-width: 140px; }
.tray-sel b { font-size: 12px; font-weight: 600; }
.tray-sel small { font-size: 9px; opacity: .8; line-height: 1.2; }
.tray-sel .ts-x { width: 30px; height: 30px; border-radius: 50%; border: 1px solid #ffd27a66; background: #0d1023; color: #ffd27a; font-size: 18px; line-height: 1; }
#app.tray-dragging, #app.tray-dragging * { cursor: grabbing !important; user-select: none; }
@media (prefers-reduced-motion: reduce) { .tray-item, .tray-sel { transition: none; animation: none; } }

/* A built bridge's card: one row per material with what's in its core, its flow, and its ports. */
.br-info { display: flex; flex-direction: column; gap: 6px; }
.br-row { display: grid; grid-template-columns: 26px 1.3fr 1fr 1fr .8fr .8fr; align-items: center; gap: 6px; font-size: 12px; font-variant-numeric: tabular-nums; }
.br-row .br-mat { width: 24px; height: 24px; }
.br-row .br-mat svg { width: 100%; height: 100%; }
.br-head small { font-size: 9px; opacity: .7; }
.br-row .ok { color: #5bf08d; }
.br-row .no { color: #ff7a9c; opacity: .8; }

/* A producer's live panel on its card */
.pi { display: flex; flex-direction: column; gap: 5px; }
.pi-bar { height: 6px; border-radius: 99px; background: #ffffff14; overflow: hidden; }
.pi-bar i { display: block; height: 100%; background: linear-gradient(90deg, #8edbe7, #ffd27a); transition: width .3s; }
.pi-why { font-size: 11px; color: #ff9ab8; }
.pi-row { display: grid; grid-template-columns: 22px 1fr auto auto; align-items: center; gap: 8px; font-size: 12px; font-variant-numeric: tabular-nums; }
.pi-row .pi-ico { width: 20px; height: 20px; display: flex; align-items: center; justify-content: center; }
.pi-row .pi-ico svg { width: 100%; height: 100%; }
.pi-row .pi-l { opacity: .75; }
.pi-row small { opacity: .6; min-width: 44px; text-align: right; }
.pi-main b { color: #ffd27a; font-size: 14px; }
.pi-low b, .pi-low small { color: #ff9ab8; opacity: 1; }
.pi-use b { color: #ffd27a; }
.pi-gain b { color: #5bf08d; }

/* The energy chart: tap the energy chip or the rate under the counter */
.flow-bar .fl.en, #rate { pointer-events: auto; cursor: pointer; }
.flow-bar .fl.en { border-color: #8edbe766; }
#modal-body.energy { display: flex; flex-direction: column; gap: 8px; }
.en-legend { display: flex; flex-wrap: wrap; gap: 10px; font-size: 12px; }
.en-legend span { display: flex; align-items: center; gap: 5px; }
.en-legend i { width: 10px; height: 10px; border-radius: 50%; }
.en-chart { width: 100%; height: 160px; border-radius: 12px; background: #0a0d1d; }
.en-span { opacity: .6; font-size: 10px; }

/* The first cumulus: its ghost under a fingertip, gliding from the tray to its slot */
.drag-hint { position: fixed; left: 0; top: 0; z-index: 60; width: 0; height: 0; pointer-events: none; }
.drag-hint .dh-ico { position: absolute; left: -20px; top: -20px; width: 40px; height: 40px; opacity: .75;
  filter: drop-shadow(0 0 8px #ffd27a); }
.drag-hint .dh-ico svg { width: 100%; height: 100%; }
.drag-hint .swipe-finger { left: 4px; top: 10px; margin-top: 0; opacity: .9; }

/* Holding a tray piece: a ring of gold fills around it until it lifts (HOLD_MS). No callout or
   selection on a long press. */
.tray-item { -webkit-touch-callout: none; user-select: none; -webkit-user-select: none; }
.tray-item.holding { animation: tray-hold .6s linear forwards; }
@keyframes tray-hold {
  from { box-shadow: 0 0 0 0 rgba(255,210,122,0), 0 0 0 rgba(255,210,122,0); transform: scale(1); }
  to { box-shadow: 0 0 0 3px rgba(255,210,122,.85), 0 0 18px rgba(255,210,122,.55); transform: scale(1.06); }
}
@media (prefers-reduced-motion: reduce) { .tray-item.holding { animation-duration: .01s; animation-delay: .59s; } }
.tray-item.on::after { animation: tick-pop .28s cubic-bezier(.3,1.6,.5,1); }
@keyframes tick-pop { from { transform: scale(0); opacity: 0; } }
@media (prefers-reduced-motion: reduce) { .tray-item.on::after { animation: none; } }
