/* ==========================================================================
   components.css —— 通用组件
   ========================================================================== */

/* ---------- 按钮 ---------- */

.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  min-height: 56px;            /* 触屏友好，远超 44px 最小可点区 */
  padding: 0 22px;
  border: 1px solid transparent;
  border-radius: var(--r-btn);
  background: var(--surface);
  box-shadow: var(--sh-1);
  font-size: var(--fs-body);
  font-weight: 600;
  cursor: pointer;
  transition: transform var(--t-fast) var(--ease-out),
              box-shadow var(--t-fast) var(--ease-out),
              background-color var(--t-fast) linear;
}
.btn:active { transform: translateY(1px) scale(.99); }
.btn[disabled] { opacity: .45; cursor: not-allowed; transform: none; }

.btn--primary { background: var(--board); color: var(--chalk); border-color: var(--board); }
.btn--primary:hover:not([disabled]) { box-shadow: var(--sh-2); }

.btn--ghost { background: transparent; border-color: var(--line-2); box-shadow: none; }
.btn--ghost:hover:not([disabled]) { background: var(--surface); }

.btn--warn { background: transparent; border-color: var(--no); color: var(--no); box-shadow: none; }

.btn--block { width: 100%; }
.btn--lg { min-height: 64px; font-size: var(--fs-lg); }

.iconbtn {
  flex: 0 0 auto;
  width: 44px; height: 44px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border: 1px solid transparent;
  border-radius: 12px;
  background: transparent;
  font-size: 1.05rem;
  font-weight: 700;
  cursor: pointer;
  transition: background-color var(--t-fast) linear;
}
.iconbtn:hover { background: rgba(22,32,43,.06); }
.iconbtn[hidden] { display: none; }

/* ---------- 卡片 ---------- */

.card {
  background: var(--surface);
  border: 1px solid var(--line);
  border-radius: var(--r-card);
  box-shadow: var(--sh-2);
  padding: 20px;
}
.card + .card { margin-top: 16px; }

.card__title {
  font-size: var(--fs-lg);
  font-weight: 700;
  margin-bottom: 10px;
}

