Merge "Add UI for insertion in FilmStripView." into gb-ub-photos-carlsbad
diff --git a/src/com/android/camera/NewPhotoModule.java b/src/com/android/camera/NewPhotoModule.java
index e045d5d..3cb9733 100644
--- a/src/com/android/camera/NewPhotoModule.java
+++ b/src/com/android/camera/NewPhotoModule.java
@@ -64,8 +64,8 @@
 import com.android.gallery3d.exif.ExifInterface;
 import com.android.gallery3d.exif.ExifTag;
 import com.android.gallery3d.exif.Rational;
+import com.android.gallery3d.filtershow.crop.CropActivity;
 import com.android.gallery3d.filtershow.crop.CropExtras;
-import com.android.gallery3d.filtershow.FilterShowActivity;
 import com.android.gallery3d.util.UsageStatistics;
 
 import java.io.File;
@@ -1127,7 +1127,7 @@
                 newExtras.putBoolean(CropExtras.KEY_SHOW_WHEN_LOCKED, true);
             }
 
-            Intent cropIntent = new Intent(FilterShowActivity.CROP_ACTION);
+            Intent cropIntent = new Intent(CropActivity.CROP_ACTION);
 
             cropIntent.setData(tempUri);
             cropIntent.putExtras(newExtras);
diff --git a/src/com/android/camera/PhotoModule.java b/src/com/android/camera/PhotoModule.java
index 5b35271..17ed237 100644
--- a/src/com/android/camera/PhotoModule.java
+++ b/src/com/android/camera/PhotoModule.java
@@ -65,6 +65,7 @@
 import com.android.gallery3d.exif.ExifTag;
 import com.android.gallery3d.exif.Rational;
 import com.android.gallery3d.filtershow.FilterShowActivity;
+import com.android.gallery3d.filtershow.crop.CropActivity;
 import com.android.gallery3d.filtershow.crop.CropExtras;
 import com.android.gallery3d.util.UsageStatistics;
 
@@ -1191,7 +1192,7 @@
                 newExtras.putBoolean(CropExtras.KEY_SHOW_WHEN_LOCKED, true);
             }
 
-            Intent cropIntent = new Intent(FilterShowActivity.CROP_ACTION);
+            Intent cropIntent = new Intent(CropActivity.CROP_ACTION);
 
             cropIntent.setData(tempUri);
             cropIntent.putExtras(newExtras);
diff --git a/src/com/android/gallery3d/app/AlbumPage.java b/src/com/android/gallery3d/app/AlbumPage.java
index 001ce87..658abbb 100644
--- a/src/com/android/gallery3d/app/AlbumPage.java
+++ b/src/com/android/gallery3d/app/AlbumPage.java
@@ -39,7 +39,7 @@
 import com.android.gallery3d.data.MediaObject;
 import com.android.gallery3d.data.MediaSet;
 import com.android.gallery3d.data.Path;
-import com.android.gallery3d.filtershow.FilterShowActivity;
+import com.android.gallery3d.filtershow.crop.CropActivity;
 import com.android.gallery3d.filtershow.crop.CropExtras;
 import com.android.gallery3d.glrenderer.FadeTexture;
 import com.android.gallery3d.glrenderer.GLCanvas;
