diff options
author | Wu-cheng Li <wuchengli@google.com> | 2010-09-10 12:48:00 -0700 |
---|---|---|
committer | Wu-cheng Li <wuchengli@google.com> | 2010-09-15 09:21:49 -0700 |
commit | 4aaa2130af7241f128ee561cafd17a4fb560b92c (patch) | |
tree | 0d92d61f352c0605a2fdaa63c909e4f2edd3a55d | |
parent | 8eaa6919f0d5c10c95c99f2f937d57ea5c4a5bba (diff) | |
download | LegacyCamera-4aaa2130af7241f128ee561cafd17a4fb560b92c.zip LegacyCamera-4aaa2130af7241f128ee561cafd17a4fb560b92c.tar.gz LegacyCamera-4aaa2130af7241f128ee561cafd17a4fb560b92c.tar.bz2 |
Fix the wrong rotation on naturally landscape devices.
The orientation of on-screen icons and thumbnails are
wrong on devices that are naturally landscape in their
orientation. Display.getRotation should be used to
compensate.
Parameters.setRotation should also be compensated by
camera's orientation.
Change-Id: Ia0684fcd606252c49fa2d701ab07c73f7e29b70b
-rw-r--r-- | src/com/android/camera/Camera.java | 75 | ||||
-rw-r--r-- | src/com/android/camera/ImageManager.java | 24 | ||||
-rw-r--r-- | src/com/android/camera/Util.java | 23 | ||||
-rw-r--r-- | tests/src/com/android/camera/UnitTests.java | 4 | ||||
-rw-r--r-- | tests/src/com/android/camera/unittest/CameraTest.java | 26 |
5 files changed, 92 insertions, 60 deletions
diff --git a/src/com/android/camera/Camera.java b/src/com/android/camera/Camera.java index 26b14f9..1c5ebed 100644 --- a/src/com/android/camera/Camera.java +++ b/src/com/android/camera/Camera.java @@ -30,6 +30,7 @@ import android.content.res.Configuration; import android.content.res.Resources; import android.graphics.Bitmap; import android.graphics.BitmapFactory; +import android.hardware.Camera.CameraInfo; import android.hardware.Camera.Parameters; import android.hardware.Camera.PictureCallback; import android.hardware.Camera.Size; @@ -133,8 +134,11 @@ public class Camera extends NoSearchActivity implements View.OnClickListener, private Parameters mParameters; private Parameters mInitialParams; - private OrientationEventListener mOrientationListener; - private int mLastOrientation = 0; // No rotation (landscape) by default. + private MyOrientationEventListener mOrientationListener; + // The device orientation in degrees. Default is unknown. + private int mOrientation = OrientationEventListener.ORIENTATION_UNKNOWN; + // The orientation compensation for icons and thumbnails. + private int mOrientationCompensation = 0; private ComboPreferences mPreferences; private static final int IDLE = 1; @@ -302,24 +306,7 @@ public class Camera extends NoSearchActivity implements View.OnClickListener, // Create orientation listenter. This should be done first because it // takes some time to get first orientation. - mOrientationListener = new OrientationEventListener(Camera.this) { - @Override - public void onOrientationChanged(int orientation) { - // We keep the last known orientation. So if the user - // first orient the camera then point the camera to - if (orientation != ORIENTATION_UNKNOWN) { - orientation += 90; - } - orientation = ImageManager.roundOrientation(orientation); - if (orientation != mLastOrientation) { - mLastOrientation = orientation; - if (!mIsImageCaptureIntent) { - setOrientationIndicator(mLastOrientation); - } - mHeadUpDisplay.setOrientation(mLastOrientation); - } - } - }; + mOrientationListener = new MyOrientationEventListener(Camera.this); mOrientationListener.enable(); // Initialize location sevice. @@ -789,8 +776,18 @@ public class Camera extends NoSearchActivity implements View.OnClickListener, private void capture() { mCaptureOnlyData = null; - // Set rotation. - mParameters.setRotation(mLastOrientation); + // Set JPEG rotation to match the orientation of what users see. The + // rotation is relative to the orientation of the camera. The value + // from OrientationEventListener is relative to the natural + // orientation of the device. CameraInfo.mOrientation is the angle + // between camera orientation and natural device orientation. The + // sum of the two is the value for setRotation. + int rotation = 0; + if (mOrientation != OrientationEventListener.ORIENTATION_UNKNOWN) { + CameraInfo info = CameraHolder.instance().getCameraInfo()[mCameraId]; + rotation = (mOrientation + info.mOrientation) % 360; + } + mParameters.setRotation(rotation); // Clear previous GPS location from the parameters. mParameters.removeGpsData(); @@ -1000,7 +997,7 @@ public class Camera extends NoSearchActivity implements View.OnClickListener, CameraHolder.instance().getCameraInfo()); mHeadUpDisplay.initialize(this, settings.getPreferenceGroup(R.xml.camera_preferences), - getZoomRatios(), mLastOrientation); + getZoomRatios(), mOrientationCompensation); if (mParameters.isZoomSupported()) { mHeadUpDisplay.setZoomIndex(mZoomValue); mHeadUpDisplay.setZoomListener(new ZoomControllerListener() { @@ -1016,7 +1013,7 @@ public class Camera extends NoSearchActivity implements View.OnClickListener, } private void attachHeadUpDisplay() { - mHeadUpDisplay.setOrientation(mLastOrientation); + mHeadUpDisplay.setOrientation(mOrientationCompensation); FrameLayout frame = (FrameLayout) findViewById(R.id.frame); mGLRootView = new GLRootView(this); mGLRootView.setContentPane(mHeadUpDisplay); @@ -1030,6 +1027,36 @@ public class Camera extends NoSearchActivity implements View.OnClickListener, mGLRootView = null; } + public static int roundOrientation(int orientation) { + return ((orientation + 45) / 90 * 90) % 360; + } + + private class MyOrientationEventListener + extends OrientationEventListener { + public MyOrientationEventListener(Context context) { + super(context); + } + + @Override + public void onOrientationChanged(int orientation) { + // We keep the last known orientation. So if the user first orient + // the camera then point the camera to floor or sky, we still have + // the correct orientation. + if (orientation == ORIENTATION_UNKNOWN) return; + orientation = roundOrientation(orientation); + if (orientation != mOrientation) { + mOrientation = orientation; + mOrientationCompensation = orientation + + Util.getDisplayRotation(Camera.this); + + if (!mIsImageCaptureIntent) { + setOrientationIndicator(mOrientationCompensation); + } + mHeadUpDisplay.setOrientation(mOrientationCompensation); + } + } + } + private void setOrientationIndicator(int degree) { ((RotateImageView) findViewById( R.id.review_thumbnail)).setDegree(degree); diff --git a/src/com/android/camera/ImageManager.java b/src/com/android/camera/ImageManager.java index 7251af8..76a6d1d 100644 --- a/src/com/android/camera/ImageManager.java +++ b/src/com/android/camera/ImageManager.java @@ -155,30 +155,6 @@ public class ImageManager { } } - public static int roundOrientation(int orientationInput) { - int orientation = orientationInput; - - if (orientation == OrientationEventListener.ORIENTATION_UNKNOWN) { - orientation = 0; - } - - orientation = orientation % 360; - int retVal; - if (orientation < (0 * 90) + 45) { - retVal = 0; - } else if (orientation < (1 * 90) + 45) { - retVal = 90; - } else if (orientation < (2 * 90) + 45) { - retVal = 180; - } else if (orientation < (3 * 90) + 45) { - retVal = 270; - } else { - retVal = 0; - } - - return retVal; - } - // // Stores a bitmap or a jpeg byte array to a file (using the specified // directory and filename). Also add an entry to the media store for diff --git a/src/com/android/camera/Util.java b/src/com/android/camera/Util.java index de99562..c5de1f8 100644 --- a/src/com/android/camera/Util.java +++ b/src/com/android/camera/Util.java @@ -280,21 +280,24 @@ public class Util { return x; } - public static void setCameraDisplayOrientation(Activity activity, - int cameraId, android.hardware.Camera camera) { - android.hardware.Camera.CameraInfo info = - new android.hardware.Camera.CameraInfo(); - android.hardware.Camera.getCameraInfo(cameraId, info); + public static int getDisplayRotation(Activity activity) { int rotation = activity.getWindowManager().getDefaultDisplay() .getRotation(); - int degrees = 0; switch (rotation) { - case Surface.ROTATION_0: degrees = 0; break; - case Surface.ROTATION_90: degrees = 90; break; - case Surface.ROTATION_180: degrees = 180; break; - case Surface.ROTATION_270: degrees = 270; break; + case Surface.ROTATION_0: return 0; + case Surface.ROTATION_90: return 90; + case Surface.ROTATION_180: return 180; + case Surface.ROTATION_270: return 270; } + return 0; + } + public static void setCameraDisplayOrientation(Activity activity, + int cameraId, android.hardware.Camera camera) { + android.hardware.Camera.CameraInfo info = + new android.hardware.Camera.CameraInfo(); + android.hardware.Camera.getCameraInfo(cameraId, info); + int degrees = getDisplayRotation(activity); int result = (info.mOrientation - degrees + 360) % 360; camera.setDisplayOrientation(result); } diff --git a/tests/src/com/android/camera/UnitTests.java b/tests/src/com/android/camera/UnitTests.java index aeed001..4fc0e7d 100644 --- a/tests/src/com/android/camera/UnitTests.java +++ b/tests/src/com/android/camera/UnitTests.java @@ -28,8 +28,8 @@ public class UnitTests extends TestSuite { public static Test suite() { return new UnitTestSuiteBuilder(UnitTests.class) - .includeAllPackagesUnderHere() - .excludePackages("com.android.camera.stress") + .includePackages("com.android.camera.unittest", + "com.android.camera.gallery") .named("Camera Unit Tests") .build(); } diff --git a/tests/src/com/android/camera/unittest/CameraTest.java b/tests/src/com/android/camera/unittest/CameraTest.java new file mode 100644 index 0000000..0e851e4 --- /dev/null +++ b/tests/src/com/android/camera/unittest/CameraTest.java @@ -0,0 +1,26 @@ +package com.android.camera.unittest; + +import com.android.camera.Camera; + +import android.test.suitebuilder.annotation.SmallTest; + +import junit.framework.TestCase; + +@SmallTest +public class CameraTest extends TestCase { + public void testRoundOrientation() { + assertEquals(0, Camera.roundOrientation(0)); + assertEquals(0, Camera.roundOrientation(0 + 44)); + assertEquals(90, Camera.roundOrientation(0 + 45)); + assertEquals(90, Camera.roundOrientation(90)); + assertEquals(90, Camera.roundOrientation(90 + 44)); + assertEquals(180, Camera.roundOrientation(90 + 45)); + assertEquals(180, Camera.roundOrientation(180)); + assertEquals(180, Camera.roundOrientation(180 + 44)); + assertEquals(270, Camera.roundOrientation(180 + 45)); + assertEquals(270, Camera.roundOrientation(270)); + assertEquals(270, Camera.roundOrientation(270 + 44)); + assertEquals(0, Camera.roundOrientation(270 + 45)); + assertEquals(0, Camera.roundOrientation(359)); + } +} |