【问题标题】:How to avoid crackling popping sounds after increase volume in Oboe?增加双簧管音量后如何避免噼里啪啦的爆裂声?
【发布时间】:2018-12-07 17:12:32
【问题描述】:

我开始为 Android 实现 Oboe c++ 库。 (根据Build a Musical Game using Oboe 我只是缩放样本以增加音量,它可以工作,但会发出噼啪声。 我可以增加振幅而不会发出噼啪声吗? 我试图用一点增益来保存我的样本声音,但听起来很糟糕。 谢谢。

顺便说一句,在不增加音量的情况下,它听起来很清晰,但与其他音乐应用相比,音量非常低。

for (int i = 0; i < mNextFreeTrackIndex; ++i) {

    mTracks[i]->renderAudio(mixingBuffer, numFrames);

    for (int j = 0; j < numFrames * kChannelCount; ++j) {
        audioData[j] += (mixingBuffer[j] * ((float)volume));
    }

已编辑:

int16_t Mixer::hardLimiter(int16_t sample) {
    int16_t audioData = sample * volume;
    if(audioData >= INT16_MAX){
        return INT16_MAX;
    }else if(audioData <= INT16_MIN){
        return  INT16_MIN;
    }
    return audioData;
};

【问题讨论】:

  • 听起来好像调高音量会导致削波。对此的补救措施是不要调高音量,或者调低音量。
  • 解决办法是不要调高音量?所以呢?
  • 剪辑就是您所描述的。当任何数字系统的音量开得太高时,就会发生这种情况。发生这种情况是因为您没有足够的位来表示波形。
  • 我明白,但我怎样才能“保护”并避免这些噪音?在我的应用中,音量必须由用户设置,有时我播放的音频文件音量也很小。
  • 不要把音量开得太高。

标签: android oboe


【解决方案1】:

您发布的代码来自Mixer::renderAudio(int16_t *audioData, int32_t numFrames)。它的工作是将来自各个轨道的样本值混合到一个 16 位样本数组中。

如果您将 2 个或更多轨道混合在一起而不先降低值,那么您可能会超过最大样本值 32,767(又名INT16_MAX)。这样做会导致回绕(即,将 32,768 写入 int16_t 将导致存储值 -32,768),因此会出现失真/噼啪声。

考虑到这一点,您可以编写一个非常基本(硬)的限制器 - 使用 int32_t 进行音量缩放,如果值不超过最大值,则仅将其写入 int16_t 数组,否则只需编写最大值。

但这并不是一个真正的好方法,因为您不应该达到 16 位值的限制。最好先按比例缩小输入样本值,然后在混音器之后(或在混音器内的各个轨道上)添加增益级,以将整体幅度提高到可接受的水平。

【讨论】:

  • 谢谢唐,你能看看我编辑的问题,让我知道你的意思吗?
  • int32_t 需要使用audioData,否则您将立即得到环绕
猜你喜欢
  • 2014-08-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-04-25
相关资源
最近更新 更多