@@ -318,7 +318,7 @@
         Activity activity = mActivity;
         if (mData.getString(Gallery.EXTRA_CROP) != null) {
             Uri uri = dm.getContentUri(item.getPath());
-            Intent intent = new Intent(FilterShowActivity.CROP_ACTION, uri)
+            Intent intent = new Intent(CropActivity.CROP_ACTION, uri)
                     .addFlags(Intent.FLAG_ACTIVITY_FORWARD_RESULT)
                     .putExtras(getData());
             if (mData.getParcelable(MediaStore.EXTRA_OUTPUT) == null) {
diff --git a/src/com/android/gallery3d/app/Wallpaper.java b/src/com/android/gallery3d/app/Wallpaper.java
index 91bc772..b0a26c2 100644
--- a/src/com/android/gallery3d/app/Wallpaper.java
+++ b/src/com/android/gallery3d/app/Wallpaper.java
@@ -26,7 +26,7 @@
 import android.view.Display;
 
 import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.filtershow.FilterShowActivity;
+import com.android.gallery3d.filtershow.crop.CropActivity;
 import com.android.gallery3d.filtershow.crop.CropExtras;
 
 /**
@@ -100,7 +100,7 @@
                 Point size = getDefaultDisplaySize(new Point());
                 float spotlightX = (float) size.x / width;
                 float spotlightY = (float) size.y / height;
-                Intent request = new Intent(FilterShowActivity.CROP_ACTION)
+                Intent request = new Intent(CropActivity.CROP_ACTION)
                         .setDataAndType(mPickedItem, IMAGE_TYPE)
                         .addFlags(Intent.FLAG_ACTIVITY_FORWARD_RESULT)
                         .putExtra(CropExtras.KEY_OUTPUT_X, width)
diff --git a/src/com/android/gallery3d/filtershow/FilterShowActivity.java b/src/com/android/gallery3d/filtershow/FilterShowActivity.java
index 2986f96..ab7051a 100644
--- a/src/com/android/gallery3d/filtershow/FilterShowActivity.java
+++ b/src/com/android/gallery3d/filtershow/FilterShowActivity.java
@@ -19,7 +19,6 @@
 import android.app.ActionBar;
 import android.app.AlertDialog;
 import android.app.ProgressDialog;
-import android.app.WallpaperManager;
 import android.content.ContentValues;
 import android.content.DialogInterface;
 import android.content.Intent;
@@ -36,7 +35,6 @@
 import android.support.v4.app.FragmentActivity;
 import android.support.v4.app.FragmentTransaction;
 import android.util.DisplayMetrics;
-import android.util.Log;
 import android.util.TypedValue;
 import android.view.Display;
 import android.view.Menu;
@@ -49,17 +47,35 @@
 import android.widget.FrameLayout;
 import android.widget.ShareActionProvider;
 import android.widget.ShareActionProvider.OnShareTargetSelectedListener;
-
 import android.widget.Toast;
+
 import com.android.gallery3d.R;
 import com.android.gallery3d.data.LocalAlbum;
 import com.android.gallery3d.filtershow.cache.CachingPipeline;
 import com.android.gallery3d.filtershow.cache.FilteringPipeline;
 import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.category.*;
-import com.android.gallery3d.filtershow.crop.CropExtras;
-import com.android.gallery3d.filtershow.editors.*;
-import com.android.gallery3d.filtershow.filters.*;
+import com.android.gallery3d.filtershow.category.Action;
+import com.android.gallery3d.filtershow.category.CategoryAdapter;
+import com.android.gallery3d.filtershow.category.CategoryView;
+import com.android.gallery3d.filtershow.category.MainPanel;
+import com.android.gallery3d.filtershow.editors.BasicEditor;
+import com.android.gallery3d.filtershow.editors.Editor;
+import com.android.gallery3d.filtershow.editors.EditorCrop;
+import com.android.gallery3d.filtershow.editors.EditorDraw;
+import com.android.gallery3d.filtershow.editors.EditorFlip;
+import com.android.gallery3d.filtershow.editors.EditorInfo;
+import com.android.gallery3d.filtershow.editors.EditorManager;
+import com.android.gallery3d.filtershow.editors.EditorPanel;
+import com.android.gallery3d.filtershow.editors.EditorRedEye;
+import com.android.gallery3d.filtershow.editors.EditorRotate;
+import com.android.gallery3d.filtershow.editors.EditorStraighten;
+import com.android.gallery3d.filtershow.editors.EditorTinyPlanet;
+import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
+import com.android.gallery3d.filtershow.filters.FilterFxRepresentation;
+import com.android.gallery3d.filtershow.filters.FilterImageBorderRepresentation;
+import com.android.gallery3d.filtershow.filters.FilterRepresentation;
+import com.android.gallery3d.filtershow.filters.FiltersManager;
+import com.android.gallery3d.filtershow.filters.ImageFilter;
 import com.android.gallery3d.filtershow.imageshow.GeometryMetadata;
 import com.android.gallery3d.filtershow.imageshow.ImageCrop;
 import com.android.gallery3d.filtershow.imageshow.ImageShow;
@@ -67,7 +83,6 @@
 import com.android.gallery3d.filtershow.presets.ImagePreset;
 import com.android.gallery3d.filtershow.provider.SharedImageProvider;
 import com.android.gallery3d.filtershow.state.StateAdapter;
-import com.android.gallery3d.filtershow.tools.BitmapTask;
 import com.android.gallery3d.filtershow.tools.SaveCopyTask;
 import com.android.gallery3d.filtershow.tools.XmpPresets;
 import com.android.gallery3d.filtershow.tools.XmpPresets.XMresults;
@@ -77,16 +92,12 @@
 import com.android.photos.data.GalleryBitmapPool;
 
 import java.io.File;
-import java.io.IOException;
 import java.lang.ref.WeakReference;
 import java.util.Vector;
 
 public class FilterShowActivity extends FragmentActivity implements OnItemClickListener,
         OnShareTargetSelectedListener {
 
-    // fields for supporting crop action
-    public static final String CROP_ACTION = "com.android.camera.action.CROP";
-    private CropExtras mCropExtras = null;
     private String mAction = "";
     MasterImage mMasterImage = null;
 
@@ -94,7 +105,6 @@
 
     public static final String TINY_PLANET_ACTION = "com.android.camera.action.TINY_PLANET";
     public static final String LAUNCH_FULLSCREEN = "launch-fullscreen";
-    public static final int MAX_BMAP_IN_INTENT = 990000;
     private ImageLoader mImageLoader = null;
     private ImageShow mImageShow = null;
 
@@ -957,111 +967,23 @@
         }
     }
 
-    private boolean mSaveToExtraUri = false;
-    private boolean mSaveAsWallpaper = false;
-    private boolean mReturnAsExtra = false;
-    private boolean mOutputted = false;
 
     public void saveImage() {
-        handleSpecialExitCases();
-        if (!mOutputted) {
-            if (mImageShow.hasModifications()) {
-                // Get the name of the album, to which the image will be saved
-                File saveDir = SaveCopyTask.getFinalSaveDirectory(this, mImageLoader.getUri());
-                int bucketId = GalleryUtils.getBucketId(saveDir.getPath());
-                String albumName = LocalAlbum.getLocalizedName(getResources(), bucketId, null);
-                showSavingProgress(albumName);
-                mImageShow.saveImage(this, null);
-            } else {
-                done();
-            }
-        }
-    }
-
-    public boolean detectSpecialExitCases() {
-        return mCropExtras != null && (mCropExtras.getExtraOutput() != null
-                || mCropExtras.getSetAsWallpaper() || mCropExtras.getReturnData());
-    }
-
-    public void handleSpecialExitCases() {
-        if (mCropExtras != null) {
-            if (mCropExtras.getExtraOutput() != null) {
-                mSaveToExtraUri = true;
-                mOutputted = true;
-            }
-            if (mCropExtras.getSetAsWallpaper()) {
-                mSaveAsWallpaper = true;
-                mOutputted = true;
-            }
-            if (mCropExtras.getReturnData()) {
-                mReturnAsExtra = true;
-                mOutputted = true;
-            }
-            if (mOutputted) {
-                mImageShow.getImagePreset().mGeoData.setUseCropExtrasFlag(true);
-                showSavingProgress(null);
-                mImageShow.returnFilteredResult(this);
-            }
-        }
-    }
-
-    public void onFilteredResult(Bitmap filtered) {
-        Intent intent = new Intent();
-        intent.putExtra(CropExtras.KEY_CROPPED_RECT, mImageShow.getImageCropBounds());
-        if (mSaveToExtraUri) {
-            mImageShow.saveToUri(filtered, mCropExtras.getExtraOutput(),
-                    mCropExtras.getOutputFormat(), this);
-        }
-        if (mSaveAsWallpaper) {
-            setWallpaperInBackground(filtered);
-        }
-        if (mReturnAsExtra) {
-            if (filtered != null) {
-                int bmapSize = filtered.getRowBytes() * filtered.getHeight();
-                /*
-                 * Max size of Binder transaction buffer is 1Mb, so constrain
-                 * Bitmap to be somewhat less than this, otherwise we get
-                 * TransactionTooLargeExceptions.
-                 */
-                if (bmapSize > MAX_BMAP_IN_INTENT) {
-                    Log.w(LOGTAG, "Bitmap too large to be returned via intent");
-                } else {
-                    intent.putExtra(CropExtras.KEY_DATA, filtered);
-                }
-            }
-        }
-        setResult(RESULT_OK, intent);
-        if (!mSaveToExtraUri) {
+        if (mImageShow.hasModifications()) {
+            // Get the name of the album, to which the image will be saved
+            File saveDir = SaveCopyTask.getFinalSaveDirectory(this, mImageLoader.getUri());
+            int bucketId = GalleryUtils.getBucketId(saveDir.getPath());
+            String albumName = LocalAlbum.getLocalizedName(getResources(), bucketId, null);
+            showSavingProgress(albumName);
+            mImageShow.saveImage(this, null);
+        } else {
             done();
         }
     }
 
