diff options
8 files changed, 124 insertions, 53 deletions
diff --git a/src/com/android/camera/CameraManager.java b/src/com/android/camera/CameraManager.java index e89c2eb81..be82ea613 100644 --- a/src/com/android/camera/CameraManager.java +++ b/src/com/android/camera/CameraManager.java @@ -29,7 +29,6 @@ import android.hardware.Camera.Parameters; import android.hardware.Camera.PictureCallback; import android.hardware.Camera.PreviewCallback; import android.hardware.Camera.ShutterCallback; -import android.os.ConditionVariable; import android.os.Handler; import android.os.HandlerThread; import android.os.Looper; @@ -40,7 +39,6 @@ import android.view.SurfaceHolder; import com.android.gallery3d.common.ApiHelper; import java.io.IOException; -import java.util.concurrent.SynchronousQueue; public class CameraManager { private static final String TAG = "CameraManager"; @@ -48,10 +46,7 @@ public class CameraManager { private Parameters mParameters; private boolean mParametersIsDirty; - private SynchronousQueue<Parameters> mParametersQueue = - new SynchronousQueue<Parameters>(); - private SynchronousQueue<IOExceptionHolder> mReconnectExceptionQueue = - new SynchronousQueue<IOExceptionHolder>(); + private IOException mReconnectIOException; private static final int RELEASE = 1; private static final int RECONNECT = 2; @@ -148,16 +143,11 @@ public class CameraManager { return; case RECONNECT: - IOExceptionHolder holder = new IOExceptionHolder(); - holder.ex = null; + mReconnectIOException = null; try { mCamera.reconnect(); } catch (IOException ex) { - holder.ex = ex; - } - try { - mReconnectExceptionQueue.put(holder); - } catch (InterruptedException ex) { + mReconnectIOException = ex; } return; @@ -240,11 +230,7 @@ public class CameraManager { return; case GET_PARAMETERS: - try { - mParametersQueue.put(mCamera.getParameters()); - } catch (InterruptedException e) { - throw new RuntimeException(e); - } + mParameters = mCamera.getParameters(); return; case SET_PARAMETERS_ASYNC: @@ -303,14 +289,6 @@ public class CameraManager { } public class CameraProxy { - private ConditionVariable mWaitDoneLock = new ConditionVariable(); - private Runnable mUnlockRunnable = new Runnable() { - @Override - public void run() { - mWaitDoneLock.open(); - } - }; - private CameraProxy() { Assert(mCamera != null); @@ -329,13 +307,9 @@ public class CameraManager { public void reconnect() throws IOException { mCameraHandler.sendEmptyMessage(RECONNECT); - IOExceptionHolder holder = null; - try { - holder = mReconnectExceptionQueue.take(); - } catch (InterruptedException ex) { - } - if (holder != null && holder.ex != null) { - throw holder.ex; + waitDone(); + if (mReconnectIOException != null) { + throw mReconnectIOException; } } @@ -446,12 +420,20 @@ public class CameraManager { } public void setParameters(Parameters params) { - // TODO: check if this synchronous version is necessary + if (params == null) { + Log.v(TAG, "null parameters in setParameters()"); + return; + } mParametersIsDirty = true; mCameraHandler.obtainMessage(SET_PARAMETERS, params).sendToTarget(); } public void setParametersAsync(Parameters params) { + // TODO: remove this. + if (params == null) { + Log.v(TAG, "null parameters in setParameters()"); + return; + } mParametersIsDirty = true; mCameraHandler.removeMessages(SET_PARAMETERS_ASYNC); mCameraHandler.obtainMessage(SET_PARAMETERS_ASYNC, params).sendToTarget(); @@ -460,11 +442,7 @@ public class CameraManager { public Parameters getParameters() { if (mParametersIsDirty || mParameters == null) { mCameraHandler.sendEmptyMessage(GET_PARAMETERS); - try { - mParameters = mParametersQueue.take(); - mParametersIsDirty = false; - } catch (InterruptedException ex) { - } + if (waitDone()) mParametersIsDirty = false; } return mParameters; } @@ -474,10 +452,28 @@ public class CameraManager { ENABLE_SHUTTER_SOUND, (enable ? 1 : 0), 0).sendToTarget(); } - public void waitDone() { - mWaitDoneLock.close(); - mCameraHandler.post(mUnlockRunnable); - mWaitDoneLock.block(); + // return false if cancelled. + public boolean waitDone() { + final Object waitDoneLock = new Object(); + final Runnable unlockRunnable = new Runnable() { + @Override + public void run() { + synchronized (waitDoneLock) { + waitDoneLock.notifyAll(); + } + } + }; + + synchronized (waitDoneLock) { + mCameraHandler.post(unlockRunnable); + try { + waitDoneLock.wait(); + } catch (InterruptedException ex) { + Log.v(TAG, "waitDone interrupted"); + return false; + } + } + return true; } } } diff --git a/src/com/android/camera/ComboPreferences.java b/src/com/android/camera/ComboPreferences.java index c561e6b9c..e17e47aa8 100644 --- a/src/com/android/camera/ComboPreferences.java +++ b/src/com/android/camera/ComboPreferences.java @@ -22,6 +22,8 @@ import android.content.SharedPreferences; import android.content.SharedPreferences.OnSharedPreferenceChangeListener; import android.preference.PreferenceManager; +import com.android.gallery3d.util.UsageStatistics; + import java.util.Map; import java.util.Set; import java.util.WeakHashMap; @@ -205,9 +207,7 @@ public class ComboPreferences implements @Override public boolean contains(String key) { - if (mPrefLocal.contains(key)) return true; - if (mPrefGlobal.contains(key)) return true; - return false; + return mPrefLocal.contains(key) || mPrefGlobal.contains(key); } private class MyEditor implements Editor { @@ -330,5 +330,6 @@ public class ComboPreferences implements listener.onSharedPreferenceChanged(this, key); } BackupManager.dataChanged(mPackageName); + UsageStatistics.onEvent("CameraSettingsChange", null, key); } } diff --git a/src/com/android/gallery3d/filtershow/editors/EditorFlip.java b/src/com/android/gallery3d/filtershow/editors/EditorFlip.java index c996dcbe3..de6240c7a 100644 --- a/src/com/android/gallery3d/filtershow/editors/EditorFlip.java +++ b/src/com/android/gallery3d/filtershow/editors/EditorFlip.java @@ -17,13 +17,18 @@ package com.android.gallery3d.filtershow.editors; import android.content.Context; +import android.view.View; +import android.view.View.OnClickListener; +import android.widget.Button; import android.widget.FrameLayout; +import android.widget.LinearLayout; import com.android.gallery3d.R; import com.android.gallery3d.filtershow.imageshow.ImageFlip; import com.android.gallery3d.filtershow.imageshow.MasterImage; public class EditorFlip extends Editor implements EditorInfo { + public static final String LOGTAG = "EditorFlip"; public static final int ID = R.id.editorFlip; ImageFlip mImageFlip; @@ -44,6 +49,18 @@ public class EditorFlip extends Editor implements EditorInfo { } @Override + public void openUtilityPanel(final LinearLayout accessoryViewList) { + final Button button = (Button) accessoryViewList.findViewById(R.id.applyEffect); + button.setOnClickListener(new OnClickListener() { + @Override + public void onClick(View arg0) { + mImageFlip.flip(); + mImageFlip.saveAndSetPreset(); + } + }); + } + + @Override public int getTextId() { return R.string.mirror; } diff --git a/src/com/android/gallery3d/filtershow/editors/EditorRotate.java b/src/com/android/gallery3d/filtershow/editors/EditorRotate.java index e49555831..a637c08ff 100644 --- a/src/com/android/gallery3d/filtershow/editors/EditorRotate.java +++ b/src/com/android/gallery3d/filtershow/editors/EditorRotate.java @@ -17,13 +17,18 @@ package com.android.gallery3d.filtershow.editors; import android.content.Context; +import android.view.View; +import android.view.View.OnClickListener; +import android.widget.Button; import android.widget.FrameLayout; +import android.widget.LinearLayout; import com.android.gallery3d.R; import com.android.gallery3d.filtershow.imageshow.ImageRotate; import com.android.gallery3d.filtershow.imageshow.MasterImage; public class EditorRotate extends Editor implements EditorInfo { + public static final String LOGTAG = "EditorRotate"; public static final int ID = R.id.editorRotate; ImageRotate mImageRotate; @@ -44,6 +49,19 @@ public class EditorRotate extends Editor implements EditorInfo { } @Override + public void openUtilityPanel(final LinearLayout accessoryViewList) { + final Button button = (Button) accessoryViewList.findViewById(R.id.applyEffect); + button.setOnClickListener(new OnClickListener() { + @Override + public void onClick(View arg0) { + mImageRotate.rotate(); + button.setText(mContext.getString(getTextId()) + " " + mImageRotate.getLocalValue()); + mImageRotate.saveAndSetPreset(); + } + }); + } + + @Override public int getTextId() { return R.string.rotate; } diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageFlip.java b/src/com/android/gallery3d/filtershow/imageshow/ImageFlip.java index 70637a30c..15197b055 100644 --- a/src/com/android/gallery3d/filtershow/imageshow/ImageFlip.java +++ b/src/com/android/gallery3d/filtershow/imageshow/ImageFlip.java @@ -58,6 +58,22 @@ public class ImageFlip extends ImageGeometry { return (rot / 90) % 2 != 0; } + public void flip() { + FLIP flip = getLocalFlip(); + boolean next = true; + // Picks next flip in order from enum FLIP (wrapping) + for (FLIP f : FLIP.values()) { + if (next) { + mNextFlip = f; + next = false; + } + if (f.equals(flip)) { + next = true; + } + } + setLocalFlip(mNextFlip); + } + @Override protected void setActionMove(float x, float y) { super.setActionMove(x, y); diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageRotate.java b/src/com/android/gallery3d/filtershow/imageshow/ImageRotate.java index c4b9aa27d..ab8023e02 100644 --- a/src/com/android/gallery3d/filtershow/imageshow/ImageRotate.java +++ b/src/com/android/gallery3d/filtershow/imageshow/ImageRotate.java @@ -54,6 +54,13 @@ public class ImageRotate extends ImageGeometry { mAngle = (mBaseAngle - angle) % 360; } + public void rotate() { + mAngle += 90; + mAngle = snappedAngle(mAngle); + mAngle %= 360; + setLocalRotation(mAngle); + } + @Override protected void setActionDown(float x, float y) { super.setActionDown(x, y); @@ -76,7 +83,7 @@ public class ImageRotate extends ImageGeometry { } @Override - protected int getLocalValue() { + public int getLocalValue() { return constrainedRotation(snappedAngle(getLocalRotation())); } diff --git a/src/com/android/gallery3d/ingest/data/MtpBitmapFetch.java b/src/com/android/gallery3d/ingest/data/MtpBitmapFetch.java index 5e1fb34fd..30868c22b 100644 --- a/src/com/android/gallery3d/ingest/data/MtpBitmapFetch.java +++ b/src/com/android/gallery3d/ingest/data/MtpBitmapFetch.java @@ -38,16 +38,28 @@ public class MtpBitmapFetch { public static Bitmap getThumbnail(MtpDevice device, MtpObjectInfo info) { byte[] imageBytes = device.getThumbnail(info.getObjectHandle()); - if (imageBytes == null) return null; + if (imageBytes == null) { + return null; + } BitmapFactory.Options o = new BitmapFactory.Options(); o.inJustDecodeBounds = true; BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, o); - if (o.outWidth == 0 || o.outHeight == 0) return null; + if (o.outWidth == 0 || o.outHeight == 0) { + return null; + } o.inBitmap = GalleryBitmapPool.getInstance().get(o.outWidth, o.outHeight); o.inMutable = true; o.inJustDecodeBounds = false; o.inSampleSize = 1; - return BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, o); + try { + return BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, o); + } catch (IllegalArgumentException e) { + // BitmapFactory throws an exception rather than returning null + // when image decoding fails and an existing bitmap was supplied + // for recycling, even if the failure was not caused by the use + // of that bitmap. + return BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length); + } } public static BitmapWithMetadata getFullsize(MtpDevice device, MtpObjectInfo info) { @@ -56,7 +68,9 @@ public class MtpBitmapFetch { public static BitmapWithMetadata getFullsize(MtpDevice device, MtpObjectInfo info, int maxSide) { byte[] imageBytes = device.getObject(info.getObjectHandle(), info.getCompressedSize()); - if (imageBytes == null) return null; + if (imageBytes == null) { + return null; + } Bitmap created; if (maxSide > 0) { BitmapFactory.Options o = new BitmapFactory.Options(); @@ -76,7 +90,9 @@ public class MtpBitmapFetch { } else { created = BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length); } - if (created == null) return null; + if (created == null) { + return null; + } return new BitmapWithMetadata(created, Exif.getOrientation(imageBytes)); } diff --git a/src/com/android/photos/data/GalleryBitmapPool.java b/src/com/android/photos/data/GalleryBitmapPool.java index 4c3279f73..a5a17ede2 100644 --- a/src/com/android/photos/data/GalleryBitmapPool.java +++ b/src/com/android/photos/data/GalleryBitmapPool.java @@ -106,7 +106,7 @@ public class GalleryBitmapPool { } public boolean put(Bitmap b) { - if (b == null) { + if (b == null || b.getConfig() != Bitmap.Config.ARGB_8888) { return false; } SparseArrayBitmapPool pool = getPoolForDimensions(b.getWidth(), b.getHeight()); |