zz birthday mix chunk 4 of 5 (Claude, hidden, do not edit)
Keep');tone(600,.15,.05)};
$('#toCake').onclick=()=⟩go('cake');$('#toWish').onclick=()=⟩go('wish');
/* ---------- mix code: song, layers, name, up to 40 taps ---------- */
const B36='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ';
function makeCode(){const layerBits=song.layers.map(l=⟩l.on&&!l.err?'1':'0').join('');const tp=taps.map(t=⟩t[0]+B36[Math.min(35,Math.round(t[1]*4)%36)]+B36[Math.floor(Math.round(t[1]*4)/36)]).join('');return 'BMX-'+song.k+layerBits+'-'+(tp||'0')}
function parseCode(c){c=String(c||'').trim().toUpperCase().replace(/\s+/g,'');const m=c.match(/^BMX-([TS])([01]+)-([0-9A-Z]+)$/);if(!m)return null;const s=SONGS.find(x=⟩x.k===m[1]);if(!s)return null;const bits=m[2];const list=[];if(m[3]!=='0'){if(m[3].length%3)return null;for(let i=0;i+2⟨m[3].length;i+=3){const k=m[3][i],lo=B36.indexOf(m[3][i+1]),hi=B36.indexOf(m[3][i+2]);if(!playSfx[k]||lo⟨0||hi⟨0)return null;list.push([k,(hi*36+lo)/4,1])}}return {s,bits,list}}
$('#codeBtn').onclick=()=⟩{const c=makeCode();st.code=c;st.name=esc($('#mixName').value.trim());save();taps=taps.map(t=⟩[t[0],t[1],1]);$('#codeTxt').textContent=(st.name?st.name+' · ':'')+c;$('#codeOut').hidden=false;$('#loadBox').hidden=true;tone(880,.3,.08);burst(80)};
$('#loadBtn').onclick=()=⟩{$('#loadBox').hidden=false;$('#codeOut').hidden=true;$('#codeIn').focus()};
$('#codeGo').onclick=()=⟩{const r=parseCode($('#codeIn').value);if(!r){$('#loadMsg').textContent='That code is shy. Check the letters and try again.';return}stop();song=r.s;song.layers.forEach((l,i)=⟩{l.on=r.bits[i]==='1'});taps=r.list.map(t=⟩[t[0],t[1],1]);renderSongs();renderLayers();dots();$('#loadMsg').textContent='Loaded. Tap the record to hear it, '+taps.length+' Bacci sounds included.';tone(784,.3,.08)};
/* ---------- cake ---------- */
const BODY=[['Chocolate','🍫','#6b3e26'],['Vanilla','🍦','#f7e2b0'],['Strawberry','🍓','#ff9fc0'],['Fruit rainbow','🌈','linear-gradient(180deg,#ff9a9e,#fad0c4 40%,#a1c4fd 70%,#c2e9fb)'],['Something new','✨','#c9a6ff']];
const MIND=[['Calm','🌙'],['Silly','🤪'],['Brave','🦁'],['Proud','🏆'],['Curious','🔭']];
const SOUL=[['My friends','👯'],['My family','🏡'],['Quiet time','🫖'],['An adventure','🗺️'],['Everyone I love','💛']];
function pick(id,list,key){$('#'+id).innerHTML=list.map(o=⟩`⟨button class="chip" type="button" data-v="${o[0]}" aria-pressed="${st[key]===o[0]}"⟩${o[1]} ${o[0]}⟨/button⟩`).join('');$$('#'+id+' .chip').forEach(b=⟩b.onclick=()=⟩{st[key]=b.dataset.v;save();$$('#'+id+' .chip').forEach(x=⟩x.setAttribute('aria-pressed',x.dataset.v===st[key]));b.scrollIntoView({block:'nearest',inline:'center',behavior:reduce?'auto':'smooth'});tone(600,.15,.06);cakeRender(true)})}
pick('pickBody',BODY,'body');pick('pickMind',MIND,'mind');pick('pickSoul',SOUL,'soul');
let lit=true;
const stg=$('#cakeStage'),cw=$('#cakeWrap');function cakeFit(){const h=stg.clientHeight-18;const sc=Math.max(.55,Math.min(1,h/196));cw.style.setProperty('--cs',sc.toFixed(3))}try{new ResizeObserver(cakeFit).observe(stg)}catch(e){addEventListener('resize',cakeFit)}cakeFit();
[stage,...$$('.scene'),...$$('.ui')].forEach(el=⟩el.addEventListener('scroll',()=⟩{el.scrollTop=0;el.scrollLeft=0}));
function cakeRender(fromTap){const b=BODY.find(x=⟩x[0]===st.body);const col=b?b[2]:'#8b5a3c';const mi=MIND.findIndex(x=⟩x[0]===st.mind);const frost=['#fff','#fff0f5','#e6fbff','#fff3cf','#efe6ff'][mi⟨0?0:mi];$$('.tier').forEach(t=⟩{t.style.setProperty('--col',col);t.style.setProperty('--frost',frost)});$('#cakeArt').classList.toggle('sprinkles',!!st.soul);$('#cakeBadge').textContent=st.mind?st.mind+' cake':'Dream Cake';if(st.body&&st.mind&&st.soul){$('#cakeWish').textContent=`My Dream Cake is a ${st.body.toLowerCase()} cake with a ${st.mind.toLowerCase()} feeling, shared with ${st.soul.toLowerCase()}.`;if(fromTap)burst(70)}else{$('#cakeWish').textContent='Tap your three wishes and your Dream Cake appears.'}}
cakeRender(false);
function blow(){const c=$('#cakeArt');if(lit){lit=false;c.classList.add('out');playSfx[5]();setTimeout(()=⟩{tone(523,.3,.08);tone(659,.4,.08);burst(110)},500);$('#cakeHint').textContent='You did it! Make a wish, then tap again to light the candles.'}else{lit=true;c.classList.remove('out');playSfx[1]();$('#cakeHint').textContent='Tap the cake to blow out the candles'}}
$('#cakeStage').onclick=blow;$('#cakeStage').onkeydown=e=⟩{if(e.key==='Enter'||e.key===' '){e.preventDefault();blow()}};
$('#toRecipe').onclick=()=⟩{openSheet('shRecipe');tone(600,.15,.05)};
$('#printBtn').onclick=()=⟩{$('#printCard').innerHTML='⟨h1 style="font:400 28px Georgia,serif;color:#b4762a;margin:0 0 8px"⟩Bacci’s No-Bake Dream Cake⟨/h1⟩'+$('#recipeBody').innerHTML;$('#printCard').hidden=false;setTimeout(()=⟩{try{window.print()}catch(e){}},50)};
/* ---------- wish ---------- */
function wishSummary(){const parts=[];if(st.code)parts.push('Mix: '+(st.name?st.name+' ':'')+st.code);if(st.body&&st.mind&&st.soul)parts.push('Cake: '+st.body+', '+st.mind.toLowerCase()+', shared with '+st.soul.toLowerCase());$('#wishSummary').textContent=parts.length?parts.join(' · '):'Make a mix and a cake first, or go straight to DandiWish.';const q=new URLSearchParams();if(st.code)q.set('mix',st.code);if(st.body&&st.mind&&st.soul)q.set('cake',st.body+'|'+st.mind+'|'+st.soul);$('#dandiLink').href='https://baccikid.com/pages/dandiwish-the-birthday-wish-star'+(q.toString()?'?'+q.toString():'')}
/* ---------- start ---------- */
renderSongs();renderLayers();renderSfx();SONGS.forEach(s=⟩s.layers.filter(l=⟩l.maybe).forEach(audioFor));
if(st.name)$('#mixName').value=st.name;if(st.code){$('#codeTxt').textContent=(st.name?st.name+' · ':'')+st.code;$('#codeOut').hidden=false;const r=parseCode(st.code);if(r){song=r.s;song.layers.forEach((l,i)=⟩{l.on=r.bits[i]==='1'});taps=r.list;renderSongs();renderLayers();dots()}}
if(st.agreed)showBack();
go('arrive');
document.addEventListener('visibilitychange',()=⟩{if(document.hidden&&playing)stop()});
window.__mix={st,SONGS,makeCode,parseCode,play,stop,go,ver:'2.0'};
})();
⟨/script⟩