一. ? 基礎(chǔ)知識(shí)
TextToSpeech ? 簡(jiǎn)稱? ? TTS ? , ? 稱為語(yǔ)音合成, ? 是 ? Android? ? 從 ? 1.6版本 ? 開始支持 ? 的新功能 ? ,能 ? 將所指定的文本轉(zhuǎn)成不同語(yǔ)言音頻輸出。
在具體介紹前我們先來(lái)看下Adnroid系統(tǒng)帶的TTS設(shè)置界面,點(diǎn)擊Settings->Speech?synthesis,如下圖所示:
圖?1?Android?TTS設(shè)置界面
??? 當(dāng)點(diǎn)擊“Listen?to?an?example”時(shí),會(huì)發(fā)出“ This?is?an?example?of?speech?synthesis?in?English. ? ”,如果沒(méi)有安裝 ? TTS?Data的話可以點(diǎn)擊第二項(xiàng)安裝,在? Default?settings ?可以設(shè)置? Speech?rate ?和? Language ?,如下圖? 2 ?所示可以知道? TTS ?支持的語(yǔ)言。
圖 2?TTS ?語(yǔ)言選擇
??? 如果勾選“ Always?use?my?settings ?”時(shí)要注意,設(shè)置了這個(gè)選項(xiàng)后那么我們就不能在程序中對(duì) speech?rate ?和? Languages ?進(jìn)行設(shè)置了,這里的設(shè)置回覆蓋我們程序中的設(shè)置。
TTS功能需要有TTS?Engine的支持,下面我們就來(lái)了解下android提供的TTS?Engine。
Android使用了叫Pico的支持多種語(yǔ)言的語(yǔ)音合成引擎,Pico在后臺(tái)負(fù)責(zé)把分析輸入的文本,把分本分成他能識(shí)別的各個(gè)片段,再把合成的各個(gè)語(yǔ)音片段以聽起來(lái)比較自然的方式連接在一起,這個(gè)過(guò)程Android系統(tǒng)幫我們做,我們只把他當(dāng)做一個(gè)神奇的過(guò)程就可以了。
TTS?engine 依托于當(dāng)前 ?Android?Platform? 所支持的幾種主要的語(yǔ)言: ?English? 、 ?French? 、 ?German? 、 ?Italian? 和 Spanish? 五大語(yǔ)言 ? (暫時(shí)也是沒(méi)有對(duì)中文提供支持)。 ? TTS 可以將文本隨意的轉(zhuǎn)換成以上任意五種語(yǔ)言的語(yǔ)音輸出。與此同時(shí),對(duì)于個(gè)別的語(yǔ)言版本將取決于不同的時(shí)區(qū),例如:對(duì)于 ?English? ,在 ?TTS? 中可以分別輸出美式和英式兩種不同的版本 ? 。
二. ? 實(shí)例分析
下面我們先做一個(gè)具體的實(shí)例來(lái)親自體會(huì)一下Android的TTS的效果。
我們做一個(gè)簡(jiǎn)單的輸入英文句子然后朗讀出來(lái)的例子,了解Android的TTS使用方法。
在具體做之前給個(gè)AndroidTTS的API的鏈接,
http://androidappdocs.appspot.com/reference/android/speech/tts/package-summary.html
可以先看下大概了解TTS提供的功能。
圖3?Android?TTS?API
可以看到TTS提供了兩個(gè)接口和兩個(gè)類。
我們希望做的效果如下:
圖4?實(shí)現(xiàn)效果圖
上面一個(gè)輸入框,點(diǎn)擊Speak按鈕則朗讀上面的文字內(nèi)容。
創(chuàng)建一個(gè)Android工程,工程名為AndroidTTSDemoFirst,其中SDK必須選擇1.6版本及以上。
其中Main.xml文件很簡(jiǎn)單,如下所示:
?
- <? xml ? version = "1.0" ? encoding = "utf-8" ?> ??
- < LinearLayout ? xmlns:android = "http://schemas.android.com/apk/res/android" ??
- ???? android:orientation = "vertical" ??
- ???? android:layout_width = "fill_parent" ??
- ???? android:layout_height = "fill_parent" ??
- ???? > ??
- ???? < EditText ? android:id = "@+id/inputText" ???
- ???????????????? android:hint = "Input?the?text?here!" ???
- ???????????????? android:layout_width = "fill_parent" ???
- ???????????????? android:layout_height = "wrap_content" > ??
- ???????????????? </ EditText > ??
- ???? < Button ? android:text = "Speak" ???
- ???????????????? android:id = "@+id/speakBtn" ???
- ???????????????? android:layout_width = "wrap_content" ???
- ???????????????? android:layout_height = "wrap_content" ??
- ???????????????? android:layout_gravity = "center_horizontal" ??
- ???????????????? android:enabled = "false" ??
- ???????????????? > </ Button > ??
- </ LinearLayout > ??
?
Java文件的編寫:
要使用TTS得實(shí)現(xiàn)OnInitListener接口
?
- public ? class ?AndroidTTSDemoFirst? extends ?Activity? implements ?OnInitListener?{??
- ???? /**?Called?when?the?activity?is?first?created.?*/ ??
- ???? @Override ??
- ???? public ? void ?onCreate(Bundle?savedInstanceState)?{??
- ???????? super .onCreate(savedInstanceState);??
- ????????setContentView(R.layout.main);??
- ????}??
- ?? //實(shí)現(xiàn)TTS初始化接口 ??
- ???? @Override ??
- ???? public ? void ?onInit( int ?status)?{??
- ???????? //?TODO?Auto-generated?method?stub ??
- ??????????
- ????}??
- }??
?
接著定義好下面要用到的幾個(gè)變量:
?
- private ?EditText?inputText?=? null ;??
- private ?Button?speakBtn?=? null ;??
- ??? private ? static ? final ? int ?REQ_TTS_STATUS_CHECK?=? 0 ;??
- ??? private ? static ? final ?String?TAG?=? "TTS?Demo" ;??
- private ?TextToSpeech?mTts;??
?
雖然安裝Android1.6版本及之后的Android機(jī)器都默認(rèn)安裝了TTS引擎,但某些設(shè)備可能會(huì)因?yàn)榇鎯?chǔ)容量的限制而缺少安裝和語(yǔ)言對(duì)應(yīng)的資源文件,因此在使用TTS前,得先要檢查是否安裝了TTS語(yǔ)言數(shù)據(jù),在onCreate函數(shù)中添加以下內(nèi)容:
?
- //檢查TTS數(shù)據(jù)是否已經(jīng)安裝并且可用 ??
- ??Intent?checkIntent?=? new ?Intent();??
- ??checkIntent.setAction(TextToSpeech.Engine.ACTION_CHECK_TTS_DATA);??
- ??startActivityForResult(checkIntent,?REQ_TTS_STATUS_CHECK);??
?
這里啟動(dòng)一個(gè)新的Intent去檢查TTS數(shù)據(jù)是否已經(jīng)安裝,我們根據(jù)其返回的結(jié)果進(jìn)行處理,如下所示:
?
- protected ?? void ?onActivityResult( int ?requestCode,? int ?resultCode,?Intent?data)?{??
- ???????? if (requestCode?==?REQ_TTS_STATUS_CHECK)??
- ????????{??
- ???????????? switch ?(resultCode)?{??
- ???????????? case ?TextToSpeech.Engine.CHECK_VOICE_DATA_PASS:??
- ???????????????? //這個(gè)返回結(jié)果表明TTS?Engine可以用 ??
- ????????????{??
- ????????????????mTts?=? new ?TextToSpeech( this ,? this );??
- ????????????????Log.v(TAG,? "TTS?Engine?is?installed!" );??
- ??????????????????
- ????????????}??
- ??????????????????
- ???????????????? break ;??
- ???????????? case ?TextToSpeech.Engine.CHECK_VOICE_DATA_BAD_DATA:??
- ???????????????? //需要的語(yǔ)音數(shù)據(jù)已損壞 ??
- ???????????? case ?TextToSpeech.Engine.CHECK_VOICE_DATA_MISSING_DATA:??
- ???????????????? //缺少需要語(yǔ)言的語(yǔ)音數(shù)據(jù) ??
- ???????????? case ?TextToSpeech.Engine.CHECK_VOICE_DATA_MISSING_VOLUME:??
- ???????????????? //缺少需要語(yǔ)言的發(fā)音數(shù)據(jù) ??
- ????????????{??
- ???????????????? //這三種情況都表明數(shù)據(jù)有錯(cuò),重新下載安裝需要的數(shù)據(jù) ??
- ????????????????Log.v(TAG,? "Need?language?stuff:" +resultCode);??
- ????????????????Intent?dataIntent?=? new ?Intent();??
- ????????????????dataIntent.setAction(TextToSpeech.Engine.ACTION_INSTALL_TTS_DATA);??
- ????????????????startActivity(dataIntent);??
- ??????????????????
- ????????????}??
- ???????????????? break ;??
- ???????????? case ?TextToSpeech.Engine.CHECK_VOICE_DATA_FAIL:??
- ???????????????? //檢查失敗 ??
- ???????????? default :??
- ????????????????Log.v(TAG,? "Got?a?failure.?TTS?apparently?not?available" );??
- ???????????????? break ;??
- ????????????}??
- ????????}??
- ???????? else ??
- ????????{??
- ???????????? //其他Intent返回的結(jié)果 ??
- ????????}??
- ????????}??
?
如果返回CHECK_VOICE_DATA_PASS表示檢查成功,可以新建一個(gè) ? TextToSpeech ? ,否則就去下載 ? TTS數(shù)據(jù)。
當(dāng)TTS數(shù)據(jù)檢測(cè)成功創(chuàng)建一個(gè)TextToSpeech后,就會(huì)調(diào)用接口OnInitListener中定義的回調(diào)函數(shù)
?
- ? //實(shí)現(xiàn)TTS初始化接口 ??
- @Override ??
- public ? void ?onInit( int ?status)?{??
- ???? //?TODO?Auto-generated?method?stub ??
- ???? //TTS?Engine初始化完成 ??
- ???? if (status?==?TextToSpeech.SUCCESS)??
- ????{??
- ???????? int ?result?=?mTts.setLanguage(Locale.US);??
- ???????? //設(shè)置發(fā)音語(yǔ)言 ??
- ???????? if (result?==?TextToSpeech.LANG_MISSING_DATA?||?result?==?TextToSpeech.LANG_NOT_SUPPORTED)??
- ???????? //判斷語(yǔ)言是否可用 ??
- ????????{??
- ????????????Log.v(TAG,? "Language?is?not?available" );??
- ????????????speakBtn.setEnabled( false );??
- ????????}??
- ???????? else ??
- ????????{??
- mTts.speak( "This?is?an?example?of?speech?synthesis." ,?TextToSpeech.QUEUE_ADD,? null );??
- ????????????speakBtn.setEnabled( true );??
- ????????}??
- ????}??
- ??????
- }??
?
在這個(gè)回調(diào)函數(shù)里,我們?cè)O(shè)置語(yǔ)言,然后就可以進(jìn)行使用 ? TTS引擎進(jìn)行操作了。
創(chuàng)建一個(gè)TextToSpeech是需要占用資源的,因此我們要適時(shí)的釋放這個(gè)資源:
?
- @Override ??
- protected ? void ?onPause()?{??
- ???? //?TODO?Auto-generated?method?stub ??
- ???? super .onPause();??
- ???? if (mTts?!=? null )??
- ???????? //activity暫停時(shí)也停止TTS ??
- ????{??
- ????????mTts.stop();??
- ????}??
- }??
- ??
- @Override ??
- protected ? void ?onDestroy()?{??
- ???? //?TODO?Auto-generated?method?stub ??
- ???? super .onDestroy();??
- ???? //釋放TTS的資源 ??
- ????mTts.shutdown();??
- ????}??
?
最后,在onCreate函數(shù)中設(shè)置 ? EditText和Button的使用:
?
- ?????inputText?=?(EditText)findViewById(R.id.inputText);??
- ?????speakBtn?=?(Button)findViewById(R.id.speakBtn);??????????
- ??inputText.setText( "This?is?an?example?of?speech?synthesis." );??
- ?????speakBtn.setOnClickListener( new ?OnClickListener()?{??
- ??
- public ? void ?onClick(View?v)?{??
- ???? //?TODO?Auto-generated?method?stub ??
- ????mTts.speak(inputText.getText().toString(),?TextToSpeech.QUEUE_ADD,? null );??
- ???? //朗讀輸入框里的內(nèi)容 ??
- }??
- });??
?
至此,我們的 ? Demo就完成了,當(dāng)啟動(dòng)程序后,首先會(huì)朗讀“ This?is?an?example?of?speech?synthesis?in?English. ? ”,然后你在EditText中輸入內(nèi)容,點(diǎn)擊Speak按鈕就能把內(nèi)容給朗讀出來(lái)。
文章對(duì)應(yīng)的完整代碼例子可以在這里下載:
http://download.csdn.net/source/2610740
注:文章參加“
?首屆Google暑期大學(xué)生博客分享大賽——2010 Andriod篇
”
更多文章、技術(shù)交流、商務(wù)合作、聯(lián)系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號(hào)聯(lián)系: 360901061
您的支持是博主寫作最大的動(dòng)力,如果您喜歡我的文章,感覺(jué)我的文章對(duì)您有幫助,請(qǐng)用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點(diǎn)擊下面給點(diǎn)支持吧,站長(zhǎng)非常感激您!手機(jī)微信長(zhǎng)按不能支付解決辦法:請(qǐng)將微信支付二維碼保存到相冊(cè),切換到微信,然后點(diǎn)擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對(duì)您有幫助就好】元
