I'm trying to tap the microphone and also get SRC.
@main
struct TapSilenceApp: App {
let engine = AVAudioEngine()
let mixer = AVAudioMixerNode()
let mixer2 = AVAudioMixerNode()
init() {
let format = AVAudioFormat(standardFormatWithSampleRate: 16000, channels: 2)!
let inputNode = engine.inputNode
// Try using two mixers:
engine.attach(mixer)
engine.attach(mixer2)
engine.connect(inputNode, to: mixer, format: nil)
engine.connect(mixer, to: mixer2, format: format)
mixer2.installTap(onBus: 0, bufferSize: 256, format: format) { buffer, _ in
assert(!buffer.isSilent)
}
print("engine: \(engine)")
engine.prepare()
try! engine.start()
}
var body: some Scene {
WindowGroup {
ContentView()
}
}
}
That throws an exception with AUGraphParser::InitializeActiveNodesInInputChain(ThisGraph, *GetInputNode())
. (AVAudioEngine wins the award for lousiest error messages of any Apple API)
Interestingly, when I remove the call to installTap
, it runs.
I still need the tap of course. So trying to connect mixer2
to the output, I do get the tap to run, but the buffers are silent.
Here's the version that's silent:
let session = AVAudioSession.sharedInstance()
do {
try session.setCategory(.playAndRecord, options: .defaultToSpeaker)
} catch {
print("Could not set audio category: \(error.localizedDescription)")
}
let format = AVAudioFormat(standardFormatWithSampleRate: 16000, channels: 2)!
let inputNode = engine.inputNode
// Try using two mixers:
engine.attach(mixer)
engine.attach(mixer2)
engine.connect(inputNode, to: mixer, format: nil)
engine.connect(mixer, to: mixer2, format: format)
engine.connect(mixer2, to: engine.mainMixerNode, format: nil)
mixer2.installTap(onBus: 0, bufferSize: 256, format: mixer2.outputFormat(forBus: 0)) { buffer, _ in
// assert(!buffer.isSilent)
print("max value: \(buffer.maxValue)")
}
print("engine: \(engine)")
engine.prepare()
try! engine.start()
If I just put a tap on the inputNode
and remove the mixers, I do get audio input, but of course no SRC.