如何等待/订阅从null更新的内部变量



我在浏览器中使用SpeechRecognition,并创建了一个语音服务:

this.recognition.addEventListener('result', (e) => {
if (e.results) {
let result = e.results[e.resultIndex];
console.log('Final? ' + result.isFinal);
let _transcript = result[0].transcript;
let _confidence = result[0].confidence;
if (result.isFinal) {
console.log('Final result: ' + _transcript);
this.finalText = _transcript; // <---------------- FinalText updated
} else {
console.log('Confidence? ' + _confidence);
if (_confidence > 0.6) {
this.finalText = _transcript;  // <---------------- FinalText updated
}
}
}
});

在我的服务中,我有一个start()函数,它用finalText string返回一个promise,但我目前检查finalText是否更新的方法是不对的。

return new Promise(async (resolve, reject) => {
let i = 0;
for (i = 0; i < 100; i++) {
// Keep checking for final text to update
if (this.finalText != null) {
console.log('Final text submitting response');
this.finalText = null;
return resolve('Success');
} else {
console.log('waiting');
if (this.isStoppedSpeech) { // True if we clicked stop() or if the 'end' event listener fires
return reject('Timeout');
}
}
await new Promise((r) => setTimeout(r, 500)); // sleep
}
}).catch((error) => {
console.error(error); // Timeout
this.stop();
});

我只想在this.FinalText有文本时返回。我在想也许我应该以某种方式订阅它,然后await this.FinalText。我只需要承诺就可以正常工作。

示例用法:

this.speech.start().then((s) => {
console.log('Done speaking');
if (this.speech.getLastPhrase() != null)
this.pushChat({
speak: this.speech.getLastPhrase()
});
});

我不想使用setTimeoutsetInterval。如何等待this.FinalText,然后返回start() function promise中的值?

这似乎是RXJSsubject的一个很好的用例。它是一个可观察到的,您可以根据需要发出值。

将最终文本实例化为Subject,并在想要发出值时调用.next()

finalText = new Subject<string>();
this.recognition.addEventListener('result', (e: any) => {
if (e.results) {
let result = e.results[e.resultIndex];
console.log('Final? ' + result.isFinal);
let _transcript = result[0].transcript;
let _confidence = result[0].confidence;
if (result.isFinal) {
console.log('Final result: ' + _transcript);
this.finalText.next(_transcript); // <---------------- FinalText updated
} else {
console.log('Confidence? ' + _confidence);
if (_confidence > 0.6) {
this.finalText.next(_transcript); // <---------------- FinalText updated
}
}
}
});

您可以订阅Subject,在每次.next()调用时执行代码:

this.finalText.subscribe((text) => {
console.log('Done speaking');
if (text)
this.pushChat({
speak: text,
});
});

还可以使用Angular的async管道自动更新html中的值。

<p>{{ finalText | async }}</p>

您绝对应该研究rxjs库/可观察性。您基本上用start()函数制作了一个可观测的原始版本。

最新更新