当AVSpeechUtterance
说话时,我想等到它完成之后再做其他事情。
有AVSpeechSynthesizer
的财产似乎表明发言时间:
这个问题听起来很愚蠢和简单,我想知道如何使用/检查这个属性,等到语音结束后再继续?
可替换地:
有一个代表,我对如何使用也毫无头绪,它有能力在话语结束时做某事:
有一个答案,here,说要使用它。但这对我没有帮助,因为我不知道如何使用代表。
这就是我设置口语课的方式:
import AVFoundation
class CanSpeak: NSObject, AVSpeechSynthesizerDelegate {
let voices = AVSpeechSynthesisVoice.speechVoices()
let voiceSynth = AVSpeechSynthesizer()
var voiceToUse: AVSpeechSynthesisVoice?
override init(){
voiceToUse = AVSpeechSynthesisVoice.speechVoices().filter({ $0.name == "Karen" }).first
}
func sayThis(_ phrase: String){
let utterance = AVSpeechUtterance(string: phrase)
utterance.voice = voiceToUse
utterance.rate = 0.5
voiceSynth.speak(utterance)
}
}
使用上面提到的isSpeaking
属性,在gameScene:
voice.sayThis(targetsToSay)
let initialPause = SKAction.wait(forDuration: 1.0)
let holdWhileSpeaking = SKAction.run {
while self.voice.voiceSynth.isSpeaking {print("STILL SPEAKING!")}
}
let pauseAfterSpeaking = SKAction.wait(forDuration: 0.5)
let doneSpeaking = SKAction.run {print("TIME TO GET ON WITH IT!!!")}
run(SKAction.sequence(
[ initialPause,
holdWhileSpeaking,
pauseAfterSpeaking,
doneSpeaking
]))
答案 0 :(得分:7)
委托模式是面向对象编程中最常用的设计模式之一,它并不像看起来那么难。对于您的情况,您可以简单地让您的类(游戏场景)成为CanSpeak类的委托。
protocol CanSpeakDelegate {
func speechDidFinish()
}
接下来将AVSpeechSynthesizerDelegate设置为CanSpeak类,声明CanSpeakDelegate然后使用AVSpeechSynthesizerDelegate委托函数。
class CanSpeak: NSObject, AVSpeechSynthesizerDelegate {
let voices = AVSpeechSynthesisVoice.speechVoices()
let voiceSynth = AVSpeechSynthesizer()
var voiceToUse: AVSpeechSynthesisVoice?
var delegate: CanSpeakDelegate!
override init(){
voiceToUse = AVSpeechSynthesisVoice.speechVoices().filter({ $0.name == "Karen" }).first
self.voiceSynth.delegate = self
}
func sayThis(_ phrase: String){
let utterance = AVSpeechUtterance(string: phrase)
utterance.voice = voiceToUse
utterance.rate = 0.5
voiceSynth.speak(utterance)
}
func speechSynthesizer(_ synthesizer: AVSpeechSynthesizer, didFinish utterance: AVSpeechUtterance) {
self.delegate.speechDidFinish()
}
}
最后,在您的游戏场景类中,只需符合CanSpeakDelegate并将其设置为CanSpeak类的委托。
class GameScene: NSObject, CanSpeakDelegate {
let canSpeak = CanSpeak()
override init() {
self.canSpeak.delegate = self
}
// This function will be called every time a speech finishes
func speechDidFinish() {
// Do something
}
}
答案 1 :(得分:1)
设置AVSpeechSynthesizer实例的委托。
voiceSynth.delegate = self
然后,实现didFinish
方法如下:
func speechSynthesizer(_ synthesizer: AVSpeechSynthesizer,
didFinish utterance: AVSpeechUtterance) {
// Implements here.
}
答案 2 :(得分:-1)
使用方法尝试AVSpeechSynthesizerDelegate
:
- (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer didFinishSpeechUtterance:(AVSpeechUtterance *)utterance;