/* ============================================================
   萤岛物语 · 样式表
   风格：糖果扁平 + 粗圆描边。舞台 960×600，移动端流式适配。
   ============================================================ */

/* ---------- 10.2 配色变量 ---------- */
:root {
  --cream: #FFF7E6;
  --ink: #2E3A4B;
  --grass: #7BC96F;
  --lake: #5DB7DE;
  --apricot: #FFA552;
  --berry: #F26D85;

  --type-fire: #FF6B4A;
  --type-tide: #4FA8E8;
  --type-vine: #6CC24A;
  --type-volt: #FFD23F;
  --type-rock: #B08968;
  --type-wind: #9ED8DB;
  --type-normal: #A8A8A8;

  --map-ground: #F3E3B8;
  --map-tree: #4E9A57;
  --map-wall: #8C7B6B;
  --map-roof: #E8735A;
  --map-house-wall: #FBEFD9;
  --map-gate: #B08968;

  --cream-2: #FFEFD0;        /* 略深奶油，用于面板分区 */
  --ink-2: #4B5A6E;          /* 次级文字 */
  --ink-3: #8A97A8;          /* 禁用文字 */
  --line: 3px;               /* 粗描边宽度 */
  --radius: 16px;
  --radius-sm: 10px;
  --shadow: 0 4px 0 rgba(46, 58, 75, .18);
  --shadow-lg: 0 10px 30px rgba(46, 58, 75, .25);

  /* 10.3 字体：只用系统字体栈 */
  --font-title: "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Source Han Sans SC", "Noto Sans CJK SC", sans-serif;
  --font-body: "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Source Han Sans SC", "Noto Sans CJK SC", sans-serif;
  --font-num: "Segoe UI", "SF Pro Rounded", "Helvetica Neue", Arial, "PingFang SC", "Microsoft YaHei", sans-serif;

  --stage-w: 960px;
  --stage-h: 600px;
}

/* ---------- 基础 ---------- */
*, *::before, *::after { box-sizing: border-box; }
html, body { margin: 0; padding: 0; height: 100%; }
body {
  background: var(--ink);
  background-image:
    radial-gradient(circle at 20% 20%, rgba(93, 183, 222, .18) 0, transparent 40%),
    radial-gradient(circle at 80% 80%, rgba(255, 165, 82, .18) 0, transparent 40%);
  color: var(--ink);
  font-family: var(--font-body);
  font-size: 16px;
  line-height: 1.5;
  -webkit-font-smoothing: antialiased;
  overflow: hidden;
  touch-action: manipulation;
  user-select: none;
  -webkit-user-select: none;
}
[hidden] { display: none !important; }
button { font: inherit; color: inherit; cursor: pointer; }
input { font: inherit; color: inherit; }
h1, h2, h3, h4 { margin: 0; font-family: var(--font-title); }
img, svg { max-width: 100%; }

/* ---------- 屏幕舞台 ---------- */
.screen {
  position: fixed;
  left: 50%;
  top: 50%;
  width: min(var(--stage-w), 100vw);
  height: min(var(--stage-h), 100vh);
  transform: translate(-50%, -50%);
  background: var(--cream);
  border-radius: 0;
  overflow: hidden;
  box-shadow: var(--shadow-lg);
}
@media (min-width: 961px) and (min-height: 601px) {
  .screen { border-radius: 22px; border: var(--line) solid var(--ink); }
}

