I am trying to write an app that would detect when loud noise (i.e clap) has happened, via microphone, and how many noises have actually happen while recording users microphone.
This is the code that I wrote based on the solutions I found:
func startRecording(timerCheckInterval: TimeInterval = 0.3) {
let audioURL = FileManager.default.demoAudioURL
print("demoAudioURL: ", audioURL.absoluteString)
let settings = [
AVFormatIDKey: Int(kAudioFormatMPEG4AAC),
AVSampleRateKey: 44100,
AVNumberOfChannelsKey: 1,
AVEncoderAudioQualityKey: AVAudioQuality.high.rawValue
]
do {
audioRecorder = try AVAudioRecorder(url: audioURL, settings: settings)
audioRecorder?.isMeteringEnabled = true
audioRecorder?.delegate = self
audioRecorder?.prepareToRecord()
audioRecorder?.record()
timerCancellable = Timer.publish(every: timerCheckInterval, on: .main, in: .default)
.autoconnect()
.receive(on: DispatchQueue.main)
.sink { [weak self] timestamp in
guard let self, let audioRecorder = self.audioRecorder else {
return
}
audioRecorder.updateMeters()
let averagePower = Double(audioRecorder.averagePower(forChannel: 0))
let peakPower = Double(audioRecorder.peakPower(forChannel: 0))
let alpha: Double = 0.05
let peakPowerForChannel = pow(10, (0.05 * peakPower))
self.lowPassResults = alpha * peakPowerForChannel + (1.0 - alpha) * self.lowPassResults
if peakPower > 30 {
print(String(format:">>>+++Peak power: %.2f Average power: %.2f, currentTime: %.2f", peakPower, averagePower, audioRecorder.currentTime))
}
}
} catch {
//...
}
}
this seems to provide me with some info. However, if, for example clap, I clap loud enough peakPower may logged to be more than 30 like 3-4 times. I tried to look into AVAudioEngine, but my noob search was fruitless.
So my question is, is there a way to tell the difference when one loud noise ended and new one has begun while recording audio? Or maybe a library that can do that?