#include "CWinTTS.h"
CWinTTS::CWinTTS(void)
{
m_pIEnumSpObjectTokens = NULL;
m_pISpObjectToken = NULL;
m_pISpVoice = NULL;
m_bComInit = FALSE;
initEngine();
}
CWinTTS::~CWinTTS(void)
{
UnInit();
m_pIEnumSpObjectTokens->Release();
m_pISpObjectToken->Release();
DeleteSpVoice();
}
void CWinTTS::initEngine()
{
Init();
QString arrayVoicePackageName[50] = {0};
int nVoicePackageNameCount = 50;
int nCount = EnumAudioToken(arrayVoicePackageName,nVoicePackageNameCount);
CreateSpVoice();
ISpObjectToken* ppToken = NULL;
GetVoice(0,&ppToken);
SetVoice(ppToken);
SetRate(0);
SetVolume(100);
}
int CWinTTS::Init()
{
//初始化COM组件
if(FAILED(::CoInitializeEx(NULL,0)))
{
return -1;
}
m_bComInit = TRUE;
return 0;
}
int CWinTTS::UnInit()
{
if(m_bComInit)
{
::CoUninitialize();
}
return 0;
}
int CWinTTS::EnumAudioToken(QString arrayVoicePackageName[],int nVoicePackageNameCount)
{
//枚举所有语音Token
if(SUCCEEDED(SpEnumTokens(SPCAT_VOICES, NULL, NULL, &m_pIEnumSpObjectTokens)))
{
//得到所有语音Token的个数
ULONG ulTokensNumber = 0;
m_pIEnumSpObjectTokens->GetCount(&ulTokensNumber);
//检测该机器是否安装有语音包
if(ulTokensNumber == 0)
{
return -1;
}
if(ulTokensNumber > nVoicePackageNameCount)
{
return 0;
}
//将语音包的名字加入数组中
QString strVoicePackageName = "";
QString strTokenPrefixText = "HKEY_LOCAL_MACHINE\\SOFTWARE\\Microsoft\\Speech\\Voices\\Tokens\\" ;
for(ULONG i=0; i<ulTokensNumber; i++)
{
m_pIEnumSpObjectTokens->Item(i, &m_pISpObjectToken);
WCHAR* pChar;
m_pISpObjectToken->GetId(&pChar);
strVoicePackageName = QString::fromStdWString(pChar) ;
strVoicePackageName = strVoicePackageName.mid(strTokenPrefixText.size());
arrayVoicePackageName[i] = strVoicePackageName;
}
return ulTokensNumber;
}
return -1;
}
//创建SpVoice
int CWinTTS::CreateSpVoice()
{
//获取ISpVoice接口
if(FAILED(CoCreateInstance(CLSID_SpVoice, NULL, CLSCTX_INPROC_SERVER, IID_ISpVoice, (void**)&m_pISpVoice)))
{
return -1;
}
return 0;
}
//释放SpVoice
int CWinTTS::DeleteSpVoice()
{
if(m_pISpVoice != NULL)
{
m_pISpVoice->Release();
}
m_pISpVoice = NULL;
return 0;
}
//重置SpVoice
int CWinTTS::ResetSpVoice()
{
DeleteSpVoice();
return CreateSpVoice();
}
//设置朗读速度(取值范围:-10到10)
int CWinTTS::SetRate( long RateAdjust)
{
if(m_pISpVoice == NULL)
{
return -1;
}
//设置播放速度
m_pISpVoice->SetRate(RateAdjust);
return 0;
}
//获取朗读速度
int CWinTTS::GetRate(long *pRateAdjust)
{
if(m_pISpVoice == NULL)
{
return -1;
}
m_pISpVoice->GetRate(pRateAdjust);
return 0;
}
//设置使用的语音库
int CWinTTS::SetVoice(ISpObjectToken *pToken)
{
if(m_pISpVoice == NULL)
{
return -1;
}
m_pISpVoice->SetVoice(pToken);
return 0;
}
//获取语音库
int CWinTTS::GetVoice(unsigned int nIndex,ISpObjectToken** ppToken)
{
if(m_pIEnumSpObjectTokens == NULL)
{
return -1;
}
//设置语言
m_pIEnumSpObjectTokens->Item(nIndex, ppToken);
m_pISpObjectToken = *ppToken;
return 0;
}
//设置音量(取值范围:0到100)
int CWinTTS::SetVolume(USHORT usVolume)
{
if(m_pISpVoice == NULL)
{
return -1;
}
//设置音量大小
m_pISpVoice->SetVolume(usVolume);
return 0;
}
//获取音量
int CWinTTS::GetVolume(USHORT *pusVolume)
{
if(m_pISpVoice == NULL)
{
return -1;
}
//设置音量大小
m_pISpVoice->GetVolume(pusVolume);
return 0;
}
bool CWinTTS::isVoiceReady()
{
if(m_pISpVoice == NULL)
{
return false;
}
SPVOICESTATUS voiceStatus;
// 当前播放
if(S_OK == m_pISpVoice->GetStatus(&voiceStatus, NULL))
{
if (voiceStatus.dwRunningState == SPRS_DONE )
{
return true;
}
}
return false;
}
// 停止朗读
int CWinTTS::Stop()
{
return ResetSpVoice();
}
//开始朗读
int CWinTTS::Speak(QString strContent, DWORD dwFlags)
{
if(m_pISpVoice == NULL)
{
return -1;
}
LPCTSTR speakContent = reinterpret_cast<const wchar_t *>(strContent.utf16());
//开始进行朗读
HRESULT hSucess = m_pISpVoice->Speak(speakContent, dwFlags, NULL);
return 0;
}
//朗读生成文件
int CWinTTS::SpeakToWaveFile(QString strContent,char *pFilePathName,DWORD dwFlags)
{
if(m_pISpVoice == NULL || pFilePathName == NULL)
{
return -1;
}
//生成WAV文件
CComPtr<ISpStream> cpISpStream;
CComPtr<ISpStreamFormat> cpISpStreamFormat;
CSpStreamFormat spStreamFormat;
m_pISpVoice->GetOutputStream(&cpISpStreamFormat);
spStreamFormat.AssignFormat(cpISpStreamFormat);
HRESULT hResult = SPBindToFile(pFilePathName, SPFM_CREATE_ALWAYS,
&cpISpStream, &spStreamFormat.FormatId(), spStreamFormat.WaveFormatExPtr());
if(SUCCEEDED(hResult))
{
LPCTSTR speakContent = reinterpret_cast<const wchar_t *>(strContent.utf16());
m_pISpVoice->SetOutput(cpISpStream, TRUE);
m_pISpVoice->Speak(speakContent, dwFlags, NULL);
return 0;
}
else
{
return 1;
}
}
//暂停朗读
int CWinTTS::Pause()
{
if(m_pISpVoice != NULL)
{
m_pISpVoice->Pause();
}
return 0;
}
//继续朗读
int CWinTTS::Resume()
{
if(m_pISpVoice != NULL)
{
m_pISpVoice->Resume();
}
return 0;
}