问题描述
我在我的 C# WPF 项目中实现了一个 TTS.
I implemented a TTS in my C# WPF project.
之前,我使用 System.Speech.Synthesis 命名空间中的 TTS 来说话.演讲内容为 SSML 格式(Speech Synthesizer Markup Language,支持自定义语速、语音、强调)如下:
Previously, I use the TTS in System.Speech.Synthesis namespace to speak. The speaking content is in SSML format (Speech Synthesizer Markup Language, support customize the speaking rate, voice, emphasize) like following:
<speak version="1.0" xmlns="http://www.w3.org/2001/10/synthesis" xml:lang="en-US"><prosody rate="x-fast">hello world. This is a long sentence speaking very fast!</prosody></speak>
但不幸的是 System.Speech.Synthesis TTS 存在内存泄漏问题,正如我在问题中提到的 .Net Speech.Synthesizer 内存泄漏?.
But unfortunately the System.Speech.Synthesis TTS has a memory leak problem, as I mentioned in question Memory leak in .Net Speech.Synthesizer?.
所以我决定使用 SAPI COM 组件.我可以轻松地让 SAPI 说出纯文本内容.但是后来我继续尝试让它说 SSML 字符串,我失败了.代码如下:
So I decide to use SAPI COM component. I can easily let SAPI to speak plain text content. But then I continue to try letting it speak SSML string, I failed. The code is like following:
//Initialize TTS instance
SpeechLib.SpVoiceClass tts = new SpeechLib.SpVoiceClass();
//Generate SSML string
string textToSpeak = "hello world speak Extra Fast.";
PromptBuilder pb = new PromptBuilder();
pb.StartStyle(new PromptStyle(PromptRate.ExtraFast));
pb.AppendText(textToSpeak);
pb.EndStyle();
ssmlString = pb.ToXml(); //ssmlString = @"<speak version=""1.0"" ....
//Speak!
tts.Speak(ssmlString, SpeechLib.SpeechVoiceSpeakFlags.SVSFParseSsml);
代码的基本部分是
tts.Speak(ssmlString, SpeechLib.SpeechVoiceSpeakFlags.SVSFParseSsml);
Which uses the SpeechVoiceSpeakFlags enumerations to specify the TTS speaking behavior. I have tried several combinations of the flags, but none of them successfully speak out the SSML content.
特别是,上面的代码还会引发以下异常:
Particularly, the above code will also raise following exceptions:
System.Runtime.InteropServices.COMException 未处理
消息="来自 HRESULT 的异常:0x80045003"
Source="Interop.SpeechLib" ErrorCode=-2147201021 StackTrace:在 SpeechLib.SpVoiceClass.Speak(字符串文本,SpeechVoiceSpeakFlags 标志)在 SpeechSynthesisMemLeakTest.Program.Test2() 在 D:\Proj\TestSolutions\CSharp_Quick_Apps\SpeechSynthesisMemLeakTest\Program.cs:line60在 SpeechSynthesisMemLeakTest.Program.Main(String[] args) 在 D:\Proj\TestSolutions\CSharp_Quick_Apps\SpeechSynthesisMemLeakTest\Program.cs:line17在 System.AppDomain._nExecuteAssembly(Assembly assembly, String[] args)在 Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()在 System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)在 System.Threading.ThreadHelper.ThreadStart() 内部异常:
谁能告诉我如何正确使用标志来说出 SSML 内容?
Could anyone tell me how to correctly use the flag to speak out SSML content?
推荐答案
您使用的是什么 TTS 引擎/语音?Microsoft TTS 引擎绝对支持使用您正在使用的代码的 SSML;但是,其他语音/引擎可能不支持 SSML.
What TTS engine/voice are you using? The Microsoft TTS engines definitely support SSML using the code that you're using; however, other voices/engines may not support SSML.
错误 0x80045003 是 SPERR_UNSUPPORTED_FORMAT(调用方指定了不受支持的格式),这让我相信您需要使用不同的 TTS 引擎(支持 SSML).
Error 0x80045003 is SPERR_UNSUPPORTED_FORMAT (The caller has specified an unsupported format), which leads me to believe that you need to use a different TTS engine (that supports SSML).
这篇关于C# SAPI 可以说 SSML 字符串吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!