使用语音合成来说出字符串数组之间的暂停

时间:2016-05-14 20:34:02

标签: javascript text-to-speech speech-synthesis

我试图找出一种将字符串数组传递给Speech Synthesis API的可靠方法,并在说出每个数组项之间暂停。例如。说第1项,暂停x秒,说第2项等等。

我尝试使用API​​的onend方法/事件,但它只能在它完全停止工作之前工作几次,从那时起将其余的数组项目背靠背读取。

建议?



var dropdown = $('#item-select'),
  interval = $('#item-interval').val() * 1000,
  itemBtn = $('#item-btn'),
  stopBtn = $('#item-stop'),
  items = {
    'first': ['hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine', 'hello, sunshine'],
    'second': ['hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world', 'hello, world']
  };

if ('speechSynthesis' in window) {
  function speak(text) {
    var msg = new SpeechSynthesisUtterance();
    msg.text = text;

    speechSynthesis.speak(msg);
    
    msg.addEventListener('end', function(e) {
      speechSynthesis.pause();
      window.setTimeout(function() {
        speechSynthesis.resume();
      }, interval);
    });
  }
  
  itemBtn.on('click', function(evt) {
    currItem = items[dropdown.val()];
    for (var phrase in currItem) {
      speak(currItem[phrase]);
    }
  });
  stopBtn.on('click', function(evt) {
    speechSynthesis.cancel();
  });
} else {
  console.log('Voice synthesis isn\'t supported in your browser.');
}

<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

<select id='item-select'>
  <option selected value='first'>First Item</option>
  <option value='second'>Second Item</option>
</select>
<label for='item-interval'>Interval (seconds)</label>
<input id='item-interval' max='10' name='item-interval' type='range' value='2'>
<button id='item-btn'>Speak!</button>
<button id='item-stop'>CEASE FIRE</button>
&#13;
&#13;
&#13;

1 个答案:

答案 0 :(得分:3)

通过项目数组超时延迟的递归旅行怎么样:

function speak(list) {
    if (list.length) {
      var msg = new SpeechSynthesisUtterance();
      msg.text = list[0];

      speechSynthesis.speak(msg);

      msg.addEventListener('end', function(e) {
        window.setTimeout(() => {
            speak(list.slice(1));
        }, interval);
      });
    }
  }

  itemBtn.on('click', function(evt) {
    const list = items[dropdown.val()];  
    speak(list);
  });

它对我有用,但后来我遇到了一些奇怪的事情。 有时,SpeechSynthesis只是停止触发&#39;结束&#39;事件:

这个小提琴添加了一些日志来显示话语何时开始/结束;观察&#39;结束&#39;事件只是无缘无故地停止

https://jsfiddle.net/cak4bju9/2/

关于越野车行为的这篇文章很有用:

SpeechSynthesis API onend callback not working