Commit 026f16bd authored by 董政锦's avatar 董政锦

fix

parent 6d5045b7
......@@ -26,18 +26,25 @@ export function stopAllMusic() {
backgroundMusic = null;
}
function getBackgroundMusic(music: string, force: boolean = true) {
if (force) { //
function getBackgroundMusic(music: string, force: boolean = false) {
console.log('[Music] getBackgroundMusic called, music:', music, 'force:', force, 'current backgroundMusic:', backgroundMusic?.src)
// 检查当前背景音乐是否是同一首(比较路径末尾,处理相对路径和完整URL的情况)
const isSameMusic = backgroundMusic &&
(backgroundMusic.src === music || backgroundMusic.src.endsWith(music));
// 只有在需要切换不同音乐或强制重建时才停止并重建
if (force || (!backgroundMusic || !isSameMusic)) {
console.log('[Music] 重建背景音乐, 原因:', force ? '强制重建' : backgroundMusic ? '音乐URL变更' : '无现有音乐')
if (backgroundMusic) {
stopAllMusic();
}
}
if (!backgroundMusic) {
backgroundMusic = new Audio(music)
backgroundMusic.loop = true
backgroundMusic.preload = 'auto'
backgroundMusic.volume = 0.6
backgroundMusic.load()
console.log('[Music] 新背景音乐创建完成:', backgroundMusic.src)
}
return backgroundMusic
......@@ -60,7 +67,13 @@ export async function playApplauseMusic() {
export function stopApplauseMusic() {
window.removeEventListener('pointerdown', playApplauseMusic)
window.removeEventListener('keydown', playApplauseMusic)
backgroundMusic?.pause()
// 只有当当前播放的是喝彩音乐时才暂停,避免误伤背景音乐
if (backgroundMusic && backgroundMusic.src.endsWith(applause)) {
console.log('[Music] 停止喝彩音乐')
backgroundMusic.pause()
} else {
console.log('[Music] stopApplauseMusic 被调用,但当前播放的不是喝彩音乐,不暂停')
}
}
......@@ -103,13 +116,25 @@ export function stopGame2Music() {
}
export async function playGame4Music() {
console.log('[Music] playGame4Music called')
const audio = getBackgroundMusic(game4MusicUrl)
console.log('[Music] 播放音乐文件:', game4MusicUrl, '完整路径:', audio.src)
console.log('[Music] audio element readyState:', audio.readyState, 'paused:', audio.paused, 'currentTime:', audio.currentTime)
try {
console.log('[Music] 尝试播放音乐...')
await audio.play()
console.log('[Music] 音乐播放成功!文件:', game4MusicUrl, 'paused:', audio.paused, 'currentTime:', audio.currentTime, 'duration:', audio.duration)
// 添加延迟检查,看是否被其他代码暂停
setTimeout(() => {
console.log('[Music] 100ms后检查 - 文件:', game4MusicUrl, 'paused:', audio.paused, 'currentTime:', audio.currentTime)
}, 100)
window.removeEventListener('pointerdown', playGame4Music)
window.removeEventListener('keydown', playGame4Music)
} catch {
} catch (error) {
console.log('[Music] 音乐播放失败,注册交互监听器:', error)
window.addEventListener('pointerdown', playGame4Music, { once: true })
window.addEventListener('keydown', playGame4Music, { once: true })
}
......
......@@ -108,9 +108,7 @@ const gotoRank1WithIntro = async () => {
isPlayingStartAnimation = true
seedRankPlayersFromLoading()
// 对齐 game3:进入赛马画面前确保背景音乐播放中
// 必须在 startIntro 之前调用,因为 startIntro 内部会 stopApplauseMusic() 误伤 BGM
playGame4Music()
// 参考 game2:不在这里调用 playGame4Music(),依赖 watch 和 pointerdown 监听器触发
screen.value = 'rank1'
await nextTick()
await rank1Ref.value?.startIntro()
......@@ -196,22 +194,19 @@ const { startGame, createRoom, backRoom, closeRoom } = useAdminGameSocket({
})
const startGameWithMusic = () => {
// 本地调试模式:跳过 WebSocket,直接进入赛马画面(对齐 game3)
// 注意:不在这里调 playGame4Music(),因为 onMounted 中已注册 pointerdown 监听器,
// 点击按钮时 pointerdown 事件先于 click 触发,会自动播放 BGM。
// 如果在此额外调用 playGame4Music(),会导致 stopAllMusic 销毁并重建 Audio,
// 在复杂时序下可能 play() 失败,需要再点一次页面才能听到音乐。
console.log('[Game4] startGameWithMusic called, local mode:', $is_local_mode(), 'playerCount:', playerCount.value)
// 确保背景音乐播放(参考 game2 的 watch 模式,但直接在点击时调用更可靠)
playGame4Music()
if ($is_local_mode()) {
console.log('[Game4] 本地模式,直接进入赛马画面')
gotoRank1WithIntro()
return
}
if (playerCount.value == 0) {
// alert('房间中没有玩家')
$toast('房间中没有玩家');
return;
}
// 对齐 game3:点击"开始挑战"时确保背景音乐播放中
playGame4Music()
console.log('[Game4] 调用 startGame()')
startGame()
}
......
......@@ -335,15 +335,14 @@ const stopMockBoost = () => {
};
const computeFinalRank = (): RankItem[] => {
// 从 WebSocket rankList 中取有效玩家
// 从 WebSocket rankList 中取有效玩家(不排序,直接使用 WebSocket 返回的顺序)
const valid = (props.rankList || []).filter(
(p) => p.nickname !== "虚位以待" && !(p.wechat_id || "").startsWith("empty-"),
);
if (valid.length > 0) {
// 优先用 WebSocket 的 score 排序
const sorted = [...valid].sort((a, b) => Number(b.score ?? 0) - Number(a.score ?? 0));
return sorted.map((p, i) => ({
// 直接使用 WebSocket 返回的顺序,不进行排序
return valid.map((p, i) => ({
rank: i + 1,
userid: p.userid || p.wechat_id || `unknown-${i}`,
nickname: p.nickname,
......@@ -352,7 +351,7 @@ const computeFinalRank = (): RankItem[] => {
}));
}
// 无 WebSocket 数据时降级:按 xPercent 降序
// 无 WebSocket 数据时降级:按 xPercent 降序(本地模拟模式)
return horses.value
.slice()
.sort((a, b) => b.xPercent - a.xPercent)
......@@ -404,7 +403,7 @@ const startIntro = async () => {
Object.keys(prevScores).forEach((k) => delete prevScores[k]);
// 启动完整倒计时:3s 开场 + 3s 游戏(DesignStage 内部管理两个阶段的 UI)
const countdownPromise = designStage.value?.startCountdown(3, 3);
const countdownPromise = designStage.value?.startCountdown(3, 10);
// 等待 3-2-1 开场倒计时结束(~3.5s 后安全触发)
await new Promise((r) => setTimeout(r, 3500));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment