javascript - SpeechSynthesis in Android-Chrome: cannot change English voice from US English - Stack Overflow

admin2025-04-09  0

I'm using the speech synthesis API on Android-Chrome. The issue is that although there are 4 English voices available, it is always US English that is used by the browser, no matter what the code specifies. I can use other languages e.g. French, just not other English voices e.g en-AU, GB, or IN.

This code filters British English voice objects from the getVoices array and uses the first to utter the word 'tomato'. The problem is that the word is always pronounced "to-may-lo" not "to-mar-to" which means my text doesn't rhyme as it should.

The voice object that was used is displayed and (on the phones I've tried) is an GB one.

The html...

<!DOCTYPE html>
<html lang="en-GB">
    <head>
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>Let's not call the whole thing off</title>
        <script src="tomato.js" defer></script>
    </head>
    <body>
        <div id="tomato" lang="en-GB">Tomato</div>
        <div id="platform"></div>
    </body>
</html>

And the script...

var platform = document.getElementById("platform");
var tomato = document.getElementById("tomato");

var voices = [];
var voicesGB = [];
voices = speechSynthesis.getVoices();
speechSynthesis.onvoiceschanged = function() {
    voices = speechSynthesis.getVoices();
    voicesGB = voices.filter(voice => /en(-|_)GB/.test(voice.lang));
};

function speak(word) {
    var msg = new SpeechSynthesisUtterance();
    msg.default = false;
    msg.text = word;
    msg.voice = voicesGB[0];
    msg.lang = voicesGB[0].lang;
    window.speechSynthesis.speak(msg);
    for (var p in msg.voice) {
        platform.innerHTML += p + ': ' + msg.voice[p] + '<br>\n';
    }
}

tomato.addEventListener("click",() => {speak('tomato');});

And a jsbin: ,js,output Run this in Android Chrome and tap the word 'tomato'.

I have searched all over and tried various fixes. How do you control what voice Android-Chrome uses?

I'm using the speech synthesis API on Android-Chrome. The issue is that although there are 4 English voices available, it is always US English that is used by the browser, no matter what the code specifies. I can use other languages e.g. French, just not other English voices e.g en-AU, GB, or IN.

This code filters British English voice objects from the getVoices array and uses the first to utter the word 'tomato'. The problem is that the word is always pronounced "to-may-lo" not "to-mar-to" which means my text doesn't rhyme as it should.

The voice object that was used is displayed and (on the phones I've tried) is an GB one.

The html...

<!DOCTYPE html>
<html lang="en-GB">
    <head>
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>Let's not call the whole thing off</title>
        <script src="tomato.js" defer></script>
    </head>
    <body>
        <div id="tomato" lang="en-GB">Tomato</div>
        <div id="platform"></div>
    </body>
</html>

And the script...

var platform = document.getElementById("platform");
var tomato = document.getElementById("tomato");

var voices = [];
var voicesGB = [];
voices = speechSynthesis.getVoices();
speechSynthesis.onvoiceschanged = function() {
    voices = speechSynthesis.getVoices();
    voicesGB = voices.filter(voice => /en(-|_)GB/.test(voice.lang));
};

function speak(word) {
    var msg = new SpeechSynthesisUtterance();
    msg.default = false;
    msg.text = word;
    msg.voice = voicesGB[0];
    msg.lang = voicesGB[0].lang;
    window.speechSynthesis.speak(msg);
    for (var p in msg.voice) {
        platform.innerHTML += p + ': ' + msg.voice[p] + '<br>\n';
    }
}

tomato.addEventListener("click",() => {speak('tomato');});

And a jsbin: https://jsbin./xefukemuga/edit?html,js,output Run this in Android Chrome and tap the word 'tomato'.

I have searched all over and tried various fixes. How do you control what voice Android-Chrome uses?

Share Improve this question edited Oct 24, 2018 at 19:34 Frazer asked Oct 24, 2018 at 17:42 FrazerFrazer 1,0891 gold badge10 silver badges16 bronze badges 6
  • Did you fix it? I had a similar issue and found a workaround, see my answer here: stackoverflow./questions/56728654/… – royappa Commented Jun 24, 2019 at 13:19
  • Well, I see your code filters on '_' so maybe that is not the issue unless voicesGB[0].long still has a dash. – royappa Commented Jun 24, 2019 at 13:26
  • @royappa the code filters on dash or underscore: /en(-|_)GB/ – Frazer Commented Jun 24, 2019 at 18:46
  • I saw, but I assume what ends up in msg.lang would match what the platform stores, but if not, maybe you have replace '-' with '_'? Or have you resolved the issue already some other way? I'm still interested in this problem as it doesn't make sense why the platforms don't follow the clear standard. – royappa Commented Jun 25, 2019 at 0:47
  • 1 @royappa No, the issue is still unresolved. – Frazer Commented Jun 27, 2019 at 14:17
 |  Show 1 more ment

2 Answers 2

Reset to default 6

The only way to work around this issue on Android version 5.0.2 is to change the default voice in the Android settings and then restart the device. That will let you use the voice you want, but the other English ones will then be unavailable. Here is some more detail:

SpeechSynthesis.getVoices() will return several options for English (United States, Australia, Nigeria, India, and United Kingdom) but only one is available at a time. You can pick which one by going to the Settings app, then Controls->Language and input->Text-to-speech options. Select the gear icon next to Google Text-to-speech Engine, then under Language you can update the exact locale you want to use. If you select "Install voice data" you can even select from a sample of different voices for some locales. You need to restart the device after changing this setting for it to take effect.

The voice used on an Android device when you play a SpeechSynthesisUtterance will depend on what you have selected in the Android settings. You can choose which language you want to play from javascript (see below for details) but you have no control over the locale or exact voice used.

This problem occurs on Chrome and Firefox, so it is likely a problem with the Android platform's implementation of the speechSynthesis API. It's unlikely that a browser update will fix this, but different versions of Android might. (My test device is on Android 5.0.2, so if this is fixed in a future update, please let me know).

With the latest version of Android (13) you can switch the system settings (System -> Languages & input -> Text-to-speech output). If you change the language to "English (United Kingdom)" you can then use that in your web app. This is obviously not ideal for your users, but if you are developing an app only for yourself, it works great.

转载请注明原文地址:http://conceptsofalgorithm.com/Algorithm/1744202733a235876.html

最新回复(0)