音量を取得する
iPhoneでマイクから拾った音の音量を取得する方法。
① AudioToolBoxをインポートする
#import <AudioToolbox/AudioToolbox.h>
②音声入力用のキューとタイマーのインスタンス変数を用意する
@implementation ViewController{ AudioQueueRef _queue; NSTimer *_timer; }
③コールバック関数を宣言する(今回は録音をしないので、中身は空)
static void AudioInputCallback( void* inUserData, AudioQueueRef inAQ, AudioQueueBufferRef inBuffer, const AudioTimeStamp *inStartTime, UInt32 inNumberPacketDescriptions, const AudioStreamPacketDescription *inPacketDescs) { }
④音検知の設定、開始
- (void)startUpdatingVolume{ // 記録するデータフォーマットを決める AudioStreamBasicDescription dataFormat; //サンプリング周波数(1秒間のフレーム数) dataFormat.mSampleRate = 44100.0f; //フォーマットID(リニアPCM、MP3、AACなど) dataFormat.mFormatID = kAudioFormatLinearPCM; //フォーマットフラグ(エンディアン、整数or浮動小数点数) dataFormat.mFormatFlags = kLinearPCMFormatFlagIsBigEndian | kLinearPCMFormatFlagIsSignedInteger | kLinearPCMFormatFlagIsPacked; //1バケットのバイト数 dataFormat.mBytesPerPacket = 2; //1バケットのフレーム数 dataFormat.mFramesPerPacket = 1; //1フレームのバイト数 dataFormat.mBytesPerFrame = 2; //1フレームのチャンネル数 dataFormat.mChannelsPerFrame = 1; //1チャンネルののビット数 dataFormat.mBitsPerChannel = 16; //? dataFormat.mReserved = 0; // レベルの監視を開始する AudioQueueNewInput(&dataFormat, AudioInputCallback, (__bridge void *)(self), CFRunLoopGetCurrent(), kCFRunLoopCommonModes, 0, &_queue); AudioQueueStart(_queue, NULL); // レベルメータを有効化する UInt32 enabledLevelMeter = true; AudioQueueSetProperty(_queue, kAudioQueueProperty_EnableLevelMetering, &enabledLevelMeter, sizeof(UInt32)); // 定期的にレベルメーターを監視するタイマーを設定 _timer = [NSTimer scheduledTimerWithTimeInterval:0.1 target:self selector:@selector(detectVolume:) userInfo:nil repeats:YES]; }
⑤一定時間ごとにレベルを取得する(④で指定した秒数ごとに呼ばれる)
- (void)detectVolume:(NSTimer *)timer { // レベルを取得 AudioQueueLevelMeterState levelMeter; UInt32 levelMeterSize = sizeof(AudioQueueLevelMeterState); AudioQueueGetProperty(_queue, kAudioQueueProperty_CurrentLevelMeterDB, &levelMeter, &levelMeterSize); // 最大レベルと平均レベルを表示(値はマイナスを取る、最大が0.0) NSLog(@"mPeakPower:%f",levelMeter.mPeakPower); NSLog(@"mAveragePower:%f",levelMeter.mAveragePower); if (levelMeter.mPeakPower > -1.0) { //音量が一定値を越えると処理を行う } }
⑥音の検知の終了
- (void)stopUpdatingVolume{ // キューを空にして停止 AudioQueueFlush(_queue); AudioQueueStop(_queue, NO); AudioQueueDispose(_queue, YES); //タイマーを停止する if ([_timer isValid]) { [_timer invalidate]; _timer = nil; } }
使ったあとは停止しましょう。