问题描述
我正在尝试将 libsndfile 与 xaudio2 集成。我在互联网上找不到太多,所以我会在这里问。
我成功地将 libsndfile 与 OpenAL preatty 轻松集成,但我正在努力使用 xaudio2。
它会产生爆裂声和噼啪声。我确定是因为我没有给出 xaudio 期望的正确格式......但我似乎无法弄清楚应该将哪些值发送到 xaudio2。
这是我加载声音文件的方式...
SF_INFO info;
SNDFILE* file =
sf_open(
filename.c_str(),SFM_READ,&info);
std::vector<uint16_t> wav;
std::array<int16_t,READ_BLOCK_SIZE> read_buf;
sf_count_t read_size = 0;
while ((read_size =
sf_read_short(
file,read_buf.data(),read_buf.size())) != 0)
wav.insert(
wav.end(),read_buf.begin(),read_buf.begin() + read_size);
所以 wav 向量被 uhsorts 填充,而 xaudio 需要一个 BYTE 数组......不确定这是否也是一个问题。
info 填充您所知道的声音文件信息。
这就是我填充 xaudio 缓冲区的方式。
waveFormat = {};
waveFormat.wFormatTag = WAVE_FORMAT_PCM;
waveFormat.nChannels = info.channels;
waveFormat.nSamplesPerSec = info.samplerate;
waveFormat.wBitsPerSample = 8;
waveFormat.nBlockAlign =
waveFormat.nChannels *
waveFormat.wBitsPerSample / 8;
waveFormat.nAvgBytesPerSec =
waveFormat.nSamplesPerSec *
waveFormat.nBlockAlign;
waveFormat.cbSize = sizeof(WAVEFORMATEX);
buffer = { 0 };
buffer.AudioBytes = (UINT32)(wav.size() * sizeof(uint16_t));
buffer.Flags = xaudio2_END_OF_STREAM;
buffer.LoopBegin = 0;
buffer.LoopCount = 0;
buffer.LoopLength = 0;
buffer.pAudioData = (BYTE*)wav.data();
buffer.pContext = nullptr;
buffer.PlayBegin = 0;
buffer.PlayLength = (UINT32)wav.size();
我也不确定 AudioBytes 是否正确......正如您可能已经知道的那样,我对 xaudio2 的内容一无所知。
如何使用 libsndfile 提供的正确值填充 xaudio 缓冲区?
谢谢。
解决方法
所以,问题确实是格式......
所以我改变了读取音频文件的方法,从shorts到float,并将格式从WAVE_FORMAT_PCM改为WAVE_FORMAT_IEEE_FLOAT。 还给它一个 32 位的样本。
并使用 reinterpret_cast 将浮点数组转换为字节数组.... 希望以下代码能帮助其他人使用 LibSndFile 将文件音频文件加载到 Xaudio2 缓冲区。
干杯。
std::vector<float> wav;
std::array<float,READ_BLOCK_SIZE> read_buf;
while ((read_size =
sf_read_float(
file,read_buf.data(),read_buf.size())) != 0)
wav.insert(
wav.end(),read_buf.begin(),read_buf.begin() + read_size);
waveFormat = {};
waveFormat.wFormatTag = WAVE_FORMAT_IEEE_FLOAT;
waveFormat.nChannels = info.channels;
waveFormat.nSamplesPerSec = info.samplerate;
waveFormat.wBitsPerSample = 32;
waveFormat.nBlockAlign =
(waveFormat.nChannels *
waveFormat.wBitsPerSample) / 8;
waveFormat.nAvgBytesPerSec =
waveFormat.nSamplesPerSec *
waveFormat.nBlockAlign;
waveFormat.cbSize = 0;// sizeof(waveFormat);
buffer = { 0 };
buffer.AudioBytes =
(UINT32)(wav.size() * sizeof(float));
buffer.Flags = XAUDIO2_END_OF_STREAM;
buffer.pAudioData =
(BYTE*)new BYTE[
wav.size() * sizeof(float)];
std::memcpy(
(void*)buffer.pAudioData,reinterpret_cast<BYTE*>(wav.data()),wav.size() * sizeof(float));
buffer.pContext = nullptr;
buffer.PlayLength = (UINT32)info.frames;