我正在创建一个电子应用程序,允许用户裁剪和重排多个音频样本,并无视地播放它们。样本的总持续时间比小时长,因此我不能将它们全部解码,并将它们存储为PCM数据。下面是我实现的:
-首先解码音频ArrayBuffers,创建第一段AudioBufferSourceNode所需的音频。
在播放第一个AudioBufferSourceNode时,以相同的方式创建下一个缓冲区,并在第一个缓冲区结束后立即播放它们。
问题是,音频有时似乎有一个爆裂的声音。每一个缓冲区都在一个接一个地播放,我在音频的开头和结尾应用了几毫秒的衰变,所以我确信这不是因为音频的突然启动/停止。
奇怪的是,只有当音频解码异步运行时,才会出现破裂噪声。我已经实现了这个功能来存储最近解码的pcm,当从缓存中播放时,没有这样的破解噪声。此外,当我在背景中运行无限循环的音频解码时,音频中显然会有更多的裂缝。
我一直在寻找谷歌的这种问题,但我找不到任何人谁也有同样的问题。所以我的问题是,decodeAudioData真的会引起爆裂声吗?如果是的话,我该怎么解决呢?
这在每台计算机上都会发生,但低性能计算机似乎有更多的裂缝。
这里是我用来解码的代码,它是一个针对cc*>的单独的代码。

class AudioDecoder {
  // Number of audioContext of limited,
  // using a singleton to prevent hitting the limit
  private audioCtx: AudioContext;
  private static instance: AudioDecoder;
  private constructor() {
    const AudioContextClass =
      (window as any).AudioContext || (window as any).webkitAudioContext;
    this.audioCtx = new AudioContextClass();
  }
  public static decode = (arrayBuffer: ArrayBuffer) => {
    if (!AudioDecoder.instance) {
      AudioDecoder.instance = new AudioDecoder();
    }
    return new Promise<AudioBuffer>((resolve, reject) => {
      AudioDecoder.instance.audioCtx.decodeAudioData(
        arrayBuffer,
        buffer => {
          resolve(buffer);
        },
        error => reject(error),
      );
    });
  };
}

最佳答案

原则上,除非原声源有裂纹噪声,否则decodeAudioData不应产生裂纹噪声。
但是,如果压缩音频文件的采样率与AudioContext的采样率不同,则解码音频将重新采样以匹配上下文。一般来说,这是不明显的,但你连接缓冲区播放,可能有一个不连续性,不在原来的。您应该检查音频文件的采样率是否与上下文的采样率不同。如果它们不同,请使用采样率与上下文匹配的音频文件重试。或者用与文件匹配的采样率构造上下文。(尚未在所有浏览器上可用。)
最后,如果这不能解决问题,请向浏览器提交一个问题,并确保包含一个简短但完整的测试用例。

09-25 16:40
查看更多