-    void setWallpaperInBackground(final Bitmap bmap) {
-        Toast.makeText(this, R.string.setting_wallpaper, Toast.LENGTH_LONG).show();
-        BitmapTask.Callbacks<FilterShowActivity> cb = new BitmapTask.Callbacks<FilterShowActivity>() {
-            @Override
-            public void onComplete(Bitmap result) {}
-
-            @Override
-            public void onCancel() {}
-
-            @Override
-            public Bitmap onExecute(FilterShowActivity param) {
-                try {
-                    WallpaperManager.getInstance(param).setBitmap(bmap);
-                } catch (IOException e) {
-                    Log.w(LOGTAG, "fail to set wall paper", e);
-                }
-                return null;
-            }
-        };
-        (new BitmapTask<FilterShowActivity>(cb)).execute(this);
-    }
 
     public void done() {
-        if (mOutputted) {
-            hideSavingProgress();
-        }
+        hideSavingProgress();
         finish();
     }
 
diff --git a/src/com/android/gallery3d/filtershow/cache/ImageLoader.java b/src/com/android/gallery3d/filtershow/cache/ImageLoader.java
index b4e98e1..7ddd9be 100644
--- a/src/com/android/gallery3d/filtershow/cache/ImageLoader.java
+++ b/src/com/android/gallery3d/filtershow/cache/ImageLoader.java
@@ -22,12 +22,10 @@
 import android.database.Cursor;
 import android.database.sqlite.SQLiteException;
 import android.graphics.Bitmap;
