我正在研究flashcard程序的文本到語音實現。應該讀出不同語言的文本。爲了正確地做到這一點,用戶必須選擇要閱讀的文本的語言(稍後將被存儲和使用而沒有問題)。獲取可用於文本到語音的語言環境(TTS)
是否有可能在Android系統上獲得可用的TTS語言?如果沒有,是否有可能獲得系統上所有可用的語言環境?
我想,我知道了:getAvailableLocales()
和tts.isLocaleAvailable(locale)
我正在研究flashcard程序的文本到語音實現。應該讀出不同語言的文本。爲了正確地做到這一點,用戶必須選擇要閱讀的文本的語言(稍後將被存儲和使用而沒有問題)。獲取可用於文本到語音的語言環境(TTS)
是否有可能在Android系統上獲得可用的TTS語言?如果沒有,是否有可能獲得系統上所有可用的語言環境?
我想,我知道了:getAvailableLocales()
和tts.isLocaleAvailable(locale)
您可以使用以下功能的設備的所有可用的語言環境。
Locale loc = new Locale("en");
Log.i("-------------",Arrays.toString(loc.getAvailableLocales()));
輸出
I/-------------(4390): [ar, ar_EG, bg, bg_BG, ca, ca_ES, cs, cs_CZ, da, da_DK, de, de_AT, de_BE, de_CH, de_DE, de_LI, de_LU, el, el_CY, el_GR, en, en
_AU, en_BE, en_BW, en_BZ, en_CA, en_GB, en_HK, en_IE, en_IN, en_JM, en_MH, en_MT, en_NA, en_NZ, en_PH, en_PK, en_RH, en_SG, en_TT, en_US, en_US_POSIX,
en_VI, en_ZA, en_ZW, es, es_AR, es_BO, es_CL, es_CO, es_CR, es_DO, es_EC, es_ES, es_GT, es_HN, es_MX, es_NI, es_PA, es_PE, es_PR, es_PY, es_SV, es_US
, es_UY, es_VE, et, et_EE, eu, eu_ES, fa, fa_IR, fi, fi_FI, fr, fr_BE, fr_CA, fr_CH, fr_FR, fr_LU, fr_MC, gl, gl_ES, hr, hr_HR, hu, hu_HU, in, in_ID,
is, is_IS, it, it_CH, it_IT, iw, iw_IL, ja, ja_JP, kk, kk_KZ, ko, ko_KR, lt, lt_LT, lv, lv_LV, mk, mk_MK, ms, ms_BN, ms_MY, nl, nl_BE, nl_NL, no, no_N
O, no_NO_NY, pl, pl_PL, pt, pt_BR, pt_PT, ro, ro_RO, ru, ru_RU, ru_UA, sh, sh_BA, sh_CS, sh_YU, sk, sk_SK, sl, sl_SI, sq, sq_AL, sr, sr_BA, sr_ME, sr_
RS, sv, sv_FI, sv_SE, th, th_TH, tr, tr_TR, uk, uk_UA, vi, vi_VN, zh, zh_CN, zh_HK, zh_HANS_SG, zh_HANT_MO, zh_MO, zh_TW]
別人已經做的辛勤工作,在http://kaviddiss.com/2012/08/12/android-text-to-speech-languages/
爲了節省您的時間,這裏是他們的代碼片段
TextToSpeech tts = ...
// let's assume tts is already inited at this point:
Locale[] locales = Locale.getAvailableLocales();
List<Locale> localeList = new ArrayList<Locale>();
for (Locale locale : locales) {
int res = tts.isLanguageAvailable(locale);
if (res == TextToSpeech.LANG_COUNTRY_AVAILABLE) {
localeList.add(locale);
}
}
// at this point the localeList object will contain
// all available languages for Text to Speech
結果取決於在其上選擇了TTS引擎。例如,我的一部手機包括Pico-TTS和Google文本到語音引擎。
Q-智能(越南手機與谷歌TTS作爲選擇的發動機)
D/SpeakRepeatedly(3979): Engine Google Text-to-speech Engine:com.google.android.tts
D/SpeakRepeatedly(3979): Engine Pico TTS:com.svox.pico
D/SpeakRepeatedly(3979): German (Germany):German:de_DE
D/SpeakRepeatedly(3979): English (United Kingdom):English:en_GB
D/SpeakRepeatedly(3979): English (United States):English:en_US
D/SpeakRepeatedly(3979): English (United States,Computer):English:en_US_POSIX
D/SpeakRepeatedly(3979): Spanish (Spain):Spanish:es_ES
D/SpeakRepeatedly(3979): French (France):French:fr_FR
D/SpeakRepeatedly(3979): Italian (Italy):Italian:it_IT
D/SpeakRepeatedly(3979): Portuguese (Brazil):Portuguese:pt_BR
D/SpeakRepeatedly(3979): Portuguese (Portugal):Portuguese:pt_PT
而且隨着微微選擇
D/SpeakRepeatedly(4837): Engine Google Text-to-speech Engine:com.google.android.tts
D/SpeakRepeatedly(4837): Engine Pico TTS:com.svox.pico
D/SpeakRepeatedly(4837): German (Germany):German:de_DE
D/SpeakRepeatedly(4837): English (United Kingdom):English:en_GB
D/SpeakRepeatedly(4837): English (United States):English:en_US
D/SpeakRepeatedly(4837): English (United States,Computer):English:en_US_POSIX
D/SpeakRepeatedly(4837): Spanish (Spain):Spanish:es_ES
D/SpeakRepeatedly(4837): French (France):French:fr_FR
D/SpeakRepeatedly(4837): Italian (Italy):Italian:it_IT
注: 葡萄牙沒有在TTS設置UI上市。當我在我的應用程序中以編程方式選擇葡萄牙語時,它會說葡萄牙語口音! FWIW這裏是我的代碼選擇葡萄牙語(它接受巴西和葡萄牙語區域設置)。
if (locale.getDisplayName().startsWith("Portuguese")) {
Log.i(SPEAK_REPEATEDLY, "Setting Locale to: " + locale.toString());
tts.setLanguage(locale);
}
}
由於不同的TTS引擎isLanguageAvailable
返回不同的結果,我發現以下解決方案最上幾種常見的TTS引擎。
另請注意,從Android Lollipop開始,在TextToSpeech
中有一個簡單的方法,名爲getAvailableLanguages
,它很容易爲您(如果設備運行API 21或更高版本)執行此操作。
您需要在OnInitListener
的onInit
方法中指定TextToSpeech
對象的方法調用以下方法。
ArrayList<Locale> languages;
TextToSpeech initTTS;
private void initSupportedLanguagesLollipop()
{
Set<Locale> availableLocales = initTTS.getAvailableLanguages();
for (Locale locale : availableLocales)
{
languages.add(locale);
}
}
private void initSupportedLanguagesLegacy()
{
Locale[] allLocales = Locale.getAvailableLocales();
for (Locale locale : allLocales)
{
try
{
int res = initTTS.isLanguageAvailable(locale);
boolean hasVariant = (null != locale.getVariant() && locale.getVariant().length() > 0);
boolean hasCountry = (null != locale.getCountry() && locale.getCountry().length() > 0);
boolean isLocaleSupported =
false == hasVariant && false == hasCountry && res == TextToSpeech.LANG_AVAILABLE ||
false == hasVariant && true == hasCountry && res == TextToSpeech.LANG_COUNTRY_AVAILABLE ||
res == TextToSpeech.LANG_COUNTRY_VAR_AVAILABLE;
Log.d(TAG, "TextToSpeech Engine isLanguageAvailable " + locale + " (supported=" + isLocaleSupported + ",res=" + res + ", country=" + locale.getCountry() + ", variant=" + locale.getVariant() + ")");
if (true == isLocaleSupported)
{
languages.add(locale);
}
}
catch (Exception ex)
{
Log.e(TAG, "Error checking if language is available for TTS (locale=" + locale +"): " + ex.getClass().getSimpleName() + "-" + ex.getMessage());
}
}
}
在Android 5.0(API級21)開始,TextToSpeech.getAvailableLanguages
已被添加到提取一組由TTS引擎所支持的所有語言環境。
TextToSpeech tts; // assume this is initialized
tts.getAvailableLanguages(); // returns a set of available locales
我也注意到,由TextToSpeech.getAvailableLanguages
返回的Locale集合可能不是的Locale.getAvailableLocales
嚴格的子集,即有可能是由不被系統支持TTS引擎所支持的語言環境。
根據文檔http://developer.android.com/reference/java/util/Locale.html#getAvailableLocales%28%29 getAvailableLocales()是靜態的,因此不需要創建Locale對象。使用「Locale.getAvailableLocales()」是使用此方法的適當方式。 – JonnyBoy 2012-06-28 17:22:33
它以其他方式幫助我。謝謝。 – 2013-10-09 14:02:22