/* ---------- 按钮 ---------- */
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 6px;
  min-width: 48px;
  min-height: 48px;
  padding: 8px 18px;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  background: #fff;
  color: var(--ink);
  font-family: var(--font-title);
  font-weight: 700;
  font-size: 16px;
  line-height: 1.2;
  box-shadow: var(--shadow);
  transition: transform .12s ease, box-shadow .12s ease, background .12s ease, opacity .12s;
  white-space: nowrap;
}
.btn:hover { transform: translateY(-2px); box-shadow: 0 6px 0 rgba(46, 58, 75, .18); }
.btn:active { transform: scale(.96); box-shadow: 0 2px 0 rgba(46, 58, 75, .18); }
.btn.primary { background: var(--apricot); }
.btn.info { background: var(--lake); color: #fff; }
.btn.danger { background: var(--berry); color: #fff; }
.btn.ghost { background: transparent; box-shadow: none; }
.btn.big { font-size: 20px; min-height: 56px; padding: 10px 28px; }
.btn.small { padding: 6px 12px; min-height: 48px; font-size: 15px; }
.btn:disabled, .btn.disabled {
  opacity: .45;
  cursor: not-allowed;
  transform: none;
  box-shadow: var(--shadow);
  filter: grayscale(.4);
}

/* ============================================================
   大厅
   ============================================================ */
#screen-lobby {
  display: flex;
  align-items: center;
  justify-content: center;
  background:
    radial-gradient(circle at 15% 15%, rgba(123, 201, 111, .35) 0, transparent 35%),
    radial-gradient(circle at 85% 90%, rgba(93, 183, 222, .35) 0, transparent 40%),
    var(--cream);
}
.lobby-card {
  width: min(440px, 92%);
  max-height: 96%;
  overflow: auto;
  padding: 28px 30px;
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: 24px;
  box-shadow: 0 8px 0 rgba(46, 58, 75, .18);
  display: flex;
  flex-direction: column;
  gap: 14px;
}
.lobby-title { font-size: 34px; text-align: center; letter-spacing: 2px; }
.lobby-sub { margin: 0; text-align: center; color: var(--ink-2); font-size: 16px; }
.field { display: flex; flex-direction: column; gap: 6px; font-weight: 700; }
.field input, .row input {
  width: 100%;
  min-height: 48px;
  padding: 8px 14px;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  background: var(--cream);
  font-size: 18px;
  outline: none;
}
.field input:focus, .row input:focus { box-shadow: 0 0 0 4px rgba(93, 183, 222, .4); }
.color-row { display: flex; gap: 10px; flex-wrap: wrap; }
.color-row button, .color-row .color {
  width: 48px;
  height: 48px;
  border-radius: 50%;
  border: var(--line) solid var(--ink);
  box-shadow: var(--shadow);
  cursor: pointer;
  transition: transform .12s;
}
.color-row button.on, .color-row .color.on { transform: scale(1.15); box-shadow: 0 0 0 4px #fff, 0 0 0 7px var(--ink); }
.color-row [data-color="0"] { background: #FFA552; }
.color-row [data-color="1"] { background: #5DB7DE; }
.color-row [data-color="2"] { background: #7BC96F; }
.color-row [data-color="3"] { background: #F26D85; }
.color-row [data-color="4"] { background: #FFD23F; }
.color-row [data-color="5"] { background: #B08968; }
.lobby-or { text-align: center; color: var(--ink-3); font-size: 15px; }
.row { display: flex; gap: 10px; align-items: center; }
.row input { flex: 1; text-transform: uppercase; letter-spacing: 4px; text-align: center; }
.lobby-msg { margin: 0; min-height: 24px; text-align: center; color: var(--berry); font-weight: 700; }

/* ============================================================
   地图屏
   ============================================================ */
#screen-map {
  display: grid;
  grid-template-rows: 48px 1fr 64px;
  background: var(--cream);
}
#topbar {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 0 12px;
  background: var(--ink);
  color: #fff;
  font-size: 15px;
  overflow: hidden;
}
#topbar .brand { font-family: var(--font-title); font-weight: 700; font-size: 18px; white-space: nowrap; }
.code-chip {
  padding: 2px 10px;
  border-radius: 999px;
  background: rgba(255, 255, 255, .15);
  white-space: nowrap;
}
.code-chip b { letter-spacing: 2px; color: var(--apricot); }
.online-list { display: flex; gap: 8px; flex: 1; overflow: hidden; white-space: nowrap; }
.online-list .who { display: inline-flex; align-items: center; gap: 4px; }
.online-list .dot { width: 10px; height: 10px; border-radius: 50%; border: 2px solid #fff; display: inline-block; }
.net-status { color: var(--apricot); font-size: 14px; white-space: nowrap; }
.net-status.ok { color: var(--grass); }
.net-status.bad { color: var(--berry); }
.topnav { display: flex; gap: 6px; }
.topnav .btn { min-height: 40px; padding: 4px 12px; box-shadow: none; }

#stage { display: flex; min-height: 0; }
#map-wrap {
  position: relative;
  width: 640px;
  height: 480px;
  flex: none;
  background: var(--map-ground);
  overflow: hidden;
  border-right: var(--line) solid var(--ink);
}
#map-canvas { display: block; width: 640px; height: 480px; image-rendering: auto; }
#map-overlay { position: absolute; inset: 0; pointer-events: none; }
#map-overlay > * { pointer-events: auto; }
.bubble {
  position: absolute;
  transform: translate(-50%, -100%);
  padding: 4px 8px;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  background: #fff;
  font-size: 20px;
  line-height: 1;
  animation: bubble-in .2s cubic-bezier(.34, 1.56, .64, 1), bubble-out .4s ease 1.6s forwards;
  pointer-events: none;
}
.challenge-btn {
  position: absolute;
  transform: translate(-50%, -100%);
  min-height: 48px;
  padding: 6px 14px;
  background: var(--apricot);
}

#side {
  flex: 1;
  display: flex;
  flex-direction: column;
  gap: 10px;
  padding: 12px;
  background: var(--cream-2);
  overflow: auto;
}
.side-block {
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: var(--radius);
  padding: 10px 12px;
}
.zone-name { font-family: var(--font-title); font-weight: 700; font-size: 20px; }
.zone-levels { color: var(--ink-2); font-size: 15px; }
.party-mini {
  flex: 1;
  display: grid;
  grid-template-columns: repeat(2, 1fr);
  grid-auto-rows: max-content;
  gap: 8px;
  align-content: start;
}
.party-mini .mini {
  display: flex;
  align-items: center;
  gap: 6px;
  padding: 4px;
  border-radius: 12px;
  background: var(--cream);
}
.party-mini .mini svg, .party-mini .mini .sprite-ph { width: 48px; height: 48px; flex: none; }
.party-mini .mini .mini-info { flex: 1; min-width: 0; font-size: 13px; line-height: 1.2; }
.party-mini .mini .hp-bar { height: 8px; margin-top: 3px; }
.side-stats { display: flex; justify-content: space-between; align-items: center; }
.money { font-family: var(--font-num); font-weight: 700; font-size: 18px; color: #B87218; }
.badges { display: flex; gap: 6px; }
.badge {
  width: 32px;
  height: 32px;
  border-radius: 50%;
  border: var(--line) solid var(--ink);
  background: #ddd;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 16px;
}
.badge.tide { background: var(--type-tide); }
.badge.forge { background: var(--type-fire); }
.badge.got { animation: badge-pop 1.2s cubic-bezier(.34, 1.56, .64, 1); }

#bottombar {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 6px 12px;
  background: var(--cream-2);
  border-top: var(--line) solid var(--ink);
}
.emotes { display: flex; gap: 6px; }
.emotes .btn { padding: 0; width: 48px; font-size: 22px; }
.dialog {
  flex: 1;
  min-width: 0;
  display: flex;
  align-items: center;
  gap: 10px;
  min-height: 52px;
  padding: 4px 14px;
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  font-size: 18px;
}
.dialog-name { font-weight: 700; color: var(--lake); white-space: nowrap; }
.dialog-text { flex: 1; min-width: 0; overflow: hidden; }
.dialog-options { display: flex; gap: 6px; }
.dialog-options .btn { min-height: 40px; padding: 4px 12px; font-size: 15px; }
.dpad {
  display: none;
  grid-template-columns: repeat(3, 44px);
  grid-template-rows: repeat(2, 44px);
  gap: 2px;
  flex: none;
}
.dpad-btn { width: 44px; height: 44px; min-width: 44px; min-height: 44px; padding: 0; border-radius: 12px; }
.dpad-btn.up { grid-column: 2; grid-row: 1; }
.dpad-btn.left { grid-column: 1; grid-row: 2; }
.dpad-btn.right { grid-column: 3; grid-row: 2; }
.dpad-btn.down { grid-column: 2; grid-row: 2; }

/* ============================================================
   战斗层
   ============================================================ */
#screen-battle {
  z-index: 20;
  display: grid;
  grid-template-rows: 1fr 60px 210px;
  background:
    linear-gradient(180deg, #CFEFFB 0, #E9F8FF 45%, var(--map-ground) 45.1%, #EAD9A9 100%);
}
#screen-battle.battle-night {
  background: linear-gradient(180deg, #2D3E63 0, #4E5F8E 45%, #7B6A54 45.1%, #5F5142 100%);
}
.battle-tag {
  position: absolute;
  top: 10px;
  left: 50%;
  transform: translateX(-50%);
  z-index: 5;
  padding: 4px 16px;
  border: var(--line) solid var(--ink);
  border-radius: 999px;
  background: var(--apricot);
  font-family: var(--font-title);
  font-weight: 700;
  font-size: 15px;
  box-shadow: var(--shadow);
}
.battle-field { position: relative; min-height: 0; overflow: hidden; }
.battle-field::before, .battle-field::after {
  content: "";
  position: absolute;
  border-radius: 50%;
  background: rgba(123, 201, 111, .55);
  pointer-events: none;
}
.battle-field::before { right: 150px; top: 158px; width: 240px; height: 54px; }
.battle-field::after { left: 40px; bottom: 6px; width: 320px; height: 70px; }

.mon-panel {
  position: absolute;
  z-index: 3;
  width: 300px;
  padding: 10px 14px;
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: 18px;
  box-shadow: var(--shadow);
}
.mon-panel.foe { left: 22px; top: 22px; }
.mon-panel.me { right: 22px; bottom: 14px; width: 320px; }
.mon-head { display: flex; align-items: center; gap: 8px; }
.mon-name { font-family: var(--font-title); font-weight: 700; font-size: 19px; }
.mon-level { font-family: var(--font-num); font-weight: 700; color: var(--ink-2); }
.type-chip {
  margin-left: auto;
  padding: 1px 9px;
  border: 2px solid var(--ink);
  border-radius: 999px;
  font-size: 13px;
  font-weight: 700;
  color: var(--ink);
  background: var(--type-normal);
}
.type-chip:empty { display: none; }
.type-chip.fire, .t-fire { background: var(--type-fire); }
.type-chip.tide, .t-tide { background: var(--type-tide); }
.type-chip.vine, .t-vine { background: var(--type-vine); }
.type-chip.volt, .t-volt { background: var(--type-volt); }
.type-chip.rock, .t-rock { background: var(--type-rock); }
.type-chip.wind, .t-wind { background: var(--type-wind); }
.type-chip.normal, .t-normal { background: var(--type-normal); }

.hp-row { display: flex; align-items: center; gap: 8px; margin-top: 6px; }
.hp-bar {
  flex: 1;
  height: 14px;
  border: 2px solid var(--ink);
  border-radius: 999px;
  background: #E6E0D2;
  overflow: hidden;
}
.hp-fill {
  height: 100%;
  width: 100%;
  border-radius: 999px;
  background: var(--grass);
  transition: width .6s cubic-bezier(.2, .7, .2, 1), background-color .3s;
}
.hp-fill.mid { background: var(--apricot); }
.hp-fill.low { background: var(--berry); }
.hp-text { font-family: var(--font-num); font-weight: 700; font-size: 14px; min-width: 58px; text-align: right; }
.exp-bar {
  height: 8px;
  margin-top: 6px;
  border: 2px solid var(--ink);
  border-radius: 999px;
  background: #E6E0D2;
  overflow: hidden;
}
.exp-fill {
  height: 100%;
  width: 0;
  background: var(--apricot);
  transition: width .6s ease;
}
.exp-fill.flash { animation: exp-flash .8s ease; }
.mon-foot { display: flex; align-items: center; gap: 8px; min-height: 22px; margin-top: 4px; }
.status-chip {
  padding: 1px 8px;
  border-radius: 999px;
  border: 2px solid var(--ink);
  font-size: 12px;
  font-weight: 700;
  color: #fff;
}
.status-chip:empty { display: none; }
.status-chip.poison { background: #9B5DE5; }
.status-chip.para { background: #E0B400; }
.status-chip.sleep { background: var(--lake); }
.status-chip.pop { animation: status-pop .2s cubic-bezier(.34, 1.56, .64, 1); }
.balls { margin-left: auto; display: flex; gap: 4px; }
.balls .ball-dot {
  width: 12px;
  height: 12px;
  border-radius: 50%;
  border: 2px solid var(--ink);
  background: var(--berry);
}
.balls .ball-dot.out { background: #cfc8ba; }

/* 立绘 */
.sprite {
  position: absolute;
  z-index: 2;
  width: 160px;
  height: 160px;
}
.sprite::after {
  content: "";
  position: absolute;
  left: 20%;
  right: 20%;
  bottom: -2px;
  height: 22px;
  border-radius: 50%;
  background: rgba(46, 58, 75, .22);
  z-index: -1;
}
.sprite .sprite-inner { width: 100%; height: 100%; position: relative; }
.sprite svg, .sprite .sprite-ph { width: 100%; height: 100%; display: block; }
.foe-sprite { right: 190px; top: 26px; width: 160px; height: 160px; }
.foe-sprite .sprite-inner { transform: scaleX(-1); }
.me-sprite { left: 90px; bottom: 22px; width: 200px; height: 200px; }
.sprite-ph {
  display: flex;
  align-items: center;
  justify-content: center;
  font-family: var(--font-title);
  font-weight: 700;
  font-size: 34px;
  color: var(--ink);
  border-radius: 50%;
  border: var(--line) solid var(--ink);
  background: var(--type-normal);
}
.sprite.enter .sprite-inner { animation: mon-enter .35s cubic-bezier(.34, 1.56, .64, 1); }
.me-sprite.attack .sprite-inner { animation: attack-me .25s ease-out; }
.foe-sprite.attack .sprite-inner { animation: attack-foe .25s ease-out, scalex-keep .25s; }
.sprite.hit .sprite-inner { animation: hit .3s ease; }
.sprite.faint .sprite-inner { animation: faint .6s ease forwards; }
.sprite.leave .sprite-inner { animation: mon-leave .25s ease forwards; }
.sprite.shrink .sprite-inner { animation: shrink-into-ball .3s ease forwards; }
.sprite.gone .sprite-inner { opacity: 0; transform: scale(0); }
.sprite.levelup::before {
  content: "";
  position: absolute;
  inset: 10%;
  border-radius: 50%;
  animation: level-ring .8s ease-out forwards;
  pointer-events: none;
}
.sprite.evolve-glow { animation: evolve-glow 1.6s ease; }
.sprite.hidden-mon { visibility: hidden; }

/* 特效层 */
.battle-fx { position: absolute; inset: 0; z-index: 4; pointer-events: none; overflow: hidden; }
.dmg-num {
  position: absolute;
  transform: translate(-50%, -50%);
  font-family: var(--font-num);
  font-weight: 900;
  font-size: 30px;
  color: var(--berry);
  -webkit-text-stroke: 2px #fff;
  paint-order: stroke fill;
  text-shadow: 0 2px 0 var(--ink);
  animation: dmg-float .7s ease-out forwards;
}
.dmg-num.crit { font-size: 44px; color: #FFB020; }
.dmg-num.heal { color: var(--grass); }
.fx-text {
  position: absolute;
  left: 50%;
  top: 40%;
  transform: translate(-50%, -50%);
  font-family: var(--font-title);
  font-weight: 900;
  font-size: 34px;
  color: var(--apricot);
  -webkit-text-stroke: 2px var(--ink);
  paint-order: stroke fill;
  white-space: nowrap;
  animation: fx-text .5s ease-out forwards;
}
.fx-text.crit { color: #FFB020; font-size: 30px; }
.fx-text.weak { color: var(--lake); font-size: 28px; }
.fx-text.lv { color: #FFD23F; font-size: 40px; animation-duration: .8s; }
.fx-text.stage-up { color: var(--grass); font-size: 26px; }
.fx-text.stage-down { color: var(--berry); font-size: 26px; }
.particle {
  position: absolute;
  width: 14px;
  height: 14px;
  border-radius: 50%;
  border: 2px solid var(--ink);
  transform: translate(-50%, -50%);
  animation: particle .5s ease-out forwards;
}
.star {
  position: absolute;
  font-size: 26px;
  transform: translate(-50%, -50%);
  animation: particle .8s ease-out forwards;
}
.catch-ball {
  position: absolute;
  width: 40px;
  height: 40px;
  border-radius: 50%;
  border: var(--line) solid var(--ink);
  background: linear-gradient(180deg, var(--berry) 0 48%, var(--ink) 48% 56%, #fff 56% 100%);
  transform: translate(-50%, -50%);
}
.catch-ball::after {
  content: "";
  position: absolute;
  left: 50%;
  top: 50%;
  width: 12px;
  height: 12px;
  border-radius: 50%;
  border: 2px solid var(--ink);
  background: #fff;
  transform: translate(-50%, -50%);
}
.catch-ball.fly { animation: ball-fly .6s ease-in forwards; }
.catch-ball.shake { animation: ball-shake .5s ease-in-out; }
.catch-ball.crack { animation: ball-crack .4s ease forwards; }
.catch-ball.caught { animation: ball-caught .5s ease forwards; }
.white-flash {
  position: absolute;
  inset: 0;
  background: #fff;
  animation: white-flash 1.6s ease forwards;
}
.confetti {
  position: absolute;
  width: 10px;
  height: 16px;
  border-radius: 3px;
  animation: confetti-fall 1.4s ease-in forwards;
}

/* 消息框 */
.battle-msg {
  display: flex;
  align-items: center;
  padding: 6px 22px;
  margin: 0 12px;
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  font-size: 20px;
  font-weight: 700;
  min-height: 52px;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

/* 菜单 */
.battle-menu {
  position: relative;
  display: grid;
  grid-template-columns: 1fr 150px;
  gap: 10px;
  padding: 10px 12px 12px;
}
.battle-menu.off { visibility: hidden; }
.moves-grid {
  display: grid;
  grid-template-columns: repeat(2, 1fr);
  grid-template-rows: repeat(2, 1fr);
  gap: 10px;
}
.move-btn {
  position: relative;
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  justify-content: center;
  gap: 2px;
  min-height: 48px;
  padding: 8px 14px;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  background: var(--type-normal);
  box-shadow: var(--shadow);
  font-family: var(--font-title);
  text-align: left;
  transition: transform .12s, box-shadow .12s, opacity .12s;
}
.move-btn:hover { transform: translateY(-2px); }
.move-btn:active { transform: scale(.96); }
.move-btn:disabled { opacity: .5; filter: grayscale(.6); cursor: not-allowed; transform: none; }
.move-btn .move-name { font-size: 19px; font-weight: 700; }
.move-btn .move-meta { display: flex; gap: 10px; font-size: 13px; font-weight: 700; color: var(--ink-2); font-family: var(--font-num); }
.move-btn .move-eff {
  position: absolute;
  right: 10px;
  top: 6px;
  width: 30px;
  height: 30px;
  border-radius: 50%;
  border: 2px solid var(--ink);
  background: #fff;
  display: flex;
  align-items: center;
  justify-content: center;
  font-weight: 900;
  font-size: 15px;
}
.move-eff.up { color: var(--berry); }
.move-eff.down { color: var(--lake); }
.move-eff.flat { color: var(--ink-3); }
.move-eff.aux { color: #9B5DE5; font-size: 12px; }
.move-btn .move-pp.empty { color: var(--berry); }
.battle-actions { display: flex; flex-direction: column; gap: 8px; }
.battle-actions .btn { width: 100%; min-height: 48px; padding: 4px 10px; }
#btn-b-party { background: var(--grass); }
#btn-b-bag { background: var(--lake); color: #fff; }
#btn-b-flee { background: #fff; }

/* 子菜单（换宠/背包） */
.battle-sub {
  position: absolute;
  left: 12px;
  right: 12px;
  bottom: 12px;
  height: 198px;
  z-index: 6;
  display: flex;
  flex-direction: column;
  gap: 8px;
  padding: 10px 12px;
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: 18px;
  box-shadow: var(--shadow-lg);
  animation: pop-in .2s cubic-bezier(.34, 1.56, .64, 1);
}
.sub-head { display: flex; align-items: center; gap: 10px; font-family: var(--font-title); font-weight: 700; font-size: 18px; }
.sub-head .btn { margin-left: auto; min-height: 40px; padding: 4px 12px; }
.sub-list { display: grid; grid-template-columns: repeat(3, 1fr); gap: 8px; overflow: auto; flex: 1; min-height: 0; }
.sub-item {
  display: flex;
  align-items: center;
  gap: 8px;
  min-height: 60px;
  padding: 6px 10px;
  border: var(--line) solid var(--ink);
  border-radius: 12px;
  background: var(--cream);
  box-shadow: var(--shadow);
  text-align: left;
  transition: transform .12s;
}
.sub-item:hover { transform: translateY(-2px); }
.sub-item:disabled { opacity: .45; cursor: not-allowed; transform: none; }
.sub-item svg, .sub-item .sprite-ph { width: 44px; height: 44px; flex: none; font-size: 18px; }
.sub-item .sub-info { flex: 1; min-width: 0; font-size: 14px; line-height: 1.25; }
.sub-item .sub-info b { font-family: var(--font-title); font-size: 15px; }
.sub-item .hp-bar { height: 8px; margin-top: 3px; }
.sub-item .count { font-family: var(--font-num); font-weight: 700; color: var(--ink-2); }

/* PvP 等待 */
.battle-wait {
  position: absolute;
  left: 12px;
  right: 12px;
  bottom: 12px;
  height: 198px;
  z-index: 6;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 24px;
  background: rgba(255, 255, 255, .92);
  border: var(--line) solid var(--ink);
  border-radius: 18px;
  font-family: var(--font-title);
  font-weight: 700;
  font-size: 22px;
}
.wait-ring { width: 84px; height: 84px; position: relative; }
.wait-ring svg { width: 100%; height: 100%; transform: rotate(-90deg); }
.wait-ring circle { fill: none; stroke-width: 8; }
.wait-ring .track { stroke: #E6E0D2; }
.wait-ring .arc { stroke: var(--apricot); stroke-linecap: round; transition: stroke-dashoffset 1s linear; }
.wait-ring .num {
  position: absolute;
  inset: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  font-family: var(--font-num);
  font-size: 24px;
}
.wait-dots::after { content: "…"; animation: dots 1.2s steps(3) infinite; }

/* 结果卡 */
.result-card {
  position: absolute;
  left: 50%;
  top: 50%;
  transform: translate(-50%, -50%);
  z-index: 8;
  min-width: 320px;
  padding: 24px 32px;
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: 24px;
  box-shadow: var(--shadow-lg);
  text-align: center;
  animation: pop-in .35s cubic-bezier(.34, 1.56, .64, 1);
  pointer-events: auto;
}
.result-card h2 { font-size: 30px; margin-bottom: 8px; }
.result-card.win h2 { color: #B87218; }
.result-card.lose h2 { color: var(--ink-2); }
.result-card .rewards { display: flex; flex-direction: column; gap: 6px; font-size: 18px; margin-bottom: 14px; }
.result-card .reward-badge { display: inline-flex; align-items: center; gap: 8px; justify-content: center; }
.result-card .badge { animation: badge-pop 1.2s cubic-bezier(.34, 1.56, .64, 1); width: 44px; height: 44px; font-size: 22px; }

/* ============================================================
   面板（队伍 / 背包 / 图鉴 / 商店 / 通关）
   ============================================================ */
.panel {
  position: fixed;
  left: 50%;
  top: 50%;
  transform: translate(-50%, -50%);
  z-index: 30;
  width: min(900px, 96vw);
  height: min(560px, 96vh);
  display: flex;
  flex-direction: column;
  background: var(--cream);
  border: var(--line) solid var(--ink);
  border-radius: 24px;
  box-shadow: var(--shadow-lg);
  overflow: hidden;
  animation: pop-in .25s cubic-bezier(.34, 1.56, .64, 1);
}
.panel-head {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 12px 18px;
  background: var(--ink);
  color: #fff;
  font-family: var(--font-title);
  font-size: 22px;
  font-weight: 700;
}
.panel-head .sub { font-size: 15px; font-weight: 400; color: rgba(255, 255, 255, .8); }
.panel-head .spacer { flex: 1; }
.panel-head .btn { min-height: 44px; padding: 4px 14px; box-shadow: none; }
.panel-body { flex: 1; min-height: 0; display: flex; gap: 12px; padding: 14px; overflow: hidden; }
.panel-col { display: flex; flex-direction: column; gap: 10px; min-height: 0; overflow: auto; }
.panel-col.main { flex: 1.4; }
.panel-col.aside { flex: 1; }
.panel-hint { color: var(--ink-2); font-size: 15px; }
.panel-foot { display: flex; gap: 10px; padding: 10px 14px; border-top: var(--line) solid var(--ink); background: #fff; align-items: center; }
.card {
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: var(--radius);
  padding: 12px 14px;
}
.card h3 { font-size: 18px; margin-bottom: 6px; }

/* 队伍格 */
.slot-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 10px; }
.slot {
  position: relative;
  display: flex;
  align-items: center;
  gap: 8px;
  min-height: 78px;
  padding: 8px 10px;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  background: #fff;
  box-shadow: var(--shadow);
  text-align: left;
  transition: transform .12s, box-shadow .12s;
}
.slot:hover { transform: translateY(-2px); }
.slot.selected { box-shadow: 0 0 0 4px var(--apricot), var(--shadow); }
.slot.empty { background: transparent; border-style: dashed; box-shadow: none; color: var(--ink-3); justify-content: center; }
.slot svg, .slot .sprite-ph { width: 56px; height: 56px; flex: none; font-size: 22px; }
.slot .slot-info { flex: 1; min-width: 0; font-size: 14px; line-height: 1.25; }
.slot .slot-info b { font-family: var(--font-title); font-size: 16px; white-space: nowrap; }
.slot .hp-bar { height: 8px; margin-top: 4px; }
.slot .slot-no {
  position: absolute;
  left: -8px;
  top: -8px;
  width: 24px;
  height: 24px;
  border-radius: 50%;
  border: 2px solid var(--ink);
  background: var(--apricot);
  font-family: var(--font-num);
  font-size: 13px;
  font-weight: 700;
  display: flex;
  align-items: center;
  justify-content: center;
}
.slot.faint-slot { filter: grayscale(.7); }
.box-grid { display: grid; grid-template-columns: repeat(4, 1fr); gap: 8px; }
.box-grid .slot { min-height: 64px; padding: 6px; }
.box-grid .slot svg, .box-grid .slot .sprite-ph { width: 44px; height: 44px; }

/* 详情 */
.detail-top { display: flex; align-items: center; gap: 12px; }
.detail-top svg, .detail-top .sprite-ph { width: 96px; height: 96px; flex: none; font-size: 30px; }
.detail-top h3 { font-size: 22px; }
.stat-grid { display: grid; grid-template-columns: repeat(4, 1fr); gap: 6px; margin-top: 8px; }
.stat {
  text-align: center;
  padding: 4px;
  border-radius: 10px;
  background: var(--cream);
  font-size: 13px;
  color: var(--ink-2);
}
.stat b { display: block; font-family: var(--font-num); font-size: 18px; color: var(--ink); }
.move-list { display: flex; flex-direction: column; gap: 6px; margin-top: 8px; }
.move-row {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 6px 10px;
  border: 2px solid var(--ink);
  border-radius: 10px;
  font-size: 15px;
  font-weight: 700;
}
.move-row .pp { margin-left: auto; font-family: var(--font-num); font-weight: 700; color: var(--ink-2); }
.action-row { display: flex; gap: 8px; flex-wrap: wrap; }
.action-row .btn { flex: 1; }

/* 背包 */
.item-list { display: flex; flex-direction: column; gap: 10px; }
.item-row {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 10px 14px;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  background: #fff;
  box-shadow: var(--shadow);
}
.item-icon {
  width: 48px;
  height: 48px;
  border-radius: 50%;
  border: var(--line) solid var(--ink);
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 22px;
  flex: none;
}
.item-icon.ball { background: linear-gradient(180deg, var(--berry) 0 48%, var(--ink) 48% 56%, #fff 56% 100%); }
.item-icon.potion { background: var(--grass); }
.item-icon.bigpotion { background: var(--lake); }
.item-row { flex-wrap: wrap; }
.item-info { flex: 1 1 140px; min-width: 140px; }
.item-info .desc { min-width: 0; }
.item-info b { font-family: var(--font-title); font-size: 17px; white-space: nowrap; }
.item-info .desc { font-size: 14px; color: var(--ink-2); }
.item-count { font-family: var(--font-num); font-weight: 700; font-size: 22px; min-width: 56px; text-align: right; }
.item-price { font-family: var(--font-num); font-weight: 700; color: #B87218; white-space: nowrap; }
.qty { display: flex; align-items: center; gap: 4px; flex: none; }
.qty .btn { min-width: 44px; padding: 0; white-space: nowrap; }
.qty .qty-num { min-width: 36px; text-align: center; font-family: var(--font-num); font-weight: 700; font-size: 18px; }

/* 图鉴 */
.dex-grid { display: grid; grid-template-columns: repeat(6, 1fr); gap: 8px; }
.dex-cell {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
  padding: 6px 4px;
  border: var(--line) solid var(--ink);
  border-radius: 14px;
  background: #fff;
  box-shadow: var(--shadow);
  font-size: 13px;
  font-weight: 700;
  transition: transform .12s;
}
.dex-cell:hover { transform: translateY(-2px); }
.dex-cell svg, .dex-cell .sprite-ph { width: 64px; height: 64px; }
.dex-cell.seen svg, .dex-cell.seen .sprite-ph { filter: grayscale(1) opacity(.55); }
.dex-cell.unknown { color: var(--ink-3); background: var(--cream-2); }
.dex-cell.unknown .q {
  width: 64px;
  height: 64px;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 34px;
  color: var(--ink-3);
}
.dex-cell.selected { box-shadow: 0 0 0 4px var(--apricot), var(--shadow); }
.dex-cell .no { font-family: var(--font-num); font-size: 11px; color: var(--ink-3); }
.dex-cell.caught { border-color: var(--ink); }
.dex-cell.caught .no { color: #B87218; }
.ring-wrap { display: flex; gap: 12px; align-items: center; }
.ring-wrap svg { width: 150px; height: 150px; flex: none; }
.ring-tips { display: flex; flex-direction: column; gap: 3px; font-size: 14px; }
.ring-tips .tip { display: flex; align-items: center; gap: 6px; }
.ring-tips .sw { width: 14px; height: 14px; border-radius: 50%; border: 2px solid var(--ink); flex: none; }

/* 商店 */
.shop-money { margin-left: auto; font-family: var(--font-num); font-weight: 700; font-size: 20px; color: var(--apricot); }

/* 通关 */
#panel-ending { background: linear-gradient(180deg, #2D3E63 0, #4E5F8E 60%, #7B6A54 100%); color: #fff; }
#panel-ending .panel-head { background: rgba(0, 0, 0, .25); }
.ending-title { text-align: center; font-size: 34px; color: #FFD23F; text-shadow: 0 3px 0 var(--ink); margin: 6px 0; }
.ending-sub { text-align: center; font-size: 17px; color: rgba(255, 255, 255, .85); }
.ending-photo {
  display: flex;
  justify-content: center;
  align-items: flex-end;
  gap: 4px;
  min-height: 150px;
  padding: 10px;
  margin: 6px auto;
  background: rgba(255, 255, 255, .12);
  border: var(--line) solid rgba(255, 255, 255, .6);
  border-radius: 20px;
  width: max-content;
  max-width: 100%;
}
.ending-photo .photo-mon { display: flex; flex-direction: column; align-items: center; font-size: 13px; font-weight: 700; animation: mon-enter .5s cubic-bezier(.34, 1.56, .64, 1) both; }
.ending-photo .photo-mon svg, .ending-photo .photo-mon .sprite-ph { width: 110px; height: 110px; }
.ending-table { width: 100%; border-collapse: collapse; font-size: 15px; }
.ending-table th, .ending-table td { padding: 6px 10px; text-align: center; border-bottom: 1px solid rgba(255, 255, 255, .3); }
.ending-table th { color: #FFD23F; }
.ending-table td:first-child { text-align: left; font-weight: 700; }
.ending-table .crown { color: #FFD23F; }
.ending-body { flex-direction: column; overflow: auto; }

/* ============================================================
   通用：弹窗 / 提示 / 过场
   ============================================================ */
.modal {
  position: fixed;
  inset: 0;
  z-index: 40;
  display: flex;
  align-items: center;
  justify-content: center;
  background: rgba(46, 58, 75, .55);
}
.modal-box {
  width: min(460px, 92vw);
  max-height: 90vh;
  overflow: auto;
  padding: 24px 26px 20px;
  background: #fff;
  border: var(--line) solid var(--ink);
  border-radius: 22px;
  box-shadow: var(--shadow-lg);
  display: flex;
  flex-direction: column;
  gap: 16px;
  animation: pop-in .25s cubic-bezier(.34, 1.56, .64, 1);
  font-size: 18px;
}
.modal-box h2, .modal-box h3 { font-size: 22px; }
#modal-close { align-self: center; min-width: 140px; }
.starter-row { display: flex; gap: 10px; justify-content: center; }
.starter-card {
  flex: 1;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 4px;
  padding: 10px 6px;
  border: var(--line) solid var(--ink);
  border-radius: 16px;
  background: var(--cream);
  box-shadow: var(--shadow);
  font-family: var(--font-title);
  font-weight: 700;
  transition: transform .12s;
}
.starter-card:hover { transform: translateY(-3px); }
.starter-card svg, .starter-card .sprite-ph { width: 96px; height: 96px; }

.toasts {
  position: fixed;
  left: 50%;
  top: 16px;
  transform: translateX(-50%);
  z-index: 50;
  display: flex;
  flex-direction: column;
  gap: 8px;
  align-items: center;
  pointer-events: none;
}
.toast {
  padding: 8px 18px;
  border: var(--line) solid var(--ink);
  border-radius: 999px;
  background: #fff;
  font-weight: 700;
  font-size: 16px;
  box-shadow: var(--shadow);
  animation: toast-in .25s cubic-bezier(.34, 1.56, .64, 1), toast-out .4s ease 2.6s forwards;
}
.toast.warn { background: var(--berry); color: #fff; }
.toast.good { background: var(--grass); }

.transition {
  position: fixed;
  inset: 0;
  z-index: 60;
  background: var(--ink);
  clip-path: circle(0 at 50% 50%);
  pointer-events: none;
}
.transition.in { animation: iris-in .4s ease-in forwards; }
.transition.out { animation: iris-out .3s ease-out forwards; }
.transition.hold { clip-path: circle(0 at 50% 50%); }

/* ============================================================
   10.6 动画 keyframes
   ============================================================ */
/* 1 角色走路：Canvas 插值（无 CSS）。2 草丛晃动：Canvas。 */

/* 3 遇敌过场：黑圆收缩/展开 */
@keyframes iris-in { from { clip-path: circle(80% at 50% 50%); } to { clip-path: circle(0 at 50% 50%); } }
@keyframes iris-out { from { clip-path: circle(0 at 50% 50%); } to { clip-path: circle(80% at 50% 50%); } }
/* 说明：iris-in 在 .transition 上表现为「黑幕从边缘收到中心」需要反向 —— 用 .transition.cover 先铺满 */
.transition.cover { clip-path: circle(80% at 50% 50%); }
@keyframes iris-close { from { clip-path: circle(0 at 50% 50%); } to { clip-path: circle(80% at 50% 50%); } }
@keyframes iris-open { from { clip-path: circle(80% at 50% 50%); } to { clip-path: circle(0 at 50% 50%); } }
.transition.close { animation: iris-close .4s ease-in forwards; }
.transition.open { animation: iris-open .3s ease-out forwards; }

/* 4 萤兽入场：0.6 → 1 + 落地回弹 */
@keyframes mon-enter {
  0% { transform: scale(.6) translateY(-20px); opacity: 0; }
  60% { transform: scale(1.05) translateY(4px); opacity: 1; }
  100% { transform: scale(1) translateY(0); }
}
@keyframes mon-leave {
  0% { transform: scale(1); opacity: 1; }
  100% { transform: scale(.4) translateY(20px); opacity: 0; }
}

/* 5 攻击：向对方冲 24px 再回弹 */
@keyframes attack-me {
  0% { transform: translate(0, 0); }
  45% { transform: translate(24px, -16px); }
  100% { transform: translate(0, 0); }
}
@keyframes attack-foe {
  0% { transform: scaleX(-1) translate(0, 0); }
  45% { transform: scaleX(-1) translate(24px, 16px); }
  100% { transform: scaleX(-1) translate(0, 0); }
}
@keyframes scalex-keep { from { } to { } }

/* 6 受击：闪两次 + 左右抖 4px */
@keyframes hit {
  0% { filter: brightness(1); transform: translateX(0); }
  20% { filter: brightness(3); transform: translateX(-4px); }
  40% { filter: brightness(1); transform: translateX(4px); }
  60% { filter: brightness(3); transform: translateX(-4px); }
  80% { filter: brightness(1); transform: translateX(4px); }
  100% { filter: brightness(1); transform: translateX(0); }
}
.foe-sprite.hit .sprite-inner { animation: hit-foe .3s ease; }
@keyframes hit-foe {
  0% { filter: brightness(1); transform: scaleX(-1) translateX(0); }
  20% { filter: brightness(3); transform: scaleX(-1) translateX(-4px); }
  40% { filter: brightness(1); transform: scaleX(-1) translateX(4px); }
  60% { filter: brightness(3); transform: scaleX(-1) translateX(-4px); }
  80% { filter: brightness(1); transform: scaleX(-1) translateX(4px); }
  100% { filter: brightness(1); transform: scaleX(-1) translateX(0); }
}

/* 7 属性粒子：从落点散开淡出（方向由 --dx/--dy 提供） */
@keyframes particle {
  0% { transform: translate(-50%, -50%) scale(1); opacity: 1; }
  100% { transform: translate(calc(-50% + var(--dx, 0px)), calc(-50% + var(--dy, 0px))) scale(.3); opacity: 0; }
}

/* 8 HP 条缓动：transition（见 .hp-fill）。 */

/* 9 伤害数字上浮 30px 淡出 */
@keyframes dmg-float {
  0% { transform: translate(-50%, -50%) scale(.6); opacity: 0; }
  20% { transform: translate(-50%, -50%) scale(1.2); opacity: 1; }
  100% { transform: translate(-50%, calc(-50% - 30px)) scale(1); opacity: 0; }
}

/* 10 「效果拔群！」放大淡出 */
@keyframes fx-text {
  0% { transform: translate(-50%, -50%) scale(.5); opacity: 0; }
  30% { transform: translate(-50%, -50%) scale(1.15); opacity: 1; }
  70% { transform: translate(-50%, -50%) scale(1); opacity: 1; }
  100% { transform: translate(-50%, -50%) scale(1.3); opacity: 0; }
}

/* 11 状态图标弹入 */
@keyframes status-pop {
  0% { transform: scale(0); }
  100% { transform: scale(1); }
}

/* 12 捕捉球 */
@keyframes ball-fly {
  0% { transform: translate(-50%, -50%) rotate(0); offset-distance: 0; }
  100% { transform: translate(-50%, -50%) rotate(720deg); offset-distance: 100%; }
}
@keyframes shrink-into-ball {
  0% { transform: scaleX(-1) scale(1); filter: brightness(1); }
  40% { filter: brightness(3); }
  100% { transform: scaleX(-1) scale(0); filter: brightness(3); opacity: 0; }
}
@keyframes ball-shake {
  0% { transform: translate(-50%, -50%) rotate(0); }
  25% { transform: translate(-50%, -50%) rotate(-24deg); }
  50% { transform: translate(-50%, -50%) rotate(0); }
  75% { transform: translate(-50%, -50%) rotate(24deg); }
  100% { transform: translate(-50%, -50%) rotate(0); }
}
@keyframes ball-crack {
  0% { transform: translate(-50%, -50%) scale(1); opacity: 1; }
  50% { transform: translate(-50%, -50%) scale(1.3); filter: brightness(2); }
  100% { transform: translate(-50%, -50%) scale(.2) translateY(30px); opacity: 0; }
}
@keyframes ball-caught {
  0% { transform: translate(-50%, -50%) scale(1); }
  50% { transform: translate(-50%, -50%) scale(1.15); filter: brightness(1.4); }
  100% { transform: translate(-50%, -50%) scale(1); }
}

/* 13 升级：经验条闪光 + 金色光环扩散 */
@keyframes exp-flash {
  0%, 100% { filter: brightness(1); }
  50% { filter: brightness(2); }
}
@keyframes level-ring {
  0% { box-shadow: 0 0 0 0 rgba(255, 210, 63, .9); transform: scale(.6); opacity: 1; }
  100% { box-shadow: 0 0 0 40px rgba(255, 210, 63, 0); transform: scale(1.4); opacity: 0; }
}

/* 14 进化：白光覆盖 + 交叉淡入 */
@keyframes white-flash {
  0% { opacity: 0; }
  25% { opacity: 1; }
  75% { opacity: 1; }
  100% { opacity: 0; }
}
@keyframes evolve-glow {
  0%, 100% { filter: drop-shadow(0 0 0 #fff); }
  50% { filter: drop-shadow(0 0 24px #fff) brightness(1.4); }
}
.cross-fade-out { animation: cross-out .5s ease forwards; }
.cross-fade-in { animation: cross-in .5s ease both; }
@keyframes cross-out { to { opacity: 0; transform: scale(.9); } }
@keyframes cross-in { from { opacity: 0; transform: scale(1.1); } to { opacity: 1; transform: scale(1); } }

/* 15 徽章：中心旋转放大 + 纸屑 */
@keyframes badge-pop {
  0% { transform: scale(0) rotate(-180deg); }
  60% { transform: scale(1.3) rotate(20deg); }
  100% { transform: scale(1) rotate(0); }
}
@keyframes confetti-fall {
  0% { transform: translateY(-20px) rotate(0); opacity: 1; }
  100% { transform: translateY(calc(var(--fall, 300px))) rotate(720deg) translateX(var(--dx, 0px)); opacity: 0; }
}

/* 16 表情气泡 */
@keyframes bubble-in { from { transform: translate(-50%, -80%) scale(.3); opacity: 0; } to { transform: translate(-50%, -100%) scale(1); opacity: 1; } }
@keyframes bubble-out { to { opacity: 0; transform: translate(-50%, -120%); } }

/* 17 按钮 hover/按下：transition（见 .btn）；打字机由 JS setInterval 实现。 */

/* 通用 */
@keyframes pop-in {
  0% { transform: translate(-50%, -50%) scale(.85); opacity: 0; }
  100% { transform: translate(-50%, -50%) scale(1); opacity: 1; }
}
.battle-sub { animation-name: sub-in; }
@keyframes sub-in { from { transform: translateY(20px); opacity: 0; } to { transform: none; opacity: 1; } }
@keyframes toast-in { from { transform: translateY(-20px) scale(.9); opacity: 0; } to { transform: none; opacity: 1; } }
@keyframes toast-out { to { opacity: 0; transform: translateY(-10px); } }
@keyframes dots { to { width: 0; } }
@keyframes faint {
  0% { transform: translateY(0); opacity: 1; }
  100% { transform: translateY(60px); opacity: 0; }
}
.foe-sprite.faint .sprite-inner { animation: faint-foe .6s ease forwards; }
@keyframes faint-foe {
  0% { transform: scaleX(-1) translateY(0); opacity: 1; }
  100% { transform: scaleX(-1) translateY(60px); opacity: 0; }
}
.foe-sprite.leave .sprite-inner { animation: leave-foe .25s ease forwards; }
@keyframes leave-foe { to { transform: scaleX(-1) scale(.4) translateY(20px); opacity: 0; } }
.foe-sprite.enter .sprite-inner { animation: enter-foe .35s cubic-bezier(.34, 1.56, .64, 1); }
@keyframes enter-foe {
  0% { transform: scaleX(-1) scale(.6) translateY(-20px); opacity: 0; }
  60% { transform: scaleX(-1) scale(1.05) translateY(4px); opacity: 1; }
  100% { transform: scaleX(-1) scale(1) translateY(0); }
}

/* 施放辅助招式：原地弹跳 + 微光 */
.sprite.cast .sprite-inner { animation: cast .4s ease; }
.foe-sprite.cast .sprite-inner { animation: cast-foe .4s ease; }
@keyframes cast {
  0%, 100% { transform: translateY(0) scale(1); filter: brightness(1); }
  40% { transform: translateY(-14px) scale(1.06); filter: brightness(1.25); }
}
@keyframes cast-foe {
  0%, 100% { transform: scaleX(-1) translateY(0) scale(1); filter: brightness(1); }
  40% { transform: scaleX(-1) translateY(-14px) scale(1.06); filter: brightness(1.25); }
}
/* 能力升降：绿光 / 粉光 */
.sprite.buff { animation: glow-up .5s ease; }
.sprite.debuff { animation: glow-down .5s ease; }
@keyframes glow-up { 50% { filter: drop-shadow(0 0 16px var(--grass)) drop-shadow(0 -8px 6px rgba(123, 201, 111, .6)); } }
@keyframes glow-down { 50% { filter: drop-shadow(0 0 16px var(--berry)) drop-shadow(0 8px 6px rgba(242, 109, 133, .6)); } }
/* 道具图标弹出 */
.item-fx {
  position: absolute;
  transform: translate(-50%, -50%);
  animation: item-pop .8s cubic-bezier(.34, 1.56, .64, 1) forwards;
}
@keyframes item-pop {
  0% { transform: translate(-50%, 0) scale(.3); opacity: 0; }
  40% { transform: translate(-50%, -50%) scale(1.15); opacity: 1; }
  80% { transform: translate(-50%, -60%) scale(1); opacity: 1; }
  100% { transform: translate(-50%, -90%) scale(.8); opacity: 0; }
}

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after { animation-duration: .01ms !important; transition-duration: .01ms !important; }
}

/* ============================================================
   补充：战斗菜单 / 面板小组件
   ============================================================ */
.battle { }                                   /* #screen-battle 的语义类，样式由 id 规则承担 */
.dpad-btn.active { background: var(--apricot); transform: scale(.96); }
.net-status[data-status="open"], .net-status[data-status="ok"] { color: var(--grass); }
.net-status[data-status="closed"], .net-status[data-status="error"] { color: var(--berry); }
.move-btn.empty-move { opacity: .35; border-style: dashed; box-shadow: none; background: transparent; justify-content: center; align-items: center; }
.sub-tag {
  margin-left: auto;
  padding: 2px 8px;
  border-radius: 999px;
  background: var(--cream-2);
  border: 2px solid var(--ink);
  font-size: 12px;
  font-weight: 700;
  white-space: nowrap;
}
.sub-empty { grid-column: 1 / -1; align-self: center; text-align: center; color: var(--ink-3); font-weight: 700; }
.sub-item .item-icon { width: 44px; height: 44px; font-size: 20px; }
.wait-label { display: flex; flex-direction: column; align-items: flex-start; gap: 4px; }
.wait-sub { font-size: 14px; font-weight: 400; color: var(--ink-2); }
.reward-caught { display: flex; align-items: center; justify-content: center; gap: 10px; }
.reward-caught svg, .reward-caught .sprite-ph { width: 64px; height: 64px; font-size: 24px; }
.slot-hp { font-family: var(--font-num); font-size: 12px; color: var(--ink-2); }
.tips { margin: 0; padding-left: 18px; font-size: 15px; display: flex; flex-direction: column; gap: 6px; }
.badges.big .badge { width: 44px; height: 44px; font-size: 22px; }
.tip-line { margin-top: 8px; padding: 6px 10px; border-radius: 10px; background: var(--cream); font-weight: 700; font-size: 15px; }
.move-type-mini { padding: 0 6px; border-radius: 999px; background: rgba(255, 255, 255, .55); font-size: 12px; }
.move-power-mini { font-size: 12px; color: var(--ink-2); font-family: var(--font-num); }
.shop-ctrl { flex-basis: 100%; display: flex; align-items: center; gap: 10px; flex-wrap: wrap; justify-content: flex-end; }
.shop-ctrl .btn.primary { min-width: 150px; white-space: nowrap; }
.ending-card { width: min(720px, 100%); margin: 0 auto; color: var(--ink); }
.ending-card h3 { text-align: center; }
.ending-card .ending-table th { color: #B87218; }
.ending-card .ending-table th, .ending-card .ending-table td { border-bottom-color: rgba(46, 58, 75, .15); }
.dex-bar { margin: 0 auto 2px; width: 90px; }
.type-ring text { font-family: var(--font-title); }
.detail .hp-row { margin-top: 10px; }
.detail .exp-bar { margin-top: 8px; }
.detail .status-chip { display: inline-block; margin-top: 6px; }
.exp-text { font-size: 13px; }
.look { font-style: italic; }

/* ============================================================
   手机适配
   ============================================================ */
@media (max-width: 960px), (max-height: 600px) {
  .screen { width: 100vw; height: 100vh; height: 100dvh; }
}
@media (max-width: 900px) {
  .mon-panel { width: 240px; }
  .mon-panel.me { width: 260px; }
  .foe-sprite { right: 120px; }
  .me-sprite { left: 30px; }
  .panel { width: 100vw; height: 100vh; height: 100dvh; border-radius: 0; }
  .dex-grid { grid-template-columns: repeat(4, 1fr); }
}
@media (max-width: 760px) {
  /* 地图屏：顶栏 44px / 舞台自适应 / 底栏按内容高 */
  #screen-map { grid-template-rows: 44px minmax(0, 1fr) auto; }
  #topbar { padding: 0 6px; gap: 6px; font-size: 13px; }
  #topbar .brand { display: none; }
  .online-list { display: none; }
  .code-chip { padding: 2px 6px; }
  .net-status { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; font-size: 12px; }
  .topnav { gap: 4px; }
  .topnav .btn { min-height: 36px; padding: 4px 8px; font-size: 14px; }

  #stage { flex-direction: column; overflow: auto; }
  /* 画布等比缩放到屏幕宽度：640×480 → 100vw × 75vw */
  #map-wrap { flex: none; width: 100%; max-width: 100%; height: auto; aspect-ratio: 4 / 3; border-right: 0; border-bottom: var(--line) solid var(--ink); }
  #map-canvas { width: 100%; height: 100%; }

  /* 右栏 → 地图下方的紧凑横条：第一行 区域 + 金币/徽章，第二行 队伍缩略一行 6 只 */
  #side {
    flex: none;
    display: grid;
    grid-template-columns: 1fr auto;
    gap: 6px;
    padding: 6px;
    overflow: visible;
  }
  .side-block { padding: 4px 8px; border-width: 2px; border-radius: 12px; min-width: 0; }
  #side > .side-block:first-child { grid-column: 1; grid-row: 1; }
  .side-stats { grid-column: 2; grid-row: 1; }
  .party-mini { grid-row: 2; }
  .zone-name { font-size: 15px; line-height: 1.2; }
  .zone-levels { font-size: 12px; line-height: 1.2; }
  .side-stats { gap: 8px; }
  .money { font-size: 15px; }
  .badge { width: 26px; height: 26px; font-size: 13px; border-width: 2px; }
  .party-mini { grid-column: 1 / -1; grid-template-columns: repeat(6, 1fr); gap: 4px; flex: none; }
  .party-mini .mini { flex-direction: column; gap: 1px; padding: 2px; }
  .party-mini .mini svg, .party-mini .mini .sprite-ph { width: 34px; height: 34px; font-size: 14px; }
  .party-mini .mini .mini-info { width: 100%; font-size: 10px; text-align: center; line-height: 1.1; }
  .party-mini .mini .hp-bar { height: 5px; margin-top: 2px; border-width: 1px; }

  /* 底栏：表情一行，对话框整行在下方 */
  #bottombar { flex-wrap: wrap; gap: 6px; padding: 6px; }
  .emotes { flex: none; gap: 6px; }
  .emotes .btn { width: 44px; min-width: 44px; min-height: 44px; }
  .dialog { flex: 1 1 100%; width: 100%; min-width: 0; font-size: 16px; padding: 6px 10px; flex-wrap: wrap; }
  .dialog-text { white-space: normal; word-break: break-word; overflow: visible; }
  .dialog-options { flex-basis: 100%; justify-content: flex-end; }

  /* 方向键：半透明悬浮在地图右下角（#screen-map 为定位上下文，地图底边 = 44px + 75vw） */
  .dpad {
    display: grid;
    position: absolute;
    right: 8px;
    top: calc(44px + 75vw - 146px);
    z-index: 5;
    grid-template-columns: repeat(3, 44px);
    grid-template-rows: repeat(2, 44px);
    gap: 4px;
    opacity: .78;
  }
  .dpad-btn { background: rgba(255, 255, 255, .85); box-shadow: 0 2px 0 rgba(46, 58, 75, .25); }

  #screen-battle { grid-template-rows: 1fr 52px 200px; }
  .mon-panel { width: 200px; padding: 6px 10px; }
  .mon-panel.foe { left: 8px; top: 8px; }
  .mon-panel.me { right: 8px; bottom: 8px; width: 210px; }
  .mon-name { font-size: 16px; }
  .foe-sprite { right: 10px; top: 40px; width: 120px; height: 120px; }
  .me-sprite { left: 10px; bottom: 10px; width: 140px; height: 140px; }
  .battle-field::before { right: 10px; top: 140px; width: 160px; height: 40px; }
  .battle-field::after { left: 6px; width: 200px; height: 46px; }
  .battle-msg { font-size: 16px; min-height: 44px; padding: 4px 12px; margin: 0 8px; }
  .battle-menu { grid-template-columns: 1fr 96px; gap: 6px; padding: 6px 8px 8px; }
  .moves-grid { gap: 6px; }
  .move-btn { padding: 6px 10px; }
  .move-btn .move-name { font-size: 16px; }
  .battle-actions .btn { padding: 4px 6px; font-size: 15px; }
  .battle-sub, .battle-wait { left: 8px; right: 8px; bottom: 8px; height: 186px; }
  .sub-list { grid-template-columns: repeat(2, 1fr); }
  .panel-body { flex-direction: column; overflow: auto; }
  .panel-col, .panel-col.main, .panel-col.aside { flex: none; overflow: visible; }
  .slot-grid { grid-template-columns: repeat(2, 1fr); }
  .box-grid { grid-template-columns: repeat(3, 1fr); }
  .dex-grid { grid-template-columns: repeat(3, 1fr); }
  .result-card { min-width: 260px; padding: 18px 20px; }
}
@media (pointer: coarse) {
  .dpad { display: grid; }
}

@media (max-width: 480px) {
  /* 战斗：窄屏招式格元信息只留属性与 PP */
  .move-btn .move-meta { flex-wrap: wrap; gap: 4px 8px; }
  .move-btn .move-type { white-space: nowrap; }
  .move-btn .move-pp { white-space: nowrap; }
  .move-btn .move-power { display: none; }
  .move-btn .move-eff { width: 26px; height: 26px; font-size: 13px; right: 6px; top: 6px; }
  .foe-sprite { right: 3%; top: 14%; width: 150px; height: 150px; }
  .battle-field::before { right: 2%; top: calc(14% + 128px); width: 200px; height: 44px; }
  .panel-head { font-size: 19px; padding: 10px 12px; gap: 8px; }
  .panel-head .sub { display: none; }
  .panel-body { padding: 10px; gap: 10px; }
  .item-row { padding: 8px 10px; gap: 8px; }
  .item-info { flex-basis: 110px; min-width: 110px; }
  .item-count { min-width: 44px; font-size: 18px; }
  .shop-ctrl { justify-content: flex-start; gap: 8px; }
  .shop-ctrl .btn.primary { min-width: 0; flex: 1 1 100%; }
  .slot-grid { grid-template-columns: repeat(2, 1fr); gap: 8px; }
  .slot { min-height: 64px; padding: 6px 8px; }
  .slot svg, .slot .sprite-ph { width: 44px; height: 44px; }
  .box-grid { grid-template-columns: repeat(2, 1fr); }
  .box-grid .slot svg, .box-grid .slot .sprite-ph { width: 40px; height: 40px; }
  .dex-grid { grid-template-columns: repeat(3, 1fr); gap: 6px; }
  .dex-cell svg, .dex-cell .sprite-ph, .dex-cell.unknown .q { width: 56px; height: 56px; }
  .ring-wrap { flex-direction: column; align-items: flex-start; }
  .stat-grid { grid-template-columns: repeat(2, 1fr); }
  .detail-top svg, .detail-top .sprite-ph { width: 72px; height: 72px; }
  .ending-photo .photo-mon svg, .ending-photo .photo-mon .sprite-ph { width: 64px; height: 64px; }
  .ending-table { font-size: 13px; }
  .ending-table th, .ending-table td { padding: 4px 4px; }
}
