diff --git a/quickstep/src/com/android/launcher3/taskbar/LauncherTaskbarUIController.java b/quickstep/src/com/android/launcher3/taskbar/LauncherTaskbarUIController.java index b9b4fc3b5a..03d00c4758 100644 --- a/quickstep/src/com/android/launcher3/taskbar/LauncherTaskbarUIController.java +++ b/quickstep/src/com/android/launcher3/taskbar/LauncherTaskbarUIController.java @@ -276,13 +276,6 @@ public class LauncherTaskbarUIController extends TaskbarUIController { && !mLauncher.getOnboardingPrefs().getBoolean(OnboardingPrefs.TASKBAR_EDU_SEEN); } - /** - * Manually ends the taskbar education flow. - */ - public void hideEdu() { - mControllers.taskbarEduController.hideEdu(); - } - @Override public void onTaskbarIconLaunched(ItemInfo item) { InstanceId instanceId = new InstanceIdSequence().newInstanceId(); diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarActivityContext.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarActivityContext.java index 6cd5332de5..28f526234c 100644 --- a/quickstep/src/com/android/launcher3/taskbar/TaskbarActivityContext.java +++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarActivityContext.java @@ -76,6 +76,7 @@ import com.android.launcher3.model.data.ItemInfo; import com.android.launcher3.model.data.WorkspaceItemInfo; import com.android.launcher3.popup.PopupDataProvider; import com.android.launcher3.taskbar.allapps.TaskbarAllAppsController; +import com.android.launcher3.taskbar.overlay.TaskbarOverlayController; import com.android.launcher3.testing.TestLogging; import com.android.launcher3.testing.shared.TestProtocol; import com.android.launcher3.touch.ItemClickHandler; @@ -212,7 +213,8 @@ public class TaskbarActivityContext extends BaseTaskbarContext { new TaskbarAutohideSuspendController(this), new TaskbarPopupController(this), new TaskbarForceVisibleImmersiveController(this), - new TaskbarAllAppsController(this, dp), + new TaskbarOverlayController(this, dp), + new TaskbarAllAppsController(), new TaskbarInsetsController(this), new VoiceInteractionWindowController(this), isDesktopMode @@ -244,7 +246,7 @@ public class TaskbarActivityContext extends BaseTaskbarContext { /** Updates {@link DeviceProfile} instances for any Taskbar windows. */ public void updateDeviceProfile(DeviceProfile dp, NavigationMode navMode) { mNavMode = navMode; - mControllers.taskbarAllAppsController.updateDeviceProfile(dp); + mControllers.taskbarOverlayController.updateDeviceProfile(dp); mDeviceProfile = dp.copy(this); updateIconSize(getResources()); diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarControllers.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarControllers.java index 707023b2ec..9c2d21ef8c 100644 --- a/quickstep/src/com/android/launcher3/taskbar/TaskbarControllers.java +++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarControllers.java @@ -22,6 +22,7 @@ import androidx.annotation.Nullable; import androidx.annotation.VisibleForTesting; import com.android.launcher3.taskbar.allapps.TaskbarAllAppsController; +import com.android.launcher3.taskbar.overlay.TaskbarOverlayController; import com.android.systemui.shared.rotation.RotationButtonController; import java.io.PrintWriter; @@ -54,6 +55,7 @@ public class TaskbarControllers { public final TaskbarInsetsController taskbarInsetsController; public final VoiceInteractionWindowController voiceInteractionWindowController; public final TaskbarRecentAppsController taskbarRecentAppsController; + public final TaskbarOverlayController taskbarOverlayController; @Nullable private LoggableTaskbarController[] mControllersToLog = null; @@ -81,6 +83,7 @@ public class TaskbarControllers { TaskbarAutohideSuspendController taskbarAutoHideSuspendController, TaskbarPopupController taskbarPopupController, TaskbarForceVisibleImmersiveController taskbarForceVisibleImmersiveController, + TaskbarOverlayController taskbarOverlayController, TaskbarAllAppsController taskbarAllAppsController, TaskbarInsetsController taskbarInsetsController, VoiceInteractionWindowController voiceInteractionWindowController, @@ -101,6 +104,7 @@ public class TaskbarControllers { this.taskbarAutohideSuspendController = taskbarAutoHideSuspendController; this.taskbarPopupController = taskbarPopupController; this.taskbarForceVisibleImmersiveController = taskbarForceVisibleImmersiveController; + this.taskbarOverlayController = taskbarOverlayController; this.taskbarAllAppsController = taskbarAllAppsController; this.taskbarInsetsController = taskbarInsetsController; this.voiceInteractionWindowController = voiceInteractionWindowController; @@ -129,6 +133,7 @@ public class TaskbarControllers { taskbarEduController.init(this); taskbarPopupController.init(this); taskbarForceVisibleImmersiveController.init(this); + taskbarOverlayController.init(this); taskbarAllAppsController.init(this, sharedState.allAppsVisible); navButtonController.init(this); taskbarInsetsController.init(this); @@ -179,7 +184,7 @@ public class TaskbarControllers { taskbarAutohideSuspendController.onDestroy(); taskbarPopupController.onDestroy(); taskbarForceVisibleImmersiveController.onDestroy(); - taskbarAllAppsController.onDestroy(); + taskbarOverlayController.onDestroy(); navButtonController.onDestroy(); taskbarInsetsController.onDestroy(); voiceInteractionWindowController.onDestroy(); diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarEduController.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarEduController.java index 95b93febe0..16cc0ac0af 100644 --- a/quickstep/src/com/android/launcher3/taskbar/TaskbarEduController.java +++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarEduController.java @@ -35,6 +35,7 @@ import android.view.View; import com.android.launcher3.R; import com.android.launcher3.icons.BitmapInfo; import com.android.launcher3.model.data.ItemInfo; +import com.android.launcher3.taskbar.overlay.TaskbarOverlayContext; import com.android.launcher3.uioverrides.PredictedAppIcon; import java.io.PrintWriter; @@ -87,8 +88,10 @@ public class TaskbarEduController implements TaskbarControllers.LoggableTaskbarC void showEdu() { mActivity.setTaskbarWindowFullscreen(true); mActivity.getDragLayer().post(() -> { - mTaskbarEduView = (TaskbarEduView) mActivity.getLayoutInflater().inflate( - R.layout.taskbar_edu, mActivity.getDragLayer(), false); + TaskbarOverlayContext overlayContext = + mControllers.taskbarOverlayController.requestWindow(); + mTaskbarEduView = (TaskbarEduView) overlayContext.getLayoutInflater().inflate( + R.layout.taskbar_edu, overlayContext.getDragLayer(), false); mTaskbarEduView.init(new TaskbarEduCallbacks()); mControllers.navbarButtonsViewController.setSlideInViewVisible(true); mTaskbarEduView.setOnCloseBeginListener( @@ -99,12 +102,6 @@ public class TaskbarEduController implements TaskbarControllers.LoggableTaskbarC }); } - void hideEdu() { - if (mTaskbarEduView != null) { - mTaskbarEduView.close(true /* animate */); - } - } - /** * Starts the given animation, ending the previous animation first if it's still playing. */ diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarEduView.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarEduView.java index c0cbbd697d..bb87f48a92 100644 --- a/quickstep/src/com/android/launcher3/taskbar/TaskbarEduView.java +++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarEduView.java @@ -28,10 +28,11 @@ import android.widget.Button; import com.android.launcher3.Insettable; import com.android.launcher3.R; +import com.android.launcher3.taskbar.overlay.TaskbarOverlayContext; import com.android.launcher3.views.AbstractSlideInView; /** Education view about the Taskbar. */ -public class TaskbarEduView extends AbstractSlideInView +public class TaskbarEduView extends AbstractSlideInView implements Insettable { private static final int DEFAULT_OPEN_DURATION = 500; diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarInsetsController.kt b/quickstep/src/com/android/launcher3/taskbar/TaskbarInsetsController.kt index 45e2b77f76..32c1972934 100644 --- a/quickstep/src/com/android/launcher3/taskbar/TaskbarInsetsController.kt +++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarInsetsController.kt @@ -29,7 +29,7 @@ import android.view.WindowManager import android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD import android.view.WindowManager.LayoutParams.TYPE_VOICE_INTERACTION import com.android.launcher3.AbstractFloatingView -import com.android.launcher3.AbstractFloatingView.TYPE_TASKBAR_ALL_APPS +import com.android.launcher3.AbstractFloatingView.TYPE_TASKBAR_OVERLAY_PROXY import com.android.launcher3.DeviceProfile import com.android.launcher3.R import com.android.launcher3.anim.AlphaUpdateListener @@ -157,8 +157,11 @@ class TaskbarInsetsController(val context: TaskbarActivityContext): LoggableTask } else if (controllers.taskbarDragController.isSystemDragInProgress) { // Let touches pass through us. insetsInfo.setTouchableInsets(TOUCHABLE_INSETS_REGION) - } else if (AbstractFloatingView.hasOpenView(context, TYPE_TASKBAR_ALL_APPS)) { - // Let touches pass through us. + } else if (AbstractFloatingView.hasOpenView(context, TYPE_TASKBAR_OVERLAY_PROXY)) { + // Let touches pass through us if icons are hidden. + if (controllers.taskbarViewController.areIconsVisible()) { + insetsInfo.touchableRegion.set(touchableRegion) + } insetsInfo.setTouchableInsets(TOUCHABLE_INSETS_REGION) } else if (controllers.taskbarViewController.areIconsVisible() || AbstractFloatingView.hasOpenView(context, AbstractFloatingView.TYPE_ALL) diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarUIController.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarUIController.java index 114bfecb6e..49dba95151 100644 --- a/quickstep/src/com/android/launcher3/taskbar/TaskbarUIController.java +++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarUIController.java @@ -80,10 +80,10 @@ public class TaskbarUIController { } /** - * Manually closes the all apps window. + * Manually closes the overlay window. */ - public void hideAllApps() { - mControllers.taskbarAllAppsController.hide(); + public void hideOverlayWindow() { + mControllers.taskbarOverlayController.hideWindow(); } /** diff --git a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsContainerView.java b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsContainerView.java index 51fa4d9f3a..ce51f7dc71 100644 --- a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsContainerView.java +++ b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsContainerView.java @@ -24,10 +24,11 @@ import com.android.launcher3.allapps.AllAppsGridAdapter; import com.android.launcher3.allapps.AlphabeticalAppsList; import com.android.launcher3.allapps.BaseAdapterProvider; import com.android.launcher3.allapps.BaseAllAppsAdapter; +import com.android.launcher3.taskbar.overlay.TaskbarOverlayContext; /** All apps container accessible from taskbar. */ public class TaskbarAllAppsContainerView extends - ActivityAllAppsContainerView { + ActivityAllAppsContainerView { public TaskbarAllAppsContainerView(Context context, AttributeSet attrs) { this(context, attrs, 0); @@ -44,8 +45,8 @@ public class TaskbarAllAppsContainerView extends } @Override - protected BaseAllAppsAdapter createAdapter( - AlphabeticalAppsList appsList, + protected BaseAllAppsAdapter createAdapter( + AlphabeticalAppsList appsList, BaseAdapterProvider[] adapterProviders) { return new AllAppsGridAdapter<>(mActivityContext, getLayoutInflater(), appsList, adapterProviders); diff --git a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsContext.java b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsContext.java deleted file mode 100644 index 0372f67b75..0000000000 --- a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsContext.java +++ /dev/null @@ -1,248 +0,0 @@ -/* - * Copyright (C) 2022 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.launcher3.taskbar.allapps; - -import static android.view.KeyEvent.ACTION_UP; -import static android.view.KeyEvent.KEYCODE_BACK; -import static android.view.ViewTreeObserver.InternalInsetsInfo.TOUCHABLE_INSETS_REGION; -import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY; - -import android.content.Context; -import android.graphics.Insets; -import android.view.KeyEvent; -import android.view.MotionEvent; -import android.view.View; -import android.view.ViewTreeObserver; -import android.view.ViewTreeObserver.OnComputeInternalInsetsListener; -import android.view.WindowInsets; - -import com.android.launcher3.AbstractFloatingView; -import com.android.launcher3.DeviceProfile; -import com.android.launcher3.R; -import com.android.launcher3.Utilities; -import com.android.launcher3.allapps.ActivityAllAppsContainerView; -import com.android.launcher3.allapps.search.DefaultSearchAdapterProvider; -import com.android.launcher3.allapps.search.SearchAdapterProvider; -import com.android.launcher3.dot.DotInfo; -import com.android.launcher3.model.data.ItemInfo; -import com.android.launcher3.popup.PopupDataProvider; -import com.android.launcher3.taskbar.BaseTaskbarContext; -import com.android.launcher3.taskbar.TaskbarActivityContext; -import com.android.launcher3.taskbar.TaskbarControllers; -import com.android.launcher3.taskbar.TaskbarDragController; -import com.android.launcher3.taskbar.TaskbarStashController; -import com.android.launcher3.testing.TestLogging; -import com.android.launcher3.testing.shared.TestProtocol; -import com.android.launcher3.util.OnboardingPrefs; -import com.android.launcher3.util.TouchController; -import com.android.launcher3.views.BaseDragLayer; - -/** - * Window context for the taskbar all apps overlay. - *

- * All apps has its own window and needs a window context. Some properties are delegated to the - * {@link TaskbarActivityContext} such as {@link DeviceProfile} and {@link PopupDataProvider}. - */ -class TaskbarAllAppsContext extends BaseTaskbarContext { - private final TaskbarActivityContext mTaskbarContext; - private final OnboardingPrefs mOnboardingPrefs; - - private final TaskbarAllAppsController mWindowController; - private final TaskbarAllAppsViewController mAllAppsViewController; - private final TaskbarDragController mDragController; - private final TaskbarAllAppsDragLayer mDragLayer; - private final TaskbarAllAppsContainerView mAppsView; - - // We automatically stash taskbar when all apps is opened in gesture navigation mode. - private final boolean mWillTaskbarBeVisuallyStashed; - private final int mStashedTaskbarHeight; - - TaskbarAllAppsContext( - TaskbarActivityContext taskbarContext, - TaskbarAllAppsController windowController, - TaskbarControllers taskbarControllers) { - super(taskbarContext.createWindowContext(TYPE_APPLICATION_OVERLAY, null)); - mTaskbarContext = taskbarContext; - mWindowController = windowController; - mDragController = new TaskbarDragController(this); - mOnboardingPrefs = new OnboardingPrefs<>(this, Utilities.getPrefs(this)); - - mDragLayer = new TaskbarAllAppsDragLayer(this); - TaskbarAllAppsSlideInView slideInView = (TaskbarAllAppsSlideInView) mLayoutInflater.inflate( - R.layout.taskbar_all_apps, mDragLayer, false); - mAllAppsViewController = new TaskbarAllAppsViewController( - this, - slideInView, - windowController, - taskbarControllers); - mAppsView = slideInView.getAppsView(); - - TaskbarStashController taskbarStashController = taskbarControllers.taskbarStashController; - mWillTaskbarBeVisuallyStashed = taskbarStashController.supportsVisualStashing(); - mStashedTaskbarHeight = taskbarStashController.getStashedHeight(); - } - - TaskbarAllAppsViewController getAllAppsViewController() { - return mAllAppsViewController; - } - - @Override - public DeviceProfile getDeviceProfile() { - return mWindowController.getDeviceProfile(); - } - - @Override - public TaskbarDragController getDragController() { - return mDragController; - } - - @Override - public TaskbarAllAppsDragLayer getDragLayer() { - return mDragLayer; - } - - @Override - public TaskbarAllAppsContainerView getAppsView() { - return mAppsView; - } - - @Override - public OnboardingPrefs getOnboardingPrefs() { - return mOnboardingPrefs; - } - - @Override - public boolean isBindingItems() { - return mTaskbarContext.isBindingItems(); - } - - @Override - public View.OnClickListener getItemOnClickListener() { - return mTaskbarContext.getItemOnClickListener(); - } - - @Override - public PopupDataProvider getPopupDataProvider() { - return mTaskbarContext.getPopupDataProvider(); - } - - @Override - public DotInfo getDotInfoForItem(ItemInfo info) { - return mTaskbarContext.getDotInfoForItem(info); - } - - @Override - public void onDragStart() {} - - @Override - public void onDragEnd() { - mWindowController.maybeCloseWindow(); - } - - @Override - public void onPopupVisibilityChanged(boolean isVisible) {} - - @Override - public SearchAdapterProvider createSearchAdapterProvider( - ActivityAllAppsContainerView appsView) { - return new DefaultSearchAdapterProvider(this); - } - - /** Root drag layer for this context. */ - private static class TaskbarAllAppsDragLayer extends - BaseDragLayer implements OnComputeInternalInsetsListener { - - private TaskbarAllAppsDragLayer(Context context) { - super(context, null, 1); - setClipChildren(false); - recreateControllers(); - } - - @Override - protected void onAttachedToWindow() { - super.onAttachedToWindow(); - getViewTreeObserver().addOnComputeInternalInsetsListener(this); - } - - @Override - protected void onDetachedFromWindow() { - super.onDetachedFromWindow(); - getViewTreeObserver().removeOnComputeInternalInsetsListener(this); - } - - @Override - public void recreateControllers() { - mControllers = new TouchController[]{mActivity.mDragController}; - } - - @Override - public boolean dispatchTouchEvent(MotionEvent ev) { - TestLogging.recordMotionEvent(TestProtocol.SEQUENCE_MAIN, "Touch event", ev); - return super.dispatchTouchEvent(ev); - } - - @Override - public boolean dispatchKeyEvent(KeyEvent event) { - if (event.getAction() == ACTION_UP && event.getKeyCode() == KEYCODE_BACK) { - AbstractFloatingView topView = AbstractFloatingView.getTopOpenView(mActivity); - if (topView != null && topView.onBackPressed()) { - return true; - } - } - return super.dispatchKeyEvent(event); - } - - @Override - public void onComputeInternalInsets(ViewTreeObserver.InternalInsetsInfo inoutInfo) { - if (mActivity.mDragController.isSystemDragInProgress()) { - inoutInfo.touchableRegion.setEmpty(); - inoutInfo.setTouchableInsets(TOUCHABLE_INSETS_REGION); - } - } - - @Override - public WindowInsets onApplyWindowInsets(WindowInsets insets) { - return updateInsetsDueToStashing(insets); - } - - /** - * Taskbar automatically stashes when opening all apps, but we don't report the insets as - * changing to avoid moving the underlying app. But internally, the apps view should still - * layout according to the stashed insets rather than the unstashed insets. So this method - * does two things: - * 1) Sets navigationBars bottom inset to stashedHeight. - * 2) Sets tappableInsets bottom inset to 0. - */ - private WindowInsets updateInsetsDueToStashing(WindowInsets oldInsets) { - if (!mActivity.mWillTaskbarBeVisuallyStashed) { - return oldInsets; - } - WindowInsets.Builder updatedInsetsBuilder = new WindowInsets.Builder(oldInsets); - - Insets oldNavInsets = oldInsets.getInsets(WindowInsets.Type.navigationBars()); - Insets newNavInsets = Insets.of(oldNavInsets.left, oldNavInsets.top, oldNavInsets.right, - mActivity.mStashedTaskbarHeight); - updatedInsetsBuilder.setInsets(WindowInsets.Type.navigationBars(), newNavInsets); - - Insets oldTappableInsets = oldInsets.getInsets(WindowInsets.Type.tappableElement()); - Insets newTappableInsets = Insets.of(oldTappableInsets.left, oldTappableInsets.top, - oldTappableInsets.right, 0); - updatedInsetsBuilder.setInsets(WindowInsets.Type.tappableElement(), newTappableInsets); - - return updatedInsetsBuilder.build(); - } - } -} diff --git a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsController.java b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsController.java index 1671a0f1d7..ea37944d69 100644 --- a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsController.java +++ b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsController.java @@ -15,34 +15,17 @@ */ package com.android.launcher3.taskbar.allapps; -import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS; -import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY; - -import static com.android.launcher3.AbstractFloatingView.TYPE_ALL; -import static com.android.launcher3.AbstractFloatingView.TYPE_REBIND_SAFE; - -import android.content.Context; -import android.graphics.PixelFormat; -import android.view.Gravity; -import android.view.MotionEvent; -import android.view.WindowManager; -import android.view.WindowManager.LayoutParams; - import androidx.annotation.Nullable; -import com.android.launcher3.AbstractFloatingView; -import com.android.launcher3.DeviceProfile; +import com.android.launcher3.R; import com.android.launcher3.appprediction.PredictionRowView; import com.android.launcher3.config.FeatureFlags; import com.android.launcher3.model.data.AppInfo; import com.android.launcher3.model.data.ItemInfo; -import com.android.launcher3.taskbar.TaskbarActivityContext; import com.android.launcher3.taskbar.TaskbarControllers; -import com.android.systemui.shared.system.TaskStackChangeListener; -import com.android.systemui.shared.system.TaskStackChangeListeners; +import com.android.launcher3.taskbar.overlay.TaskbarOverlayContext; import java.util.List; -import java.util.Optional; /** * Handles the all apps overlay window initialization, updates, and its data. @@ -57,36 +40,14 @@ import java.util.Optional; */ public final class TaskbarAllAppsController { - private static final String WINDOW_TITLE = "Taskbar All Apps"; - - private final TaskbarActivityContext mTaskbarContext; - private final TaskbarAllAppsProxyView mProxyView; - private final LayoutParams mLayoutParams; - - private final TaskStackChangeListener mTaskStackListener = new TaskStackChangeListener() { - @Override - public void onTaskStackChanged() { - mProxyView.close(false); - } - }; - - private DeviceProfile mDeviceProfile; private TaskbarControllers mControllers; - /** Window context for all apps if it is open. */ - private @Nullable TaskbarAllAppsContext mAllAppsContext; + private @Nullable TaskbarAllAppsContainerView mAppsView; // Application data models. private AppInfo[] mApps; private int mAppsModelFlags; private List mPredictedApps; - public TaskbarAllAppsController(TaskbarActivityContext context, DeviceProfile dp) { - mDeviceProfile = dp; - mTaskbarContext = context; - mProxyView = new TaskbarAllAppsProxyView(mTaskbarContext); - mLayoutParams = createLayoutParams(); - } - /** Initialize the controller. */ public void init(TaskbarControllers controllers, boolean allAppsVisible) { if (!FeatureFlags.ENABLE_ALL_APPS_IN_TASKBAR.get()) { @@ -111,8 +72,8 @@ public final class TaskbarAllAppsController { mApps = apps; mAppsModelFlags = flags; - if (mAllAppsContext != null) { - mAllAppsContext.getAppsView().getAppsStore().setApps(mApps, mAppsModelFlags); + if (mAppsView != null) { + mAppsView.getAppsStore().setApps(mApps, mAppsModelFlags); } } @@ -123,8 +84,8 @@ public final class TaskbarAllAppsController { } mPredictedApps = predictedApps; - if (mAllAppsContext != null) { - mAllAppsContext.getAppsView().getFloatingHeaderView() + if (mAppsView != null) { + mAppsView.getFloatingHeaderView() .findFixedRowByType(PredictionRowView.class) .setPredictedApps(mPredictedApps); } @@ -136,120 +97,30 @@ public final class TaskbarAllAppsController { } private void show(boolean animate) { - if (mProxyView.isOpen()) { + if (mAppsView != null) { return; } - mProxyView.show(); // mControllers and getSharedState should never be null here. Do not handle null-pointer // to catch invalid states. mControllers.getSharedState().allAppsVisible = true; - mAllAppsContext = new TaskbarAllAppsContext(mTaskbarContext, this, mControllers); - mAllAppsContext.getDragController().init(mControllers); - TaskStackChangeListeners.getInstance().registerTaskStackListener(mTaskStackListener); - Optional.ofNullable(mAllAppsContext.getSystemService(WindowManager.class)) - .ifPresent(m -> m.addView(mAllAppsContext.getDragLayer(), mLayoutParams)); + TaskbarOverlayContext overlayContext = + mControllers.taskbarOverlayController.requestWindow(); + TaskbarAllAppsSlideInView slideInView = + (TaskbarAllAppsSlideInView) overlayContext.getLayoutInflater().inflate( + R.layout.taskbar_all_apps, overlayContext.getDragLayer(), false); + slideInView.addOnCloseListener(() -> { + mControllers.getSharedState().allAppsVisible = false; + mAppsView = null; + }); + TaskbarAllAppsViewController viewController = new TaskbarAllAppsViewController( + overlayContext, slideInView, mControllers); - mAllAppsContext.getAppsView().getAppsStore().setApps(mApps, mAppsModelFlags); - mAllAppsContext.getAppsView().getFloatingHeaderView() + viewController.show(animate); + mAppsView = overlayContext.getAppsView(); + mAppsView.getAppsStore().setApps(mApps, mAppsModelFlags); + mAppsView.getFloatingHeaderView() .findFixedRowByType(PredictionRowView.class) .setPredictedApps(mPredictedApps); - mAllAppsContext.getAllAppsViewController().show(animate); - } - - /** Closes the {@link TaskbarAllAppsContainerView}. */ - public void hide() { - mProxyView.close(true); - } - - /** - * Removes the all apps window from the hierarchy, if all floating views are closed and there is - * no system drag operation in progress. - *

- * This method should be called after an exit animation finishes, if applicable. - */ - void maybeCloseWindow() { - if (mAllAppsContext != null && (AbstractFloatingView.hasOpenView(mAllAppsContext, TYPE_ALL) - || mAllAppsContext.getDragController().isSystemDragInProgress())) { - return; - } - mProxyView.close(false); - // mControllers and getSharedState should never be null here. Do not handle null-pointer - // to catch invalid states. - mControllers.getSharedState().allAppsVisible = false; - onDestroy(); - } - - /** Destroys the controller and any All Apps window if present. */ - public void onDestroy() { - TaskStackChangeListeners.getInstance().unregisterTaskStackListener(mTaskStackListener); - Optional.ofNullable(mAllAppsContext) - .map(c -> c.getSystemService(WindowManager.class)) - .ifPresent(m -> m.removeViewImmediate(mAllAppsContext.getDragLayer())); - mAllAppsContext = null; - } - - /** Updates {@link DeviceProfile} instance for Taskbar's All Apps window. */ - public void updateDeviceProfile(DeviceProfile dp) { - mDeviceProfile = dp; - Optional.ofNullable(mAllAppsContext).ifPresent(c -> { - AbstractFloatingView.closeAllOpenViewsExcept(c, false, TYPE_REBIND_SAFE); - c.dispatchDeviceProfileChanged(); - }); - } - - DeviceProfile getDeviceProfile() { - return mDeviceProfile; - } - - private LayoutParams createLayoutParams() { - LayoutParams layoutParams = new LayoutParams( - TYPE_APPLICATION_OVERLAY, - WindowManager.LayoutParams.FLAG_SPLIT_TOUCH, - PixelFormat.TRANSLUCENT); - layoutParams.setTitle(WINDOW_TITLE); - layoutParams.gravity = Gravity.BOTTOM; - layoutParams.packageName = mTaskbarContext.getPackageName(); - layoutParams.setFitInsetsTypes(0); // Handled by container view. - layoutParams.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS; - layoutParams.setSystemApplicationOverlay(true); - return layoutParams; - } - - /** - * Proxy view connecting taskbar drag layer to the all apps window. - *

- * The all apps view is in a separate window and has its own drag layer, but this proxy lets it - * behave as though its in the taskbar drag layer. For instance, when the taskbar closes all - * {@link AbstractFloatingView} instances, the all apps window will also close. - */ - private class TaskbarAllAppsProxyView extends AbstractFloatingView { - - private TaskbarAllAppsProxyView(Context context) { - super(context, null); - } - - private void show() { - mIsOpen = true; - mTaskbarContext.getDragLayer().addView(this); - } - - @Override - protected void handleClose(boolean animate) { - mTaskbarContext.getDragLayer().removeView(this); - Optional.ofNullable(mAllAppsContext) - .map(TaskbarAllAppsContext::getAllAppsViewController) - .ifPresent(v -> v.close(animate)); - } - - @Override - protected boolean isOfType(int type) { - return (type & TYPE_TASKBAR_ALL_APPS) != 0; - } - - @Override - public boolean onControllerInterceptTouchEvent(MotionEvent ev) { - return false; - } } } diff --git a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsSlideInView.java b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsSlideInView.java index 9d48c8de89..c8bfc2aed0 100644 --- a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsSlideInView.java +++ b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsSlideInView.java @@ -28,10 +28,11 @@ import android.view.animation.Interpolator; import com.android.launcher3.DeviceProfile; import com.android.launcher3.Insettable; import com.android.launcher3.R; +import com.android.launcher3.taskbar.overlay.TaskbarOverlayContext; import com.android.launcher3.views.AbstractSlideInView; /** Wrapper for taskbar all apps with slide-in behavior. */ -public class TaskbarAllAppsSlideInView extends AbstractSlideInView +public class TaskbarAllAppsSlideInView extends AbstractSlideInView implements Insettable, DeviceProfile.OnDeviceProfileChangeListener { private TaskbarAllAppsContainerView mAppsView; private float mShiftRange; diff --git a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsViewController.java b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsViewController.java index 128fa5e81e..54392b21c0 100644 --- a/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsViewController.java +++ b/quickstep/src/com/android/launcher3/taskbar/allapps/TaskbarAllAppsViewController.java @@ -25,6 +25,7 @@ import com.android.launcher3.appprediction.PredictionRowView; import com.android.launcher3.taskbar.NavbarButtonsViewController; import com.android.launcher3.taskbar.TaskbarControllers; import com.android.launcher3.taskbar.TaskbarStashController; +import com.android.launcher3.taskbar.overlay.TaskbarOverlayContext; /** * Handles the {@link TaskbarAllAppsContainerView} behavior and synchronizes its transitions with @@ -32,16 +33,15 @@ import com.android.launcher3.taskbar.TaskbarStashController; */ final class TaskbarAllAppsViewController { - private final TaskbarAllAppsContext mContext; + private final TaskbarOverlayContext mContext; private final TaskbarAllAppsSlideInView mSlideInView; private final TaskbarAllAppsContainerView mAppsView; private final TaskbarStashController mTaskbarStashController; private final NavbarButtonsViewController mNavbarButtonsViewController; TaskbarAllAppsViewController( - TaskbarAllAppsContext context, + TaskbarOverlayContext context, TaskbarAllAppsSlideInView slideInView, - TaskbarAllAppsController windowController, TaskbarControllers taskbarControllers) { mContext = context; @@ -53,7 +53,6 @@ final class TaskbarAllAppsViewController { setUpIconLongClick(); setUpAppDivider(); setUpTaskbarStashing(); - mSlideInView.addOnCloseListener(windowController::maybeCloseWindow); } /** Starts the {@link TaskbarAllAppsSlideInView} enter transition. */ diff --git a/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayContext.java b/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayContext.java new file mode 100644 index 0000000000..5701de0e9c --- /dev/null +++ b/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayContext.java @@ -0,0 +1,146 @@ +/* + * Copyright (C) 2022 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.launcher3.taskbar.overlay; + +import android.content.Context; +import android.view.View; + +import com.android.launcher3.DeviceProfile; +import com.android.launcher3.R; +import com.android.launcher3.Utilities; +import com.android.launcher3.allapps.ActivityAllAppsContainerView; +import com.android.launcher3.allapps.search.DefaultSearchAdapterProvider; +import com.android.launcher3.allapps.search.SearchAdapterProvider; +import com.android.launcher3.dot.DotInfo; +import com.android.launcher3.model.data.ItemInfo; +import com.android.launcher3.popup.PopupDataProvider; +import com.android.launcher3.taskbar.BaseTaskbarContext; +import com.android.launcher3.taskbar.TaskbarActivityContext; +import com.android.launcher3.taskbar.TaskbarControllers; +import com.android.launcher3.taskbar.TaskbarDragController; +import com.android.launcher3.taskbar.TaskbarStashController; +import com.android.launcher3.taskbar.allapps.TaskbarAllAppsContainerView; +import com.android.launcher3.util.OnboardingPrefs; + +/** + * Window context for the taskbar overlays such as All Apps and EDU. + *

+ * Overlays have their own window and need a window context. Some properties are delegated to the + * {@link TaskbarActivityContext} such as {@link PopupDataProvider}. + */ +public class TaskbarOverlayContext extends BaseTaskbarContext { + private final TaskbarActivityContext mTaskbarContext; + private final OnboardingPrefs mOnboardingPrefs; + + private final TaskbarOverlayController mOverlayController; + private final TaskbarDragController mDragController; + private final TaskbarOverlayDragLayer mDragLayer; + + // We automatically stash taskbar when All Apps is opened in gesture navigation mode. + private final boolean mWillTaskbarBeVisuallyStashed; + private final int mStashedTaskbarHeight; + + public TaskbarOverlayContext( + Context windowContext, + TaskbarActivityContext taskbarContext, + TaskbarControllers controllers) { + super(windowContext); + mTaskbarContext = taskbarContext; + mOverlayController = controllers.taskbarOverlayController; + mDragController = new TaskbarDragController(this); + mDragController.init(controllers); + mOnboardingPrefs = new OnboardingPrefs<>(this, Utilities.getPrefs(this)); + mDragLayer = new TaskbarOverlayDragLayer(this); + + TaskbarStashController taskbarStashController = controllers.taskbarStashController; + mWillTaskbarBeVisuallyStashed = taskbarStashController.supportsVisualStashing(); + mStashedTaskbarHeight = taskbarStashController.getStashedHeight(); + } + + boolean willTaskbarBeVisuallyStashed() { + return mWillTaskbarBeVisuallyStashed; + } + + int getStashedTaskbarHeight() { + return mStashedTaskbarHeight; + } + + public TaskbarOverlayController getOverlayController() { + return mOverlayController; + } + + @Override + public DeviceProfile getDeviceProfile() { + return mOverlayController.getDeviceProfile(); + } + + @Override + public TaskbarDragController getDragController() { + return mDragController; + } + + @Override + public TaskbarOverlayDragLayer getDragLayer() { + return mDragLayer; + } + + @Override + public TaskbarAllAppsContainerView getAppsView() { + return mDragLayer.findViewById(R.id.apps_view); + } + + @Override + public OnboardingPrefs getOnboardingPrefs() { + return mOnboardingPrefs; + } + + @Override + public boolean isBindingItems() { + return mTaskbarContext.isBindingItems(); + } + + @Override + public View.OnClickListener getItemOnClickListener() { + return mTaskbarContext.getItemOnClickListener(); + } + + @Override + public PopupDataProvider getPopupDataProvider() { + return mTaskbarContext.getPopupDataProvider(); + } + + @Override + public DotInfo getDotInfoForItem(ItemInfo info) { + return mTaskbarContext.getDotInfoForItem(info); + } + + @Override + public void onDragStart() {} + + @Override + public void onDragEnd() { + mOverlayController.maybeCloseWindow(); + } + + @Override + public void onPopupVisibilityChanged(boolean isVisible) {} + + @Override + public SearchAdapterProvider createSearchAdapterProvider( + ActivityAllAppsContainerView appsView) { + return new DefaultSearchAdapterProvider(this); + } +} diff --git a/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayController.java b/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayController.java new file mode 100644 index 0000000000..0574058dcc --- /dev/null +++ b/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayController.java @@ -0,0 +1,197 @@ +/* + * Copyright (C) 2022 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.launcher3.taskbar.overlay; + +import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS; +import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY; + +import static com.android.launcher3.AbstractFloatingView.TYPE_ALL; +import static com.android.launcher3.AbstractFloatingView.TYPE_REBIND_SAFE; + +import android.annotation.SuppressLint; +import android.content.Context; +import android.graphics.PixelFormat; +import android.view.Gravity; +import android.view.MotionEvent; +import android.view.WindowManager; +import android.view.WindowManager.LayoutParams; + +import androidx.annotation.Nullable; + +import com.android.launcher3.AbstractFloatingView; +import com.android.launcher3.DeviceProfile; +import com.android.launcher3.taskbar.TaskbarActivityContext; +import com.android.launcher3.taskbar.TaskbarControllers; +import com.android.systemui.shared.system.TaskStackChangeListener; +import com.android.systemui.shared.system.TaskStackChangeListeners; + +import java.util.Optional; + +/** + * Handles the Taskbar overlay window lifecycle. + *

+ * Overlays need to be inflated in a separate window so that have the correct hierarchy. For + * instance, they need to be below the notification tray. If there are multiple overlays open, the + * same window is used. + */ +public final class TaskbarOverlayController { + + private static final String WINDOW_TITLE = "Taskbar Overlay"; + + private final TaskbarActivityContext mTaskbarContext; + private final Context mWindowContext; + private final TaskbarOverlayProxyView mProxyView; + private final LayoutParams mLayoutParams; + + private final TaskStackChangeListener mTaskStackListener = new TaskStackChangeListener() { + @Override + public void onTaskStackChanged() { + mProxyView.close(false); + } + }; + + private DeviceProfile mDeviceProfile; + private @Nullable TaskbarOverlayContext mOverlayContext; + private TaskbarControllers mControllers; // Initialized in init. + + public TaskbarOverlayController( + TaskbarActivityContext taskbarContext, DeviceProfile deviceProfile) { + mTaskbarContext = taskbarContext; + mWindowContext = mTaskbarContext.createWindowContext(TYPE_APPLICATION_OVERLAY, null); + mProxyView = new TaskbarOverlayProxyView(); + mLayoutParams = createLayoutParams(); + mDeviceProfile = deviceProfile; + } + + /** Initialize the controller. */ + public void init(TaskbarControllers controllers) { + mControllers = controllers; + } + + /** + * Creates a window for Taskbar overlays, if it does not already exist. Returns the window + * context for the current overlay window. + */ + public TaskbarOverlayContext requestWindow() { + if (mOverlayContext == null) { + mOverlayContext = new TaskbarOverlayContext( + mWindowContext, mTaskbarContext, mControllers); + } + + if (!mProxyView.isOpen()) { + mProxyView.show(); + Optional.ofNullable(mOverlayContext.getSystemService(WindowManager.class)) + .ifPresent(m -> m.addView(mOverlayContext.getDragLayer(), mLayoutParams)); + TaskStackChangeListeners.getInstance().registerTaskStackListener(mTaskStackListener); + } + + return mOverlayContext; + } + + /** Hides the current overlay window with animation. */ + public void hideWindow() { + mProxyView.close(true); + } + + /** + * Removes the overlay window from the hierarchy, if all floating views are closed and there is + * no system drag operation in progress. + *

+ * This method should be called after an exit animation finishes, if applicable. + */ + @SuppressLint("WrongConstant") + void maybeCloseWindow() { + if (mOverlayContext != null && (AbstractFloatingView.hasOpenView(mOverlayContext, TYPE_ALL) + || mOverlayContext.getDragController().isSystemDragInProgress())) { + return; + } + mProxyView.close(false); + onDestroy(); + } + + /** Destroys the controller and any overlay window if present. */ + public void onDestroy() { + TaskStackChangeListeners.getInstance().unregisterTaskStackListener(mTaskStackListener); + Optional.ofNullable(mOverlayContext) + .map(c -> c.getSystemService(WindowManager.class)) + .ifPresent(m -> m.removeViewImmediate(mOverlayContext.getDragLayer())); + mOverlayContext = null; + } + + /** The current device profile for the overlay window. */ + public DeviceProfile getDeviceProfile() { + return mDeviceProfile; + } + + /** Updates {@link DeviceProfile} instance for Taskbar's overlay window. */ + public void updateDeviceProfile(DeviceProfile dp) { + mDeviceProfile = dp; + Optional.ofNullable(mOverlayContext).ifPresent(c -> { + AbstractFloatingView.closeAllOpenViewsExcept(c, false, TYPE_REBIND_SAFE); + c.dispatchDeviceProfileChanged(); + }); + } + + @SuppressLint("WrongConstant") + private LayoutParams createLayoutParams() { + LayoutParams layoutParams = new LayoutParams( + TYPE_APPLICATION_OVERLAY, + LayoutParams.FLAG_SPLIT_TOUCH, + PixelFormat.TRANSLUCENT); + layoutParams.setTitle(WINDOW_TITLE); + layoutParams.gravity = Gravity.BOTTOM; + layoutParams.packageName = mTaskbarContext.getPackageName(); + layoutParams.setFitInsetsTypes(0); // Handled by container view. + layoutParams.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS; + layoutParams.setSystemApplicationOverlay(true); + return layoutParams; + } + + /** + * Proxy view connecting taskbar drag layer to the overlay window. + * + * Overlays are in a separate window and has its own drag layer, but this proxy lets its views + * behave as though they are in the taskbar drag layer. For instance, when the taskbar closes + * all {@link AbstractFloatingView} instances, the overlay window will also close. + */ + private class TaskbarOverlayProxyView extends AbstractFloatingView { + + private TaskbarOverlayProxyView() { + super(mTaskbarContext, null); + } + + private void show() { + mIsOpen = true; + mTaskbarContext.getDragLayer().addView(this); + } + + @Override + protected void handleClose(boolean animate) { + mTaskbarContext.getDragLayer().removeView(this); + Optional.ofNullable(mOverlayContext).ifPresent(c -> closeAllOpenViews(c, animate)); + } + + @Override + protected boolean isOfType(int type) { + return (type & TYPE_TASKBAR_OVERLAY_PROXY) != 0; + } + + @Override + public boolean onControllerInterceptTouchEvent(MotionEvent ev) { + return false; + } + } +} diff --git a/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayDragLayer.java b/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayDragLayer.java new file mode 100644 index 0000000000..044afd6725 --- /dev/null +++ b/quickstep/src/com/android/launcher3/taskbar/overlay/TaskbarOverlayDragLayer.java @@ -0,0 +1,126 @@ +/* + * Copyright (C) 2022 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.launcher3.taskbar.overlay; + +import static android.view.KeyEvent.ACTION_UP; +import static android.view.KeyEvent.KEYCODE_BACK; +import static android.view.ViewTreeObserver.InternalInsetsInfo.TOUCHABLE_INSETS_REGION; + +import android.content.Context; +import android.graphics.Insets; +import android.view.KeyEvent; +import android.view.MotionEvent; +import android.view.View; +import android.view.ViewTreeObserver; +import android.view.WindowInsets; + +import com.android.launcher3.AbstractFloatingView; +import com.android.launcher3.testing.TestLogging; +import com.android.launcher3.testing.shared.TestProtocol; +import com.android.launcher3.util.TouchController; +import com.android.launcher3.views.BaseDragLayer; + +/** Root drag layer for the Taskbar overlay window. */ +public class TaskbarOverlayDragLayer extends + BaseDragLayer implements + ViewTreeObserver.OnComputeInternalInsetsListener { + + TaskbarOverlayDragLayer(Context context) { + super(context, null, 1); + setClipChildren(false); + recreateControllers(); + } + + @Override + protected void onAttachedToWindow() { + super.onAttachedToWindow(); + getViewTreeObserver().addOnComputeInternalInsetsListener(this); + } + + @Override + protected void onDetachedFromWindow() { + super.onDetachedFromWindow(); + getViewTreeObserver().removeOnComputeInternalInsetsListener(this); + } + + @Override + public void recreateControllers() { + mControllers = new TouchController[]{mActivity.getDragController()}; + } + + @Override + public boolean dispatchTouchEvent(MotionEvent ev) { + TestLogging.recordMotionEvent(TestProtocol.SEQUENCE_MAIN, "Touch event", ev); + return super.dispatchTouchEvent(ev); + } + + @Override + public boolean dispatchKeyEvent(KeyEvent event) { + if (event.getAction() == ACTION_UP && event.getKeyCode() == KEYCODE_BACK) { + AbstractFloatingView topView = AbstractFloatingView.getTopOpenView(mActivity); + if (topView != null && topView.onBackPressed()) { + return true; + } + } + return super.dispatchKeyEvent(event); + } + + @Override + public void onComputeInternalInsets(ViewTreeObserver.InternalInsetsInfo inoutInfo) { + if (mActivity.getDragController().isSystemDragInProgress()) { + inoutInfo.touchableRegion.setEmpty(); + inoutInfo.setTouchableInsets(TOUCHABLE_INSETS_REGION); + } + } + + @Override + public WindowInsets onApplyWindowInsets(WindowInsets insets) { + return updateInsetsDueToStashing(insets); + } + + @Override + public void onViewRemoved(View child) { + super.onViewRemoved(child); + mActivity.getOverlayController().maybeCloseWindow(); + } + + /** + * Taskbar automatically stashes when opening all apps, but we don't report the insets as + * changing to avoid moving the underlying app. But internally, the apps view should still + * layout according to the stashed insets rather than the unstashed insets. So this method + * does two things: + * 1) Sets navigationBars bottom inset to stashedHeight. + * 2) Sets tappableInsets bottom inset to 0. + */ + private WindowInsets updateInsetsDueToStashing(WindowInsets oldInsets) { + if (!mActivity.willTaskbarBeVisuallyStashed()) { + return oldInsets; + } + WindowInsets.Builder updatedInsetsBuilder = new WindowInsets.Builder(oldInsets); + + Insets oldNavInsets = oldInsets.getInsets(WindowInsets.Type.navigationBars()); + Insets newNavInsets = Insets.of(oldNavInsets.left, oldNavInsets.top, oldNavInsets.right, + mActivity.getStashedTaskbarHeight()); + updatedInsetsBuilder.setInsets(WindowInsets.Type.navigationBars(), newNavInsets); + + Insets oldTappableInsets = oldInsets.getInsets(WindowInsets.Type.tappableElement()); + Insets newTappableInsets = Insets.of(oldTappableInsets.left, oldTappableInsets.top, + oldTappableInsets.right, 0); + updatedInsetsBuilder.setInsets(WindowInsets.Type.tappableElement(), newTappableInsets); + + return updatedInsetsBuilder.build(); + } +} diff --git a/quickstep/src/com/android/quickstep/BaseActivityInterface.java b/quickstep/src/com/android/quickstep/BaseActivityInterface.java index a343c2d965..d4320043b0 100644 --- a/quickstep/src/com/android/quickstep/BaseActivityInterface.java +++ b/quickstep/src/com/android/quickstep/BaseActivityInterface.java @@ -188,7 +188,8 @@ public abstract class BaseActivityInterface thumbnailDatas, diff --git a/quickstep/src/com/android/quickstep/LauncherActivityInterface.java b/quickstep/src/com/android/quickstep/LauncherActivityInterface.java index e9588d60fb..8522a87ba7 100644 --- a/quickstep/src/com/android/quickstep/LauncherActivityInterface.java +++ b/quickstep/src/com/android/quickstep/LauncherActivityInterface.java @@ -290,10 +290,6 @@ public final class LauncherActivityInterface extends } else { om.hideOverlay(150); } - LauncherTaskbarUIController taskbarController = getTaskbarController(); - if (taskbarController != null) { - taskbarController.hideEdu(); - } } @Override diff --git a/src/com/android/launcher3/AbstractFloatingView.java b/src/com/android/launcher3/AbstractFloatingView.java index 5ee6fce1f7..73acd878c7 100644 --- a/src/com/android/launcher3/AbstractFloatingView.java +++ b/src/com/android/launcher3/AbstractFloatingView.java @@ -94,6 +94,7 @@ public abstract class AbstractFloatingView extends LinearLayout implements Touch public static final int TYPE_TASKBAR_EDUCATION_DIALOG = 1 << 16; public static final int TYPE_TASKBAR_ALL_APPS = 1 << 17; public static final int TYPE_ADD_TO_HOME_CONFIRMATION = 1 << 18; + public static final int TYPE_TASKBAR_OVERLAY_PROXY = 1 << 19; public static final int TYPE_ALL = TYPE_FOLDER | TYPE_ACTION_POPUP | TYPE_WIDGETS_BOTTOM_SHEET | TYPE_WIDGET_RESIZE_FRAME | TYPE_WIDGETS_FULL_SHEET