-import android.graphics.Bitmap.CompressFormat;
 import android.graphics.BitmapFactory;
 import android.graphics.BitmapRegionDecoder;
 import android.graphics.Matrix;
 import android.graphics.Rect;
-import android.graphics.Bitmap.CompressFormat;
 import android.net.Uri;
 import android.provider.MediaStore;
 import android.util.Log;
@@ -36,27 +34,19 @@
 import com.adobe.xmp.XMPMeta;
 import com.android.gallery3d.R;
 import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.exif.ExifTag;
 import com.android.gallery3d.exif.ExifInterface;
 import com.android.gallery3d.filtershow.FilterShowActivity;
 import com.android.gallery3d.filtershow.HistoryAdapter;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
 import com.android.gallery3d.filtershow.imageshow.ImageShow;
 import com.android.gallery3d.filtershow.imageshow.MasterImage;
 import com.android.gallery3d.filtershow.presets.ImagePreset;
-import com.android.gallery3d.filtershow.tools.BitmapTask;
 import com.android.gallery3d.filtershow.tools.SaveCopyTask;
-import com.android.gallery3d.util.InterruptableOutputStream;
 import com.android.gallery3d.util.XmpUtilHelper;
 
-import java.io.ByteArrayInputStream;
-import java.io.Closeable;
 import java.io.File;
