大缓冲区大小播放,小大小不播放
Large buffer sizes plays, small size doesn't
当缓冲区大小很小(1920帧)时,我在获取声音输出时遇到问题。如果我在48kHz
采样并使缓冲区大小为480000
,则正弦波正确播放1秒。我想做的只是为40ms
播放正弦波。
我已经计算出是48000 samples/sec * 1sec/1000ms * 40ms = 1920 frames
。然而,当我尝试调用只有1920帧的snd_pcm_writei
时,什么都没有出来!
这是有问题的代码:
void PCM::playSound(float freqHz, uint16_t durationMs)
{
int FRAMES_LEN=48000;
//Send the sine_buffer to sound card, with correct buffer length
snd_pcm_sframes_t frames = snd_pcm_writei(handle, sine_buffer, FRAMES_LEN);
if (frames < 0){
HW_INFO() << "PCM::playSound-- snd_pcm_writei failed,trying to recover:"
<< snd_strerror(frames);
frames = snd_pcm_recover(handle, frames, 0);
}
if (frames < 0) {
HW_INFO() << "PCM::playSound-- snd_pcm_writei recovery failed: "
<< snd_strerror(frames);
}
HW_INFO() << "Wrote " << frames << " frames";
return;
}
如果FRAMES_LEN
是48000
,则此代码工作正常,并产生持续1秒的正弦波。
如果FRAMES_LEN
是1920
,我根本听不到正弦波,但日志显示Wrote 1920 frames
。
发生了什么?
如果使用长度>=1920帧的滤波器进行任何类型的后处理,这是合理的。例如,这样的过滤可以丢弃任何点击声音。使用ALSA而不仅仅是与D/a转换器交谈的全部原因是为了进行音频特定处理。
您的日志记录没有欺骗您。你要求它向设备写入1920个样本,它做到了。由于您的48000个样本实验播放的声音持续了一秒钟,因此您的硬件必须以48 kHz的频率运行。假设1920帧将持续百分之四百秒。根据正弦缓冲区中正弦的频率,您可能听不到。
以下是更深入的讨论:https://sound.stackexchange.com/q/28163
相关文章:
- 比较并显示使用最小值(a,b)和最大值(a、b)升序排列的4个数字
- 为什么在浮点中从大到小会引入更多的误差
- 最大和最小 1 C++函数
- 如何创建一个函数来计算并返回平均值、最大值和最小值
- 在二维数组中查找最小值和最大值?
- 查找矩阵C++中每一列和每一行的最小和最大元素
- 有没有办法在 c++ 中按更大的 int 和更小的对对 int 和对的集合进行排序?
- 如何在数组中交换最小和最大的位置?
- 查找数组中第一个最小值和最后一个最大值元素之间的算术平均值
- 从较小的阵列到较大的阵列的元素级转换
- C++ 函数,用于查找传入的 N 个数字的平均值、总和、最小值和最大值
- txt 文件中浮点数的最大和最小值
- 查找最小的下一个更大的元素
- 在最小堆中查找最大元素
- C++不同的最小最大值实现
- 查找数组中指示性较大但数组中值较小的元素
- CUDA - 将 float3 数组的 (x,y,z) 分量的最小值/最大值分开?
- 查找包含 N 个元素的数组的最小值和最大值
- 井字游戏具有奇怪行为的最小最大值算法(C++)
- 大缓冲区大小播放,小大小不播放