• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2018 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.launcher3;
18 
19 import static com.android.launcher3.util.DisplayController.CHANGE_ROTATION;
20 
21 import android.content.Context;
22 import android.content.res.Configuration;
23 import android.graphics.Point;
24 import android.graphics.Rect;
25 import android.os.Bundle;
26 import android.view.ActionMode;
27 import android.view.Display;
28 import android.view.View;
29 
30 import androidx.annotation.MainThread;
31 import androidx.annotation.NonNull;
32 import androidx.annotation.Nullable;
33 
34 import com.android.launcher3.model.data.ItemInfo;
35 import com.android.launcher3.touch.ItemClickHandler;
36 import com.android.launcher3.util.ActivityOptionsWrapper;
37 import com.android.launcher3.util.DisplayController;
38 import com.android.launcher3.util.DisplayController.DisplayInfoChangeListener;
39 import com.android.launcher3.util.DisplayController.Info;
40 import com.android.launcher3.util.OnColorHintListener;
41 import com.android.launcher3.util.RunnableList;
42 import com.android.launcher3.util.Themes;
43 import com.android.launcher3.util.TraceHelper;
44 import com.android.launcher3.util.WallpaperColorHints;
45 import com.android.launcher3.util.WindowBounds;
46 
47 /**
48  * Extension of BaseActivity allowing support for drag-n-drop
49  */
50 @SuppressWarnings("NewApi")
51 public abstract class BaseDraggingActivity extends BaseActivity
52         implements OnColorHintListener, DisplayInfoChangeListener {
53 
54     private static final String TAG = "BaseDraggingActivity";
55 
56     // When starting an action mode, setting this tag will cause the action mode to be cancelled
57     // automatically when user interacts with the launcher.
58     public static final Object AUTO_CANCEL_ACTION_MODE = new Object();
59 
60     private ActionMode mCurrentActionMode;
61     protected boolean mIsSafeModeEnabled;
62 
63     private Runnable mOnStartCallback;
64     private final RunnableList mOnResumeCallbacks = new RunnableList();
65     private int mThemeRes = R.style.AppTheme;
66 
67     @Override
onCreate(Bundle savedInstanceState)68     protected void onCreate(Bundle savedInstanceState) {
69         super.onCreate(savedInstanceState);
70 
71         mIsSafeModeEnabled = TraceHelper.allowIpcs("isSafeMode",
72                 () -> getPackageManager().isSafeMode());
73         DisplayController.INSTANCE.get(this).addChangeListener(this);
74 
75         // Update theme
76         WallpaperColorHints.get(this).registerOnColorHintsChangedListener(this);
77         int themeRes = Themes.getActivityThemeRes(this);
78         if (themeRes != mThemeRes) {
79             mThemeRes = themeRes;
80             setTheme(themeRes);
81         }
82     }
83 
84     @Override
onResume()85     protected void onResume() {
86         super.onResume();
87         mOnResumeCallbacks.executeAllAndClear();
88     }
89 
addOnResumeCallback(Runnable callback)90     public void addOnResumeCallback(Runnable callback) {
91         mOnResumeCallbacks.add(callback);
92     }
93 
94     @MainThread
95     @Override
onColorHintsChanged(int colorHints)96     public void onColorHintsChanged(int colorHints) {
97         updateTheme();
98     }
99 
100     @Override
onConfigurationChanged(Configuration newConfig)101     public void onConfigurationChanged(Configuration newConfig) {
102         super.onConfigurationChanged(newConfig);
103         updateTheme();
104     }
105 
updateTheme()106     private void updateTheme() {
107         if (mThemeRes != Themes.getActivityThemeRes(this)) {
108             recreate();
109         }
110     }
111 
112     @Override
onActionModeStarted(ActionMode mode)113     public void onActionModeStarted(ActionMode mode) {
114         super.onActionModeStarted(mode);
115         mCurrentActionMode = mode;
116     }
117 
118     @Override
onActionModeFinished(ActionMode mode)119     public void onActionModeFinished(ActionMode mode) {
120         super.onActionModeFinished(mode);
121         mCurrentActionMode = null;
122     }
123 
isInAutoCancelActionMode()124     protected boolean isInAutoCancelActionMode() {
125         return mCurrentActionMode != null && AUTO_CANCEL_ACTION_MODE == mCurrentActionMode.getTag();
126     }
127 
128     @Override
finishAutoCancelActionMode()129     public boolean finishAutoCancelActionMode() {
130         if (isInAutoCancelActionMode()) {
131             mCurrentActionMode.finish();
132             return true;
133         }
134         return false;
135     }
136 
getOverviewPanel()137     public abstract <T extends View> T getOverviewPanel();
138 
getRootView()139     public abstract View getRootView();
140 
returnToHomescreen()141     public void returnToHomescreen() {
142         // no-op
143     }
144 
145     @Override
146     @NonNull
getActivityLaunchOptions(View v, @Nullable ItemInfo item)147     public ActivityOptionsWrapper getActivityLaunchOptions(View v, @Nullable ItemInfo item) {
148         ActivityOptionsWrapper wrapper = super.getActivityLaunchOptions(v, item);
149         addOnResumeCallback(wrapper.onEndCallback::executeAllAndDestroy);
150         return wrapper;
151     }
152 
153     @Override
makeDefaultActivityOptions(int splashScreenStyle)154     public ActivityOptionsWrapper makeDefaultActivityOptions(int splashScreenStyle) {
155         ActivityOptionsWrapper wrapper = super.makeDefaultActivityOptions(splashScreenStyle);
156         addOnResumeCallback(wrapper.onEndCallback::executeAllAndDestroy);
157         return wrapper;
158     }
159 
160     @Override
onStart()161     protected void onStart() {
162         super.onStart();
163 
164         if (mOnStartCallback != null) {
165             mOnStartCallback.run();
166             mOnStartCallback = null;
167         }
168     }
169 
170     @Override
onDestroy()171     protected void onDestroy() {
172         super.onDestroy();
173         DisplayController.INSTANCE.get(this).removeChangeListener(this);
174         WallpaperColorHints.get(this).unregisterOnColorsChangedListener(this);
175     }
176 
runOnceOnStart(Runnable action)177     public void runOnceOnStart(Runnable action) {
178         mOnStartCallback = action;
179     }
180 
clearRunOnceOnStartCallback()181     public void clearRunOnceOnStartCallback() {
182         mOnStartCallback = null;
183     }
184 
onDeviceProfileInitiated()185     protected void onDeviceProfileInitiated() {
186         if (mDeviceProfile.isVerticalBarLayout()) {
187             mDeviceProfile.updateIsSeascape(this);
188         }
189     }
190 
191     @Override
onDisplayInfoChanged(Context context, Info info, int flags)192     public void onDisplayInfoChanged(Context context, Info info, int flags) {
193         if ((flags & CHANGE_ROTATION) != 0 && mDeviceProfile.updateIsSeascape(this)) {
194             reapplyUi();
195         }
196     }
197 
198     @Override
getItemOnClickListener()199     public View.OnClickListener getItemOnClickListener() {
200         return ItemClickHandler.INSTANCE;
201     }
202 
reapplyUi()203     protected abstract void reapplyUi();
204 
getMultiWindowDisplaySize()205     protected WindowBounds getMultiWindowDisplaySize() {
206         if (Utilities.ATLEAST_R) {
207             return WindowBounds.fromWindowMetrics(getWindowManager().getCurrentWindowMetrics());
208         }
209         // Note: Calls to getSize() can't rely on our cached DefaultDisplay since it can return
210         // the app window size
211         Display display = getWindowManager().getDefaultDisplay();
212         Point mwSize = new Point();
213         display.getSize(mwSize);
214         return new WindowBounds(new Rect(0, 0, mwSize.x, mwSize.y), new Rect());
215     }
216 
217     @Override
isAppBlockedForSafeMode()218     public boolean isAppBlockedForSafeMode() {
219         return mIsSafeModeEnabled;
220     }
221 }
222