-import java.io.FileInputStream;
 import java.io.FileNotFoundException;
 import java.io.IOException;
 import java.io.InputStream;
-import java.io.OutputStream;
 import java.util.Vector;
 import java.util.concurrent.locks.ReentrantLock;
 
@@ -71,8 +61,6 @@
     private Bitmap mOriginalBitmapHighres = null;
     private Bitmap mBackgroundBitmap = null;
 
-    private final ZoomCache mZoomCache = new ZoomCache();
-
     private int mOrientation = 0;
     private HistoryAdapter mAdapter = null;
 
@@ -511,116 +499,6 @@
         return bmap;
     }
 
-    public void returnFilteredResult(ImagePreset preset,
-            final FilterShowActivity filterShowActivity) {
-        BitmapTask.Callbacks<ImagePreset> cb = new BitmapTask.Callbacks<ImagePreset>() {
-
-            @Override
-            public void onComplete(Bitmap result) {
-                filterShowActivity.onFilteredResult(result);
-            }
-
-            @Override
-            public void onCancel() {
-            }
-
-            @Override
-            public Bitmap onExecute(ImagePreset param) {
-                if (param == null || mUri == null) {
-                    return null;
-                }
-                BitmapFactory.Options options = new BitmapFactory.Options();
-                boolean noBitmap = true;
-                int num_tries = 0;
-                if (options.inSampleSize < 1) {
-                    options.inSampleSize = 1;
-                }
-                Bitmap bitmap = null;
-                // Stopgap fix for low-memory devices.
-                while (noBitmap) {
-                    try {
-                        // Try to do bitmap operations, downsample if low-memory
-                        bitmap = loadMutableBitmap(mContext, mUri, options);
-                        if (bitmap == null) {
-                            Log.w(LOGTAG, "Failed to save image!");
-                            return null;
-                        }
-                        CachingPipeline pipeline = new CachingPipeline(
-                                FiltersManager.getManager(), "Saving");
-                        bitmap = pipeline.renderFinalImage(bitmap, param);
-                        noBitmap = false;
-                    } catch (java.lang.OutOfMemoryError e) {
-                        // Try 5 times before failing for good.
-                        if (++num_tries >= 5) {
-                            throw e;
-                        }
-                        bitmap = null;
-                        System.gc();
-                        options.inSampleSize *= 2;
-                    }
-                }
-                return bitmap;
-            }
-        };
-
-        (new BitmapTask<ImagePreset>(cb)).execute(preset);
-    }
-
-    private String getFileExtension(String requestFormat) {
-        String outputFormat = (requestFormat == null)
-                ? "jpg"
-                : requestFormat;
-        outputFormat = outputFormat.toLowerCase();
-        return (outputFormat.equals("png") || outputFormat.equals("gif"))
-                ? "png" // We don't support gif compression.
-                : "jpg";
-    }
-
-    private CompressFormat convertExtensionToCompressFormat(String extension) {
-        return extension.equals("png") ? CompressFormat.PNG : CompressFormat.JPEG;
-    }
-
-    public void saveToUri(Bitmap bmap, Uri uri, final String outputFormat,
-            final FilterShowActivity filterShowActivity) {
-
-        OutputStream out = null;
-        try {
-            out = filterShowActivity.getContentResolver().openOutputStream(uri);
-        } catch (FileNotFoundException e) {
-            Log.w(LOGTAG, "cannot write output", e);
-            out = null;
-        } finally {
-            if (bmap == null || out == null) {
-                return;
-            }
-        }
-
-        final InterruptableOutputStream ios = new InterruptableOutputStream(out);
-
-        BitmapTask.Callbacks<Bitmap> cb = new BitmapTask.Callbacks<Bitmap>() {
-
-            @Override
-            public void onComplete(Bitmap result) {
-                filterShowActivity.done();
-            }
-
-            @Override
-            public void onCancel() {
-                ios.interrupt();
-            }
-
-            @Override
-            public Bitmap onExecute(Bitmap param) {
-                CompressFormat cf = convertExtensionToCompressFormat(getFileExtension(outputFormat));
-                param.compress(cf, DEFAULT_COMPRESS_QUALITY, ios);
-                Utils.closeSilently(ios);
-                return null;
-            }
-        };
-
-        (new BitmapTask<Bitmap>(cb)).execute(bmap);
-    }
-
     public void setAdapter(HistoryAdapter adapter) {
         mAdapter = adapter;
     }
