Comment faire pour capturer une image sans l'affichage de l'aperçu d'iOS

Je veux capturer des images à des cas particuliers, par exemple lorsqu'un bouton est enfoncé; mais je ne veux pas montrer une vidéo de l'écran de prévisualisation. Je suppose que captureStillImageAsynchronouslyFromconnection est ce que je dois utiliser pour ce scénario. Actuellement, je peux capturer l'image si je montre un aperçu de la vidéo. Cependant, si je supprime le code pour afficher la prévisualisation, l'application se bloque avec la sortie suivante:

2012-04-07 11:25:54.898 imCapWOPreview[748:707] *** fin de l'app
en raison de uncaught exception 'NSInvalidArgumentException', la raison: '***
-[AVCaptureStillImageOutput captureStillImageAsynchronouslyFromconnection:completionHandler:] -
inactif/connexion non valide passé.'
*** Premier lancer de pile d'appel: (0x336ee8bf 0x301e21e5 0x3697c35d 0x34187 0x33648435 0x310949eb 0x310949a7 0x31094985 0x310946f5 0x3109502d
0x3109350f 0x31092f01 0x310794ed 0x31078d2d 0x37db7df3 0x336c2553
0x336c24f5 0x336c1343 0x336444dd 0x336443a5 0x37db6fcd 0x310a7743
0x33887 0x3382c) de mettre un terme appelé à la levée d'une exception(lldb)

Voici donc ma mise en œuvre:

BIDViewController.h:

#import <UIKit/UIKit.h>
#import <AVFoundation/AVFoundation.h>

@interface BIDViewController : UIViewController
{
    AVCaptureStillImageOutput *stillImageOutput;
}
@property (strong, nonatomic) IBOutlet UIView *videoPreview;
- (IBAction)doCap:(id)sender;

@end

Personnel concerné à l'intérieur de BIDViewController.m :

#import "BIDViewController.h"

@interface BIDViewController ()

@end

@implementation BIDViewController
@synthesize capturedIm;
@synthesize videoPreview;

- (void)viewDidLoad
{
[super viewDidLoad];
[self setupAVCapture];
}

- (BOOL)setupAVCapture
{
NSError *error = nil;

AVCaptureSession *session = [AVCaptureSession new];
[session setSessionPreset:AVCaptureSessionPresetHigh];

/*
AVCaptureVideoPreviewLayer *captureVideoPreviewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:session];
captureVideoPreviewLayer.frame = self.videoPreview.bounds;
[self.videoPreview.layer addSublayer:captureVideoPreviewLayer];    
 */

//Select a video device, make an input
AVCaptureDevice *backCamera = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
AVCaptureDeviceInput *input = [AVCaptureDeviceInput deviceInputWithDevice:backCamera error:&error];
if (error)
    return NO;
if ([session canAddInput:input])
    [session addInput:input];

//Make a still image output
stillImageOutput = [AVCaptureStillImageOutput new];
NSDictionary *outputSettings = [[NSDictionary alloc] initWithObjectsAndKeys: AVVideoCodecJPEG, AVVideoCodecKey, nil];
[stillImageOutput setOutputSettings:outputSettings];    
if ([session canAddOutput:stillImageOutput])
    [session addOutput:stillImageOutput];

[session startRunning];

return YES;
}

- (IBAction)doCap:(id)sender {
AVCaptureConnection *videoConnection = nil;
for (AVCaptureConnection *connection in stillImageOutput.connections)
{
    for (AVCaptureInputPort *port in [connection inputPorts])
    {
        if ([[port mediaType] isEqual:AVMediaTypeVideo] )
        {
            videoConnection = connection;
            break;
        }
    }
    if (videoConnection) { break; }
}

[stillImageOutput captureStillImageAsynchronouslyFromConnection:videoConnection 
  completionHandler:^(CMSampleBufferRef imageDataSampleBuffer, NSError *__strong error) {
      //Do something with the captured image
  }];

}

Avec le code ci-dessus, si doCap est appelé, alors que l'incident se produit. D'autre part, si je supprime les commentaires suivants dans setupAVCapture fonction

/*
AVCaptureVideoPreviewLayer *captureVideoPreviewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:session];
captureVideoPreviewLayer.frame = self.videoPreview.bounds;
[self.videoPreview.layer addSublayer:captureVideoPreviewLayer];    
 */

puis, il fonctionne sans aucun problème.

En résumé, mes questions, Comment puis-je capturer des images à des instances sans montrer aperçu ?

le plus simple serait de self.videoPreview.hidden = YES;
le code fonctionne sur mon iphone 4S
le masquage de la videoPreview a fonctionné pour moi aussi... Alors la prochaine question est; est-il des performances avec cette approche ? c'est à dire traitement redondant passé pour l'envoi de la vidéo d'aperçu des données à une couche cachée ?

OriginalL'auteur ali gurbuz | 2012-04-07