Closed andrewcking closed 7 years ago
If you want to display the full uncropped preview, then the preview size must have the same aspect ratio with the photo aspect ratio. That's right.
Personally I have not tried this myself to know the edge cases and cannot think of any right now. What have you encountered with this approach?
Currently, the camera view is resized to make sure that the smallest side of the camera frame matches the smallest side of the view. That is to make sure that there won't be any blank lines on the screen.
We can add an option to fit camera preview inside of the view, but that would introduce blank lines mentioned above.
To be sure that we understand the problem correctly, could you please provide us some screenshots?
So far my approach seems to be working on the devices I have tested it on (Galaxy s8, nexus 5, nexus 5x). I understand that showing the full sensor will result in gaps. Here is what my solution results in for the tall galaxy s8:
And the standard sized Nexus 5x:
As I said, there are probably far better way to do this but I basically call this method in my onCreate to get the aspect ratios for each camera (does Fotoapparat expose the dimensions it will be taking photos in when the cameras are created? That could simplify this).
public float getAspectRatios(Camera camera){
Camera.Parameters params = camera.getParameters();
List sizes = params.getSupportedPictureSizes();
Camera.Size result = null;
int biggestW = 0;
int biggestH = 0;
for (int i=0;i<sizes.size();i++){
result = (Camera.Size) sizes.get(i);
if (result.width >= biggestW && result.height >= biggestH) {
biggestH = result.height;
biggestW = result.width;
}
}
camera.release();
float aspect = (float)Math.max(biggestW,biggestH)/(float)Math.min(biggestW,biggestH);
System.out.println("$$"+aspect);
return aspect;
}
And the calls in onCreate:
aspectRatioFront = getAspectRatios(Camera.open(CAMERA_FACING_FRONT));
aspectRatioBack = getAspectRatios(Camera.open(CAMERA_FACING_BACK));
Then whenever the camera is changed or initialized I just change the cameraView dimensions. I do this in case the aspect ratio that the front camera takes pictures in is different than the back camera (as is the case with my nexus 5 where the back camera is only near 4:3 and the front is perfect 4:3).
cameraView.getLayoutParams().height = (int)(size.x*aspectRatio)
Where size.x is the screen width and aspectRatio is either aspectRatioFront or aspectRatioBack from above.
This seems to be working for me, though it involves a couple workarounds.
I believe the cleanest solution is to have a parameter in the builder to allow you choose if you want the preview to be cropped or be full size. Like:
Fotoapparat
.with(context)
.into(cameraView)
.preview(cropped()) // of full()
I am curious to know if there is a simple solution that I am overlooking (there probably is, I am not yet great with layouts). I am wanting my cameraView to show the full uncropped sensor. I was thinking that the following would work in my layout:
But it is still cropping to fill the screen. I worked out a solution by programmatically setting the width to the screen width, getting the biggest size photo parameter, figuring out the aspect ratio from that parameter and then setting the view height based on the calculated aspect ratio. I feel like this should work for most purposes but there may be edge cases where this breaks. What is the best practice for showing the full uncropped camera preview? Thank you for this amazing library, it has been extremely helpful to me and has been great to work with.