Files
HaishinKit.swift/Examples/iOS/AudioEngineCapture.swift
2025-12-21 16:49:40 +09:00

63 lines
1.6 KiB
Swift

import AVFoundation
import Foundation
import HaishinKit
protocol AudioEngineCaptureDelegate: AnyObject {
func audioCapture(_ audioCapture: AudioEngineCapture, buffer: AVAudioPCMBuffer, time: AVAudioTime)
}
final class AudioEngineCapture {
var delegate: (any AudioEngineCaptureDelegate)?
private(set) var isRunning = false
private var audioEngine = AVAudioEngine()
func startCaptureIfNeeded() {
guard isRunning else {
return
}
audioEngine.stop()
audioEngine.inputNode.removeTap(onBus: 0)
audioEngine = AVAudioEngine()
do {
try startCapture()
} catch {
logger.warn(error)
}
}
private func startCapture() throws {
let input = audioEngine.inputNode
let mixer = audioEngine.mainMixerNode
audioEngine.connect(input, to: mixer, format: input.inputFormat(forBus: 0))
input.installTap(onBus: 0, bufferSize: 1024, format: input.inputFormat(forBus: 0)) { buffer, when in
self.delegate?.audioCapture(self, buffer: buffer, time: when)
}
audioEngine.prepare()
try audioEngine.start()
}
}
extension AudioEngineCapture: Runner {
// MARK: Runner
func startRunning() {
guard !isRunning else {
return
}
do {
try startCapture()
isRunning = true
} catch {
logger.error(error)
}
}
func stopRunning() {
guard isRunning else {
return
}
audioEngine.stop()
isRunning = false
}
}