iOS录音主要通过两种方式来实现:
其一:使用底层的AudioToolbox.framework 、CoreAudioTypes.framework相关主要类:AudioQueueRef、AudioStreamBasicDescription、AudioQueueBufferRef,此方式的好处是能实现边录制边缓存数据,在线播放无需等待音频文件全部下载完成,可以边缓冲边播放,提高用户体验。另外实现混音、去除回音也得使用底层Api来实现。
AudioStreamBasicDescription recordFormat; //音频流配置
- (void)initFormat {
recordFormat.mSampleRate= KDefaultSampleRate; //采样率
recordFormat.mChannelsPerFrame = KDefalutChannel; //声道数量
//编码格式
recordFormat.mFormatID = kAudioFormatLinearPCM;
recordFormat.mFormatFlags = kLinearPCMFormatFlagIsSignedInteger | kLinearPCMFormatFlagIsPacked;
//每采样点占用位数
recordFormat.mBitsPerChannel = KBitsPerChannel;
//每帧的字节数
recordFormat.mBytesPerFrame = (recordFormat.mBitsPerChannel / 8) * recordFormat.mChannelsPerFrame;
//每包的字节数
recordFormat.mBytesPerPacket = recordFormat.mBytesPerFrame;
//每帧的字节数
recordFormat.mFramesPerPacket = 1;
}
其二:使用苹果的AVFoundation.framework 的相关主要类:AVAudioSession、AVAudioRecorder
此方式使用起来简单,容易理解各种参数配置。
- (NSDictionary *)getAudioSetting{
NSMutableDictionary *dicM = [NSMutableDictionary dictionary];
[dicM setObject:@(kAudioFormatLinearPCM) forKey:AVFormatIDKey];
[dicM setObject:@(ETRECORD_RATE) forKey:AVSampleRateKey];
[dicM setObject:@(2) forKey:AVNumberOfChannelsKey];
[dicM setObject:@(16) forKey:AVLinearPCMBitDepthKey];
[dicM setObject:[NSNumber numberWithInt:AVAudioQualityMin] forKey:AVEncoderAudioQualityKey];
return dicM;
}
录音时设置的编码通常是kAudioFormatLinearPCM或者kAudioFormatMPEG4AAC,但是发现一个问题,无论你使用何种编码,哪怕设置kAudioFormatMPEGLayer3编码后录制的音频文件在Android端或Chrome浏览器端都无法播放?那如何解决呢?
通过录制pcm编码的原始音频,然后通过mp3的转码库Lame(demo链接:https://github.com/CivelXu/iOS-Lame-Audio-transcoding)转码成mp3的编码后再上传到服务器,这样解决了跨端播放的兼容问题。
文件大小如何?
本人测试了一下录音文件的大小,近30秒钟的音频录音测试,设备iPhone6s、双声道、采样率11025 、16位。
pcm编码 :1.3 MB,转换成mp3编码后的大小: 109 KB 。(由此推算5分钟的录音大致1MB大小)
如果改成单声道、采样率还是11025:
pcm编码 : 673 KB,转换成mp3编码后的大小 :85 KB 。
但是单声道的文件通过Lame转换后发现实际音频时长变成了二分之一?这个估计需要修改demo的相关转码算法?具体还清楚!