Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Immediately freeze-frame an AVCaptureSession

I'm building an app that allows users to snap pictures using the iPhone camera, and am using AVFoundation when it's available (iOS4) so users can use the tap-to-focus feature, even with a custom overlay.

The problem I'm having is that captureStillImageAsynchronouslyFromConnection takes several seconds to complete, during which I'd like to freeze-frame the main video feed so there isn't a confusing state where the video is still running, but the user has snapped a photo (and the camera shutter sound has gone off).

I've tried calling [session stopRunning] right after I request a still image capture, but this leads to unpredictable results; the still image completion block often doesn't get fired in that case.

Any ideas on how I could have the video preview layer "pause" as soon as the shutter is hit?

like image 573
Zeppomedio Avatar asked Aug 18 '10 23:08

Zeppomedio


3 Answers

You just need to set your captureVideoPreviewLayer.connection.enabled = NO;

For details please see my answer here:

AVCaptureSession pause?

like image 57
Eugene Dudnyk Avatar answered Sep 29 '22 20:09

Eugene Dudnyk


I'm trying the same thing. Though in my case captureStillImageAsynchronouslyFromConnection take 0.5 seconds to return, so maybe you are doing some processing in the completion handler?

If that's the case, I came up with 2 options, both of which are not sufficient for me, but might do for you

What I came up with is either:
* call stopRunning on the capture session when the completion handler is called (again, 0.5 seconds in my case), and then after processing call startRunning again.
* have an UIImageView on top of the overlay, and store the last picture taken, either from camera or video stream in this imageview while you are doing your processing.

What discouraged me from both solutions was that they both add a couple of seconds to the process. But I hope it helps, or gives a direction.

Cheers, Oded.

like image 34
Oded Ben Dov Avatar answered Sep 29 '22 18:09

Oded Ben Dov


Simple freeze-framing gives the user the impression that the image on screen has already been taken, which is false — at least, I'd show a dimmed image. Camera.app gets around the issue by closing the "shutter".

You may be able to change the AVCaptureVideoPreviewLayer alpha to 0.5 to give the impression of a dimmed image, even though it's still running.

Another option is to use AVCaptureVideoDataOutput and some image-manipulation to get the still image. Unfortunately, it doesn't appear possible to use both AVCaptureVideoDataOutput and AVCaptureStillImageOutput at the same time; a workaround is to implement "take picture" functionality by grabbing the next video frame (of course, this is limited by your video resolution, but is fine if you just want to do image-processing on the frame).

like image 43
tc. Avatar answered Sep 29 '22 19:09

tc.