/* 波波乐园 · workbook question types (js/types-book.js) */
.bk-wrap{display:grid;grid-template-columns:repeat(auto-fit,minmax(min(100%,250px),1fr));gap:clamp(12px,2vw,24px);align-items:center}
.bk-wrap.nopic{grid-template-columns:1fr}
.bk-wrap.wide{grid-template-columns:repeat(auto-fit,minmax(min(100%,280px),1fr))}
/* Fill the board window; always contain — never crop the workbook art. */
.bk-pic{position:relative;margin:0;border:4px solid var(--ink);border-radius:20px;overflow:hidden;background:#fff;box-shadow:0 6px 0 var(--ink);aspect-ratio:var(--ar);max-height:min(58dvh,560px);justify-self:center;width:100%;max-width:min(100%,calc(min(58dvh,560px) * var(--ar)));transition:transform .3s cubic-bezier(.3,1.6,.5,1);animation:bkPicIn .5s cubic-bezier(.3,1.5,.5,1)}
.bk-pic img{display:block;width:100%;height:100%;object-fit:contain;object-position:center;user-select:none;-webkit-user-drag:none}
.bk-pic:hover{transform:rotate(-1.2deg) scale(1.02)}
.bk-pic.zoomable{cursor:zoom-in}
.bk-pic.big{max-height:min(64dvh,640px);max-width:min(100%,calc(min(64dvh,640px) * var(--ar)))}
#stage.with-sheet .bk-pic{max-height:min(48dvh,420px);max-width:min(100%,calc(min(48dvh,420px) * var(--ar)))}
@keyframes bkPicIn{from{transform:scale(.85) rotate(-3deg);opacity:0}}
.bk-zoom{position:absolute;right:6px;bottom:6px;width:34px;height:34px;border-radius:50%;border:3px solid var(--ink);background:#fff;font-size:18px;line-height:1;cursor:zoom-in;opacity:.85}
.bk-lightbox{position:fixed;inset:0;z-index:600;background:rgba(20,20,30,.72);display:grid;place-items:center;padding:16px;animation:fadeIn .2s}
.bk-lightbox img{max-width:min(94vw,1400px);max-height:88vh;border:5px solid var(--ink);border-radius:20px;background:#fff;animation:bpop .35s cubic-bezier(.3,1.6,.5,1)}
.bk-lightbox span{color:#fff;font-weight:700;margin-top:-30px}
.bk-lightbox.out{opacity:0;transition:opacity .25s}
.bk-card{background:#fff;border:4px solid var(--ink);border-radius:22px;box-shadow:0 6px 0 var(--ink);padding:clamp(12px,1.8vw,20px);display:grid;gap:10px;justify-items:start}
.bk-sent{display:grid;gap:8px;width:100%}
.bk-line{margin:0;font:700 clamp(26px,3vw,36px)/1.5 var(--f-num);color:var(--ink);display:flex;flex-wrap:wrap;align-items:center;gap:4px 6px}
.bk-blank{position:relative;display:inline-grid;place-items:center;min-width:110px;min-height:46px;padding:0 12px;border:4px dashed var(--coral);border-radius:14px;background:#fff8ee;vertical-align:middle}
.bk-blank .bk-fill{font:800 clamp(24px,2.8vw,34px) var(--f-num);color:#1d8a52}
.bk-blank .bk-peek{position:absolute;font:800 clamp(24px,2.8vw,34px) var(--f-num);color:var(--coral);opacity:.55;pointer-events:none}
.bk-blank.filled .bk-peek{display:none}
.bk-blank.yes .bk-fill{animation:bkPop .5s cubic-bezier(.3,1.8,.5,1)}
@keyframes bkPop{0%{transform:scale(.3)}60%{transform:scale(1.25)}}
.bk-choice{display:inline-flex;align-items:center;gap:4px;background:#fff8ee;border:3px dashed #e6c58f;border-radius:14px;padding:2px 6px}
.bk-choice i{font-style:normal;color:#b9a17a}
.bk-opt{position:relative;border:3px solid var(--ink);border-radius:12px;background:#fff;font:800 clamp(22px,2.6vw,30px) var(--f-num);padding:4px 14px;cursor:pointer;box-shadow:0 3px 0 var(--ink);transition:transform .15s}
.bk-opt:hover{transform:translateY(-3px)}
.bk-opt.pick{background:#dcf8e8;border-color:#1f8f55}
.bk-opt.pick::after{content:'';position:absolute;left:8%;right:8%;bottom:-7px;height:5px;border-radius:5px;background:var(--good);animation:bkLine .4s ease-out both}
@keyframes bkLine{from{transform:scaleX(0)}}
.bk-opt.nope{animation:nope .45s;background:#ffe1e1}
.bk-choice.done .bk-opt:not(.pick){opacity:.35;pointer-events:none}
.bk-speak{display:inline-flex;align-items:center;gap:6px;border:3px solid var(--ink);border-radius:999px;background:var(--sky);padding:5px 16px 5px 9px;font:700 16px var(--f-body);cursor:pointer;box-shadow:0 3px 0 var(--ink)}
.bk-speak svg{width:22px;height:22px}
.bk-speak:active{transform:translateY(2px);box-shadow:0 1px 0 var(--ink)}
.bk-note{font-size:15px;color:#8a6a3a;text-align:center;margin:6px 0 0}
.bk-tray.cards{display:grid;grid-template-columns:repeat(auto-fit,minmax(min(100%,260px),1fr))}
.bk-tray .chip.word{font-size:clamp(22px,2.5vw,30px)}
.bk-tray.cards .chip{flex-direction:row;justify-content:flex-start;gap:10px;text-align:left}
.bk-let{display:grid;place-items:center;width:30px;height:30px;flex:none;border-radius:50%;background:var(--hair);border:3px solid var(--ink);font:800 16px var(--f-num)}
.bk-tip{margin:0;font-size:15px;font-weight:700;color:#8a7a68}
/* build */
.bk-bubble{position:relative;margin:0;background:#fff7dc;border:3px solid var(--ink);border-radius:18px;padding:8px 14px;font:700 clamp(21px,2.5vw,28px) var(--f-num)}
.bk-bubble small{display:block;font:600 13px var(--f-body);color:#7a6a58}
.bk-bubble.big{font-size:clamp(26px,3vw,36px)}
.bk-slots{display:flex;flex-wrap:wrap;gap:8px;width:100%}
.bk-slot{position:relative;display:inline-grid;place-items:center;min-width:72px;min-height:50px;padding:0 10px;border:4px dashed #c9b48a;border-radius:14px;background:#fffaf0}
.bk-slot.first{border-color:var(--coral)}
.bk-slot .bk-fill{font:800 clamp(21px,2.5vw,30px) var(--f-num);color:#1d8a52}
.bk-slot .bk-peek{position:absolute;font:800 clamp(21px,2.5vw,30px) var(--f-num);color:var(--coral);opacity:.5;pointer-events:none}
.bk-slot.filled .bk-peek{display:none}
.bk-slot.yes .bk-fill{animation:bkPop .5s cubic-bezier(.3,1.8,.5,1)}
/* pairs */
.bk-pairs{position:relative;display:grid;grid-template-columns:1fr 1fr;gap:clamp(30px,8vw,110px);touch-action:none}
.bk-ropes{position:absolute;left:0;top:0;pointer-events:none;overflow:visible;z-index:2}
.bk-ropes path{fill:none;stroke-width:6;stroke-linecap:round}
.bk-ropes path.done{stroke:var(--c,#2fbf71);animation:bkRope .4s ease-out}
.bk-ropes path.live{stroke:#2b1d14;stroke-dasharray:10 8;stroke-width:5}
.bk-ropes path.bad{stroke:var(--bad);stroke-dasharray:6 6}
@keyframes bkRope{from{stroke-width:14}}
.bk-col{display:grid;gap:10px;align-content:center}
.bk-node{position:relative;display:flex;align-items:center;justify-content:center;min-height:58px;background:#fff;border:4px solid var(--ink);border-radius:16px;box-shadow:0 4px 0 var(--ink);padding:6px 12px;font:700 clamp(17px,2vw,23px)/1.25 var(--f-num);cursor:pointer;transition:transform .15s,background .2s}
.bk-node.img{padding:4px}
.bk-pairs.many .bk-col{gap:8px}.bk-pairs.many .bk-node img{max-height:clamp(46px,8.5vh,96px)}
.bk-node.img{justify-self:center;min-width:120px}
.bk-node img{display:block;max-width:100%;max-height:clamp(56px,10vh,110px);border-radius:10px;pointer-events:none}
.bk-dot{position:absolute;top:50%;width:18px;height:18px;margin-top:-9px;border-radius:50%;background:var(--hair);border:3px solid var(--ink)}
.bk-node.l .bk-dot{right:-12px}.bk-node.r .bk-dot{left:-12px}
.bk-node.l{cursor:grab}
.bk-node.active{transform:scale(1.04);background:#fff7dc}
.bk-node.hover{transform:scale(1.05);background:#fff3c4}
.bk-node.yes{background:#dcf8e8;border-color:#1f8f55;cursor:default}
.bk-node.yes .bk-dot{background:var(--good)}
.bk-node.nope{animation:nope .45s;background:#ffe1e1}
/* judge */
.bk-judge{justify-items:stretch}
.bk-who{font:400 22px var(--f-display)}
.bk-paper{display:grid;place-items:center;min-height:96px;border:4px dashed #c9b48a;border-radius:18px;background:repeating-linear-gradient(#fffdf6 0 26px,#eef4ff 26px 28px);font-weight:700;color:#a0907a}
.bk-ink{font:900 64px/1 var(--f-num);animation:bkStamp .35s cubic-bezier(.3,1.6,.5,1)}
.bk-ink.ok{color:var(--good)}.bk-ink.no{color:var(--bad)}.bk-ink.big{font-size:80px}
@keyframes bkStamp{from{transform:scale(2.4) rotate(-20deg);opacity:0}}
.bk-stamp{font:900 40px/1 var(--f-num)!important;min-width:96px}
.bk-stamp.ok{color:var(--good)}.bk-stamp.no{color:var(--bad)}
/* learn */
.bk-learn{display:grid;grid-template-columns:repeat(auto-fit,minmax(min(100%,280px),1fr));gap:clamp(12px,2vw,24px);align-items:center}
.bk-lines{display:grid;gap:10px}
.bk-say{display:grid;grid-template-columns:1fr auto;align-items:center;text-align:left;gap:2px 10px;background:#fff;border:4px solid var(--ink);border-radius:20px 20px 20px 6px;box-shadow:0 4px 0 var(--ink);padding:8px 12px;cursor:pointer;transition:transform .2s cubic-bezier(.3,1.7,.5,1)}
.bk-say:hover{transform:translateY(-3px) rotate(-1deg)}
.bk-say .bk-en{font:800 clamp(22px,2.6vw,30px) var(--f-num)}
.bk-say .bk-zh{grid-column:1;font:600 16px var(--f-body);color:#7a6a58}
.bk-say i{grid-row:1/3;grid-column:2;width:40px;height:40px;border-radius:50%;background:var(--sky);border:3px solid var(--ink);display:grid;place-items:center}
.bk-say i svg{width:22px;height:22px}
.bk-say.heard{background:#eefbf3}.bk-say.heard i{background:var(--good);color:#fff}
.bk-notecard{margin:0;background:#fff7dc;border:3px dashed var(--ink);border-radius:14px;padding:8px 12px;font:700 15px var(--f-body)}
.bk-notecard b{display:inline-block;margin-right:8px;background:var(--hair);border:2px solid var(--ink);border-radius:8px;padding:0 6px}
.bk-got{justify-self:start;opacity:.5}.bk-got.ready{opacity:1;animation:bkReady 1s ease-in-out infinite alternate}
@keyframes bkReady{to{transform:scale(1.06)}}
/* explanation sheet */
.bk-dm{display:grid;gap:10px;justify-items:center}
.bk-dimg{max-width:min(260px,100%);max-height:150px;border:3px solid var(--ink);border-radius:14px;background:#fff}
.bk-dsent{font:700 23px/1.5 var(--f-num);text-align:center}
.bk-dsent .bk-line{font-size:23px;justify-content:center}
.bk-ans{display:inline-block;background:#dcf8e8;border:3px solid #1f8f55;border-radius:10px;padding:0 8px;color:#1d8a52}
.bk-whyline s{color:var(--bad);text-decoration-thickness:3px}
.bk-train{display:flex;flex-wrap:wrap;gap:6px;justify-content:center}
.bk-car{background:#fff;border:3px solid var(--ink);border-radius:10px;padding:2px 10px;font:800 18px var(--f-num);box-shadow:0 3px 0 var(--ink)}
.bk-plist{justify-items:stretch}
.bk-prow{display:grid;grid-template-columns:1fr auto 1fr;gap:8px;align-items:center;font:700 14px var(--f-num)}
.bk-prow img{max-height:54px;border:2px solid var(--ink);border-radius:8px}
@media (max-width:760px){
  .bk-wrap,.bk-wrap.wide,.bk-learn{grid-template-columns:1fr}
  .bk-pic{max-height:min(48dvh,360px);max-width:min(100%,calc(min(48dvh,360px) * var(--ar)))}
  .bk-pairs{gap:26px}
  .bk-node{min-height:48px;font-size:16px}
}
.bk-line.solo .bk-blank{min-width:min(100%,420px);min-height:52px}

/* ---------- hover zoom ---------- */
.bk-pic,.bk-node.img,.bk-dimg,.bk-prow img{cursor:zoom-in}
.bk-node.img.l{cursor:grab}
.bk-peekimg{position:fixed;z-index:450;pointer-events:none;border:5px solid var(--ink);border-radius:20px;background:#fff;box-shadow:8px 10px 0 rgba(43,29,20,.35);overflow:hidden;animation:bkPeek .22s cubic-bezier(.3,1.5,.5,1)}
.bk-peekimg img{width:100%;height:100%;object-fit:contain;display:block}
.bk-peekimg.out{animation:bkPeekOut .18s ease-in forwards}
@keyframes bkPeek{from{transform:scale(.55);opacity:0}}
@keyframes bkPeekOut{to{transform:scale(.6);opacity:0}}

/* ---------- arrivals: pieces pop in one after another, then breathe a little ---------- */
.bk-tray .chip{animation:bkChipIn .5s cubic-bezier(.3,1.6,.5,1) both,bkIdle 3.4s ease-in-out infinite;animation-delay:calc(var(--i,0) * 70ms + .25s),calc(var(--i,0) * .37s + 1s)}
.bk-tray .chip.used,.bk-tray .chip.lifted,.chip.ghost{animation:none!important}
@keyframes bkChipIn{from{scale:.3;opacity:0;translate:0 40px}}
@keyframes bkIdle{0%,100%{translate:0 0}50%{translate:0 -4px}}
.bk-node{animation:bkNodeIn .45s cubic-bezier(.3,1.6,.5,1) both;animation-delay:calc(var(--i,0) * 60ms + .15s)}
@keyframes bkNodeIn{from{scale:.6;opacity:0}}
.bk-say{animation:bkNodeIn .45s cubic-bezier(.3,1.6,.5,1) both;animation-delay:calc(var(--i,0) * 90ms + .2s)}
.bk-opt{animation:bkNodeIn .4s cubic-bezier(.3,1.6,.5,1) both;animation-delay:calc(var(--i,0) * 60ms + .2s)}
.bk-blank:not(.yes):not(.nope),.bk-slot:not(.yes):not(.nope){animation:bkWait 1.8s ease-in-out infinite;animation-delay:calc(var(--i,0) * .3s)}
@keyframes bkWait{50%{border-color:var(--coral);background:#fff3ea}}
.bk-blank.hover,.bk-slot.hover{scale:1.08;transition:scale .15s}
.bk-tray .chip:hover{rotate:-2deg}
.bk-opt:hover{transform:translateY(-3px)}
.bk-opt:active{transform:translateY(2px);box-shadow:0 1px 0 var(--ink)}
.bk-say:active{scale:.96}
.bk-say.heard i{animation:bkPop .5s cubic-bezier(.3,1.8,.5,1)}
.bk-paper:has(.bk-ink){animation:bkThud .35s ease-out}
@keyframes bkThud{30%{transform:translateY(4px) scale(.98)}}

/* ---------- solved: the card jumps, the sentence does a wave ---------- */
.bk-win{animation:bkWin .7s cubic-bezier(.3,1.6,.5,1)}
@keyframes bkWin{30%{transform:translateY(-10px) scale(1.03)}60%{transform:translateY(2px) scale(.99)}}
.bk-card.bk-win{box-shadow:0 0 0 6px rgba(47,191,113,.35),0 6px 0 var(--ink)}
.bk-w{display:inline-block}
.bk-win .bk-w,.bk-win .bk-line>.bk-blank,.bk-win .bk-line>.bk-choice{animation:bkWave .55s ease-out both;animation-delay:calc(var(--k,0) * 70ms + .2s)}
@keyframes bkWave{40%{transform:translateY(-12px);color:#1d8a52}}
@media (prefers-reduced-motion:reduce){.bk-tray .chip,.bk-node,.bk-say,.bk-opt,.bk-blank,.bk-slot,.bk-win,.bk-win .bk-w{animation:none!important}}
.bk-blank-number{display:inline-grid;place-items:center;width:24px;height:24px;background:#ffe08b;border:2px solid var(--ink);border-radius:50%;font:800 15px var(--f-num);color:var(--ink)}
.bk-blank{display:inline-flex;gap:6px;cursor:pointer}.bk-blank.active{outline:3px solid #f6bf49;outline-offset:3px;background:#fff0c8}.bk-option-target{font-weight:700;margin:14px 0 8px;font-size:16px}
/* long tap options (sentences, phrases) wrap inside the line instead of pushing the card wider */
.bk-choice{flex-wrap:wrap;max-width:100%;row-gap:6px;vertical-align:middle}
.bk-choice .bk-opt{white-space:normal;text-align:left;max-width:100%;overflow-wrap:anywhere}
.bk-sent .bk-line{overflow-wrap:anywhere}
.bk-pairs{grid-template-columns:minmax(0,1fr) minmax(0,1fr)}
.bk-col{min-width:0}
