【问题标题】:Reset AVAudioEngine重置 AVAudioEngine
【发布时间】:2018-06-06 11:27:16
【问题描述】:

我正在创建一个基本的音板应用程序。我有两个开关。一种在激活时会使音频变慢并降低音调,另一种会使其更快且更高。我有一个 if else if if 语句查看这些开关,然后相应地播放音频,但是当我尝试第二次按下它时,无论是相同的声音还是不同的声音,它都会崩溃。

我大约 99% 确定这是由于需要重置 AVAudioEngine 或重置节点本身,但我已经超越了我的联盟。我搜索了高低,但我似乎找到的答案与使用不同按钮发出高或低声音时重置播放器有关。有什么想法吗?

class ViewController: UIViewController {

@IBOutlet weak var sassSwitch: UISwitch!
@IBOutlet weak var chipSwitch: UISwitch!

@IBAction func sassAction(_ sender: UISwitch) {
    chipSwitch.setOn(false, animated: true)
}
@IBAction func chipSwitch(_ sender: UISwitch) {
    sassSwitch.setOn(false, animated: true)
}


///Playback Engine
private let audioEngine = AVAudioEngine()

///Player's Nodes
private let pitchPlayer = AVAudioPlayerNode()
private let timePitch = AVAudioUnitTimePitch()

///Audio Files to be played
private var audioFile1 = AVAudioFile()
private var audioFile2 = AVAudioFile()

override func viewDidLoad() {
    super.viewDidLoad()
    // Do any additional setup after loading the view, typically from a nib.

    if let filePath = Bundle.main.path(forResource: "PeteNope", ofType:
        "mp3") {
        let filePathURL = URL(fileURLWithPath: filePath)

        setPlayerFile(filePathURL)

    }

    if let filePath2 = Bundle.main.path(forResource: "Law_WOW", ofType:
        "mp3") {
        let filePath2URL = URL(fileURLWithPath: filePath2)

        setPlayerFile2(filePath2URL)

    }
}

private func setPlayerFile(_ fileURL: URL) {
    do {
        let file = try AVAudioFile(forReading: fileURL)

        self.audioFile1 = file


    } catch {
        fatalError("Could not create AVAudioFile instance. error: \(error).")
    }
}

private func setPlayerFile2(_ fileURL: URL) {
    do {
        let file = try AVAudioFile(forReading: fileURL)

        self.audioFile2 = file


    } catch {
        fatalError("Could not create AVAudioFile instance. error: \(error).")
    }
}


@IBAction func sound1Play(_ sender: UIButton) {
    if sassSwitch.isOn {
        timePitch.pitch = -300
        timePitch.rate = 0.5
        audioEngine.attach(pitchPlayer)
        audioEngine.attach(timePitch)

        audioEngine.connect(pitchPlayer, to: timePitch, format: audioFile1.processingFormat)
        audioEngine.connect(timePitch, to: audioEngine.outputNode, format: audioFile1.processingFormat)
        pitchPlayer.scheduleFile(audioFile1, at: nil, completionHandler: nil)

        // Start the engine.
        do {
            try audioEngine.start()
        } catch {
            fatalError("Could not start engine. error: \(error).")
        }

        pitchPlayer.play()

    } else if chipSwitch.isOn {
        timePitch.pitch = +500
        timePitch.rate = 2.0
        audioEngine.attach(pitchPlayer)
        audioEngine.attach(timePitch)

        audioEngine.connect(pitchPlayer, to: timePitch, format: audioFile1.processingFormat)
        audioEngine.connect(timePitch, to: audioEngine.outputNode, format: audioFile1.processingFormat)
        pitchPlayer.scheduleFile(audioFile1, at: nil, completionHandler: nil)

        // Start the engine.
        do {
            try audioEngine.start()
        } catch {
            fatalError("Could not start engine. error: \(error).")
        }

        pitchPlayer.play()

    } else {
        timePitch.pitch = +0
        timePitch.rate = 1.0
        audioEngine.attach(pitchPlayer)
        audioEngine.attach(timePitch)

        audioEngine.connect(pitchPlayer, to: timePitch, format: audioFile1.processingFormat)
        audioEngine.connect(timePitch, to: audioEngine.outputNode, format: audioFile1.processingFormat)
        pitchPlayer.scheduleFile(audioFile1, at: nil, completionHandler: nil)

        // Start the engine.
        do {
            try audioEngine.start()
        } catch {
            fatalError("Could not start engine. error: \(error).")
        }
        pitchPlayer.play()
    }

}

override func didReceiveMemoryWarning() {
    super.didReceiveMemoryWarning()
    // Dispose of any resources that can be recreated.
}


}

【问题讨论】:

    标签: swift xcode avaudioplayer avaudioengine


    【解决方案1】:

    看起来您可能只需将attach、connect 和engine.start 函数移出sound1Play 函数,并将它们放入viewDidLoad。目前,您正在连接每个操作的节点,并多次重启引擎。

    【讨论】:

    • 就是这样。非常感谢您的帮助!
    猜你喜欢
    • 1970-01-01
    • 2019-01-24
    • 2015-05-01
    • 2023-04-02
    • 1970-01-01
    • 1970-01-01
    • 2015-04-15
    • 2022-01-23
    • 1970-01-01
    相关资源
    最近更新 更多