我目前正在制作一个节拍器应用程序,它使用AKMetronome作为核心部分,因为它具有回调功能,我需要回调功能以使节拍形象化,我也想将其用于自定义的点击声音(而且我会静音AKMetronome的原始声音,但仍会播放,只是没有原始声音。
现在,我有两个wav文件,它们是自定义的点击声音,将有两个AKPlayer播放它,并且需要在每个AKMetronome节拍的回调中触发AKPlayers。 由于AKPlayer和AKMetronome都需要播放,因此将它们放在AKMixer中,如下所示:
let mixer = AKMixer(playerA, playerB, metronome)
AudioKit.output = mixer
,回调将调用此函数:
func playAudio() {
playerA.play()
playerB.play()
}
然后,当执行playerA.play()时,它将崩溃。 这是错误消息:
AURemoteIO::IOThread (11): EXC_BAD_ACCESS (code=1, address=0xffff9ffffdb0e360)
same error message in screenshot
如果我仅将AKPlayer对象或AKMetronome之一放入AKMixer,则可以正常工作。 我听不懂错误信息,也不知道为什么会这样。 任何帮助将不胜感激。
这是完整的代码:
var playerA: AKPlayer!
var playerB: AKPlayer!
var clickA: AKAudioFile?
var clickB: AKAudioFile?
var metronome: AKMetronome?
override func viewDidLoad() {
super.viewDidLoad()
prepareAudio()
metronome!.start()
}
func prepareAudio() {
clickA = try? AKAudioFile(readFileName: "Click1A.wav")
clickB = try? AKAudioFile(readFileName: "Click1B.wav")
playerA = AKPlayer(audioFile: clickA!)
playerA.buffering = .always
playerB = AKPlayer(audioFile: clickB!)
playerB.buffering = .always
//metronome
metronome = AKMetronome.init()
metronome!.subdivision = 4
metronome!.frequency1 = 1000
metronome!.frequency2 = 800
metronome!.tempo = 60
metronome!.callback = {
self.playAudio()
}
let mixer = AKMixer(playerA, playerB, metronome)
AudioKit.output = mixer
do {
try AudioKit.start()
} catch {
print("audiokit start fail!")
}
}
func playAudio() {
playerA.play()
playerB.play()
}