2010-11-20 4 views
1

AVCaptureSessionを使用してフロントカメラから画像を取得して処理しようとしています。これまでは新しいフレームが利用可能になるたびに変数に代入し、NSTimerを実行して、新しいフレームがある場合は10分の1秒ごとにチェックし、それが処理される場合はチェックしました。AVCaptureSessionを使用して選択したカメラフレームのみをキャプチャする方法はありますか?

フレームを取得してカメラをフリーズし、好きなときに次のフレームを取得したいと思います。あなたは[captureSession getNextFrame]のようなものを知っていますか?私はそれがいかに役立つか分からないが、ここで

は、私のコードの一部です:

- (void)startFeed { 

loopTimerIndex = 0; 

    NSArray *captureDevices = [AVCaptureDevice devicesWithMediaType:AVMediaTypeVideo]; 

    AVCaptureDeviceInput *captureInput = [AVCaptureDeviceInput 
              deviceInputWithDevice:[captureDevices objectAtIndex:1] 
              error:nil]; 

    AVCaptureVideoDataOutput *captureOutput = [[AVCaptureVideoDataOutput alloc] init]; 
    captureOutput.minFrameDuration = CMTimeMake(1, 10); 
    captureOutput.alwaysDiscardsLateVideoFrames = true; 

    dispatch_queue_t queue; 
    queue = dispatch_queue_create("cameraQueue", nil); 

    [captureOutput setSampleBufferDelegate:self queue:queue]; 
    dispatch_release(queue); 

    NSString *key = (NSString *)kCVPixelBufferPixelFormatTypeKey; 
    NSNumber *value = [NSNumber numberWithUnsignedInt:kCVPixelFormatType_32BGRA]; 
    NSDictionary *videoSettings = [NSDictionary dictionaryWithObject:value forKey:key]; 
    [captureOutput setVideoSettings:videoSettings]; 

    captureSession = [[AVCaptureSession alloc] init]; 
    captureSession.sessionPreset = AVCaptureSessionPresetLow; 
    [captureSession addInput:captureInput]; 
    [captureSession addOutput:captureOutput]; 

    imageView = [[UIImage alloc] init]; 

    [captureSession startRunning]; 

} 

- (void)captureOutput:(AVCaptureOutput *)captureOutput 
didOutputSampleBuffer:(CMSampleBufferRef)sampleBuffer 
     fromConnection:(AVCaptureConnection *)connection { 

loopTimerIndex++; 

    NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; 

    CVImageBufferRef imageBuffer = CMSampleBufferGetImageBuffer(sampleBuffer); 
    CVPixelBufferLockBaseAddress(imageBuffer, 0); 

    uint8_t *baseAddress = (uint8_t *)CVPixelBufferGetBaseAddress(imageBuffer); 
    size_t bytesPerRow = CVPixelBufferGetBytesPerRow(imageBuffer); 
    size_t width = CVPixelBufferGetWidth(imageBuffer); 
    size_t height = CVPixelBufferGetHeight(imageBuffer); 

    CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); 
    CGContextRef newContext = CGBitmapContextCreate(baseAddress, width, height, 8, bytesPerRow, colorSpace, kCGBitmapByteOrder32Little | kCGImageAlphaPremultipliedFirst); 
    CGImageRef newImage = CGBitmapContextCreateImage(newContext); 

    CGContextRelease(newContext); 
    CGColorSpaceRelease(colorSpace); 

    imageView = [UIImage imageWithCGImage:newImage scale:1.0 orientation:UIImageOrientationLeftMirrored]; 
    [delegate updatePresentor:imageView]; 
    if(loopTimerIndex == 1) { 
     [delegate feedStarted]; 
    } 

    CGImageRelease(newImage); 
    CVPixelBufferUnlockBaseAddress(imageBuffer, 0); 

    [pool drain]; 

} 

答えて

3

その取得プロセスがどのようにではありませんので、あなたが積極的に、バックのフレームを取得するには、カメラをポーリングしません建築された。 10分の1秒ごとに1/10秒ごとにフレームを表示する場合は、その間のフレームを無視するだけです。

たとえば、-captureOutput:didOutputSampleBuffer:fromConnection:がトリガーされるたびに比較するタイムスタンプを維持できます。タイムスタンプが現在の0.1秒以上であれば、カメラフレームを処理して表示し、タイムスタンプを現在の時刻にリセットします。それ以外の場合は、フレームを無視します。