const assetRoot = '../assets/external/yumi-static/other/'; const img = (name) => `${assetRoot}${name}`; const modeData = { classic: { background: 'lucky_box_bg_new.png', prices: [500, 5000, 25000], drawAmount: 500, board: 'grid', prizes: [ ['Coral Crown', 99, 'lucky_box_reward.png'], ['Aurora Wing', 500, 'christmasCheckIn_lottery_go.png'], ['Moon Card', 520, 'lucky_box_select.png'], ['Snow Pet', 777, 'christmasCheckIn_lottery_select.png'], ['Love Banner', 1314, 'lucky_box_title_top.png'], ['Emerald Ring', 1777, 'lucky_box_reward_bg.png'], ['Royal Chest', 3999, 'lucky_box_go.png'], ['Crystal Castle', 199999, 'lucky_box_bg_new.png'] ] }, luxury: { background: 'lucky_box_tow_bg_new.png', prices: [2000, 20000, 100000], drawAmount: 2000, board: 'wheel', prizes: [ ['Pink Meteor', 2000, 'lucky_box_tow_reward.png'], ['Cupid Wand', 2999, 'lucky_box_tow_pointer.png'], ['Love Ring', 5200, 'lucky_box_tow_reward_yuan.png'], ['Lucky Palace', 6666, 'lucky_box_tow_reward_bg.png'], ['Starlight', 10000, 'lucky_box_tow_reward_desc.png'], ['Rose Horse', 15000, 'lucky_box_tow_reward_top.png'], ['Neon Gift', 50000, 'lucky_box_tow_reward_bottom.png'], ['Galaxy Badge', 299999, 'lucky_box_tow_bg_new.png'] ] }, advanced: { background: 'lucky_box_three_bg_new.png', prices: [10000, 100000, 500000], drawAmount: 10000, board: 'grid', prizes: [ ['Cyber Cat', 2000, 'lucky_box_three_notice.png'], ['Golden Ride', 4500, 'lucky_box_three_gold.png'], ['Black Rose', 6000, 'lucky_box_three_reward_bg.png'], ['Holy Trophy', 10000, 'lucky_box_three_select.png'], ['Silver Cup', 20000, 'lucky_box_three_history.png'], ['Royal Cake', 50000, 'lucky_box_three_go.png'], ['Night Throne', 100000, 'lucky_box_three_rule.png'], ['Ice Castle', 200000, 'lucky_box_three_unbtn.png'], ['Gold Palace', 300000, 'lucky_box_three_unselect.png'], ['Star Couple', 400000, 'lucky_box_three_default.png'], ['Dragon Ride', 500000, 'lucky_box_three_bg_new.png'], ['Blue Flame', 1000000, 'lucky_box_three_btn.png'] ] } }; const state = { mode: 'classic', activeButton: 0, activeIndex: null, spinning: false, rotateDeg: 0, balance: 230610000, history: [] }; const winners = [ ['ZAYAN', 'Cyber Cat'], ['Looma', 'Love Ring'], ['Rima', 'Crystal Castle'], ['M7MD', 'Golden Ride'], ['Yara', 'Pink Meteor'] ]; const page = document.querySelector('#page'); const stage = document.querySelector('#stage'); const buyRow = document.querySelector('#buyRow'); const balanceTop = document.querySelector('#balanceTop'); const balanceBottom = document.querySelector('#balanceBottom'); const tickerTrack = document.querySelector('#tickerTrack'); const rewardDialog = document.querySelector('#rewardDialog'); const rewardList = document.querySelector('#rewardList'); const rewardText = document.querySelector('#rewardText'); const historyDialog = document.querySelector('#historyDialog'); const historyList = document.querySelector('#historyList'); function money(value) { return Number(value).toLocaleString('en-US'); } function prizeObjects() { return modeData[state.mode].prizes.map(([name, value, cover]) => ({ name, value, coverUrl: img(cover) })); } function setMode(mode) { state.mode = mode; state.activeButton = 0; state.activeIndex = null; render(); } function render() { const mode = modeData[state.mode]; page.className = `wheel-page mode-${state.mode}`; page.style.backgroundImage = `url("${img(mode.background)}")`; balanceTop.textContent = money(state.balance); balanceBottom.textContent = money(state.balance); document.querySelectorAll('.tabs button').forEach((button) => { button.classList.toggle('active', button.dataset.mode === state.mode); }); tickerTrack.innerHTML = winners.concat(winners).map(([name, reward]) => ( `Congratulations to ${name} for receiving the ${reward} award` )).join(''); renderStage(); renderBuyRow(); } function renderStage() { const mode = modeData[state.mode]; if (mode.board === 'wheel') { renderWheel(); return; } const prizes = prizeObjects(); const cells = [ prizeCard(prizes[0], 0), prizeCard(prizes[1], 1), prizeCard(prizes[2], 2), prizeCard(prizes[3], 3), ``, prizeCard(prizes[4], 4), prizeCard(prizes[5], 5), prizeCard(prizes[6], 6), prizeCard(prizes[7], 7) ]; stage.innerHTML = `
${cells.join('')}
`; document.querySelector('#goButton').addEventListener('click', startLottery); } function renderWheel() { const prizes = prizeObjects(); const itemMarkup = prizes.map((prize, index) => { const angle = `${index * (360 / prizes.length)}deg`; return `
${prize.value}
`; }).join(''); stage.innerHTML = `
${itemMarkup}
`; document.querySelector('#goButton').addEventListener('click', startLottery); } function prizeCard(prize, index) { return `
${prize.name} ${money(prize.value)}
`; } function renderBuyRow() { buyRow.innerHTML = modeData[state.mode].prices.map((price, index) => ( `` )).join(''); buyRow.querySelectorAll('button').forEach((button) => { button.addEventListener('click', () => { state.activeButton = Number(button.dataset.index); renderBuyRow(); }); }); } function startLottery() { if (state.spinning) return; const mode = modeData[state.mode]; const cost = mode.prices[state.activeButton]; if (state.balance < cost) return; state.balance -= cost; state.spinning = true; const prizes = prizeObjects(); const target = Math.floor(Math.random() * prizes.length); if (mode.board === 'wheel') { state.rotateDeg += 1440 + (360 - target * (360 / prizes.length)); document.querySelector('#wheelDisc').style.transform = `rotate(${state.rotateDeg}deg)`; setTimeout(() => finishLottery(target), 2300); renderBuyRow(); balanceTop.textContent = money(state.balance); balanceBottom.textContent = money(state.balance); return; } let tick = 0; const timer = setInterval(() => { state.activeIndex = tick % prizes.length; renderStage(); tick += 1; if (tick > 22 && state.activeIndex === target) { clearInterval(timer); finishLottery(target); } }, tick < 12 ? 70 : 120); } function finishLottery(targetIndex) { const prize = prizeObjects()[targetIndex]; state.spinning = false; state.activeIndex = targetIndex; const count = state.activeButton === 0 ? 1 : state.activeButton === 1 ? 10 : 50; const record = { time: new Date(), drawTimes: count, rewards: [{ ...prize, count: 1 }], rewardValue: prize.value }; state.history.unshift(record); showReward(record); render(); } function showReward(record) { rewardList.innerHTML = record.rewards.map((item) => ( `
${item.name} x${item.count}
` )).join(''); rewardText.textContent = `Congratulations on receiving: A precious gift worth ${money(record.rewardValue)} gold coins. Already put in the backpack.`; rewardDialog.showModal(); } function renderHistory() { const records = state.history.length ? state.history : seedHistory(); historyList.innerHTML = records.map((record) => { const first = record.rewards[0]; return `
${first.name}
${record.time.toLocaleString()}
x${record.drawTimes}
`; }).join(''); } function seedHistory() { const prizes = prizeObjects(); return [0, 2, 5].map((index, offset) => ({ time: new Date(Date.now() - (offset + 1) * 260000), drawTimes: [1, 10, 50][offset], rewards: [{ ...prizes[index], count: offset + 1 }], rewardValue: prizes[index].value })); } document.querySelectorAll('.tabs button').forEach((button) => { button.addEventListener('click', () => setMode(button.dataset.mode)); }); document.querySelector('#historyBtn').addEventListener('click', () => { renderHistory(); historyDialog.showModal(); }); document.querySelector('#closeHistory').addEventListener('click', () => historyDialog.close()); document.querySelector('#closeReward').addEventListener('click', () => rewardDialog.close()); document.querySelector('#drawAgain').addEventListener('click', () => { rewardDialog.close(); startLottery(); }); render();