PhotoPage.java revision 50ea2d2938218ac6b2039f0e42998cfbbc45d1f1
1f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin/*
2f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * Copyright (C) 2010 The Android Open Source Project
3f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin *
4f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * Licensed under the Apache License, Version 2.0 (the "License");
5f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * you may not use this file except in compliance with the License.
6f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * You may obtain a copy of the License at
7f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin *
8f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin *      http://www.apache.org/licenses/LICENSE-2.0
9f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin *
10f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * Unless required by applicable law or agreed to in writing, software
11f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * distributed under the License is distributed on an "AS IS" BASIS,
12f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * See the License for the specific language governing permissions and
14f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin * limitations under the License.
15f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin */
16f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
17f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linpackage com.android.gallery3d.app;
18f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
19fc86994f86f8cfb31e151c9e730dc1e9dc7b3349Yuli Huangimport android.annotation.TargetApi;
208bc5bebba780ca4a322b466b06fc909331697cf4Owen Linimport android.app.Activity;
21604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chenimport android.content.ActivityNotFoundException;
2266ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Changimport android.content.ContentResolver;
23604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chenimport android.content.Context;
24604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chenimport android.content.Intent;
2504ac045bf8da5082bbb0bdc9ea5f9c9b5b796ad0Yuli Huangimport android.graphics.Rect;
26604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chenimport android.net.Uri;
2733ef03776b7734717b16f6fc861b831fb1b1dfacMartijn Coenenimport android.nfc.NfcAdapter;
28604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chenimport android.os.Bundle;
29604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chenimport android.os.Handler;
30604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chenimport android.os.Message;
31f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescuimport android.view.animation.AccelerateInterpolator;
32604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chenimport android.widget.Toast;
33604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chen
34b21b8e58a604f6c701245d84b141b5b87663192bOwen Linimport com.actionbarsherlock.app.ActionBar.OnMenuVisibilityListener;
35b21b8e58a604f6c701245d84b141b5b87663192bOwen Linimport com.actionbarsherlock.view.Menu;
36b21b8e58a604f6c701245d84b141b5b87663192bOwen Linimport com.actionbarsherlock.view.MenuItem;
37f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.R;
38f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescuimport com.android.gallery3d.anim.FloatAnimation;
39fc86994f86f8cfb31e151c9e730dc1e9dc7b3349Yuli Huangimport com.android.gallery3d.common.ApiHelper;
40616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Linimport com.android.gallery3d.common.Utils;
41f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.data.DataManager;
426b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Changimport com.android.gallery3d.data.FilterDeleteSet;
43f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.data.MediaDetails;
44f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.data.MediaItem;
45f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.data.MediaObject;
46f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.data.MediaSet;
476b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Changimport com.android.gallery3d.data.MtpSource;
48f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.data.Path;
49a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Liimport com.android.gallery3d.data.SecureAlbum;
50a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Liimport com.android.gallery3d.data.SecureSource;
513b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Changimport com.android.gallery3d.data.SnailAlbum;
523b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Changimport com.android.gallery3d.data.SnailItem;
5315b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Changimport com.android.gallery3d.data.SnailSource;
54f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.picasasource.PicasaSource;
55f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescuimport com.android.gallery3d.ui.AnimationTime;
564105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chenimport com.android.gallery3d.ui.DetailsHelper;
574105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chenimport com.android.gallery3d.ui.DetailsHelper.CloseListener;
584105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chenimport com.android.gallery3d.ui.DetailsHelper.DetailsSource;
59f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.ui.GLCanvas;
60616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Linimport com.android.gallery3d.ui.GLRoot;
61616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Linimport com.android.gallery3d.ui.GLRoot.OnGLIdleListener;
62f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescuimport com.android.gallery3d.ui.BitmapScreenNail;
63f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.ui.GLView;
64f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.ui.ImportCompleteListener;
65f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.ui.MenuExecutor;
66616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Linimport com.android.gallery3d.ui.PhotoFallbackEffect;
6721a412c93c9b0401b039f4eb86d4950752e5bb84Owen Linimport com.android.gallery3d.ui.PhotoView;
68f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescuimport com.android.gallery3d.ui.RawTexture;
69f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.ui.SelectionManager;
70f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.ui.SynchronizedHandler;
71f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Linimport com.android.gallery3d.util.GalleryUtils;
7266ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Changimport com.android.gallery3d.util.MediaSetUtils;
73f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
74bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Changpublic class PhotoPage extends ActivityState implements
7561f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang        PhotoView.Listener, OrientationManager.Listener, AppBridge.Server {
76f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private static final String TAG = "PhotoPage";
77f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
78f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private static final int MSG_HIDE_BARS = 1;
79bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    private static final int MSG_LOCK_ORIENTATION = 2;
80bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    private static final int MSG_UNLOCK_ORIENTATION = 3;
81bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    private static final int MSG_ON_FULL_SCREEN_CHANGED = 4;
8261f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    private static final int MSG_UPDATE_ACTION_BAR = 5;
83bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang    private static final int MSG_UNFREEZE_GLROOT = 6;
84e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang    private static final int MSG_WANT_BARS = 7;
856cf807453fb58ccd4cc513ff187b306c7090e67cOwen Lin
86f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private static final int HIDE_BARS_TIMEOUT = 3500;
87bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang    private static final int UNFREEZE_GLROOT_TIMEOUT = 250;
88f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
89f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private static final int REQUEST_SLIDESHOW = 1;
90f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private static final int REQUEST_CROP = 2;
91f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private static final int REQUEST_CROP_PICASA = 3;
92f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang    private static final int REQUEST_EDIT = 4;
9371cd89a38752bc22ae0ec2df965e4280b776623cChih-Chung Chang    private static final int REQUEST_PLAY_VIDEO = 5;
94f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
95f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    public static final String KEY_MEDIA_SET_PATH = "media-set-path";
96f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    public static final String KEY_MEDIA_ITEM_PATH = "media-item-path";
97f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    public static final String KEY_INDEX_HINT = "index-hint";
9804ac045bf8da5082bbb0bdc9ea5f9c9b5b796ad0Yuli Huang    public static final String KEY_OPEN_ANIMATION_RECT = "open-animation-rect";
99bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    public static final String KEY_APP_BRIDGE = "app-bridge";
10054fe6202b6f7d233e7645c121321fe0f3d20fc8bYuli Huang    public static final String KEY_TREAT_BACK_AS_UP = "treat-back-as-up";
101bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang
102bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    public static final String KEY_RETURN_INDEX_HINT = "return-index-hint";
103f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
104f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private GalleryApp mApplication;
105f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private SelectionManager mSelectionManager;
106f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
107f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private PhotoView mPhotoView;
108f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private PhotoPage.Model mModel;
1094105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chen    private DetailsHelper mDetailsHelper;
110f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private boolean mShowDetails;
111cf46a3abc26aac7cdb6b6993aeade053304b71d9Ray Chen    private Path mPendingSharePath;
112f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
113f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    // mMediaSet could be null if there is no KEY_MEDIA_SET_PATH supplied.
114f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    // E.g., viewing a photo in gmail attachment
1156b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    private FilterDeleteSet mMediaSet;
116f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
117a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li    // The mediaset used by camera launched from secure lock screen.
118a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li    private SecureAlbum mSecureAlbum;
119a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li
120f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private int mCurrentIndex = 0;
121f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private Handler mHandler;
122113bfc77c4468411da9ae1290553c3be89f8df9aOwen Lin    private boolean mShowBars = true;
12361f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    private volatile boolean mActionBarAllowed = true;
1248cab3e872dd95e55ba34fdb94269a0c5069e72aeRay Chen    private GalleryActionBar mActionBar;
125f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private boolean mIsMenuVisible;
126f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private MediaItem mCurrentPhoto = null;
127f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private MenuExecutor mMenuExecutor;
128f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private boolean mIsActive;
12984c220f10a643927c8a2126de8a755d8d7f7ec9eRay Chen    private String mSetPathString;
130b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang    // This is the original mSetPathString before adding the camera preview item.
131b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang    private String mOriginalSetPathString;
132bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    private AppBridge mAppBridge;
1333b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang    private SnailItem mScreenNailItem;
1343b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang    private SnailAlbum mScreenNailSet;
135bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    private OrientationManager mOrientationManager;
13671cd89a38752bc22ae0ec2df965e4280b776623cChih-Chung Chang    private boolean mHasActivityResult;
13754fe6202b6f7d233e7645c121321fe0f3d20fc8bYuli Huang    private boolean mTreatBackAsUp;
13815b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang
139f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu    private RawTexture mFadeOutTexture;
140f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu    private Rect mOpenAnimationRect;
14102ef48574ef7099ebaa0386bd6fd676bd2fd5489Bobby Georgescu    public static final int ANIM_TIME_OPENING = 400;
142f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu
1436b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    // The item that is deleted (but it can still be undeleted before commiting)
1446b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    private Path mDeletePath;
1456b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    private boolean mDeleteIsFocus;  // whether the deleted item was in focus
1466b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang
14733ef03776b7734717b16f6fc861b831fb1b1dfacMartijn Coenen    private NfcAdapter mNfcAdapter;
14833ef03776b7734717b16f6fc861b831fb1b1dfacMartijn Coenen
149b21b8e58a604f6c701245d84b141b5b87663192bOwen Lin    private Menu mActionBarMenu;
150b21b8e58a604f6c701245d84b141b5b87663192bOwen Lin
1512bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin    private final MyMenuVisibilityListener mMenuVisibilityListener =
1522bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin            new MyMenuVisibilityListener();
1532bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin
154f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    public static interface Model extends PhotoView.Model {
155f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        public void resume();
156f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        public void pause();
157f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        public boolean isEmpty();
158f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        public void setCurrentPhoto(Path path, int indexHint);
159f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
160f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
161f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private class MyMenuVisibilityListener implements OnMenuVisibilityListener {
16206c6401eededc2ec842ba4994a838c2ded0a666cPin Ting        @Override
163f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        public void onMenuVisibilityChanged(boolean isVisible) {
164f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            mIsMenuVisible = isVisible;
165f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            refreshHidingMessage();
166f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
167f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
168f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
169f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu    private static class BackgroundFadeOut extends FloatAnimation {
170f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu        public BackgroundFadeOut() {
171f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu            super(1f, 0f, ANIM_TIME_OPENING);
172f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu            setInterpolator(new AccelerateInterpolator(2f));
173f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu        }
174f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu    }
175f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu
176f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu    private final FloatAnimation mBackgroundFade = new BackgroundFadeOut();
177f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
178915c2c5b2c367df71599370613af0924bd7c4887Bobby Georgescu    @Override
179915c2c5b2c367df71599370613af0924bd7c4887Bobby Georgescu    protected int getBackgroundColorId() {
180915c2c5b2c367df71599370613af0924bd7c4887Bobby Georgescu        return R.color.photo_background;
181915c2c5b2c367df71599370613af0924bd7c4887Bobby Georgescu    }
182915c2c5b2c367df71599370613af0924bd7c4887Bobby Georgescu
183f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu    private final GLView mRootPane = new GLView() {
184f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        @Override
185f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        protected void renderBackground(GLCanvas view) {
186f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu            if(mFadeOutTexture != null) {
187f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                if(mBackgroundFade.calculate(AnimationTime.get())) invalidate();
188f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                if(!mBackgroundFade.isActive()) {
189f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                    mFadeOutTexture = null;
190f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                    mOpenAnimationRect = null;
191f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                    BitmapScreenNail.enableDrawPlaceholder();
192f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                } else {
193f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                    float fadeAlpha = mBackgroundFade.get();
194f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                    if(fadeAlpha < 1f) {
195915c2c5b2c367df71599370613af0924bd7c4887Bobby Georgescu                        view.clearBuffer(getBackgroundColor());
196f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                        view.setAlpha(fadeAlpha);
197f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                    }
198f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                    mFadeOutTexture.draw(view, 0, 0);
19902ef48574ef7099ebaa0386bd6fd676bd2fd5489Bobby Georgescu                    view.setAlpha(1f - fadeAlpha);
200f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                    return;
201f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                }
202f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu            }
203915c2c5b2c367df71599370613af0924bd7c4887Bobby Georgescu            view.clearBuffer(getBackgroundColor());
204f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
205f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
206f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        @Override
207f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        protected void onLayout(
208f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                boolean changed, int left, int top, int right, int bottom) {
209f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            mPhotoView.layout(0, 0, right - left, bottom - top);
210f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            if (mShowDetails) {
2118cab3e872dd95e55ba34fdb94269a0c5069e72aeRay Chen                mDetailsHelper.layout(left, mActionBar.getHeight(), right, bottom);
212f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            }
213f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
214f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    };
215f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
216f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    @Override
217f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    public void onCreate(Bundle data, Bundle restoreState) {
21845c56f2d34c71d0bc9b84ebeef6d1314738d0fc0Bobby Georgescu        super.onCreate(data, restoreState);
2198cab3e872dd95e55ba34fdb94269a0c5069e72aeRay Chen        mActionBar = mActivity.getGalleryActionBar();
220f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mSelectionManager = new SelectionManager(mActivity, false);
221f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mMenuExecutor = new MenuExecutor(mActivity, mSelectionManager);
222f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
223f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mPhotoView = new PhotoView(mActivity);
224bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        mPhotoView.setListener(this);
225f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mRootPane.addComponent(mPhotoView);
226f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mApplication = (GalleryApp)((Activity) mActivity).getApplication();
227bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        mOrientationManager = mActivity.getOrientationManager();
228bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        mOrientationManager.addListener(this);
2292ef46ed28b28b355d7f3f1432c7b1196b832a859Chih-Chung Chang        mActivity.getGLRoot().setOrientationSource(mOrientationManager);
230f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
23184c220f10a643927c8a2126de8a755d8d7f7ec9eRay Chen        mSetPathString = data.getString(KEY_MEDIA_SET_PATH);
232b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang        mOriginalSetPathString = mSetPathString;
23333ef03776b7734717b16f6fc861b831fb1b1dfacMartijn Coenen        mNfcAdapter = NfcAdapter.getDefaultAdapter(mActivity.getAndroidContext());
234f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        Path itemPath = Path.fromString(data.getString(KEY_MEDIA_ITEM_PATH));
23554fe6202b6f7d233e7645c121321fe0f3d20fc8bYuli Huang        mTreatBackAsUp = data.getBoolean(KEY_TREAT_BACK_AS_UP, false);
236f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
23784c220f10a643927c8a2126de8a755d8d7f7ec9eRay Chen        if (mSetPathString != null) {
238bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            mAppBridge = (AppBridge) data.getParcelable(KEY_APP_BRIDGE);
239bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            if (mAppBridge != null) {
240253c5aec7692afdd7880fbd169d4b44d5679cbc0Chih-Chung Chang                mAppBridge.setServer(this);
241bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                mOrientationManager.lockOrientation();
242b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang
243bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                // Get the ScreenNail from AppBridge and register it.
2443b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang                int id = SnailSource.newId();
245b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang                Path screenNailSetPath = SnailSource.getSetPath(id);
246bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                Path screenNailItemPath = SnailSource.getItemPath(id);
2473b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang                mScreenNailSet = (SnailAlbum) mActivity.getDataManager()
2483b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang                        .getMediaObject(screenNailSetPath);
2493b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang                mScreenNailItem = (SnailItem) mActivity.getDataManager()
250bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                        .getMediaObject(screenNailItemPath);
2513b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang                mScreenNailItem.setScreenNail(mAppBridge.attachScreenNail());
252b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang
253a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li                // Check if the path is a secure album.
254a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li                if (SecureSource.isSecurePath(mSetPathString)) {
255a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li                    mSecureAlbum = (SecureAlbum) mActivity.getDataManager()
256a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li                            .getMediaSet(mSetPathString);
257a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li                }
258a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li
2593b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang                // Combine the original MediaSet with the one for ScreenNail
2603b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang                // from AppBridge.
261b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang                mSetPathString = "/combo/item/{" + screenNailSetPath +
262b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang                        "," + mSetPathString + "}";
263b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang
264b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang                // Start from the screen nail.
265bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                itemPath = screenNailItemPath;
266788245711658188131ae2670e44fb6ca8ad5d53aWu-cheng Li
267788245711658188131ae2670e44fb6ca8ad5d53aWu-cheng Li                // Action bar should not be displayed when camera starts.
2680b2486cff0c1b951c54325596256b986307f7f3aChih-Chung Chang                mFlags |= FLAG_HIDE_ACTION_BAR | FLAG_HIDE_STATUS_BAR;
26961f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang                mShowBars = false;
270b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang            }
271b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang
2726118af9ddad8acc050133154f8f60c842c7f9bfaChih-Chung Chang            MediaSet originalSet = mActivity.getDataManager()
2736118af9ddad8acc050133154f8f60c842c7f9bfaChih-Chung Chang                    .getMediaSet(mSetPathString);
2746118af9ddad8acc050133154f8f60c842c7f9bfaChih-Chung Chang            mSelectionManager.setSourceMediaSet(originalSet);
2756b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang            mSetPathString = "/filter/delete/{" + mSetPathString + "}";
2766b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang            mMediaSet = (FilterDeleteSet) mActivity.getDataManager()
2776b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang                    .getMediaSet(mSetPathString);
278f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            mCurrentIndex = data.getInt(KEY_INDEX_HINT, 0);
279f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            if (mMediaSet == null) {
28084c220f10a643927c8a2126de8a755d8d7f7ec9eRay Chen                Log.w(TAG, "failed to restore " + mSetPathString);
281f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            }
282f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            PhotoDataAdapter pda = new PhotoDataAdapter(
283bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                    mActivity, mPhotoView, mMediaSet, itemPath, mCurrentIndex,
28443a80fd806247cb50e81bacda3ad21d210e9ae88Angus Kong                    mAppBridge == null ? -1 : 0,
285dbb6acc204ba6f095eb0e49e1298e9ceda2c3096Wu-cheng Li                    mAppBridge == null ? false : mAppBridge.isPanorama(),
286dbb6acc204ba6f095eb0e49e1298e9ceda2c3096Wu-cheng Li                    mAppBridge == null ? false : mAppBridge.isStaticCamera());
287f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            mModel = pda;
288f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            mPhotoView.setModel(mModel);
289f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
290f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            pda.setDataListener(new PhotoDataAdapter.DataListener() {
291f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
292113bfc77c4468411da9ae1290553c3be89f8df9aOwen Lin                @Override
293f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                public void onPhotoChanged(int index, Path item) {
294f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    mCurrentIndex = index;
295f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    if (item != null) {
296616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin                        MediaItem photo = mModel.getMediaItem(0);
297f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                        if (photo != null) updateCurrentPhoto(photo);
298f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    }
29961f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang                    updateBars();
300f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                }
301f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
302f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                @Override
303f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                public void onLoadingFinished() {
304f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    if (!mModel.isEmpty()) {
305616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin                        MediaItem photo = mModel.getMediaItem(0);
306f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                        if (photo != null) updateCurrentPhoto(photo);
307f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    } else if (mIsActive) {
308c370476adcf29f311ceec70a119792a0168781e9Chih-Chung Chang                        // We only want to finish the PhotoPage if there is no
309c370476adcf29f311ceec70a119792a0168781e9Chih-Chung Chang                        // deletion that the user can undo.
310c370476adcf29f311ceec70a119792a0168781e9Chih-Chung Chang                        if (mMediaSet.getNumberOfDeletions() == 0) {
311c370476adcf29f311ceec70a119792a0168781e9Chih-Chung Chang                            mActivity.getStateManager().finishState(
312c370476adcf29f311ceec70a119792a0168781e9Chih-Chung Chang                                    PhotoPage.this);
313c370476adcf29f311ceec70a119792a0168781e9Chih-Chung Chang                        }
314f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    }
315f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                }
316f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
317f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                @Override
318f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                public void onLoadingStarted() {
319f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                }
320f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            });
321f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        } else {
322f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            // Get default media set by the URI
323f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            MediaItem mediaItem = (MediaItem)
324f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    mActivity.getDataManager().getMediaObject(itemPath);
325f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            mModel = new SinglePhotoDataAdapter(mActivity, mPhotoView, mediaItem);
326f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            mPhotoView.setModel(mModel);
327f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            updateCurrentPhoto(mediaItem);
328f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
329cf46a3abc26aac7cdb6b6993aeade053304b71d9Ray Chen
330f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mHandler = new SynchronizedHandler(mActivity.getGLRoot()) {
331f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            @Override
332f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            public void handleMessage(Message message) {
333f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                switch (message.what) {
334f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    case MSG_HIDE_BARS: {
335f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                        hideBars();
336f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                        break;
337f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    }
338bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                    case MSG_LOCK_ORIENTATION: {
339bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                        mOrientationManager.lockOrientation();
340bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                        break;
341bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                    }
342bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                    case MSG_UNLOCK_ORIENTATION: {
343bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                        mOrientationManager.unlockOrientation();
344bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                        break;
345bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                    }
346bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                    case MSG_ON_FULL_SCREEN_CHANGED: {
347bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                        mAppBridge.onFullScreenChanged(message.arg1 == 1);
348bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                        break;
349bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                    }
35061f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang                    case MSG_UPDATE_ACTION_BAR: {
35161f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang                        updateBars();
35261f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang                        break;
35361f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang                    }
354e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang                    case MSG_WANT_BARS: {
355e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang                        wantBars();
356e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang                        break;
357e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang                    }
358bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang                    case MSG_UNFREEZE_GLROOT: {
359bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang                        mActivity.getGLRoot().unfreeze();
360bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang                        break;
361bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang                    }
362f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    default: throw new AssertionError(message.what);
363f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                }
364f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            }
365f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        };
366f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
36704ac045bf8da5082bbb0bdc9ea5f9c9b5b796ad0Yuli Huang        // start the opening animation only if it's not restored.
36804ac045bf8da5082bbb0bdc9ea5f9c9b5b796ad0Yuli Huang        if (restoreState == null) {
369f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu            mFadeOutTexture = mActivity.getTransitionStore().get(AlbumPage.KEY_FADE_TEXTURE);
370f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu            if(mFadeOutTexture != null) {
371f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                mBackgroundFade.start();
372f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                BitmapScreenNail.disableDrawPlaceholder();
373f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                mOpenAnimationRect = (Rect) data.getParcelable(KEY_OPEN_ANIMATION_RECT);
374f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu                mPhotoView.setOpenAnimationRect(mOpenAnimationRect);
375f4a707f9716874025b189d0e4ca4dfad0d7abbabBobby Georgescu            }
37604ac045bf8da5082bbb0bdc9ea5f9c9b5b796ad0Yuli Huang        }
377f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
378f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
3796772173d2a49b87a1d209f42fe52b5f830596f99Chih-Chung Chang    @TargetApi(ApiHelper.VERSION_CODES.JELLY_BEAN)
380fc86994f86f8cfb31e151c9e730dc1e9dc7b3349Yuli Huang    private void setNfcBeamPushUris(Uri[] uris) {
3816772173d2a49b87a1d209f42fe52b5f830596f99Chih-Chung Chang        if (mNfcAdapter != null && ApiHelper.HAS_SET_BEAM_PUSH_URIS) {
382fc86994f86f8cfb31e151c9e730dc1e9dc7b3349Yuli Huang            mNfcAdapter.setBeamPushUris(uris, (Activity)mActivity);
383fc86994f86f8cfb31e151c9e730dc1e9dc7b3349Yuli Huang        }
384fc86994f86f8cfb31e151c9e730dc1e9dc7b3349Yuli Huang    }
385fc86994f86f8cfb31e151c9e730dc1e9dc7b3349Yuli Huang
386fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li    private Intent createShareIntent(Path path) {
387fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li        DataManager manager = mActivity.getDataManager();
388fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li        int type = manager.getMediaType(path);
389fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li        Intent intent = new Intent(Intent.ACTION_SEND);
390fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li        intent.setType(MenuExecutor.getMimeType(type));
3912bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin        Uri uri = manager.getContentUri(path);
392fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li        intent.putExtra(Intent.EXTRA_STREAM, uri);
393fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li        return intent;
394fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li
395fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li    }
396fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li
3972bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin    private void updateShareURI(Path path) {
3982bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin        if (mActionBar.hasShareMenuItem()) {
3992bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin            DataManager manager = mActivity.getDataManager();
4002bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin            Uri uri = manager.getContentUri(path);
4012bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin            mActionBar.setShareIntent(createShareIntent(path));
4022bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin            setNfcBeamPushUris(new Uri[]{uri});
4032bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin            mPendingSharePath = null;
4042bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin        } else {
4052bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin            // This happens when ActionBar is not created yet.
4062bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin            mPendingSharePath = path;
407cf46a3abc26aac7cdb6b6993aeade053304b71d9Ray Chen        }
408cf46a3abc26aac7cdb6b6993aeade053304b71d9Ray Chen    }
409cf46a3abc26aac7cdb6b6993aeade053304b71d9Ray Chen
410f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private void updateCurrentPhoto(MediaItem photo) {
411f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (mCurrentPhoto == photo) return;
412f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mCurrentPhoto = photo;
413f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (mCurrentPhoto == null) return;
414f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        updateMenuOperations();
415ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang        updateTitle();
416f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (mShowDetails) {
417995c4566bed7df1aa48ba7e1351f964efa73880bMichael Kolb            mDetailsHelper.reloadDetails();
418f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
41915b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang        if ((photo.getSupportedOperations() & MediaItem.SUPPORT_SHARE) != 0) {
42015b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang            updateShareURI(photo.getPath());
42115b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang        }
422f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
423f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
424ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang    private void updateTitle() {
425ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang        if (mCurrentPhoto == null) return;
426ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang        boolean showTitle = mActivity.getAndroidContext().getResources().getBoolean(
427ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang                R.bool.show_action_bar_title);
4282bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin        if (showTitle && mCurrentPhoto.getName() != null) {
429ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang            mActionBar.setTitle(mCurrentPhoto.getName());
4302bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin        } else {
431ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang            mActionBar.setTitle("");
4322bb717f1ea38e2ce33dd102a23afe6bfacb5675cOwen Lin        }
433ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang    }
434ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang
435f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private void updateMenuOperations() {
436b21b8e58a604f6c701245d84b141b5b87663192bOwen Lin        MenuItem item = mActionBar.findMenuItem(R.id.action_slideshow);
437b21b8e58a604f6c701245d84b141b5b87663192bOwen Lin        item.setVisible(canDoSlideShow());
4382066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang        if (mCurrentPhoto == null) return;
439f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        int supportedOperations = mCurrentPhoto.getSupportedOperations();
440f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (!GalleryUtils.isEditorAvailable((Context) mActivity, "image/*")) {
441f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            supportedOperations &= ~MediaObject.SUPPORT_EDIT;
442f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
443b21b8e58a604f6c701245d84b141b5b87663192bOwen Lin        MenuExecutor.updateMenuOperation(mActionBar.getMenu(), supportedOperations);
444f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
445f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
4462066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang    private boolean canDoSlideShow() {
4472066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang        if (mMediaSet == null || mCurrentPhoto == null) {
4482066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang            return false;
4492066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang        }
4502066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang        if (mCurrentPhoto.getMediaType() != MediaObject.MEDIA_TYPE_IMAGE) {
4512066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang            return false;
4522066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang        }
4536b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        if (MtpSource.isMtpPath(mOriginalSetPathString)) {
4542066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang            return false;
4552066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang        }
4562066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang        return true;
4572066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang    }
4582066200f8fd0a2ed5b97e53115eb5de6b56320e1Chih-Chung Chang
45961f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    //////////////////////////////////////////////////////////////////////////
46061f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    //  Action Bar show/hide management
46161f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    //////////////////////////////////////////////////////////////////////////
46261f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang
463f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private void showBars() {
464f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (mShowBars) return;
465f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mShowBars = true;
466e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang        mOrientationManager.unlockOrientation();
467f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mActionBar.show();
4680b2486cff0c1b951c54325596256b986307f7f3aChih-Chung Chang        mActivity.getGLRoot().setLightsOutMode(false);
46961f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang        refreshHidingMessage();
470f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
471f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
472f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private void hideBars() {
473f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (!mShowBars) return;
474f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mShowBars = false;
475f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mActionBar.hide();
4760b2486cff0c1b951c54325596256b986307f7f3aChih-Chung Chang        mActivity.getGLRoot().setLightsOutMode(true);
47761f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang        mHandler.removeMessages(MSG_HIDE_BARS);
478f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
479f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
480f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private void refreshHidingMessage() {
481f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mHandler.removeMessages(MSG_HIDE_BARS);
48261f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang        if (!mIsMenuVisible) {
483f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            mHandler.sendEmptyMessageDelayed(MSG_HIDE_BARS, HIDE_BARS_TIMEOUT);
484f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
485f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
486f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
487aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang    private boolean canShowBars() {
488aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang        // No bars if we are showing camera preview.
489aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang        if (mAppBridge != null && mCurrentIndex == 0) return false;
490aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang        // No bars if it's not allowed.
491aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang        if (!mActionBarAllowed) return false;
492aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang
493aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang        return true;
494aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang    }
495aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang
496e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang    private void wantBars() {
497e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang        if (canShowBars()) showBars();
498e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang    }
499e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang
50061f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    private void toggleBars() {
501f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (mShowBars) {
502f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            hideBars();
503aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang        } else {
504e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang            if (canShowBars()) showBars();
505f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
506f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
507f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
50861f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    private void updateBars() {
509e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang        if (!canShowBars()) {
51061f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang            hideBars();
51161f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang        }
512f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
513f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
514f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    @Override
5152ef46ed28b28b355d7f3f1432c7b1196b832a859Chih-Chung Chang    public void onOrientationCompensationChanged() {
5162ef46ed28b28b355d7f3f1432c7b1196b832a859Chih-Chung Chang        mActivity.getGLRoot().requestLayoutContentPane();
517bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    }
518bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang
519bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    @Override
520f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    protected void onBackPressed() {
521f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (mShowDetails) {
522f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            hideDetails();
5233b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang        } else if (mAppBridge == null || !switchWithCaptureAnimation(-1)) {
524bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            // We are leaving this page. Set the result now.
525bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            setResult();
52654fe6202b6f7d233e7645c121321fe0f3d20fc8bYuli Huang            if (mTreatBackAsUp) {
52754fe6202b6f7d233e7645c121321fe0f3d20fc8bYuli Huang                onUpPressed();
52854fe6202b6f7d233e7645c121321fe0f3d20fc8bYuli Huang            } else {
52954fe6202b6f7d233e7645c121321fe0f3d20fc8bYuli Huang                super.onBackPressed();
53054fe6202b6f7d233e7645c121321fe0f3d20fc8bYuli Huang            }
531f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
532f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
533f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
534b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang    private void onUpPressed() {
535b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang        if (mActivity.getStateManager().getStateCount() > 1) {
536b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang            super.onBackPressed();
537ba12eae90b5b1a80ee002aa0df8c5c5189c4faa3Chih-Chung Chang            return;
53866ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang        }
53966ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang
54066ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang        if (mOriginalSetPathString == null) return;
54166ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang
54266ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang        if (mAppBridge == null) {
543b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang            // We're in view mode so set up the stacks on our own.
544b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang            Bundle data = new Bundle(getData());
545b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang            data.putString(AlbumPage.KEY_MEDIA_PATH, mOriginalSetPathString);
546b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang            data.putString(AlbumPage.KEY_PARENT_MEDIA_PATH,
547b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang                    mActivity.getDataManager().getTopSetPath(
548b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang                            DataManager.INCLUDE_ALL));
549b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang            mActivity.getStateManager().switchState(this, AlbumPage.class, data);
55066ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang        } else {
55166ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang            // Start the real gallery activity to view the camera roll.
55266ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang            Uri uri = Uri.parse("content://media/external/file?bucketId="
55366ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang                    + MediaSetUtils.CAMERA_BUCKET_ID);
55466ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang            Intent intent = new Intent(Intent.ACTION_VIEW);
55566ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang            intent.setDataAndType(uri, ContentResolver.CURSOR_DIR_BASE_TYPE + "/image");
55666ca848b2f58b813d366642088d274a1b7c4a90cChih-Chung Chang            ((Activity) mActivity).startActivity(intent);
557b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang        }
558b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang    }
559b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang
560bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    private void setResult() {
561bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        Intent result = null;
562bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        if (!mPhotoView.getFilmMode()) {
563bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            result = new Intent();
564bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            result.putExtra(KEY_RETURN_INDEX_HINT, mCurrentIndex);
565bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        }
566bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        setStateResult(Activity.RESULT_OK, result);
567bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    }
568bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang
569bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    //////////////////////////////////////////////////////////////////////////
570bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    //  AppBridge.Server interface
571bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    //////////////////////////////////////////////////////////////////////////
572bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang
573bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    @Override
5742ef46ed28b28b355d7f3f1432c7b1196b832a859Chih-Chung Chang    public void setCameraRelativeFrame(Rect frame) {
5752ef46ed28b28b355d7f3f1432c7b1196b832a859Chih-Chung Chang        mPhotoView.setCameraRelativeFrame(frame);
576bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    }
577bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang
578bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    @Override
5792c6173822a612597c79be41b126367ddfbb5d518Chih-Chung Chang    public boolean switchWithCaptureAnimation(int offset) {
5802c6173822a612597c79be41b126367ddfbb5d518Chih-Chung Chang        return mPhotoView.switchWithCaptureAnimation(offset);
5812c6173822a612597c79be41b126367ddfbb5d518Chih-Chung Chang    }
5822c6173822a612597c79be41b126367ddfbb5d518Chih-Chung Chang
583f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    @Override
5846575794a9c09f22d5721e212c093e0a2df376d0cChih-Chung Chang    public void setSwipingEnabled(boolean enabled) {
5856575794a9c09f22d5721e212c093e0a2df376d0cChih-Chung Chang        mPhotoView.setSwipingEnabled(enabled);
5866575794a9c09f22d5721e212c093e0a2df376d0cChih-Chung Chang    }
5876575794a9c09f22d5721e212c093e0a2df376d0cChih-Chung Chang
5886575794a9c09f22d5721e212c093e0a2df376d0cChih-Chung Chang    @Override
5893b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang    public void notifyScreenNailChanged() {
5903b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang        mScreenNailItem.setScreenNail(mAppBridge.attachScreenNail());
5913b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang        mScreenNailSet.notifyChange();
5923b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang    }
5933b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang
5943b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang    @Override
595a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li    public void addSecureAlbumItem(boolean isVideo, int id) {
596a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li        mSecureAlbum.addMediaItem(isVideo, id);
597a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li    }
598a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li
599a0ce682e40c39ce046c48d8a7f989fff01bb9f2cWu-cheng Li    @Override
600f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    protected boolean onCreateActionBar(Menu menu) {
601b21b8e58a604f6c701245d84b141b5b87663192bOwen Lin        mActionBar.createActionBarMenu(R.menu.photo, menu);
602cf46a3abc26aac7cdb6b6993aeade053304b71d9Ray Chen        if (mPendingSharePath != null) updateShareURI(mPendingSharePath);
603f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        updateMenuOperations();
604ed46d77c16cd80357f4a0feada2435dfba8104a6Yuli Huang        updateTitle();
605b21b8e58a604f6c701245d84b141b5b87663192bOwen Lin        return true;
606f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
607f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
608d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin    private MenuExecutor.ProgressListener mConfirmDialogListener =
609d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin            new MenuExecutor.ProgressListener() {
610d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        @Override
611d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        public void onProgressUpdate(int index) {}
612d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin
613d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        @Override
614d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        public void onProgressComplete(int result) {}
615d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin
616d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        @Override
617d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        public void onConfirmDialogShown() {
618d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin            mHandler.removeMessages(MSG_HIDE_BARS);
619d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        }
620d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin
621d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        @Override
622d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        public void onConfirmDialogDismissed(boolean confirmed) {
623d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin            refreshHidingMessage();
624d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        }
625ba50b9420e64731fd5aa8b1410e1f36457a1635aBobby Georgescu
626ba50b9420e64731fd5aa8b1410e1f36457a1635aBobby Georgescu        @Override
627ba50b9420e64731fd5aa8b1410e1f36457a1635aBobby Georgescu        public void onProgressStart() {}
628d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin    };
629d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin
630f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    @Override
631f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    protected boolean onItemSelected(MenuItem item) {
632d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        refreshHidingMessage();
633616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        MediaItem current = mModel.getMediaItem(0);
634f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
635f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (current == null) {
636f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            // item is not ready, ignore
637f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            return true;
638f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
639f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
640f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        int currentIndex = mModel.getCurrentIndex();
641f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        Path path = current.getPath();
642f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
643f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        DataManager manager = mActivity.getDataManager();
644f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        int action = item.getItemId();
6459a033b07b8e0d9fe7419b7a0d876e9c7febf43c8Ray Chen        String confirmMsg = null;
646f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        switch (action) {
64784c220f10a643927c8a2126de8a755d8d7f7ec9eRay Chen            case android.R.id.home: {
648b1e9fd893d62adae1f92d29dfc08bc76f8764491Chih-Chung Chang                onUpPressed();
64984c220f10a643927c8a2126de8a755d8d7f7ec9eRay Chen                return true;
65084c220f10a643927c8a2126de8a755d8d7f7ec9eRay Chen            }
651f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case R.id.action_slideshow: {
652f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                Bundle data = new Bundle();
6536cf807453fb58ccd4cc513ff187b306c7090e67cOwen Lin                data.putString(SlideshowPage.KEY_SET_PATH, mMediaSet.getPath().toString());
654604f053d040782159b61d3b74ee533bc2c0ccdd0Ray Chen                data.putString(SlideshowPage.KEY_ITEM_PATH, path.toString());
655f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                data.putInt(SlideshowPage.KEY_PHOTO_INDEX, currentIndex);
656f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                data.putBoolean(SlideshowPage.KEY_REPEAT, true);
657f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                mActivity.getStateManager().startStateForResult(
658f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                        SlideshowPage.class, REQUEST_SLIDESHOW, data);
659f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                return true;
660f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            }
661f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case R.id.action_crop: {
662f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                Activity activity = (Activity) mActivity;
663f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                Intent intent = new Intent(CropImage.CROP_ACTION);
664f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                intent.setClass(activity, CropImage.class);
665f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                intent.setData(manager.getContentUri(path));
666f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                activity.startActivityForResult(intent, PicasaSource.isPicasaImage(current)
667f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                        ? REQUEST_CROP_PICASA
668f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                        : REQUEST_CROP);
669f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                return true;
670f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            }
67150ea2d2938218ac6b2039f0e42998cfbbc45d1f1Teng-Hui Zhu            case R.id.action_trim: {
67250ea2d2938218ac6b2039f0e42998cfbbc45d1f1Teng-Hui Zhu                // TODO: Add trimming activity here.
67350ea2d2938218ac6b2039f0e42998cfbbc45d1f1Teng-Hui Zhu                return true;
67450ea2d2938218ac6b2039f0e42998cfbbc45d1f1Teng-Hui Zhu            }
675f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang            case R.id.action_edit: {
676f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                Intent intent = new Intent(Intent.ACTION_EDIT)
677f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                        .setData(manager.getContentUri(path))
678f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                        .setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
679f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                ((Activity) mActivity).startActivityForResult(Intent.createChooser(intent, null),
680f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                        REQUEST_EDIT);
681f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                return true;
682f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang            }
683f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case R.id.action_details: {
684f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                if (mShowDetails) {
685f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    hideDetails();
686f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                } else {
687995c4566bed7df1aa48ba7e1351f964efa73880bMichael Kolb                    showDetails();
688f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                }
689f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                return true;
690f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            }
69167098d1a72fd04e2af06d3a5939cde28c65f70d9Ray Chen            case R.id.action_delete:
6929a033b07b8e0d9fe7419b7a0d876e9c7febf43c8Ray Chen                confirmMsg = mActivity.getResources().getQuantityString(
6939a033b07b8e0d9fe7419b7a0d876e9c7febf43c8Ray Chen                        R.plurals.delete_selection, 1);
694f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case R.id.action_setas:
695f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case R.id.action_rotate_ccw:
696f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case R.id.action_rotate_cw:
697f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case R.id.action_show_on_map:
698f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                mSelectionManager.deSelectAll();
699f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                mSelectionManager.toggle(path);
700d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin                mMenuExecutor.onMenuClicked(item, confirmMsg, mConfirmDialogListener);
701f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                return true;
702f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case R.id.action_import:
703f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                mSelectionManager.deSelectAll();
704f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                mSelectionManager.toggle(path);
7059a033b07b8e0d9fe7419b7a0d876e9c7febf43c8Ray Chen                mMenuExecutor.onMenuClicked(item, confirmMsg,
706f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                        new ImportCompleteListener(mActivity));
707f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                return true;
708fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li            case R.id.action_share:
709fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li                Activity activity = (Activity) mActivity;
710fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li                Intent intent = createShareIntent(mCurrentPhoto.getPath());
711fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li                activity.startActivity(Intent.createChooser(intent,
712fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li                        activity.getString(R.string.share)));
713fb5571987f2555b04731b6f3e1c479efc16d542aWu-cheng Li                return true;
714f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            default :
715f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                return false;
716f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
717f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
718f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
719f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private void hideDetails() {
720f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mShowDetails = false;
7214105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chen        mDetailsHelper.hide();
722f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
723f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
724995c4566bed7df1aa48ba7e1351f964efa73880bMichael Kolb    private void showDetails() {
725f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mShowDetails = true;
7264105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chen        if (mDetailsHelper == null) {
7274105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chen            mDetailsHelper = new DetailsHelper(mActivity, mRootPane, new MyDetailsSource());
7284105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chen            mDetailsHelper.setCloseListener(new CloseListener() {
72906c6401eededc2ec842ba4994a838c2ded0a666cPin Ting                @Override
730f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                public void onClose() {
731f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    hideDetails();
732f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                }
733f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            });
734f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
7354105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chen        mDetailsHelper.show();
736f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
737f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
738bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    ////////////////////////////////////////////////////////////////////////////
739bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    //  Callbacks from PhotoView
740bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    ////////////////////////////////////////////////////////////////////////////
741bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    @Override
742f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    public void onSingleTapUp(int x, int y) {
743bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        if (mAppBridge != null) {
744bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            if (mAppBridge.onSingleTapUp(x, y)) return;
745014d9586d8145a33f4e99eaad570587f6d650026Wu-cheng Li        }
746014d9586d8145a33f4e99eaad570587f6d650026Wu-cheng Li
747616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        MediaItem item = mModel.getMediaItem(0);
748b5dc542fbaeaf99bebdcf775ef0e034e89e88eaeWu-cheng Li        if (item == null || item == mScreenNailItem) {
749b5dc542fbaeaf99bebdcf775ef0e034e89e88eaeWu-cheng Li            // item is not ready or it is camera preview, ignore
750f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            return;
751f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
752f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
753f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        boolean playVideo =
754f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                (item.getSupportedOperations() & MediaItem.SUPPORT_PLAY) != 0;
755f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
756f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (playVideo) {
757f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            // determine if the point is at center (1/6) of the photo view.
758f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            // (The position of the "play" icon is at center (1/6) of the photo)
759f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            int w = mPhotoView.getWidth();
760f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            int h = mPhotoView.getHeight();
761f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            playVideo = (Math.abs(x - w / 2) * 12 <= w)
762f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                && (Math.abs(y - h / 2) * 12 <= h);
763f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
764f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
765f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        if (playVideo) {
766f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            playVideo((Activity) mActivity, item.getPlayUri(), item.getName());
767f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        } else {
76861f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang            toggleBars();
769f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
770f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
771f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
772bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    @Override
773bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    public void lockOrientation() {
774bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        mHandler.sendEmptyMessage(MSG_LOCK_ORIENTATION);
775bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    }
776bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang
777bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    @Override
778bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    public void unlockOrientation() {
77906c6401eededc2ec842ba4994a838c2ded0a666cPin Ting        mHandler.sendEmptyMessage(MSG_UNLOCK_ORIENTATION);
780bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    }
781bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang
782bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    @Override
78361f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    public void onActionBarAllowed(boolean allowed) {
78461f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang        mActionBarAllowed = allowed;
78561f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang        mHandler.sendEmptyMessage(MSG_UPDATE_ACTION_BAR);
78661f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    }
78761f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang
78861f94714c3702115d2f89bb5f8829697be0c3680Chih-Chung Chang    @Override
789e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang    public void onActionBarWanted() {
790e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang        mHandler.sendEmptyMessage(MSG_WANT_BARS);
791e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang    }
792e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang
793e6251df06f0b3c8f556043f8b725b4b19be7474dChih-Chung Chang    @Override
794bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    public void onFullScreenChanged(boolean full) {
795bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        Message m = mHandler.obtainMessage(
796bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang                MSG_ON_FULL_SCREEN_CHANGED, full ? 1 : 0, 0);
797bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        m.sendToTarget();
798bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang    }
799bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang
8006b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    // How we do delete/undo:
8016b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    //
8026b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    // When the user choose to delete a media item, we just tell the
8036b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    // FilterDeleteSet to hide that item. If the user choose to undo it, we
8046b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    // again tell FilterDeleteSet not to hide it. If the user choose to commit
8056b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    // the deletion, we then actually delete the media item.
8066b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    @Override
8076b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    public void onDeleteImage(Path path, int offset) {
8086118af9ddad8acc050133154f8f60c842c7f9bfaChih-Chung Chang        onCommitDeleteImage();  // commit the previous deletion
8096b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        mDeletePath = path;
8106b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        mDeleteIsFocus = (offset == 0);
8116118af9ddad8acc050133154f8f60c842c7f9bfaChih-Chung Chang        mMediaSet.addDeletion(path, mCurrentIndex + offset);
8126b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    }
8136b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang
8146b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    @Override
8156b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    public void onUndoDeleteImage() {
8166118af9ddad8acc050133154f8f60c842c7f9bfaChih-Chung Chang        if (mDeletePath == null) return;
8176b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        // If the deletion was done on the focused item, we want the model to
8186b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        // focus on it when it is undeleted.
8196b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        if (mDeleteIsFocus) mModel.setFocusHintPath(mDeletePath);
8206118af9ddad8acc050133154f8f60c842c7f9bfaChih-Chung Chang        mMediaSet.removeDeletion(mDeletePath);
8216b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        mDeletePath = null;
8226b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    }
8236b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang
8246b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    @Override
8256b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    public void onCommitDeleteImage() {
8266b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        if (mDeletePath == null) return;
8276b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        mSelectionManager.deSelectAll();
8286b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        mSelectionManager.toggle(mDeletePath);
8296b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        mMenuExecutor.onMenuClicked(R.id.action_delete, null, true, false);
8306b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        mDeletePath = null;
8316b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang    }
8326b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang
833f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    public static void playVideo(Activity activity, Uri uri, String title) {
834f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        try {
835f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            Intent intent = new Intent(Intent.ACTION_VIEW)
836a3871050845b4921379add2b126add3cfbab1109Ray Chen                    .setDataAndType(uri, "video/*")
837a3871050845b4921379add2b126add3cfbab1109Ray Chen                    .putExtra(Intent.EXTRA_TITLE, title)
838a3871050845b4921379add2b126add3cfbab1109Ray Chen                    .putExtra(MovieActivity.KEY_TREAT_UP_AS_BACK, true);
83971cd89a38752bc22ae0ec2df965e4280b776623cChih-Chung Chang            activity.startActivityForResult(intent, REQUEST_PLAY_VIDEO);
840f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        } catch (ActivityNotFoundException e) {
841f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            Toast.makeText(activity, activity.getString(R.string.video_err),
842f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    Toast.LENGTH_SHORT).show();
843f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
844f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
845f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
846f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang    private void setCurrentPhotoByIntent(Intent intent) {
847f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang        if (intent == null) return;
848f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang        Path path = mApplication.getDataManager()
849f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                .findPathByUri(intent.getData(), intent.getType());
850f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang        if (path != null) {
851f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang            mModel.setCurrentPhoto(path, mCurrentIndex);
852f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang        }
853f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang    }
854f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang
855f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    @Override
856f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    protected void onStateResult(int requestCode, int resultCode, Intent data) {
85771cd89a38752bc22ae0ec2df965e4280b776623cChih-Chung Chang        mHasActivityResult = true;
858f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        switch (requestCode) {
859f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang            case REQUEST_EDIT:
860f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                setCurrentPhotoByIntent(data);
861f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                break;
862f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case REQUEST_CROP:
863f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                if (resultCode == Activity.RESULT_OK) {
864f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                    setCurrentPhotoByIntent(data);
865f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                }
866f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                break;
867f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case REQUEST_CROP_PICASA: {
868f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                if (resultCode == Activity.RESULT_OK) {
869f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                    Context context = mActivity.getAndroidContext();
87088cc2ca5f5596762a5546ec7426756f2036be455Yuli Huang                    String message = context.getString(R.string.crop_saved,
871f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                            context.getString(R.string.folder_download));
872f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                    Toast.makeText(context, message, Toast.LENGTH_SHORT).show();
873f50ce2b708c0c70930a346206fdd526f53ae6004Yuli Huang                }
874f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                break;
875f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            }
876f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            case REQUEST_SLIDESHOW: {
877f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                if (data == null) break;
878f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                String path = data.getStringExtra(SlideshowPage.KEY_ITEM_PATH);
879f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                int index = data.getIntExtra(SlideshowPage.KEY_PHOTO_INDEX, 0);
880f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                if (path != null) {
881f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                    mModel.setCurrentPhoto(Path.fromString(path), index);
882f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin                }
883f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            }
884f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
885f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
886f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
88714d3289b4867c21da93ec4032119c0091bc78c30George Mount    @Override
88814d3289b4867c21da93ec4032119c0091bc78c30George Mount    protected void clearStateResult() {
88914d3289b4867c21da93ec4032119c0091bc78c30George Mount        mHasActivityResult = false;
89014d3289b4867c21da93ec4032119c0091bc78c30George Mount    }
89114d3289b4867c21da93ec4032119c0091bc78c30George Mount
892616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin    private class PreparePhotoFallback implements OnGLIdleListener {
893616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        private PhotoFallbackEffect mPhotoFallback = new PhotoFallbackEffect();
894616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        private boolean mResultReady = false;
895616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin
896616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        public synchronized PhotoFallbackEffect get() {
897616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            while (!mResultReady) {
898616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin                Utils.waitWithoutInterrupt(this);
899616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            }
900616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            return mPhotoFallback;
901616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        }
902616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin
903616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        @Override
904616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        public boolean onGLIdle(GLCanvas canvas, boolean renderRequested) {
905616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            mPhotoFallback = mPhotoView.buildFallbackEffect(mRootPane, canvas);
906616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            synchronized (this) {
907616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin                mResultReady = true;
908616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin                notifyAll();
909616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            }
910616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            return false;
911616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        }
912616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin    }
913616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin
914616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin    private void preparePhotoFallbackView() {
915616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        GLRoot root = mActivity.getGLRoot();
916616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        PreparePhotoFallback task = new PreparePhotoFallback();
917616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        root.unlockRenderThread();
918616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        PhotoFallbackEffect anim;
919616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        try {
920616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            root.addOnGLIdleListener(task);
921616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            anim = task.get();
922616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        } finally {
923616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            root.lockRenderThread();
924616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        }
925616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        mActivity.getTransitionStore().put(
926616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin                AlbumPage.KEY_RESUME_ANIMATION, anim);
927616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin    }
928616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin
929f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    @Override
930f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    public void onPause() {
931d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        super.onPause();
932d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        mIsActive = false;
933d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin
934bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang        mActivity.getGLRoot().unfreeze();
935bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang        mHandler.removeMessages(MSG_UNFREEZE_GLROOT);
936616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin        if (isFinishing()) preparePhotoFallbackView();
937253c5aec7692afdd7880fbd169d4b44d5679cbc0Chih-Chung Chang
9384105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chen        DetailsHelper.pause();
939f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mPhotoView.pause();
940f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mModel.pause();
941f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mHandler.removeMessages(MSG_HIDE_BARS);
942f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mActionBar.removeOnMenuVisibilityListener(mMenuVisibilityListener);
94333ef03776b7734717b16f6fc861b831fb1b1dfacMartijn Coenen
9446b891c6a3739f8c49d42f9db6fc76cb92c7c5f25Chih-Chung Chang        onCommitDeleteImage();
9452785956f8f5654966a41e20f482f4af3057eea3fChih-Chung Chang        mMenuExecutor.pause();
9466118af9ddad8acc050133154f8f60c842c7f9bfaChih-Chung Chang        if (mMediaSet != null) mMediaSet.clearDeletion();
947f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
948f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
949f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    @Override
950bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang    public void onCurrentImageUpdated() {
951bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang        mActivity.getGLRoot().unfreeze();
952bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang    }
953bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang
954bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang    @Override
955f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    protected void onResume() {
956f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        super.onResume();
957d759b7c1fc449f4f0ef91997738bbef1bbd96677Owen Lin        mActivity.getGLRoot().freeze();
958f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mIsActive = true;
959f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        setContentPane(mRootPane);
96004ac045bf8da5082bbb0bdc9ea5f9c9b5b796ad0Yuli Huang
961f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mModel.resume();
962f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mPhotoView.resume();
9638cab3e872dd95e55ba34fdb94269a0c5069e72aeRay Chen        mActionBar.setDisplayOptions(mSetPathString != null, true);
964f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        mActionBar.addOnMenuVisibilityListener(mMenuVisibilityListener);
96533ef03776b7734717b16f6fc861b831fb1b1dfacMartijn Coenen
96671cd89a38752bc22ae0ec2df965e4280b776623cChih-Chung Chang        if (mAppBridge != null && !mHasActivityResult) {
96733f8567dd5003e4bb342683f3768ab7552648b02Chih-Chung Chang            mPhotoView.resetToFirstPicture();
968bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        }
96971cd89a38752bc22ae0ec2df965e4280b776623cChih-Chung Chang        mHasActivityResult = false;
970bd7c016d728853d38f98a3c6077b7bd9b08858b9Yuli Huang        mHandler.sendEmptyMessageDelayed(MSG_UNFREEZE_GLROOT, UNFREEZE_GLROOT_TIMEOUT);
971f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
972f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin
97315b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang    @Override
97415b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang    protected void onDestroy() {
975bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        if (mAppBridge != null) {
976253c5aec7692afdd7880fbd169d4b44d5679cbc0Chih-Chung Chang            mAppBridge.setServer(null);
9773b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang            mScreenNailItem.setScreenNail(null);
978bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            mAppBridge.detachScreenNail();
979bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang            mAppBridge = null;
9803b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang            mScreenNailSet = null;
9813b4a8aeb0353fa18a2b5267b3952a80a6c6d4d13Chih-Chung Chang            mScreenNailItem = null;
982b29a27f475a2c449abdda8d4e03d30914feed8c6Chih-Chung Chang        }
983bd141b5a51c96f6fcaddfa547f0928ce69cf0755Chih-Chung Chang        mOrientationManager.removeListener(this);
9842ef46ed28b28b355d7f3f1432c7b1196b832a859Chih-Chung Chang        mActivity.getGLRoot().setOrientationSource(null);
985aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang
986aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang        // Remove all pending messages.
987aeb3062e84ed28f0e25a73f511f287ae0a3e4294Chih-Chung Chang        mHandler.removeCallbacksAndMessages(null);
98815b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang        super.onDestroy();
98915b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang    }
99015b351a22d02e89d882fc9fe32b3f4c512080e0aChih-Chung Chang
991f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    private class MyDetailsSource implements DetailsSource {
9926cf807453fb58ccd4cc513ff187b306c7090e67cOwen Lin
9936cf807453fb58ccd4cc513ff187b306c7090e67cOwen Lin        @Override
994f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        public MediaDetails getDetails() {
995616a70fdb4473d2fbd7b70772a3a82b908aeae1eOwen Lin            return mModel.getMediaItem(0).getDetails();
996f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
9976cf807453fb58ccd4cc513ff187b306c7090e67cOwen Lin
9986cf807453fb58ccd4cc513ff187b306c7090e67cOwen Lin        @Override
999f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        public int size() {
1000f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin            return mMediaSet != null ? mMediaSet.getMediaItemCount() : 1;
1001f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin        }
10026cf807453fb58ccd4cc513ff187b306c7090e67cOwen Lin
10036cf807453fb58ccd4cc513ff187b306c7090e67cOwen Lin        @Override
1004995c4566bed7df1aa48ba7e1351f964efa73880bMichael Kolb        public int setIndex() {
1005995c4566bed7df1aa48ba7e1351f964efa73880bMichael Kolb            return mModel.getCurrentIndex();
10064105e22d72d7a44e67cba4a58ad88018ed664d10Ray Chen        }
1007f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin    }
1008f9a0a4306d589b4a4e20554fed512a603426bfa1Owen Lin}
1009