问题
I need to record a video with AVCaptureSession
in an iOS app.
When I add AVCaptureDeviceInput
to my current AVCaptureSession
, it always adds the iphone microphone. I have the bluetooth microphone connected to the device. But it is not recording from the external microphone.
I'm doing this:
- (BOOL)prepareAudioSession {
// deactivate session
BOOL success = [[AVAudioSession sharedInstance] setActive:NO error: nil];
if (!success) {
NSLog(@"deactivationError");
}
// Bluetooth support enable
UInt32 allowBluetoothInput = 1;
AudioSessionSetProperty (kAudioSessionProperty_OverrideCategoryEnableBluetoothInput,sizeof (allowBluetoothInput),&allowBluetoothInput);
// set audio session category AVAudioSessionCategoryPlayAndRecord options AVAudioSessionCategoryOptionAllowBluetooth
success = [[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayAndRecord withOptions:AVAudioSessionCategoryOptionAllowBluetooth|AVAudioSessionCategoryOptionMixWithOthers error:nil];
//success = [[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayAndRecord withOptions:AVAudioSessionCategoryOptionMixWithOthers error:nil];
if (!success) {
NSLog(@"setCategoryError");
}
// activate audio session
success = [[AVAudioSession sharedInstance] setActive:YES error: nil];
if (!success) {
NSLog(@"activationError");
}
return success;
}
But it's still not working. Anyone have any idea? Thanks
回答1:
I think there is a problem with how you are forming the AVCaptureSession
while setting the category with options. Try something like this to make AVCaptureSession
:
// create and set up the audio session
AVAudioSession* audioSession = [AVAudioSession sharedInstance];
[audioSession setDelegate:self];
[audioSession setCategory: AVAudioSessionCategoryPlayAndRecord error: nil];
[audioSession setActive: YES error: nil];
// set up for bluetooth microphone input
UInt32 allowBluetoothInput = 1;
OSStatus stat = AudioSessionSetProperty (
kAudioSessionProperty_OverrideCategoryEnableBluetoothInput,
sizeof (allowBluetoothInput),
&allowBluetoothInput
);
NSLog(@"status = %x", stat); // problem if this is not zero
// check the audio route
UInt32 size = sizeof(CFStringRef);
CFStringRef route;
OSStatus result = AudioSessionGetProperty(kAudioSessionProperty_AudioRoute, &size, &route);
NSLog(@"route = %@", route);
// if bluetooth headset connected, should be "HeadsetBT"
// if not connected, will be "ReceiverAndMicrophone"
// now, play a quick sound we put in the bundle (bomb.wav)
CFBundleRef mainBundle = CFBundleGetMainBundle();
CFURLRef soundFileURLRef;
SystemSoundID soundFileObject;
soundFileURLRef = CFBundleCopyResourceURL (mainBundle,CFSTR ("bomb"),CFSTR ("wav"),NULL);
NSError *error = nil;
audioRecorder = [[AVAudioRecorder alloc]
initWithURL:soundFileURLRef
settings:recordSettings
error:&error];
if (error)
{
NSLog(@"error: %@", [error localizedDescription]);
} else {
[audioRecorder prepareToRecord];
}
I took the code from here because it always works for me.
NOTE: This code will re route the audio while playing back to your headset itself. To use speaker while playing back, look at the comment section of accepted answer.
回答2:
The solution is this:
In your AppDelegate
[[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayAndRecord withOptions:AVAudioSessionCategoryOptionAllowBluetooth error:nil];
in your AVCaptureSession after add your AVCaptureDeviceInput
self.captureSession.usesApplicationAudioSession = true;
self.captureSession.automaticallyConfiguresApplicationAudioSession = false;
My setup for Audio:
/* Audio */
AVCaptureDevice *audioDevice = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeAudio];
audioIn = [[AVCaptureDeviceInput alloc] initWithDevice:audioDevice error:nil];
if ( [_captureSession canAddInput:audioIn] ) {
[_captureSession addInput:audioIn];
}
audioOut = [[AVCaptureAudioDataOutput alloc] init];
// Put audio on its own queue to ensure that our video processing doesn't cause us to drop audio
dispatch_queue_t audioCaptureQueue = dispatch_queue_create( "com.apple.sample.capturepipeline.audio", DISPATCH_QUEUE_SERIAL );
[audioOut setSampleBufferDelegate:self queue:audioCaptureQueue];
if ( [self.captureSession canAddOutput:audioOut] ) {
[self.captureSession addOutput:audioOut];
}
_audioConnection = [audioOut connectionWithMediaType:AVMediaTypeAudio];
//AVAudioSessionRouteDescription *current =[[AVAudioSession sharedInstance] currentRoute];*/
if(SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(@"7.0")){
self.captureSession.usesApplicationAudioSession = true;
self.captureSession.automaticallyConfiguresApplicationAudioSession = false;
//[[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayAndRecord withOptions:AVAudioSessionCategoryOptionAllowBluetooth error:nil];
}
来源:https://stackoverflow.com/questions/29835019/how-add-avcapturedeviceinput-to-avcapturesession-from-bluetooth-device