/* 黑板绿卡：公式卡、结算页、Day7 游戏专用 */
.card--board {
  background: var(--board);
  border-color: var(--board);
  color: var(--chalk);
}
.card--board .card__title { color: #fff; }

/* ---------- 选项（选择题） ---------- */

.opts { display: flex; flex-direction: column; gap: 12px; }

.opt {
  display: flex;
  align-items: center;
  gap: 14px;
  width: 100%;
  min-height: 64px;
  padding: 14px 20px;
  border: 2px solid var(--line);
  border-radius: var(--r-btn);
  background: var(--surface);
  text-align: left;
  font-size: var(--fs-body);
  cursor: pointer;
  transition: border-color var(--t-fast) linear,
              background-color var(--t-fast) linear,
              transform var(--t-fast) var(--ease-out);
}
.opt:hover:not([disabled]) { border-color: var(--line-2); transform: translateX(2px); }
.opt__key {
  flex: 0 0 auto;
  width: 28px; height: 28px;
  display: inline-flex; align-items: center; justify-content: center;
  border-radius: 8px;
  background: var(--bg);
  color: var(--ink-2);
  font-size: var(--fs-mini);
  font-weight: 700;
  font-family: var(--font-num);
}
.opt__text { flex: 1; min-width: 0; word-break: break-word; }
.opt__text.en { font-size: var(--fs-en); }

/* 判定态：正确项保持绿色不消失，错误项保持红色 —— 让孩子看着对比 */
.opt.is-right { border-color: var(--ok); background: #F0FAF5; }
.opt.is-right .opt__key { background: var(--ok); color: #fff; }
.opt.is-wrong { border-color: var(--no); background: #FDF1EC; }
.opt.is-wrong .opt__key { background: var(--no); color: #fff; }
.opt.is-dim { opacity: .5; }
.opt[disabled] { cursor: default; }

/* ---------- 判断题大按钮 ---------- */

.bigchoices { display: flex; gap: 14px; }
.bigchoice {
  flex: 1;
  min-height: 96px;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 6px;
  border: 3px solid var(--line);
  border-radius: var(--r-card);
  background: var(--surface);
  font-size: var(--fs-lg);
  font-weight: 700;
  cursor: pointer;
  transition: border-color var(--t-fast) linear,
              background-color var(--t-fast) linear,
              transform var(--t-fast) var(--ease-out);
}
.bigchoice:active { transform: scale(.985); }
.bigchoice:hover:not([disabled]) { border-color: var(--line-2); }
.bigchoice__sub { font-size: var(--fs-mini); font-weight: 500; color: var(--ink-2); }
.bigchoice.is-right { border-color: var(--ok); background: #F0FAF5; }
.bigchoice.is-wrong { border-color: var(--no); background: #FDF1EC; }
.bigchoice[disabled] { cursor: default; }

/* ---------- 词块（点选拼装用） ---------- */

.pool {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  min-height: 56px;
  padding: 12px;
  border: 2px dashed var(--line);
  border-radius: var(--r-card);
  background: var(--surface-2);
}

.chip {
  display: inline-flex;
  align-items: center;
  min-height: 48px;
  padding: 10px 18px;
  border: 2px solid var(--line-2);
  border-radius: var(--r-chip);
  background: var(--surface);
  box-shadow: var(--sh-1);
  font-size: var(--fs-body);
  font-family: var(--font-en);
  cursor: pointer;
  transition: transform var(--t-fast) var(--ease-out),
              border-color var(--t-fast) linear,
              opacity var(--t-fast) linear;
}
.chip:hover { transform: translateY(-2px); }
.chip:active { transform: translateY(0) scale(.97); }
.chip[disabled] { opacity: .4; cursor: default; transform: none; }

/* FLIP 飞入用：先给元素一个过渡，再由 JS 改 transform */
.chip.is-flying { transition: transform var(--t-slow) var(--ease-out); z-index: 5; }

/* ---------- 槽位（排序题） ---------- */

.slots { display: flex; flex-direction: column; gap: 10px; }

.slot {
  display: flex;
  align-items: center;
  gap: 12px;
  min-height: 64px;
  padding: 10px 16px;
  border: 2px dashed var(--line-2);
  border-radius: var(--r-slot);
  background: var(--surface);
  transition: border-color var(--t) linear, box-shadow var(--t) linear, background-color var(--t) linear;
}
.slot__label {
  flex: 0 0 auto;
  min-width: 68px;
  font-size: var(--fs-mini);
  font-weight: 700;
  color: var(--ink-3);
}
.slot__body {
  flex: 1;
  min-width: 0;
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  min-height: 40px;
  align-items: center;
}
.slot__hint { color: var(--ink-3); font-size: var(--fs-label); }

/* 每个槽位有自己的识别色 —— 孩子靠颜色记位置，不靠术语 */
.slot--action { border-color: var(--c-action); }
.slot--manner { border-color: var(--c-manner); }
.slot--place  { border-color: var(--c-place);  }
.slot--time   { border-color: var(--c-time);   }
.slot--action .slot__label { color: var(--c-action-ink); }
.slot--manner .slot__label { color: var(--c-manner-ink); }
.slot--place  .slot__label { color: var(--c-place-ink);  }
.slot--time   .slot__label { color: var(--c-time-ink);   }

/* 放对了：实线 + 同色光晕 */
.slot.is-filled { border-style: solid; background: var(--surface); }
.slot.is-filled.slot--action { box-shadow: 0 0 0 3px var(--c-action-bg); }
.slot.is-filled.slot--manner { box-shadow: 0 0 0 3px var(--c-manner-bg); }
.slot.is-filled.slot--place  { box-shadow: 0 0 0 3px var(--c-place-bg);  }
.slot.is-filled.slot--time   { box-shadow: 0 0 0 3px var(--c-time-bg);   }
.slot.is-bad { border-color: var(--no) !important; box-shadow: 0 0 0 3px #FDF1EC !important; }

/* 槽位里已放入的块 */
.tok {
  display: inline-flex;
  align-items: center;
  padding: 8px 14px;
  border-radius: var(--r-chip);
  background: var(--bg);
  border: 1px solid var(--line-2);
  font-family: var(--font-en);
  cursor: pointer;
}
.tok[disabled] { cursor: default; }

/* ---------- 成分着色工具类（全站统一） ---------- */

.k-action { background: var(--c-action-bg); color: var(--c-action-ink); border-color: var(--c-action); }
.k-manner { background: var(--c-manner-bg); color: var(--c-manner-ink); border-color: var(--c-manner); }
.k-place  { background: var(--c-place-bg);  color: var(--c-place-ink);  border-color: var(--c-place);  }
.k-time   { background: var(--c-time-bg);   color: var(--c-time-ink);   border-color: var(--c-time);   }
.k-be     { background: var(--c-be-bg);     color: var(--c-be-ink);     border-color: var(--c-be);     }
.k-trigger{ background: var(--c-trigger-bg);color: var(--c-trigger-ink);border-color: var(--c-trigger);}

/* ---------- 字格（圈触发字） ---------- */

.chars { display: flex; flex-wrap: wrap; gap: 8px; }
.char {
  width: 52px; height: 52px;
  display: inline-flex; align-items: center; justify-content: center;
  border: 2px solid var(--line-2);
  border-radius: var(--r-slot);
  background: var(--surface);
  font-size: var(--fs-lg);
  cursor: pointer;
  transition: transform var(--t-fast) var(--ease-out),
              border-color var(--t-fast) linear,
              background-color var(--t-fast) linear;
}
.char:hover { transform: translateY(-2px); }
.char.is-on {
  border-color: var(--c-trigger);
  background: var(--c-trigger-bg);
  color: var(--c-trigger-ink);
  font-weight: 700;
}
.char.is-right { border-color: var(--ok); background: #F0FAF5; }
.char.is-miss  { border-color: var(--no); background: #FDF1EC; }
.char.is-extra { border-color: var(--no); background: #FDF1EC; opacity: .7; }

/* ---------- 英文句子（可点读） ---------- */

.en-sentence { font-family: var(--font-en); font-size: var(--fs-en); line-height: 1.9; }
.en-sentence .w {
  cursor: pointer;
  border-radius: 5px;
  padding: 1px 2px;
  transition: background-color var(--t-fast) linear;
}
.en-sentence .w:hover { background: rgba(47,107,216,.12); }
.en-sentence .w.is-speaking {
  background: linear-gradient(transparent 60%, rgba(47,107,216,.35) 60%);
  background-size: 100% 100%;
}
.speak {
  display: inline-flex; align-items: center; justify-content: center;
  width: 44px; height: 44px;
  margin-left: 8px;
  border: 1px solid var(--line-2);
  border-radius: 50%;
  background: var(--surface);
  cursor: pointer;
  vertical-align: middle;
  transition: background-color var(--t-fast) linear;
}
.speak:hover:not([disabled]) { background: var(--bg); }
.speak[disabled] { opacity: .38; cursor: not-allowed; }

/* 音节切分降级（没有英语语音包时显示） */
.syl { font-family: var(--font-num); color: var(--ink-2); font-size: var(--fs-label); }

/* ---------- 进度条 ---------- */

.bar {
  height: 10px;
  border-radius: 999px;
  background: var(--line);
  overflow: hidden;
}
.bar__in {
  height: 100%;
  width: 0;
  border-radius: 999px;
  background: var(--board);
  transition: width var(--t-slow) var(--ease-out);
}

/* ---------- 星星 ---------- */

.stars { display: inline-flex; gap: 2px; font-size: 1.1rem; line-height: 1; }
.star { color: var(--line-2); }
.star.is-on { color: var(--warn); }

/* ---------- 标签 ---------- */

.tag {
  display: inline-flex; align-items: center;
  height: 24px; padding: 0 10px;
  border-radius: var(--r-chip);
  background: var(--bg);
  border: 1px solid var(--line);
  font-size: var(--fs-mini);
  color: var(--ink-2);
}
.tag--challenge { background: #FFF6E5; border-color: var(--warn); color: #8A5B00; }

/* ---------- 抽屉 ---------- */

.sheet { position: fixed; inset: 0; z-index: 60; }
.sheet[hidden] { display: none; }
.sheet__mask {
  position: absolute; inset: 0;
  background: rgba(22,32,43,.42);
  opacity: 0;
  transition: opacity var(--t) linear;
}
.sheet.is-open .sheet__mask { opacity: 1; }
.sheet__panel {
  position: absolute; left: 0; right: 0; bottom: 0;
  max-height: 88vh;
  max-height: 88dvh;
  display: flex; flex-direction: column;
  background: var(--surface);
  border-radius: 22px 22px 0 0;
  box-shadow: var(--sh-3);
  transform: translateY(24px);
  opacity: 0;
  transition: transform var(--t-slow) var(--ease-out), opacity var(--t) linear;
  padding-bottom: env(safe-area-inset-bottom);
}
.sheet.is-open .sheet__panel { transform: translateY(0); opacity: 1; }
.sheet__grab {
  width: 44px; height: 4px; border-radius: 999px;
  background: var(--line-2);
  margin: 10px auto 0;
}
.sheet__head {
  display: flex; align-items: center; gap: 10px;
  padding: 8px 12px 8px 20px;
  border-bottom: 1px solid var(--line);
}
.sheet__title { flex: 1; font-size: var(--fs-lg); font-weight: 700; }
.sheet__body { padding: 20px; overflow-y: auto; -webkit-overflow-scrolling: touch; }

@media (min-width: 720px) {
  .sheet__panel {
    left: 50%; right: auto; bottom: auto;
    top: 50%;
    width: min(640px, 92vw);
    max-height: 84vh;
    border-radius: var(--r-card);
    transform: translate(-50%, calc(-50% + 16px));
  }
  .sheet.is-open .sheet__panel { transform: translate(-50%, -50%); }
  .sheet__grab { display: none; }
}

/* ---------- Toast ---------- */

.toasts {
  position: fixed; left: 0; right: 0; bottom: calc(var(--bottom-h) + 20px);
  z-index: 80;
  display: flex; flex-direction: column; align-items: center; gap: 8px;
  pointer-events: none;
}
.toast {
  max-width: min(520px, 88vw);
  padding: 12px 20px;
  border-radius: var(--r-chip);
  background: rgba(22,32,43,.94);
  color: #fff;
  font-size: var(--fs-label);
  box-shadow: var(--sh-3);
  animation: toastIn var(--t) var(--ease-out);
}
.toast.is-out { animation: toastOut var(--t) var(--ease-out) forwards; }

@keyframes toastIn  { from { opacity: 0; transform: translateY(12px); } to { opacity: 1; transform: none; } }
@keyframes toastOut { to   { opacity: 0; transform: translateY(8px); } }

/* ---------- 表单 ---------- */

.field { margin-bottom: 16px; }
.field__label { display: block; font-size: var(--fs-label); color: var(--ink-2); margin-bottom: 6px; }
.input, .textarea {
  width: 100%;
  padding: 12px 14px;
  border: 2px solid var(--line);
  border-radius: var(--r-btn);
  background: var(--surface);
  font: inherit;
  color: var(--ink);
}
.textarea { min-height: 110px; resize: vertical; font-family: var(--font-num); font-size: var(--fs-mini); }
.input:focus, .textarea:focus { border-color: var(--focus); outline: none; }

.switch {
  display: inline-flex; align-items: center; gap: 10px;
  cursor: pointer; user-select: none;
}
.switch input { width: 20px; height: 20px; accent-color: var(--board); }

/* ---------- 杂项 ---------- */

.row { display: flex; align-items: center; gap: 12px; }
.row--between { justify-content: space-between; }
.row--wrap { flex-wrap: wrap; }
.muted { color: var(--ink-2); }
.mini { font-size: var(--fs-mini); }
.mt-8 { margin-top: 8px; }
.mt-16 { margin-top: 16px; }
.mt-24 { margin-top: 24px; }
.stack > * + * { margin-top: 14px; }
