Skip to content

Instantly share code, notes, and snippets.

@zonble
Last active September 13, 2018 23:36
Show Gist options
  • Save zonble/412d43eac5372fb8847626c7d0f3657c to your computer and use it in GitHub Desktop.
Save zonble/412d43eac5372fb8847626c7d0f3657c to your computer and use it in GitHub Desktop.
import UIKit
import AVFoundation
class ZBSimpleRecorder: NSObject {
var audioEngine: AVAudioEngine?
var file: ExtAudioFileRef?
func start(fileURL:URL) {
self.stop()
func M4aFormat() -> AudioStreamBasicDescription {
return AudioStreamBasicDescription(mSampleRate: 44100,
mFormatID: kAudioFormatMPEG4AAC,
mFormatFlags: AudioFormatFlags(MPEG4ObjectID.aac_Main.rawValue),
mBytesPerPacket: 0,
mFramesPerPacket: 1024,
mBytesPerFrame: 0,
mChannelsPerFrame: 2,
mBitsPerChannel: 0,
mReserved: 0)
}
audioEngine = AVAudioEngine()
guard let audioEngine = audioEngine else {
return
}
let audioSession = AVAudioSession.sharedInstance()
try? audioSession.setCategory(AVAudioSessionCategoryRecord)
try? audioSession.setMode(AVAudioSessionModeVoiceChat)
try? audioSession.setActive(true, with: .notifyOthersOnDeactivation)
guard let inputNode = audioEngine.inputNode else { fatalError("Audio engine has no input node") }
let recordingFormat = inputNode.outputFormat(forBus: 0)
var outputFormat = M4aFormat()
var status = noErr
status = ExtAudioFileCreateWithURL(fileURL as CFURL, kAudioFileM4AType, &outputFormat, nil, AudioFileFlags.eraseFile.rawValue, &file)
assert(status == noErr)
var codecManufacturer = kAppleSoftwareAudioCodecManufacturer
status = ExtAudioFileSetProperty(file!, kExtAudioFileProperty_CodecManufacturer, UInt32(MemoryLayout<UInt32>.size), &codecManufacturer)
assert(status == noErr)
status = ExtAudioFileSetProperty(file!, kExtAudioFileProperty_ClientDataFormat, UInt32(MemoryLayout<AudioStreamBasicDescription>.size), recordingFormat.streamDescription)
assert(status == noErr)
inputNode.installTap(onBus: 0, bufferSize: 1024, format: recordingFormat) { (buffer: AVAudioPCMBuffer, when: AVAudioTime) in
let numberOfFrames = buffer.frameLength
let audioBufferList = buffer.audioBufferList
let status = ExtAudioFileWrite(self.file!, numberOfFrames, audioBufferList)
assert(status == noErr)
}
audioEngine.prepare()
try? audioEngine.start()
}
func stop() {
guard let audioEngine = audioEngine else {
return
}
let audioSession = AVAudioSession.sharedInstance()
try? audioSession.setActive(false, with: .notifyOthersOnDeactivation)
if let file = file {
ExtAudioFileDispose(file)
self.file = nil
}
audioEngine.stop()
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment