SpeechLib這的dll專門用來播放語音,能夠識別英語、簡體和繁體。並且可以播放聲音文件,支持WAV格式,但不支持MP3。在報警場合下已經夠用了。
基本播放語音及文件。支持異步。

using System; using System.Threading; using SpeechLib; namespace Model.AlarmHandle { /// <summary> ///語音播報 /// </summary> public class SpeechVoice { /// <summary> /// The _voice /// </summary> private SpVoice _voice; private SpVoiceClass spVoice; private readonly SpFileStreamClass spFile; /// <summary> /// Initializes a new instance of the <see cref="SpeechVoice"/> class. /// </summary> public SpeechVoice() { _voice = new SpVoice(); spVoice = new SpVoiceClass(); spFile = new SpFileStreamClass(); } /// <summary> /// 播放 /// </summary> /// <param name="text">The text.</param> /// <param name="speakFlag">The speak flag.</param> public void Speak(string text, SpeechVoiceSpeakFlags speakFlag = SpeechVoiceSpeakFlags.SVSFDefault) { _voice.Speak(string.Empty); _voice.Speak(text, speakFlag); } /// <summary> /// 異步播放 /// </summary> /// <param name="text">The text.</param> public void SpeakAsync(string text) { _voice.Speak(text, SpeechVoiceSpeakFlags.SVSFlagsAsync); } /// <summary> /// Plays the sound. /// </summary> /// <param name="fileName">Name of the file.</param> public void PlaySound(string fileName) { //要加載COM組件:Microsoft speech object Library if (!System.IO.File.Exists(fileName)) return; spFile.Open(fileName, SpeechStreamFileMode.SSFMOpenForRead, true); var istream = spFile as ISpeechBaseStream; spVoice.SpeakStream(istream, SpeechVoiceSpeakFlags.SVSFIsFilename); spFile.Close(); } /// <summary> /// 暫停 /// </summary> public void Pause() { if (_voice != null) _voice.Pause(); } /// <summary> /// Stops the voice. /// </summary> public void StopVoice() { _voice.Pause(); _voice.Speak(string.Empty, SpeechVoiceSpeakFlags.SVSFPurgeBeforeSpeak); } /// <summary> /// Pauses the file. /// </summary> public void StopFile() { try { spFile.ISpStream_Close(); } catch (Exception) { } } /// <summary> /// 恢復 /// </summary> public void Resume() { if (_voice != null) _voice.Resume(); } } /// <summary> ///語音播報狀態 /// </summary> public enum VoiceStatus { /// <summary> /// The play /// </summary> Play, /// <summary> /// The ready /// </summary> Ready, /// <summary> /// The pause /// </summary> Pause, } }
但真的運用時,還需要支持循環播放,以及播放狀態。
private SpeechVoice _speaker; private bool _isLoopAudioFile; // 是否循環播放聲音文件 private bool _isLoopSpeech; //循環語音 private VoiceStatus speakStatus=VoiceStatus.Ready; private bool IsStopPlayFile; //是否停止 private bool IsStopPlayVoice; /// <summary> /// 播放文件結束 /// </summary> public event EventHandler PlayFileComplete; /// <summary> /// 播放文件開始 /// </summary> public event EventHandler PlayFileStart; /// <summary> /// 播放文件結束 /// </summary> public event EventHandler PlayAudioComplete; /// <summary> /// 播放文件開始 /// </summary> public event EventHandler PlayAudioStart; /// <summary> /// 播放語言 /// </summary> /// <param name="voiceContent">Content of the voice.</param> public void SpeechVoice(string voiceContent) { IsStopPlayVoice = false; if (speakStatus == VoiceStatus.Play) return; //正在播放就返回 Speaker.Resume(); Action invoke = () => { OnPlayAudioStart();//觸發開始播放事件 speakStatus = VoiceStatus.Play; Speaker.Speak(voiceContent); }; invoke.BeginInvoke(VoiceCallback, invoke); } private void VoiceCallback(IAsyncResult ar) { var ac = ar.AsyncState as Action; if (ac != null) { try//原dll不能多次停止 所以加了try catch 和狀態判斷 { if ((IsLoopSpeech) && !IsStopPlayVoice) { //一次播放結束之后如果是循環播放 就繼續播放 ac.BeginInvoke(VoiceCallback, ac); } else { speakStatus = VoiceStatus.Pause; //觸發停止事件 OnPlayAudioComplete(this, new EventArgs()); ac.EndInvoke(ar); } } catch (Exception) { } } } //以下同理 /// <summary> /// 暫停播放 /// </summary> public void StopSpeechVoice() { if (IsStopPlayVoice) return; IsStopPlayVoice = true; speakStatus = VoiceStatus.Pause; Action invoke = () => Speaker.StopVoice(); invoke.BeginInvoke(null, invoke); OnPlayAudioComplete(this, new EventArgs()); } /// <summary> /// 停止播放聲音文件 /// </summary> public void StopPlayer() { if (IsStopPlayVoice) return; IsStopPlayFile = true; speakStatus = VoiceStatus.Pause; Speaker.PauseFile(); OnPlayFileComplete(this, new EventArgs()); } /// <summary> /// 播放聲音文件 /// </summary> public void PlayAudioFile() { player = new SoundPlayer { SoundLocation = _audioFile.FilePath }; if(speakStatus==VoiceStatus.Play) return; IsStopPlayFile = false; if (File.Exists(_audioFile.FilePath)) { Action invoke = () => { OnPlayFileStart(); speakStatus = VoiceStatus.Play; Speaker.PlaySound(_audioFile.FilePath); }; invoke.BeginInvoke(Callback, invoke); } } /// <summary> /// Called when [play start]. /// </summary> public void OnPlayFileStart() { var handler = PlayFileStart; if (handler != null) handler(this, EventArgs.Empty); } /// <summary> /// Called when [play start]. /// </summary> public void OnPlayAudioStart() { var handler = PlayAudioStart; if (handler != null) handler(this, EventArgs.Empty); } /// <summary> /// Called when [play complete]. /// </summary> /// <param name="sender">The sender.</param> /// <param name="e">The <see cref="EventArgs"/> instance containing the event data.</param> public void OnPlayAudioComplete(object sender, EventArgs e) { EventHandler handler = PlayAudioComplete; if (handler != null) handler(this, EventArgs.Empty); } /// <summary> /// Called when [play complete]. /// </summary> /// <param name="sender">The sender.</param> /// <param name="e">The <see cref="EventArgs"/> instance containing the event data.</param> public void OnPlayFileComplete (object sender, EventArgs e) { EventHandler handler = PlayFileComplete; if (handler != null) handler(this, EventArgs.Empty); } /// <summary> /// Callbacks the specified ar. /// </summary> /// <param name="ar">The ar.</param> private void Callback(IAsyncResult ar) { var ac = ar.AsyncState as Action; if (ac != null) { OnPlayFileComplete(this,new EventArgs()); try { if ((IsLoopAudioFile)&& !IsStopPlayFile) { ac.BeginInvoke(Callback, ac); } else { speakStatus = VoiceStatus.Pause; ac.EndInvoke(ar); } } catch (Exception) { } } }
語音播放小Demo:SpeechVoice
在繁體系統,或者英文系統下面,有時候出現只能播報英文的情況,這個是猶豫語言資源沒有安裝。
判斷操作系統是否安裝中文最簡單的方法:
64位系統:查看C:\Program Files (x86)\Common Files\SpeechEngines\Microsoft\TTS20路徑下是否有zh-CHS文件夾
32位系統:查看C:\Program Files\Common Files\SpeechEngines\Microsoft\TTS20路徑下是否有zh-CHS文件夾
如果不存在則表明缺少中文語言包,一般情況下,win7及以上的中文操作系統都自帶了,不需要安裝,其他操作系統基本上都沒有安裝,簡體XP系統也沒有安裝
安裝方法是:
1、 打開控制面板的window update,見下圖:
2. 選擇檢查更新按鈕,然后再更新列表中選擇“可用的附件程序”
3、 選擇簡體中文語言包,勾選並安裝即可
4、 安裝完成后可以檢查C:\Program Files (x86)\Common Files\SpeechEngines\Microsoft\TTS20路徑下是否有zh-CHS文件夾,有則表明安裝成功
安裝成功以后就可以使用語音播報功能了。