diff --git a/src/com/android/gallery3d/filtershow/cache/ZoomCache.java b/src/com/android/gallery3d/filtershow/cache/ZoomCache.java
deleted file mode 100644
index dbd0751..0000000
--- a/src/com/android/gallery3d/filtershow/cache/ZoomCache.java
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.cache;
-
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-
-import com.android.gallery3d.filtershow.presets.ImagePreset;
-
-public class ZoomCache {
-
-    private ImagePreset mImagePreset = null;
-    private Bitmap mBitmap = null;
-    private Rect mBounds = null;
-
-    // TODO: move the processing to a background thread...
-    public Bitmap getImage(ImagePreset preset, Rect bounds) {
-        if (mBounds != bounds) {
-            return null;
-        }
-        if (mImagePreset == null) {
-            return null;
-        }
-        if (!mImagePreset.same(preset)) {
-            return null;
-        }
-        return mBitmap;
-    }
-
-    public void setImage(ImagePreset preset, Rect bounds, Bitmap bitmap) {
-        mBitmap = bitmap;
-        mBounds = bounds;
-        mImagePreset = preset;
-    }
-
-    public void reset(ImagePreset imagePreset) {
-        if (imagePreset == mImagePreset) {
-            mBitmap = null;
-        }
-    }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageShow.java b/src/com/android/gallery3d/filtershow/imageshow/ImageShow.java
index b833cf8..4e59a5f 100644
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageShow.java
+++ b/src/com/android/gallery3d/filtershow/imageshow/ImageShow.java
@@ -539,13 +539,6 @@
         mImageLoader.saveImage(getImagePreset(), filterShowActivity, file);
     }
 
