You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用Three.js的THREE.AudioLoader实现音频源即时切换?

解决方案

问题根源

你猜的没错,问题确实出在animate函数里——它每帧都会调用sound.play(),哪怕你在changeAudio里调用了sound.stop(),下一帧animate又会重新触发原音频播放,导致新音频只能等原音频结束才会启动。

具体修复步骤

1. 限制animate中的播放触发逻辑

修改animate函数里的播放代码,只在音频未处于播放状态时才调用play(),避免每帧重复触发:

const distanceToCharacter = camera.position.distanceTo(characterPosition);
if (distanceToCharacter < distanceToShow) {
    nearCharacter.style.display = 'block';
    // 只在音频未播放时才触发播放
    if (!sound.isPlaying) {
        sound.play();
    }
    sound.setLoop(false);
} else {
    nearCharacter.style.display = 'none';
    characterRun.style.display = 'none';
    characterPayToll.style.display = 'none';
    // 离开范围时停止音频
    sound.stop();
}

2. 优化changeAudio函数,确保即时切换并播放新音频

在加载新音频buffer后,立即停止当前播放、替换buffer并启动新音频,同时避免animate的干扰:

function changeAudio() {
  console.log('Button clicked!');

  // 立即停止当前音频并重置播放位置
  sound.stop();
  sound.currentTime = 0;

  // 切换音频文件(如需来回切换,可保留判断逻辑)
  audioFile = audioFile === 'audio/police_officer.wav' ? 'audio/siren.wav' : 'audio/police_officer.wav';

  // 加载新音频并立即播放
  audioLoader.load(audioFile, function( buffer ) {
    sound.setBuffer( buffer );
    sound.setRefDistance( 0.1 );
    sound.setMaxDistance( 0.01 );
    sound.setRollOffFactor( 0.1 );
    // 加载完成后直接播放新音频
    sound.play();
  });
}

3. 可选优化:预加载所有音频(避免切换时加载延迟)

如果对话音频数量不多,建议提前预加载所有需要的buffer,切换时无需等待加载,体验更流畅:

// 预加载音频缓存
const audioBuffers = {};
const audioFiles = ['audio/police_officer.wav', 'audio/siren.wav'];

// 提前加载所有音频
audioFiles.forEach(file => {
    audioLoader.load(file, buffer => {
        audioBuffers[file] = buffer;
    });
});

// 修改changeAudio函数,直接从缓存取buffer
function changeAudio() {
  console.log('Button clicked!');

  sound.stop();
  sound.currentTime = 0;

  // 切换音频文件
  audioFile = audioFile === 'audio/police_officer.wav' ? 'audio/siren.wav' : 'audio/police_officer.wav';

  // 直接使用预加载的buffer
  sound.setBuffer(audioBuffers[audioFile]);
  sound.setRefDistance(0.1);
  sound.setMaxDistance(0.01);
  sound.setRollOffFactor(0.1);
  sound.play();
}

内容的提问来源于stack exchange,提问作者Daniel Rush

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.30 00:42:49