audio - 如何在 Rust 中将 16 位 PCM 音频的采样率从 24000 Hz 更改为 48000 Hz?

标签 audio rust resampling pcm

我从 Google 的文本转语音服务获取 16 位 PCM 数据 (24000 Hz),然后将其存储在 u8 数组中。有没有一种简单的方法可以将其重新采样到 48000 Hz,输出为 u8 数组?我不明白 FFmpeg 上的任何在线示例。

现在我将它包装在游标中以单独读取每个 i16,然后将每个 i16 复制一次(即,使 1234 变为 11223344)。我的逻辑是,既然原始音频是 24000,那么加倍就是 48000,对吗?

let mut raw = Cursor::new(raw);
let mut new_samples = Vec::new();

loop {
    match raw.read_i16::<LittleEndian>() {
        Ok(x) => {
            samples.push(x);
            samples.push(x);
        }
        Err(_) => break,
    }
}

接下来我使用 hound crate 将新样本转换为 48000 WAV。

let mut new_wav = Cursor::new(Vec::new());
let mut writer = WavWriter::new(
    &mut new_wav,
    WavSpec {
        channels: 1,
        sample_rate: 48000,
        bits_per_sample: 16,
        sample_format: SampleFormat::Int,
    },
)
.unwrap();

new_samples
    .into_iter()
    .for_each(|x| writer.write_sample(x).unwrap());

writer.finalize().unwrap();

现在 new_wav 应该具有 48000 Hz 音频。但这不起作用。当我使用 Discord 鸣禽箱播放它时,我只是听到一个非常简短的静电声:

call.lock().await.play_source(Input::new(
    false,
    new_wav.into_inner().into(),
    Codec::Pcm,
    Container::Raw,
    None,
));

最佳答案

好吧,我明白了。我就是这样做的。

let mut original = Cursor::new(original);
let mut resampled = Cursor::new(Vec::new());

loop {
    match original.read_i16::<LittleEndian>() {
        Ok(x) => {
            // Write it twice
            resampled.write_i16::<LittleEndian>(x).unwrap();
            resampled.write_i16::<LittleEndian>(x).unwrap();
        }
        Err(_) => break,
    }
}

现在“重新采样”为 48000 Hz(并且播放效果完美)。

关于audio - 如何在 Rust 中将 16 位 PCM 音频的采样率从 24000 Hz 更改为 48000 Hz?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66206380/

相关文章:

python - 如何根据数据列对不规则数据集进行上采样?

audio - XAudio2 遮挡处理

module - 如何将我的程序划分为模块?

rust - 可以定义通用闭包吗?

audio - 正确解码/编码原始 PCM 数据

python - Pandas:重新采样数据框列,获取对应于最大值的离散特征

iOS 在完成播放前播放相同的音效

java - 循环声音Java

javascript - 当上面的一个 html5 音频完成时播放下一个 html5 音频

rust - BigUint 和 "cannot move out of borrowed content"错误