-    public void saveToUri(Bitmap f, Uri u, String m, FilterShowActivity filterShowActivity) {
-        mImageLoader.saveToUri(f, u, m, filterShowActivity);
-    }
-
-    public void returnFilteredResult(FilterShowActivity filterShowActivity) {
-        mImageLoader.returnFilteredResult(getImagePreset(), filterShowActivity);
-    }
 
     public boolean scaleInProgress() {
         return mScaleGestureDetector.isInProgress();
diff --git a/src/com/android/gallery3d/filtershow/tools/BitmapTask.java b/src/com/android/gallery3d/filtershow/tools/BitmapTask.java
deleted file mode 100644
index 62801c1..0000000
--- a/src/com/android/gallery3d/filtershow/tools/BitmapTask.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.tools;
-
-import android.graphics.Bitmap;
-import android.os.AsyncTask;
-
-/**
- * Asynchronous task filtering or doign I/O with bitmaps.
- */
-public class BitmapTask <T> extends AsyncTask<T, Void, Bitmap> {
-
-    private Callbacks<T> mCallbacks;
-    private static final String LOGTAG = "BitmapTask";
-
-    public BitmapTask(Callbacks<T> callbacks) {
-        mCallbacks = callbacks;
-    }
-
-    @Override
-    protected Bitmap doInBackground(T... params) {
-        if (params == null || mCallbacks == null) {
-            return null;
-        }
-        return mCallbacks.onExecute(params[0]);
-    }
-
-    @Override
-    protected void onPostExecute(Bitmap result) {
-        if (mCallbacks == null) {
-            return;
-        }
-        mCallbacks.onComplete(result);
-    }
-
-    @Override
-    protected void onCancelled() {
-        if (mCallbacks == null) {
-            return;
-        }
-        mCallbacks.onCancel();
-    }
-
-    /**
-     * Callbacks for the asynchronous task.
-     */
-    public interface Callbacks<P> {
-        void onComplete(Bitmap result);
-
-        void onCancel();
-
-        Bitmap onExecute(P param);
-    }
-}
diff --git a/src/com/android/gallery3d/gadget/WidgetConfigure.java b/src/com/android/gallery3d/gadget/WidgetConfigure.java
index eb81b6e..2a4c6cf 100644
--- a/src/com/android/gallery3d/gadget/WidgetConfigure.java
+++ b/src/com/android/gallery3d/gadget/WidgetConfigure.java
@@ -35,7 +35,7 @@
 import com.android.gallery3d.data.LocalAlbum;
 import com.android.gallery3d.data.MediaSet;
 import com.android.gallery3d.data.Path;
-import com.android.gallery3d.filtershow.FilterShowActivity;
+import com.android.gallery3d.filtershow.crop.CropActivity;
 import com.android.gallery3d.filtershow.crop.CropExtras;
 
 public class WidgetConfigure extends Activity {
@@ -149,7 +149,7 @@
         int widgetHeight = Math.round(height * scale);
 
         mPickedItem = data.getData();
-        Intent request = new Intent(FilterShowActivity.CROP_ACTION, mPickedItem)
+        Intent request = new Intent(CropActivity.CROP_ACTION, mPickedItem)
                 .putExtra(CropExtras.KEY_OUTPUT_X, widgetWidth)
                 .putExtra(CropExtras.KEY_OUTPUT_Y, widgetHeight)
                 .putExtra(CropExtras.KEY_ASPECT_X, widgetWidth)
diff --git a/src/com/android/photos/MultiChoiceManager.java b/src/com/android/photos/MultiChoiceManager.java
index f315cf9..49519ca 100644
--- a/src/com/android/photos/MultiChoiceManager.java
+++ b/src/com/android/photos/MultiChoiceManager.java
@@ -35,6 +35,7 @@
 import com.android.gallery3d.app.TrimVideo;
 import com.android.gallery3d.data.MediaObject;
 import com.android.gallery3d.filtershow.FilterShowActivity;
+import com.android.gallery3d.filtershow.crop.CropActivity;
 import com.android.gallery3d.util.GalleryUtils;
 
 import java.util.ArrayList;
@@ -239,7 +240,7 @@
             case R.id.menu_crop:
                 intent.setDataAndType(uri, mime)
                       .setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
-                      .setAction(FilterShowActivity.CROP_ACTION)
+                      .setAction(CropActivity.CROP_ACTION)
                       .setClass(mContext, FilterShowActivity.class);
                 mContext.startActivity(intent);
                 return;
diff --git a/src/com/android/photos/data/BitmapDecoder.java b/src/com/android/photos/data/BitmapDecoder.java
index 3e5a0f7..c5101cd 100644
--- a/src/com/android/photos/data/BitmapDecoder.java
+++ b/src/com/android/photos/data/BitmapDecoder.java
@@ -97,13 +97,13 @@
 
     private static <T> Bitmap delegateDecode(Decoder<T> decoder, T input) {
         BitmapFactory.Options options = getOptions();
+        GalleryBitmapPool pool = GalleryBitmapPool.getInstance();
         try {
             options.inJustDecodeBounds = true;
             if (!decoder.decodeBounds(input, options)) {
                 return null;
             }
             options.inJustDecodeBounds = false;
-            GalleryBitmapPool pool = GalleryBitmapPool.getInstance();
             Bitmap reuseBitmap = pool.get(options.outWidth, options.outHeight);
             options.inBitmap = reuseBitmap;
             Bitmap decodedBitmap = decoder.decode(input, options);
@@ -111,6 +111,13 @@
                 pool.put(reuseBitmap);
             }
             return decodedBitmap;
+        } catch (IllegalArgumentException e) {
+            if (options.inBitmap == null) {
+                throw e;
+            }
+            pool.put(options.inBitmap);
+            options.inBitmap = null;
+            return decoder.decode(input, options);
         } finally {
             options.inBitmap = null;
             options.inJustDecodeBounds = false;