我一直试图弄清楚如何使用 Windows SAPI 5.1 将文本“说”到内存缓冲区中,但到目前为止还没有成功,尽管它看起来应该很简单。
有一个将合成语音流式传输到 .wav 文件的示例,但没有关于如何将其流式传输到内存缓冲区的示例。
最后,我需要在 char* 数组中以 16 kHz 16 位 little-endian PCM 格式合成语音。目前我创建了一个临时 .wav 文件,在那里重定向语音输出,然后阅读它,但这似乎是一个相当愚蠢的解决方案。
有谁知道该怎么做?
谢谢!
我一直试图弄清楚如何使用 Windows SAPI 5.1 将文本“说”到内存缓冲区中,但到目前为止还没有成功,尽管它看起来应该很简单。
有一个将合成语音流式传输到 .wav 文件的示例,但没有关于如何将其流式传输到内存缓冲区的示例。
最后,我需要在 char* 数组中以 16 kHz 16 位 little-endian PCM 格式合成语音。目前我创建了一个临时 .wav 文件,在那里重定向语音输出,然后阅读它,但这似乎是一个相当愚蠢的解决方案。
有谁知道该怎么做?
谢谢!
查看 ISpStream::SetBaseStream。这里有一个小帮手:
inline HRESULT SPCreateStreamOnHGlobal(
HGLOBAL hGlobal, //Memory handle for the stream object
BOOL fDeleteOnRelease, //Whether to free memory when the object is released
const WAVEFORMATEX * pwfex, //WaveFormatEx for stream
ISpStream ** ppStream) //Address of variable to receive ISpStream pointer
{
HRESULT hr;
IStream * pMemStream;
*ppStream = NULL;
hr = ::CreateStreamOnHGlobal(hGlobal, fDeleteOnRelease, &pMemStream);
if (SUCCEEDED(hr))
{
hr = ::CoCreateInstance(CLSID_SpStream, NULL, CLSCTX_ALL, __uuidof(*ppStream), (void **)ppStream);
if (SUCCEEDED(hr))
{
hr = (*ppStream)->SetBaseStream(pMemStream, SPDFID_WaveFormatEx, pwfex);
if (FAILED(hr))
{
(*ppStream)->Release();
*ppStream = NULL;
}
}
pMemStream->Release();
}
return hr;
}
我使用 ISpStream 完成了它。使用 ispstream 的 Setbasestream 函数将其绑定到 istream,然后将 ispvoice 的输出设置为该 ispstream。
如果有人想要,这是我的工作解决方案:
你知道如何创建内存映射文件吗?您可以查看ISpStream
遗嘱是否绑定到它。