中文信息处理技术专栏
0.引言
文本语音合成又称文语转换(Text To Speech,TTS),也就是“从文本到语音”。TTS是利用计算机等平台将文本信息转变为音频数据,然后用语音的方式播放出来的技术。它是自然人机接口等研究领域的一项关键技术,具有重要的应用与经济价值。
TTS追求的目标是让计算机输出的声音不仅清晰、可懂,而且要自然、具有表现力。经过国内外大量科研机构的研究与开发,目前TTS语音的清晰度、可懂度等问题已经基本解决,但是输出的语音在自然度、表现力和个性化等方面还存在许多需要研究和解决的问题。
1.TTS的应用
如果是语音识别技术是为计算机增加了耳朵,图形图像识别技术是为计算机添加了眼睛,那么TTS技术就等同于为计算机扩展了嘴巴。TTS有极其广泛的应用领域和使用场合,即使目前该技术的研究尚有极大的提高空间,也已经在人们的生活中被广泛使用。例如:医院候诊自动叫号系统会念出病员姓名和应该去的诊室;行车导航软件能使用语音指导驾驶人员就行驾驶操作;在计算机辅助教学系统和电子词典中使用TTS能够向用户演示单词、汉字的发音。
2.TTS的工作原理
TTS系统一般包括两个主要功能模块:语言处理模块和语音处理模块。语言处理模块的主要任务是分析输入的文本句子,识别出短语、词、专用名称、缩略语、特殊符号等语言单位,将文本句子转换为注音符号表示形式并添加控制符。语言处理模块的输出作为语音处理模块的输入.语音处理模块对于每一个注音符号在语音语料库中查找它的一个合适实例,然后将文本句子对应的所有注音符号的实例拼接起来,在拼接过程中根据控制符的语义对语音实例的音长、韵律特征和停顿时间等进行调整,最后输出一个句子的完整的语音数据流。
3.汉字的发音
汉字属于单音节文字,虽然有数万个汉字,但是汉字的发音是非常少的,也就是说同音字很多。所有的汉字大约417个音节,加上声调舍去没有的发音之后大约1300个变化,因此如果有了汉字拼音对照表以及发言文件,制作一个逐字发音的TTS程序并不困难。
播放声音可以通过Windows API进行,其中最常用的函数是PlaySound函数,该函数原型如下:
BOOL PlaySound(LPCSTR pszSound, HMODULE hwnd,DWORD fdwSound);
参数pszSound是指定了要播放声音的字符串,该参数可以是WAVE文件的名字,或是WAV资源的名字,或是内存中声音数据的指针,或是在系统注册表WIN.INI中定义的系统事件声音。如果该参数为NULL则停止正在播放的声音。
参数hwnd是应用程序的实例句柄,除非pszSound的指向一个资源标识符(即fdwSound被定义为SND_RESOURCE),否则必须设置为NULL。
参数fdwSound是标志的组合,常用标记的说明如表1所示,如果需要所有标记,请参阅MSDN。
表1 PlaySound播放标志说明
标记 | 说明 |
SND_APPLICATION | 用应用程序指定的关联程序来播放声音。 |
SND_ASYNC | 用异步方式播放声音,在开始播放后函数立即返回。 |
SND_FILENAME | pszSound参数指定了WAVE文件名。 |
SND_LOOP | 重复播放声音,必须与SND_ASYNC标志一块使用。 |
SND_MEMORY | 播放载入到内存中的声音,此时pszSound是指向声音数据的指针。 |
SND_NODEFAULT | 不播放缺省声音,若无此标志,则PlaySound在没找到声音时会播放缺省声音。 |
SND_NOSTOP | PlaySound不打断原来的声音播出并立即返回FALSE。 |
SND_NOWAIT | 如果驱动程序正忙则函数就不播放声音并立即返回。 |
SND_PURGE | 停止所有与调用任务有关的声音。若参数pszSound为NULL,就停止所有的声音,否则,停止它指定的声音。 |
SND_SYNC | 同步播放声音,在播放完后PlaySound函数才返回。 |
若PlaySound播放成功则函数返回TRUE,否则返回FALSE
4.微软的SAPI
微软从2000年开始免费提供了SAPI(The Microsoft Speech API)供第三方程序员使用包装后的语音技术。在进行开发的时候只需要安装了Windows Speech SDK就可以使用SAPI,SAPI包括以下几类接口:Voice Commands API、Voice Dictation API、Voice Text API、Voice Telephone API和Audio Objects API。对于语音合成需要使用的是Voice Text API中的系列函数。
如果是Windows XP操作系统可以在微软的官网上下载到Windows Speech SDK以及语言包(https://www.microsoft.com/en-us/download/details.aspx?id=10121)。如果是XP之后版本的操作系统,例如:Windows Vista/7/8/8.1/10,其中已经携带该开发包,无需额外安装。
SAPI提供了一系列接口函数用于对朗读的过程进行设置与控制,表2列出了主要的设置和控制函数,可以参阅MSDN获取全部函数以及这些函数的详细说明。
表2 SPAI主要控制接口函数和说明
函数名 | 说明 |
SetRate | 设置朗读速度,取值范围:-10到10 |
GetRate | 获取朗读速度 |
SetVoice | 设置使用的语音库 |
GetVoice | 获取使用的语音库 |
Pause | 暂停朗读 |
Resume | 恢复朗读 |
SetVolume | 设置音量,范围:0到100 |
GetVolume | 获取音量 |
SetSyncSpeakTimeout | 设置同步朗读超时时间,单位为毫秒 |
GetSyncSpeakTimeout | 获取同步朗读超时时间,单位为毫秒 |
5.SAPI的使用
在程序中使用微软的TTS功能,主要可以分为初始化语音引擎环境、播放文本语音和释放环境几个步骤,下面以C/C++为开发语言简要介绍其中的细节。
1)添加头文件和引用lib库
主要需要添加两个头文件和一个lib库,相关代码如下:
#include sapi.h
#include sphelper.h
#pragma comment(lib,sapi.lib)
2)初始化TTS引擎环境
该引擎是以COM组件形式实现的,因此初始化的过程就是初始化一个COM组建并得到TTS引擎的指针,代码如下:
ISpVoice *pSpVoice; // 定义TTS引擎接口指针
::CoInitialize(NULL); // COM初始化
CoCreateInstance(CLSID_SpVoice,
NULL,
CLSCTX_INPROC_SERVER,
IID_ISpVoice,
(void**)&pSpVoice);
// 获取ISpVoice接口指针
3)播放文字的语音
获取到ISpVoice接口指针以后,用户就可以通过pSpVoice指针调用SAPI的表14.2中的这些接口函数完成各种设置,然后再调用Speak函数进行朗读了。Speak函数的原型如下:
HRESULT Speak(
LPCWSTR *pwcs,
DWORD dwFlags,
ULONG *pulStreamNumber
);
其中第一个参数pwcs用于指向待朗读的字符串,dwFlags是用于控制朗读方式的标志,它可以是枚举 SPEAKFLAGS成员的组合,该函数默认是同步朗读,但如果该参数SPF_ASYNC就表示使用异步朗读,这里的异步和同步的工作模式和PlaySound中的完全一样,不在累赘解释。pulStreamNumber为异步朗读时带回的流编号,当同步朗读时,该参数为NULL。如下代码是请求TTS引擎异步朗读了一段中文的语言。
pSpVoice ->SetVolume(80); //设置音量
pSpVoice ->Speak(TEXT(面朝大海,春暖花开,山海关!),
SPF_ASYNC , //异步播放
NULL);
4)释放资源
当不再需要TTS朗读的时候,需要释放TTS引擎,具体代码如下:
pSpVoice->Release();
::CoUninitialize();
6.利用XML定制SAPI TTS
人们真正的朗读过程中,会有时快有时慢,有时会因为强调而重读。为了国家贴合用户的需求,SAPI提供了对XML支持,允许用户以XML的形式描述数据,从而实现深度定制朗读过程。具体的XML描述的细节可以参见如下网页:https: //msdn.microsoft.com/en-us/library/ms717077(v=vs.85).aspx,通过该方法可以对朗读的时间、日期、货币、速度、音量、朗读音量等进行个性化定制。有时人们需要把数字以整数的形式念出来(例如:金额),但有时应该是念成每个数字符号(例如:电话号码),下面的例子演示了利用XML定制的代码。
pSpVoice->Speak(TEXT(110), //以整数朗读
SPF_DEFAULT,
NULL);
pSpVoice->Speak(TEXT(<spell>110</spell>), //依次朗读每个数字符号
SPF_DEFAULT|SPF_IS_XML,
NULL);
地址:苏州市十梓街1号 18新利体育 纵横研究所联系电话:0512-65243192电子邮箱:ckc@suda.edu.cn
Copyright © 18新利体育 纵横汉字信息技术研究所 2017