Branch
Branch

Reputation: 387

Full Screen Camera

I am having trouble with AVCapture.

Backstory: I made a new storyboard for my app for the iPad my copying the iPhone Storyboard and changing the source code of the new storyboard by adding .iPad where it was needed. Currently, my app only uses portrait mode.

AVCapture however, (which I am using to show a live feed of the camera) only fills part of the screen, with black bars on the outside. I also noticed it does this on the 3.5" screen iPhones.

I will add code as requested.

Please make all instructions super easy to follow, this is my first app, and I am a newbie.

Thanks!! Branch

EDIT: I tried this code from Apple's documentation, but it didn't work:

AVCaptureSession *captureSession; AVCaptureVideoPreviewLayer *previewLayer = [AVCaptureVideoPreviewLayer layerWithSession:captureSession]; UIView *aView; previewLayer.frame = aView.bounds; [aView.layer addSublayer:previewLayer];

Upvotes: 2

Views: 5581

Answers (2)

Jack Huang
Jack Huang

Reputation: 41

Maybe my issue is similar. For solution, do these as follow:

  1. set session preset as AVCaptureSessionPresetHigh
  2. set previewLayer's videoGravity property to AVLayerVideoGravityResizeAspectFill
  3. set preview's frame as device screen's bounds

I posted my solutions today for reporting an issue by using the DBCamera, here is the full contents:


This is maybe not a big thing, but it's useful for whoever cares about why photo taken from custom full-screen camera preview is not look exactly same.

I noticed that using a custom camera view, which subclassed from DBCameraView, and call openCustomCamera from the given example, will generate a full-screen preview. And the captured photo from this full-screen preview on iPhone 5s and 6s will get some extra space from both side, which means the final photo will not look exactly the same from the preview before trigger the camera.

This is because:
1. the session preset in code is AVCaptureSessionPresetPhoto
2. the previewLayer's videoGravity is set to AVLayerVideoGravityResizeAspectFill
3. the preview's frame is device screen's bounds

The videoGravity for previewLayer is AVLayerVideoGravityResizeAspect by system default. When you make the session preset as AVCaptureSessionPresetPhoto and make the preview's size as screen size, the system can not satisfy the both conditions because I think the AVCaptureSessionPresetPhoto will adjust the preview's size, which is resize aspect, to corresponds the high-resolution captured photo ( 4:3 ?). It's aspect ratio seems not as same as screen's (less obvious for 4s), so you can see the black areas appear on both top and bottom even if you set preview's frame equal to screen's bounds. However the DBCamera set AVLayerVideoGravityResizeAspectFill to videoGravity in code. It will cause the preview is trying to fill the full screen and maintain its correct aspect ratio. The custom camera view seems filling the entire device screen, but the actual preview is bigger than the screen size with extra spaces extended beyond screen from both left and right side.

To fix the problem to get the exact same photo from full screen preview, set AVCaptureSessionPresetHigh instead of AVCaptureSessionPresetPhoto. It will work. The downside is the quality of photo may not remain the same, that is the trade off.

Correct me if I am wrong, and hopefully it helps.

https://github.com/danielebogo/DBCamera/issues/194

Upvotes: 4

Aaron Brager
Aaron Brager

Reputation: 66244

The camera's aspect ratio is different from the iPad screen's aspect ratio. You can change the videoGravity property of your AVCaptureVideoPreviewLayer to fill the whole layer (this will crop the input, but you won't see the bars):

captureVideoPreviewLayer.videoGravity = AVLayerVideoGravityResizeAspectFill;

You'll still get the whole camera input, not just the layer preview, when you actually capture the image. You'll need to do math (geometry) based on your UI to rotate and crop it to get the image that the user is actually seeing.

Upvotes: 7

Related Questions