triniwiz / fancycamera

MIT License
8 stars 13 forks source link

Target orientation is set to wrong value if device orientation is -1 #28

Closed sublime392 closed 1 year ago

sublime392 commented 1 year ago

In my app, I take pictures from an overhead perspective, where the phone tends to be essentially flat, like you would for documents and stuff. For several days now, I have been freaking out, trying to understand why the Android app tends to zoom in when taking the picture, but mostly only when the device was moved to landscape orientation before really lining up the shot. Finally, I think I have found the reason. In the CameraBase.kt, there is this orientation handler:

private val orientationEventListener = object : OrientationEventListener(context) {
        override fun onOrientationChanged(orientation: Int) {
            if (rotation == CameraOrientation.UNKNOWN) {
                val newOrientation = when (orientation) {
                    in 45 until 135 -> 270
                    in 135 until 225 -> 180
                    in 225 until 315 -> 90
                    else -> 0
                }

                if (newOrientation != currentOrientation) {
                    currentOrientation = newOrientation
                    orientationUpdated()
                }
            }
        }
    }

After setting up an OrientationEventListener in another part of my app so I can see what is going on, I found that in landscape mode the value tended to be like

  JS: OOOOOOORIENT 290
  JS: OOOOOOORIENT 287
  JS: OOOOOOORIENT 284
  JS: OOOOOOORIENT 280

but as the phone approaches flatness, the value changes to

JS: OOOOOOORIENT -1

So what effectively happens in my app is, the phone is in landscape and the camera plus is ready to go with a 16:9 ratio and an image size of 3840x2160. The orientation handler is returning 90 at this point. But then the phone moves flat and the orientation handler starts emitting 0 because of the -1 orientation value, which changes the imageCapture?.targetRotation even though it really should not have changed.
If this line

if (rotation == CameraOrientation.UNKNOWN) {

was changed to

if (orientation > -1) {

then everything would be perfect. I think that fits logically with what should be happening (and maybe it is the original intent of that if statement?), i.e. if the orientation is unknown (-1), then don't update the targetRotation for the image capture.

sublime392 commented 1 year ago

Fixed by #29