问题描述
我想知道是否可以通过单个摄像头设备输入将多个AVCaptureVideoDataOutput
添加到AVCaptureSession
?
I was wondering if it's possible to add multiple AVCaptureVideoDataOutput
to AVCaptureSession
with a single camera device input?
我的实验表明,添加第二个VideoDataOutput
将导致canAddOutput
返回NO
.但是我在Apple文档中找不到任何地方说不允许多个数据输出.
My experiments indicate that adding a second VideoDataOutput
will cause canAddOutput
return NO
. But I couldn't find anywhere on Apple's documentation says multiple data output is disallow.
推荐答案
我们不能对多个AVCaptureVideoDataOutput
对象使用单个AVCaptureSession
.
We can not use single AVCaptureSession
for multiple AVCaptureVideoDataOutput
objects.
您可以做的是用多个AVCaptureSession
对象创建多个AVCaptureVideoDataOutput
.
What can you do is you can make multiple AVCaptureVideoDataOutput
with multiple AVCaptureSession
objects.
您可以创建AVCaptureVideoDataOutput
和AVCaptureSession
的两个不同的设置,然后可以在应用程序中一个接一个地使用它们,就可以实现目标.
You can create two different setups of the AVCaptureVideoDataOutput
and AVCaptureSession
then you can use them one after another in the app and you will be able to achieve the goal.
就我而言,我必须一次使用相机捕获正面和背面的图像.
In my case, I had to capture front and back image using the camera at a time.
我确实为AVCaptureVideoDataOutput
和AVCaptureSession
创建了两个不同的对象,如下所示.
I did create two different objects for AVCaptureVideoDataOutput
and AVCaptureSession
as given below.
/* Front camera settings */
@property bool isFrontRecording;
@property (strong, nonatomic) AVCaptureDeviceInput *videoInputBack;
@property (strong, nonatomic) AVCaptureStillImageOutput *imageOutputBack;
@property (strong, nonatomic) AVCaptureSession *sessionBack;
/* Back camera settings */
@property bool isBackRecording;
@property (strong, nonatomic) AVCaptureDeviceInput *videoInputFront;
@property (strong, nonatomic) AVCaptureStillImageOutput *imageOutputFront;
@property (strong, nonatomic) AVCaptureSession *sessionFront;
现在,鉴于视图最初已加载,所以我设置了后置摄像头并设置了会话开始记录的标志,或者不设置两个会话的标志,如下所述.
Now in view did load initially I did setup back camera and set up flags for session started recording or not for both sessions as followed.
- (void)viewDidLoad {
[super viewDidLoad];
[self setupBackAVCapture];
self.isFrontRecording = NO;
self.isBackRecording = NO;
}
- (void)setupBackAVCapture
{
NSError *error = nil;
self.sessionBack = [[AVCaptureSession alloc] init];
self.sessionBack.sessionPreset = AVCaptureSessionPresetPhoto;
AVCaptureDevice *camera = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
self.videoInputBack = [[AVCaptureDeviceInput alloc] initWithDevice:camera error:&error];
[self.sessionBack addInput:self.videoInputBack];
self.imageOutputBack = [[AVCaptureStillImageOutput alloc] init];
[self.sessionBack addOutput:self.imageOutputBack];
}
现在,无论何时用户开始拍摄照片,我们都会使用以下代码拍摄正面照片.
Now, whenever the user starts capturing photo we will capture the front photo using below code.
- (IBAction)buttonCapture:(id)sender {
[self takeBackPhoto];
}
- (void)takeBackPhoto
{
[self.sessionBack startRunning];
if (!self.isFrontRecording) {
self.isFrontRecording = YES;
AudioServicesPlaySystemSound(kSystemSoundID_Vibrate);
AVCaptureConnection *videoConnection = [self.imageOutputBack connectionWithMediaType:AVMediaTypeVideo];
if (videoConnection == nil) {
return;
}
[self.imageOutputBack
captureStillImageAsynchronouslyFromConnection:videoConnection
completionHandler:^(CMSampleBufferRef imageDataSampleBuffer, NSError *error) {
if (imageDataSampleBuffer == NULL) {
return;
}
NSData *imageData = [AVCaptureStillImageOutput jpegStillImageNSDataRepresentation:imageDataSampleBuffer];
UIImage *image = [[UIImage alloc] initWithData:imageData];
UIImageWriteToSavedPhotosAlbum(image, self, nil, nil);
[self.imageView setImage:image];
[self.sessionBack stopRunning];
// Set up front camera setting and capture photo.
[self setupFrontAVCapture];
[self takeFrontPhoto];
}];
self.isFrontRecording = NO;
}
}
一旦捕获到背面图像,我们将设置会话以使用 setupFrontAVCapture 方法捕获正面图像,然后我们将使用 takeFrontPhoto 方法捕获正面图像,如下所示
As soon as the back image will be captured we will setup session to capture front image using setupFrontAVCapture method and then we will capture front image using takeFrontPhoto method as given below.
- (void)setupFrontAVCapture
{
NSError *error = nil;
self.sessionFront = [[AVCaptureSession alloc] init];
self.sessionFront.sessionPreset = AVCaptureSessionPresetPhoto;
AVCaptureDevice *camera = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
camera = [self cameraWithPosition:AVCaptureDevicePositionFront];
self.videoInputFront = [[AVCaptureDeviceInput alloc] initWithDevice:camera error:&error];
[self.sessionFront addInput:self.videoInputFront];
self.imageOutputFront = [[AVCaptureStillImageOutput alloc] init];
[self.sessionFront addOutput:self.imageOutputFront];
}
- (void)takeFrontPhoto
{
[self.sessionFront startRunning];
if (!self.isBackRecording) {
self.isBackRecording = YES;
AudioServicesPlaySystemSound(kSystemSoundID_Vibrate);
AVCaptureConnection *videoConnection = [self.imageOutputFront connectionWithMediaType:AVMediaTypeVideo];
if (videoConnection == nil) {
return;
}
[self.imageOutputFront
captureStillImageAsynchronouslyFromConnection:videoConnection
completionHandler:^(CMSampleBufferRef imageDataSampleBuffer, NSError *error) {
if (imageDataSampleBuffer == NULL) {
return;
}
NSData *imageData = [AVCaptureStillImageOutput jpegStillImageNSDataRepresentation:imageDataSampleBuffer];
UIImage *image = [[UIImage alloc] initWithData:imageData];
UIImageWriteToSavedPhotosAlbum(image, self, nil, nil);
[self.imageViewBack setImage:image];
[self.sessionFront stopRunning];
}];
self.isBackRecording = NO;
}
}
这样,您可以使用两组不同的AVCaptureSession
和AVCaptureStillImageOutput
对象,就可以实现目标.
This way you can use two different set of AVCaptureSession
and AVCaptureStillImageOutput
objects and you can achieve your goal.
如果您有任何困惑,请告诉我.
Please let me know if you have any confusion.
这篇关于同一AVCaptureSession中有多个AVCaptureVideoDataOutput的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!