From b1d7de25f855ddee8a2fde5823a1c5bfbb82177a Mon Sep 17 00:00:00 2001 From: Sunny Goyal Date: Fri, 6 Sep 2019 10:36:54 -0700 Subject: [PATCH] Adding support for overlay and corresponding plugin to Launcher Updating various task callbacks to handle overlays Change-Id: I80077508ad35c31269c873f51f0105302a9e6a5d --- .../LauncherActivityControllerHelper.java | 15 ++ .../quickstep/TouchInteractionService.java | 26 ++- .../WindowTransformSwipeHandler.java | 4 +- .../OtherActivityInputConsumer.java | 16 +- .../inputconsumers/OverviewInputConsumer.java | 11 +- .../OverviewWithoutFocusInputConsumer.java | 10 +- quickstep/res/values/config.xml | 2 - .../launcher3/LauncherInitListener.java | 3 +- .../quickstep/ActivityControlHelper.java | 2 + .../android/quickstep/OverviewCallbacks.java | 43 ---- .../launcher3/util/TestLauncherProvider.java | 4 - src/com/android/launcher3/Launcher.java | 203 +++++++++++------- .../android/launcher3/LauncherCallbacks.java | 24 --- .../android/launcher3/LauncherProvider.java | 16 -- .../LauncherProviderChangeListener.java | 2 - src/com/android/launcher3/Workspace.java | 5 +- .../systemui/plugins/OverlayPlugin.java | 34 +++ .../plugins/shared}/LauncherExterns.java | 25 ++- .../shared/LauncherOverlayManager.java | 98 +++++++++ 19 files changed, 335 insertions(+), 208 deletions(-) delete mode 100644 quickstep/src/com/android/quickstep/OverviewCallbacks.java create mode 100644 src_plugins/com/android/systemui/plugins/OverlayPlugin.java rename {src/com/android/launcher3 => src_plugins/com/android/systemui/plugins/shared}/LauncherExterns.java (63%) create mode 100644 src_plugins/com/android/systemui/plugins/shared/LauncherOverlayManager.java diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/LauncherActivityControllerHelper.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/LauncherActivityControllerHelper.java index 25cc33df01..f8f67e8e3d 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/LauncherActivityControllerHelper.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/LauncherActivityControllerHelper.java @@ -66,6 +66,7 @@ import com.android.quickstep.util.StaggeredWorkspaceAnim; import com.android.quickstep.views.LauncherRecentsView; import com.android.quickstep.views.RecentsView; import com.android.quickstep.views.TaskView; +import com.android.systemui.plugins.shared.LauncherOverlayManager; import com.android.systemui.shared.system.RemoteAnimationTargetCompat; import java.util.function.BiPredicate; @@ -479,4 +480,18 @@ public final class LauncherActivityControllerHelper implements ActivityControlHe public void onLaunchTaskSuccess(Launcher launcher) { launcher.getStateManager().moveToRestState(); } + + @Override + public void closeOverlay() { + Launcher launcher = getCreatedActivity(); + if (launcher == null) { + return; + } + LauncherOverlayManager om = launcher.getOverlayManager(); + if (!launcher.isStarted() || launcher.isForceInvisible()) { + om.hideOverlay(false /* animate */); + } else { + om.hideOverlay(150); + } + } } \ No newline at end of file diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/TouchInteractionService.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/TouchInteractionService.java index 729287c823..d7ed090d93 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/TouchInteractionService.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/TouchInteractionService.java @@ -65,10 +65,6 @@ import android.view.InputEvent; import android.view.MotionEvent; import android.view.Surface; -import androidx.annotation.BinderThread; -import androidx.annotation.UiThread; -import androidx.annotation.WorkerThread; - import com.android.launcher3.BaseDraggingActivity; import com.android.launcher3.R; import com.android.launcher3.ResourceUtils; @@ -110,6 +106,10 @@ import java.util.Arrays; import java.util.LinkedList; import java.util.List; +import androidx.annotation.BinderThread; +import androidx.annotation.UiThread; +import androidx.annotation.WorkerThread; + /** * Wrapper around a list for processing arguments. */ @@ -271,7 +271,6 @@ public class TouchInteractionService extends Service implements private OverviewCommandHelper mOverviewCommandHelper; private OverviewComponentObserver mOverviewComponentObserver; private OverviewInteractionState mOverviewInteractionState; - private OverviewCallbacks mOverviewCallbacks; private TaskOverlayFactory mTaskOverlayFactory; private InputConsumerController mInputConsumer; private boolean mAssistantAvailable; @@ -468,7 +467,6 @@ public class TouchInteractionService extends Service implements mOverviewCommandHelper = new OverviewCommandHelper(this, mOverviewComponentObserver); mOverviewInteractionState = OverviewInteractionState.INSTANCE.get(this); - mOverviewCallbacks = OverviewCallbacks.get(this); mTaskOverlayFactory = TaskOverlayFactory.INSTANCE.get(this); mInputConsumer = InputConsumerController.getRecentsAnimationInputConsumer(); mIsUserUnlocked = true; @@ -701,20 +699,20 @@ public class TouchInteractionService extends Service implements final boolean shouldDefer; final BaseSwipeUpHandler.Factory factory; + ActivityControlHelper activityControlHelper = + mOverviewComponentObserver.getActivityControlHelper(); if (mMode == Mode.NO_BUTTON && !mOverviewComponentObserver.isHomeAndOverviewSame()) { shouldDefer = !sSwipeSharedState.recentsAnimationFinishInterrupted; factory = mFallbackNoButtonFactory; } else { - shouldDefer = mOverviewComponentObserver.getActivityControlHelper() - .deferStartingActivity(mActiveNavBarRegion, event); + shouldDefer = activityControlHelper.deferStartingActivity(mActiveNavBarRegion, event); factory = mWindowTreansformFactory; } - return new OtherActivityInputConsumer(this, runningTaskInfo, - shouldDefer, mOverviewCallbacks, this::onConsumerInactive, - sSwipeSharedState, mInputMonitorCompat, mSwipeTouchRegion, - disableHorizontalSwipe(event), factory, mLogId); + return new OtherActivityInputConsumer(this, runningTaskInfo, shouldDefer, + this::onConsumerInactive, sSwipeSharedState, mInputMonitorCompat, mSwipeTouchRegion, + disableHorizontalSwipe(event), activityControlHelper, factory, mLogId); } private InputConsumer createDeviceLockedInputConsumer(RunningTaskInfo taskInfo) { @@ -736,10 +734,10 @@ public class TouchInteractionService extends Service implements if (activity.getRootView().hasWindowFocus() || sSwipeSharedState.goingToLauncher) { return new OverviewInputConsumer(activity, mInputMonitorCompat, - false /* startingInActivityBounds */); + false /* startingInActivityBounds */, activityControl); } else { return new OverviewWithoutFocusInputConsumer(activity, mInputMonitorCompat, - disableHorizontalSwipe(event)); + activityControl, disableHorizontalSwipe(event)); } } diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/WindowTransformSwipeHandler.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/WindowTransformSwipeHandler.java index a3bd348e20..fddb523e3c 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/WindowTransformSwipeHandler.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/WindowTransformSwipeHandler.java @@ -685,8 +685,8 @@ public class WindowTransformSwipeHandler } BaseDraggingActivity activity = mActivityControlHelper.getCreatedActivity(); - return activity == null - ? InputConsumer.NO_OP : new OverviewInputConsumer(activity, null, true); + return activity == null ? InputConsumer.NO_OP + : new OverviewInputConsumer(activity, null, true, mActivityControlHelper); } private void endRunningWindowAnim(boolean cancel) { diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OtherActivityInputConsumer.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OtherActivityInputConsumer.java index e41880df50..f06702dba3 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OtherActivityInputConsumer.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OtherActivityInputConsumer.java @@ -22,6 +22,7 @@ import static android.view.MotionEvent.ACTION_POINTER_DOWN; import static android.view.MotionEvent.ACTION_POINTER_UP; import static android.view.MotionEvent.ACTION_UP; import static android.view.MotionEvent.INVALID_POINTER_ID; + import static com.android.launcher3.Utilities.EDGE_NAV_BAR; import static com.android.launcher3.Utilities.squaredHypot; import static com.android.launcher3.util.RaceConditionTracker.ENTER; @@ -44,14 +45,16 @@ import android.os.Looper; import android.view.MotionEvent; import android.view.VelocityTracker; import android.view.ViewConfiguration; + import androidx.annotation.UiThread; + import com.android.launcher3.R; import com.android.launcher3.util.Preconditions; import com.android.launcher3.util.RaceConditionTracker; import com.android.launcher3.util.TraceHelper; +import com.android.quickstep.ActivityControlHelper; import com.android.quickstep.BaseSwipeUpHandler; import com.android.quickstep.BaseSwipeUpHandler.Factory; -import com.android.quickstep.OverviewCallbacks; import com.android.quickstep.SwipeSharedState; import com.android.quickstep.SysUINavigationMode; import com.android.quickstep.SysUINavigationMode.Mode; @@ -61,6 +64,7 @@ import com.android.quickstep.util.NavBarPosition; import com.android.quickstep.util.RecentsAnimationListenerSet; import com.android.systemui.shared.system.ActivityManagerWrapper; import com.android.systemui.shared.system.InputMonitorCompat; + import java.util.function.Consumer; /** @@ -77,11 +81,11 @@ public class OtherActivityInputConsumer extends ContextWrapper implements InputC private final CachedEventDispatcher mRecentsViewDispatcher = new CachedEventDispatcher(); private final RunningTaskInfo mRunningTask; - private final OverviewCallbacks mOverviewCallbacks; private final SwipeSharedState mSwipeSharedState; private final InputMonitorCompat mInputMonitorCompat; private final SysUINavigationMode.Mode mMode; private final RectF mSwipeTouchRegion; + private final ActivityControlHelper mActivityControlHelper; private final BaseSwipeUpHandler.Factory mHandlerFactory; @@ -121,10 +125,10 @@ public class OtherActivityInputConsumer extends ContextWrapper implements InputC private int mLogId; public OtherActivityInputConsumer(Context base, RunningTaskInfo runningTaskInfo, - boolean isDeferredDownTarget, OverviewCallbacks overviewCallbacks, - Consumer onCompleteCallback, + boolean isDeferredDownTarget, Consumer onCompleteCallback, SwipeSharedState swipeSharedState, InputMonitorCompat inputMonitorCompat, RectF swipeTouchRegion, boolean disableHorizontalSwipe, + ActivityControlHelper activityControlHelper, Factory handlerFactory, int logId) { super(base); mLogId = logId; @@ -134,6 +138,7 @@ public class OtherActivityInputConsumer extends ContextWrapper implements InputC mMode = SysUINavigationMode.getMode(base); mSwipeTouchRegion = swipeTouchRegion; mHandlerFactory = handlerFactory; + mActivityControlHelper = activityControlHelper; mMotionPauseDetector = new MotionPauseDetector(base); mMotionPauseMinDisplacement = base.getResources().getDimension( @@ -144,7 +149,6 @@ public class OtherActivityInputConsumer extends ContextWrapper implements InputC boolean continuingPreviousGesture = swipeSharedState.getActiveListener() != null; mIsDeferredDownTarget = !continuingPreviousGesture && isDeferredDownTarget; - mOverviewCallbacks = overviewCallbacks; mSwipeSharedState = swipeSharedState; mNavBarPosition = new NavBarPosition(base); @@ -313,7 +317,7 @@ public class OtherActivityInputConsumer extends ContextWrapper implements InputC } mInputMonitorCompat.pilferPointers(); - mOverviewCallbacks.closeAllWindows(); + mActivityControlHelper.closeOverlay(); ActivityManagerWrapper.getInstance().closeSystemWindows( CLOSE_SYSTEM_WINDOWS_REASON_RECENTS); diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OverviewInputConsumer.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OverviewInputConsumer.java index e55389161c..4857d00260 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OverviewInputConsumer.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OverviewInputConsumer.java @@ -19,7 +19,6 @@ import static com.android.launcher3.config.FeatureFlags.ENABLE_QUICKSTEP_LIVE_TI import static com.android.quickstep.TouchInteractionService.TOUCH_INTERACTION_LOG; import static com.android.systemui.shared.system.ActivityManagerWrapper.CLOSE_SYSTEM_WINDOWS_REASON_RECENTS; -import android.util.Log; import android.view.KeyEvent; import android.view.MotionEvent; @@ -27,9 +26,8 @@ import androidx.annotation.Nullable; import com.android.launcher3.BaseDraggingActivity; import com.android.launcher3.Utilities; -import com.android.launcher3.testing.TestProtocol; import com.android.launcher3.views.BaseDragLayer; -import com.android.quickstep.OverviewCallbacks; +import com.android.quickstep.ActivityControlHelper; import com.android.systemui.shared.system.ActivityManagerWrapper; import com.android.systemui.shared.system.InputMonitorCompat; @@ -42,6 +40,7 @@ public class OverviewInputConsumer implements InputConsumer { private final T mActivity; + private final ActivityControlHelper mActivityControlHelper; private final BaseDragLayer mTarget; private final InputMonitorCompat mInputMonitor; @@ -53,10 +52,12 @@ public class OverviewInputConsumer private boolean mTargetHandledTouch; public OverviewInputConsumer(T activity, @Nullable InputMonitorCompat inputMonitor, - boolean startingInActivityBounds) { + boolean startingInActivityBounds, + ActivityControlHelper activityControlHelper) { mActivity = activity; mInputMonitor = inputMonitor; mStartingInActivityBounds = startingInActivityBounds; + mActivityControlHelper = activityControlHelper; mTarget = activity.getDragLayer(); if (startingInActivityBounds) { @@ -98,7 +99,7 @@ public class OverviewInputConsumer if (!mTargetHandledTouch && handled) { mTargetHandledTouch = true; if (!mStartingInActivityBounds) { - OverviewCallbacks.get(mActivity).closeAllWindows(); + mActivityControlHelper.closeOverlay(); ActivityManagerWrapper.getInstance() .closeSystemWindows(CLOSE_SYSTEM_WINDOWS_REASON_RECENTS); TOUCH_INTERACTION_LOG.addLog("startQuickstep"); diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OverviewWithoutFocusInputConsumer.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OverviewWithoutFocusInputConsumer.java index 05cbb789d9..e11d492331 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OverviewWithoutFocusInputConsumer.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/inputconsumers/OverviewWithoutFocusInputConsumer.java @@ -34,10 +34,9 @@ import com.android.launcher3.BaseActivity; import com.android.launcher3.BaseDraggingActivity; import com.android.launcher3.Utilities; import com.android.launcher3.logging.StatsLogUtils; -import com.android.launcher3.userevent.nano.LauncherLogProto.ContainerType; import com.android.launcher3.userevent.nano.LauncherLogProto.Action.Direction; import com.android.launcher3.userevent.nano.LauncherLogProto.Action.Touch; -import com.android.quickstep.OverviewCallbacks; +import com.android.quickstep.ActivityControlHelper; import com.android.quickstep.util.NavBarPosition; import com.android.systemui.shared.system.ActivityManagerWrapper; import com.android.systemui.shared.system.InputMonitorCompat; @@ -50,16 +49,17 @@ public class OverviewWithoutFocusInputConsumer implements InputConsumer { private final float mSquaredTouchSlop; private final Context mContext; private final NavBarPosition mNavBarPosition; + private final ActivityControlHelper mActivityControlHelper; private boolean mInterceptedTouch; private VelocityTracker mVelocityTracker; - public OverviewWithoutFocusInputConsumer(Context context, InputMonitorCompat inputMonitor, - boolean disableHorizontalSwipe) { + ActivityControlHelper activityControlHelper, boolean disableHorizontalSwipe) { mInputMonitor = inputMonitor; mDisableHorizontalSwipe = disableHorizontalSwipe; mContext = context; + mActivityControlHelper = activityControlHelper; mSquaredTouchSlop = Utilities.squaredTouchSlop(context); mNavBarPosition = new NavBarPosition(context); @@ -148,7 +148,7 @@ public class OverviewWithoutFocusInputConsumer implements InputConsumer { } if (triggerQuickstep) { - OverviewCallbacks.get(mContext).closeAllWindows(); + mActivityControlHelper.closeOverlay(); ActivityManagerWrapper.getInstance() .closeSystemWindows(CLOSE_SYSTEM_WINDOWS_REASON_RECENTS); TOUCH_INTERACTION_LOG.addLog("startQuickstep"); diff --git a/quickstep/res/values/config.xml b/quickstep/res/values/config.xml index 5c4d6d869f..98aaceb0bf 100644 --- a/quickstep/res/values/config.xml +++ b/quickstep/res/values/config.xml @@ -16,8 +16,6 @@ - - diff --git a/quickstep/src/com/android/launcher3/LauncherInitListener.java b/quickstep/src/com/android/launcher3/LauncherInitListener.java index b9ce1ceee5..38f9956203 100644 --- a/quickstep/src/com/android/launcher3/LauncherInitListener.java +++ b/quickstep/src/com/android/launcher3/LauncherInitListener.java @@ -25,7 +25,6 @@ import android.os.Handler; import com.android.launcher3.states.InternalStateHandler; import com.android.quickstep.ActivityControlHelper.ActivityInitListener; -import com.android.quickstep.OverviewCallbacks; import com.android.quickstep.util.RemoteAnimationProvider; import java.util.function.BiPredicate; @@ -63,7 +62,7 @@ public class LauncherInitListener extends InternalStateHandler implements Activi return null; }, cancellationSignal); } - OverviewCallbacks.get(launcher).onInitOverviewTransition(); + launcher.deferOverlayCallbacksUntilNextResumeOrStop(); return mOnInitListener.test(launcher, alreadyOnHome); } diff --git a/quickstep/src/com/android/quickstep/ActivityControlHelper.java b/quickstep/src/com/android/quickstep/ActivityControlHelper.java index 5c9c7d4cab..609fb26d40 100644 --- a/quickstep/src/com/android/quickstep/ActivityControlHelper.java +++ b/quickstep/src/com/android/quickstep/ActivityControlHelper.java @@ -97,6 +97,8 @@ public interface ActivityControlHelper { void onLaunchTaskSuccess(T activity); + default void closeOverlay() { } + interface ActivityInitListener { void register(); diff --git a/quickstep/src/com/android/quickstep/OverviewCallbacks.java b/quickstep/src/com/android/quickstep/OverviewCallbacks.java deleted file mode 100644 index f5573baa7f..0000000000 --- a/quickstep/src/com/android/quickstep/OverviewCallbacks.java +++ /dev/null @@ -1,43 +0,0 @@ -/* - * Copyright (C) 2018 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package com.android.quickstep; - -import android.content.Context; - -import com.android.launcher3.R; -import com.android.launcher3.util.Preconditions; -import com.android.launcher3.util.ResourceBasedOverride; - -/** - * Callbacks related to overview/quicksteps. - */ -public class OverviewCallbacks implements ResourceBasedOverride { - - private static OverviewCallbacks sInstance; - - public static OverviewCallbacks get(Context context) { - Preconditions.assertUIThread(); - if (sInstance == null) { - sInstance = Overrides.getObject(OverviewCallbacks.class, - context.getApplicationContext(), R.string.overview_callbacks_class); - } - return sInstance; - } - - public void onInitOverviewTransition() { } - - public void closeAllWindows() { } -} diff --git a/robolectric_tests/src/com/android/launcher3/util/TestLauncherProvider.java b/robolectric_tests/src/com/android/launcher3/util/TestLauncherProvider.java index 31e303eb34..9f833b15d8 100644 --- a/robolectric_tests/src/com/android/launcher3/util/TestLauncherProvider.java +++ b/robolectric_tests/src/com/android/launcher3/util/TestLauncherProvider.java @@ -2,7 +2,6 @@ package com.android.launcher3.util; import android.content.Context; import android.database.sqlite.SQLiteDatabase; -import android.database.sqlite.SQLiteOpenHelper; import com.android.launcher3.LauncherProvider; @@ -28,9 +27,6 @@ public class TestLauncherProvider extends LauncherProvider { return mOpenHelper.getWritableDatabase(); } - @Override - protected void notifyListeners() { } - private static class MyDatabaseHelper extends DatabaseHelper { public MyDatabaseHelper(Context context) { super(context, null, null); diff --git a/src/com/android/launcher3/Launcher.java b/src/com/android/launcher3/Launcher.java index 559b55fa69..ac7894b36f 100644 --- a/src/com/android/launcher3/Launcher.java +++ b/src/com/android/launcher3/Launcher.java @@ -27,6 +27,7 @@ import static com.android.launcher3.LauncherState.ALL_APPS; import static com.android.launcher3.LauncherState.NORMAL; import static com.android.launcher3.LauncherState.OVERVIEW; import static com.android.launcher3.LauncherState.OVERVIEW_PEEK; +import static com.android.launcher3.Utilities.postAsyncCallback; import static com.android.launcher3.dragndrop.DragLayer.ALPHA_INDEX_LAUNCHER_LOAD; import static com.android.launcher3.logging.LoggerUtils.newContainerTarget; import static com.android.launcher3.logging.LoggerUtils.newTarget; @@ -79,6 +80,7 @@ import android.view.animation.OvershootInterpolator; import android.widget.Toast; import androidx.annotation.Nullable; +import androidx.annotation.VisibleForTesting; import com.android.launcher3.DropTarget.DragObject; import com.android.launcher3.accessibility.LauncherAccessibilityDelegate; @@ -115,6 +117,7 @@ import com.android.launcher3.states.InternalStateHandler; import com.android.launcher3.states.RotationHelper; import com.android.launcher3.touch.ItemClickHandler; import com.android.launcher3.uioverrides.UiFactory; +import com.android.launcher3.uioverrides.plugins.PluginManagerWrapper; import com.android.launcher3.userevent.nano.LauncherLogProto; import com.android.launcher3.userevent.nano.LauncherLogProto.Action; import com.android.launcher3.userevent.nano.LauncherLogProto.ContainerType; @@ -148,6 +151,12 @@ import com.android.launcher3.widget.WidgetHostViewLoader; import com.android.launcher3.widget.WidgetListRowEntry; import com.android.launcher3.widget.WidgetsFullSheet; import com.android.launcher3.widget.custom.CustomWidgetManager; +import com.android.systemui.plugins.OverlayPlugin; +import com.android.systemui.plugins.PluginListener; +import com.android.systemui.plugins.shared.LauncherExterns; +import com.android.systemui.plugins.shared.LauncherOverlayManager; +import com.android.systemui.plugins.shared.LauncherOverlayManager.LauncherOverlay; +import com.android.systemui.plugins.shared.LauncherOverlayManager.LauncherOverlayCallbacks; import java.io.FileDescriptor; import java.io.PrintWriter; @@ -157,16 +166,14 @@ import java.util.HashMap; import java.util.HashSet; import java.util.List; import java.util.function.Predicate; - -import androidx.annotation.Nullable; -import androidx.annotation.VisibleForTesting; +import java.util.function.Supplier; /** * Default launcher application. */ public class Launcher extends BaseDraggingActivity implements LauncherExterns, Callbacks, LauncherProviderChangeListener, UserEventDelegate, - InvariantDeviceProfile.OnIDPChangeListener { + InvariantDeviceProfile.OnIDPChangeListener, PluginListener { public static final String TAG = "Launcher"; static final boolean LOGD = false; @@ -295,6 +302,11 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, private DeviceProfile mStableDeviceProfile; private RotationMode mRotationMode = RotationMode.NORMAL; + protected LauncherOverlayManager mOverlayManager; + // If true, overlay callbacks are deferred + private boolean mDeferOverlayCallbacks; + private final Runnable mDeferredOverlayCallbacks = this::checkIfOverlayStillDeferred; + @Override protected void onCreate(Bundle savedInstanceState) { RaceConditionTracker.onEvent(ON_CREATE_EVT, ENTER); @@ -391,6 +403,10 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, if (mLauncherCallbacks != null) { mLauncherCallbacks.onCreate(savedInstanceState); } + mOverlayManager = getDefaultOverlay(); + PluginManagerWrapper.INSTANCE.get(this).addPluginListener(this, + OverlayPlugin.class, false /* allowedMultiple */); + mRotationHelper.initialize(); TraceHelper.endSection("Launcher-onCreate"); @@ -416,6 +432,38 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, }); } + protected LauncherOverlayManager getDefaultOverlay() { + return new LauncherOverlayManager() { }; + } + + @Override + public void onPluginConnected(OverlayPlugin overlayManager, Context context) { + switchOverlay(() -> overlayManager.createOverlayManager(this, this)); + } + + @Override + public void onPluginDisconnected(OverlayPlugin plugin) { + switchOverlay(this::getDefaultOverlay); + } + + private void switchOverlay(Supplier overlaySupplier) { + if (mOverlayManager != null) { + mOverlayManager.onActivityDestroyed(this); + } + mOverlayManager = overlaySupplier.get(); + if (getRootView().isAttachedToWindow()) { + mOverlayManager.onAttachedToWindow(); + } + mDeferOverlayCallbacks = true; + checkIfOverlayStillDeferred(); + } + + @Override + protected void dispatchDeviceProfileChanged() { + super.dispatchDeviceProfileChanged(); + mOverlayManager.onDeviceProvideChanged(); + } + @Override public void onEnterAnimationComplete() { super.onEnterAnimationComplete(); @@ -572,6 +620,7 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, /** * Call this after onCreate to set or clear overlay. */ + @Override public void setLauncherOverlay(LauncherOverlay overlay) { if (overlay != null) { overlay.setOverlayCallbacks(new LauncherOverlayCallbacksImpl()); @@ -579,18 +628,16 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, mWorkspace.setLauncherOverlay(overlay); } + @Override + public void runOnOverlayHidden(Runnable runnable) { + getWorkspace().runOnOverlayHidden(runnable); + } + public boolean setLauncherCallbacks(LauncherCallbacks callbacks) { mLauncherCallbacks = callbacks; return true; } - @Override - public void onLauncherProviderChanged() { - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onLauncherProviderChange(); - } - } - public boolean isDraggingEnabled() { // We prevent dragging when we are loading the workspace as it is possible to pick up a view // that is subsequently removed from the workspace in startBinding(). @@ -789,9 +836,6 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, final int requestCode, final int resultCode, final Intent data) { mPendingActivityRequestCode = -1; handleActivityResult(requestCode, resultCode, data); - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onActivityResult(requestCode, resultCode, data); - } } @Override @@ -818,10 +862,6 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, getString(R.string.derived_app_name)), Toast.LENGTH_SHORT).show(); } } - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onRequestPermissionsResult(requestCode, permissions, - grantResults); - } } /** @@ -880,9 +920,12 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, protected void onStop() { super.onStop(); - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onStop(); + if (mDeferOverlayCallbacks) { + checkIfOverlayStillDeferred(); + } else { + mOverlayManager.onActivityStopped(this); } + logStopAndResume(Action.Command.STOP); mAppWidgetHost.setListenIfResumed(false); @@ -900,9 +943,10 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, protected void onStart() { RaceConditionTracker.onEvent(ON_START_EVT, ENTER); super.onStart(); - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onStart(); + if (!mDeferOverlayCallbacks) { + mOverlayManager.onActivityStarted(this); } + mAppWidgetHost.setListenIfResumed(true); RaceConditionTracker.onEvent(ON_START_EVT, EXIT); } @@ -944,15 +988,50 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, } else { getUserEventDispatcher().logActionCommand(command, containerType, -1); } + } + private void scheduleDeferredCheck() { + mHandler.removeCallbacks(mDeferredOverlayCallbacks); + postAsyncCallback(mHandler, mDeferredOverlayCallbacks); + } + + private void checkIfOverlayStillDeferred() { + if (!mDeferOverlayCallbacks) { + return; + } + if (isStarted() && (!hasBeenResumed() || mStateManager.getState().disableInteraction)) { + return; + } + mDeferOverlayCallbacks = false; + + // Move the client to the correct state. Calling the same method twice is no-op. + if (isStarted()) { + mOverlayManager.onActivityStarted(this); + } + if (hasBeenResumed()) { + mOverlayManager.onActivityResumed(this); + } else { + mOverlayManager.onActivityPaused(this); + } + if (!isStarted()) { + mOverlayManager.onActivityStopped(this); + } + } + + public void deferOverlayCallbacksUntilNextResumeOrStop() { + mDeferOverlayCallbacks = true; + } + + public LauncherOverlayManager getOverlayManager() { + return mOverlayManager; } public void onStateSetStart(LauncherState state) { if (mDeferredResumePending) { handleDeferredResume(); } - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onStateChanged(); + if (mDeferOverlayCallbacks) { + scheduleDeferredCheck(); } } @@ -981,8 +1060,10 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, resumeCallbacks.clear(); } - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onResume(); + if (mDeferOverlayCallbacks) { + scheduleDeferredCheck(); + } else { + mOverlayManager.onActivityResumed(this); } TraceHelper.endSection("ON_RESUME"); @@ -998,8 +1079,9 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, mDragController.cancelDrag(); mDragController.resetLastGestureUpTime(); mDropTargetBar.animateToVisibility(false); - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onPause(); + + if (!mDeferOverlayCallbacks) { + mOverlayManager.onActivityPaused(this); } } @@ -1015,35 +1097,6 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, mStateManager.onWindowFocusChanged(); } - public interface LauncherOverlay { - - /** - * Touch interaction leading to overscroll has begun - */ - void onScrollInteractionBegin(); - - /** - * Touch interaction related to overscroll has ended - */ - void onScrollInteractionEnd(); - - /** - * Scroll progress, between 0 and 100, when the user scrolls beyond the leftmost - * screen (or in the case of RTL, the rightmost screen). - */ - void onScrollChange(float progress, boolean rtl); - - /** - * Called when the launcher is ready to use the overlay - * @param callbacks A set of callbacks provided by Launcher in relation to the overlay - */ - void setOverlayCallbacks(LauncherOverlayCallbacks callbacks); - } - - public interface LauncherOverlayCallbacks { - void onScrollChanged(float progress); - } - class LauncherOverlayCallbacksImpl implements LauncherOverlayCallbacks { public void onScrollChanged(float progress) { @@ -1301,19 +1354,14 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, @Override public void onAttachedToWindow() { super.onAttachedToWindow(); - - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onAttachedToWindow(); - } + mOverlayManager.onAttachedToWindow(); } @Override public void onDetachedFromWindow() { super.onDetachedFromWindow(); - - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onDetachedFromWindow(); - } + mOverlayManager.onDetachedFromWindow(); + closeContextMenu(); } public AllAppsTransitionController getAllAppsController() { @@ -1362,10 +1410,16 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, return mModelWriter; } + @Override public SharedPreferences getSharedPrefs() { return mSharedPrefs; } + @Override + public SharedPreferences getDevicePrefs() { + return Utilities.getDevicePrefs(this); + } + public int getOrientation() { return mOldConfig.orientation; } @@ -1422,6 +1476,7 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, if (mLauncherCallbacks != null) { mLauncherCallbacks.onHomeIntent(internalStateHandled); } + mOverlayManager.hideOverlay(isStarted() && !isForceInvisible()); } TraceHelper.endSection("NEW_INTENT"); @@ -1467,10 +1522,7 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, } super.onSaveInstanceState(outState); - - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onSaveInstanceState(outState); - } + mOverlayManager.onActivitySaveInstanceState(this, outState); } @Override @@ -1479,6 +1531,7 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, unregisterReceiver(mScreenOffReceiver); mWorkspace.removeFolderListeners(); + PluginManagerWrapper.INSTANCE.get(this).removePluginListener(this); if (mCancelTouchController != null) { mCancelTouchController.run(); @@ -1503,9 +1556,8 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, TextKeyListener.getInstance().release(); clearPendingBinds(); LauncherAppState.getIDP(this).removeOnChangeListener(this); - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onDestroy(); - } + + mOverlayManager.onActivityDestroyed(this); } public LauncherAccessibilityDelegate getAccessibilityDelegate() { @@ -1751,9 +1803,6 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, if (finishAutoCancelActionMode()) { return; } - if (mLauncherCallbacks != null && mLauncherCallbacks.handleBackPressed()) { - return; - } if (mDragController.isDragging()) { mDragController.cancelDrag(); @@ -1878,9 +1927,6 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, // This clears all widget bitmaps from the widget tray // TODO(hyunyoungs) } - if (mLauncherCallbacks != null) { - mLauncherCallbacks.onTrimMemory(level); - } UiFactory.onTrimMemory(this, level); } @@ -2500,6 +2546,7 @@ public class Launcher extends BaseDraggingActivity implements LauncherExterns, if (mLauncherCallbacks != null) { mLauncherCallbacks.dump(prefix, fd, writer, args); } + mOverlayManager.dump(prefix, writer); } @Override diff --git a/src/com/android/launcher3/LauncherCallbacks.java b/src/com/android/launcher3/LauncherCallbacks.java index dfe75ec34a..0e529bd376 100644 --- a/src/com/android/launcher3/LauncherCallbacks.java +++ b/src/com/android/launcher3/LauncherCallbacks.java @@ -16,7 +16,6 @@ package com.android.launcher3; -import android.content.Intent; import android.os.Bundle; import java.io.FileDescriptor; @@ -36,31 +35,8 @@ public interface LauncherCallbacks { * the code in the corresponding Launcher method is executed. */ void onCreate(Bundle savedInstanceState); - void onResume(); - void onStart(); - void onStop(); - void onPause(); - void onDestroy(); - void onSaveInstanceState(Bundle outState); - void onActivityResult(int requestCode, int resultCode, Intent data); - void onRequestPermissionsResult(int requestCode, String[] permissions, - int[] grantResults); - void onAttachedToWindow(); - void onDetachedFromWindow(); void dump(String prefix, FileDescriptor fd, PrintWriter w, String[] args); void onHomeIntent(boolean internalStateHandled); - boolean handleBackPressed(); - void onTrimMemory(int level); - - /** - * Called when the launcher state changed - */ - default void onStateChanged() { } - - /* - * Extension points for providing custom behavior on certain user interactions. - */ - void onLauncherProviderChange(); /** * Starts a search with {@param initialQuery}. Return false if search was not started. diff --git a/src/com/android/launcher3/LauncherProvider.java b/src/com/android/launcher3/LauncherProvider.java index 6081300ced..d78c1b3cc8 100644 --- a/src/com/android/launcher3/LauncherProvider.java +++ b/src/com/android/launcher3/LauncherProvider.java @@ -223,7 +223,6 @@ public class LauncherProvider extends ContentProvider { mOpenHelper.onAddOrDeleteOp(db); uri = ContentUris.withAppendedId(uri, rowId); - notifyListeners(); reloadLauncherIfExternal(); return uri; } @@ -283,7 +282,6 @@ public class LauncherProvider extends ContentProvider { t.commit(); } - notifyListeners(); reloadLauncherIfExternal(); return values.length; } @@ -329,7 +327,6 @@ public class LauncherProvider extends ContentProvider { int count = db.delete(args.table, args.where, args.args); if (count > 0) { mOpenHelper.onAddOrDeleteOp(db); - notifyListeners(); reloadLauncherIfExternal(); } return count; @@ -343,8 +340,6 @@ public class LauncherProvider extends ContentProvider { addModifiedTime(values); SQLiteDatabase db = mOpenHelper.getWritableDatabase(); int count = db.update(args.table, values, args.where, args.args); - if (count > 0) notifyListeners(); - reloadLauncherIfExternal(); return count; } @@ -438,13 +433,6 @@ public class LauncherProvider extends ContentProvider { } } - /** - * Overridden in tests - */ - protected void notifyListeners() { - mListenerHandler.sendEmptyMessage(ChangeListenerWrapper.MSG_LAUNCHER_PROVIDER_CHANGED); - } - @Thunk static void addModifiedTime(ContentValues values) { values.put(LauncherSettings.Favorites.MODIFIED, System.currentTimeMillis()); } @@ -1042,7 +1030,6 @@ public class LauncherProvider extends ContentProvider { private static class ChangeListenerWrapper implements Handler.Callback { - private static final int MSG_LAUNCHER_PROVIDER_CHANGED = 1; private static final int MSG_APP_WIDGET_HOST_RESET = 2; private LauncherProviderChangeListener mListener; @@ -1051,9 +1038,6 @@ public class LauncherProvider extends ContentProvider { public boolean handleMessage(Message msg) { if (mListener != null) { switch (msg.what) { - case MSG_LAUNCHER_PROVIDER_CHANGED: - mListener.onLauncherProviderChanged(); - break; case MSG_APP_WIDGET_HOST_RESET: mListener.onAppWidgetHostReset(); break; diff --git a/src/com/android/launcher3/LauncherProviderChangeListener.java b/src/com/android/launcher3/LauncherProviderChangeListener.java index 024308863a..6afe88526d 100644 --- a/src/com/android/launcher3/LauncherProviderChangeListener.java +++ b/src/com/android/launcher3/LauncherProviderChangeListener.java @@ -7,7 +7,5 @@ package com.android.launcher3; */ public interface LauncherProviderChangeListener { - void onLauncherProviderChanged(); - void onAppWidgetHostReset(); } diff --git a/src/com/android/launcher3/Workspace.java b/src/com/android/launcher3/Workspace.java index 56a896627e..9e2c21c2b9 100644 --- a/src/com/android/launcher3/Workspace.java +++ b/src/com/android/launcher3/Workspace.java @@ -60,7 +60,6 @@ import android.view.ViewTreeObserver; import android.view.accessibility.AccessibilityNodeInfo; import android.widget.Toast; -import com.android.launcher3.Launcher.LauncherOverlay; import com.android.launcher3.LauncherAppWidgetHost.ProviderChangedListener; import com.android.launcher3.LauncherStateManager.AnimationConfig; import com.android.launcher3.accessibility.AccessibleDragListenerAdapter; @@ -101,6 +100,7 @@ import com.android.launcher3.widget.LauncherAppWidgetHostView; import com.android.launcher3.widget.PendingAddShortcutInfo; import com.android.launcher3.widget.PendingAddWidgetInfo; import com.android.launcher3.widget.PendingAppWidgetHostView; +import com.android.systemui.plugins.shared.LauncherOverlayManager.LauncherOverlay; import java.util.ArrayList; import java.util.HashSet; @@ -965,6 +965,9 @@ public class Workspace extends PagedView onOverlayScrollChanged(0); } + public boolean hasOverlay() { + return mLauncherOverlay != null; + } private boolean isScrollingOverlay() { return mLauncherOverlay != null && diff --git a/src_plugins/com/android/systemui/plugins/OverlayPlugin.java b/src_plugins/com/android/systemui/plugins/OverlayPlugin.java new file mode 100644 index 0000000000..1edb69273f --- /dev/null +++ b/src_plugins/com/android/systemui/plugins/OverlayPlugin.java @@ -0,0 +1,34 @@ +/* + * Copyright (C) 2019 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.android.systemui.plugins; + +import android.app.Activity; + +import com.android.systemui.plugins.annotations.ProvidesInterface; +import com.android.systemui.plugins.shared.LauncherExterns; +import com.android.systemui.plugins.shared.LauncherOverlayManager; + +/** + * Implement this interface to add a -1 content on the home screen. + */ +@ProvidesInterface(action = OverlayPlugin.ACTION, version = OverlayPlugin.VERSION) +public interface OverlayPlugin extends Plugin { + String ACTION = "com.android.systemui.action.PLUGIN_LAUNCHER_OVERLAY"; + int VERSION = 1; + + LauncherOverlayManager createOverlayManager(Activity activity, LauncherExterns externs); + +} diff --git a/src/com/android/launcher3/LauncherExterns.java b/src_plugins/com/android/systemui/plugins/shared/LauncherExterns.java similarity index 63% rename from src/com/android/launcher3/LauncherExterns.java rename to src_plugins/com/android/systemui/plugins/shared/LauncherExterns.java index 272bbf6987..13e4999623 100644 --- a/src/com/android/launcher3/LauncherExterns.java +++ b/src_plugins/com/android/systemui/plugins/shared/LauncherExterns.java @@ -14,19 +14,36 @@ * limitations under the License. */ -package com.android.launcher3; +package com.android.systemui.plugins.shared; import android.content.SharedPreferences; +import com.android.systemui.plugins.shared.LauncherOverlayManager.LauncherOverlay; + /** * This interface defines the set of methods that the Launcher activity exposes. Methods * here should be safe to call from classes outside of com.android.launcher3.* */ public interface LauncherExterns { - boolean setLauncherCallbacks(LauncherCallbacks callbacks); - + /** + * Returns the shared main preference + */ SharedPreferences getSharedPrefs(); - void setLauncherOverlay(Launcher.LauncherOverlay overlay); + /** + * Returns the device specific preference + */ + SharedPreferences getDevicePrefs(); + + /** + * Sets the overlay on the target activity + */ + void setLauncherOverlay(LauncherOverlay overlay); + + /** + * Executes the command, next time the overlay is hidden + */ + void runOnOverlayHidden(Runnable runnable); + } diff --git a/src_plugins/com/android/systemui/plugins/shared/LauncherOverlayManager.java b/src_plugins/com/android/systemui/plugins/shared/LauncherOverlayManager.java new file mode 100644 index 0000000000..ac02ba4528 --- /dev/null +++ b/src_plugins/com/android/systemui/plugins/shared/LauncherOverlayManager.java @@ -0,0 +1,98 @@ +/* + * Copyright (C) 2019 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.android.systemui.plugins.shared; + +import android.app.Activity; +import android.app.Application; +import android.os.Bundle; + +import java.io.PrintWriter; + +/** + * Interface to control the overlay on Launcher + */ +public interface LauncherOverlayManager extends Application.ActivityLifecycleCallbacks { + + default void onDeviceProvideChanged() { } + + default void onAttachedToWindow() { } + default void onDetachedFromWindow() { } + + default void dump(String prefix, PrintWriter w) { } + + default void openOverlay() { } + + default void hideOverlay(boolean animate) { + hideOverlay(animate ? 200 : 0); + } + + default void hideOverlay(int duration) { } + + default boolean startSearch(byte[] config, Bundle extras) { + return false; + } + + @Override + default void onActivityCreated(Activity activity, Bundle bundle) { } + + @Override + default void onActivityStarted(Activity activity) { } + + @Override + default void onActivityResumed(Activity activity) { } + + @Override + default void onActivityPaused(Activity activity) { } + + @Override + default void onActivityStopped(Activity activity) { } + + @Override + default void onActivitySaveInstanceState(Activity activity, Bundle bundle) { } + + @Override + default void onActivityDestroyed(Activity activity) { } + + interface LauncherOverlay { + + /** + * Touch interaction leading to overscroll has begun + */ + void onScrollInteractionBegin(); + + /** + * Touch interaction related to overscroll has ended + */ + void onScrollInteractionEnd(); + + /** + * Scroll progress, between 0 and 100, when the user scrolls beyond the leftmost + * screen (or in the case of RTL, the rightmost screen). + */ + void onScrollChange(float progress, boolean rtl); + + /** + * Called when the launcher is ready to use the overlay + * @param callbacks A set of callbacks provided by Launcher in relation to the overlay + */ + void setOverlayCallbacks(LauncherOverlayCallbacks callbacks); + } + + interface LauncherOverlayCallbacks { + + void onScrollChanged(float progress); + } +}