Use pinned taskbar with desktop tasks on freeform displays
Bug: 390665752
Flag: com.android.window.flags.enable_desktop_taskbar_on_freeform_displays
Test: manual on desktop device. verify correct taskbar is shown
on home screen, in overview, in desktop mode, with fullscreen
app shown. Verify opening/launching apps from taskbar works
as expected.
Change-Id: I5c1e21799609c28ec44cc190bfc681934907199f
diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarDesktopModeController.kt b/quickstep/src/com/android/launcher3/taskbar/TaskbarDesktopModeController.kt
index 8806bc6..cb399e8 100644
--- a/quickstep/src/com/android/launcher3/taskbar/TaskbarDesktopModeController.kt
+++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarDesktopModeController.kt
@@ -50,8 +50,9 @@
fun shouldShowDesktopTasksInTaskbar(): Boolean {
return desktopVisibilityController.areDesktopTasksVisible() ||
- DisplayController.showLockedTaskbarOnHome(context) &&
- taskbarControllers.taskbarStashController.isOnHome
+ DisplayController.showDesktopTaskbarForFreeformDisplay(context) ||
+ (DisplayController.showLockedTaskbarOnHome(context) &&
+ taskbarControllers.taskbarStashController.isOnHome)
}
fun getTaskbarCornerRoundness(doesAnyTaskRequireTaskbarRounding: Boolean): Float {
diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarLauncherStateController.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarLauncherStateController.java
index 9a9575d..cada5a3 100644
--- a/quickstep/src/com/android/launcher3/taskbar/TaskbarLauncherStateController.java
+++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarLauncherStateController.java
@@ -58,7 +58,6 @@
import com.android.launcher3.Utilities;
import com.android.launcher3.anim.AnimatedFloat;
import com.android.launcher3.anim.AnimatorListeners;
-import com.android.launcher3.config.FeatureFlags;
import com.android.launcher3.statemanager.StateManager;
import com.android.launcher3.taskbar.bubbles.stashing.BubbleStashController.BubbleLauncherState;
import com.android.launcher3.uioverrides.QuickstepLauncher;
@@ -714,6 +713,10 @@
private static boolean shouldShowTaskbar(Context context, boolean isInLauncher,
boolean isInOverview) {
+ if (DisplayController.showDesktopTaskbarForFreeformDisplay(context)) {
+ return true;
+ }
+
if (DisplayController.showLockedTaskbarOnHome(context) && isInLauncher) {
return true;
}
@@ -769,9 +772,14 @@
* This refers to the intended state - a transition to this state might be in progress.
*/
public boolean isTaskbarAlignedWithHotseat() {
+ if (DisplayController.showDesktopTaskbarForFreeformDisplay(mLauncher)) {
+ return false;
+ }
+
if (DisplayController.showLockedTaskbarOnHome(mLauncher) && isInLauncher()) {
return false;
}
+
return mLauncherState.isTaskbarAlignedWithHotseat(mLauncher);
}
diff --git a/quickstep/src/com/android/launcher3/taskbar/TaskbarStashController.java b/quickstep/src/com/android/launcher3/taskbar/TaskbarStashController.java
index 1ca3dfb..2ded1bf 100644
--- a/quickstep/src/com/android/launcher3/taskbar/TaskbarStashController.java
+++ b/quickstep/src/com/android/launcher3/taskbar/TaskbarStashController.java
@@ -301,7 +301,8 @@
// TODO(b/390665752): Feature to "lock" pinned taskbar to home screen will be superseded by
// pinning, in other launcher states, at which point this variable can be removed.
mInAppStateAffectsDesktopTasksVisibilityInTaskbar =
- DisplayController.showLockedTaskbarOnHome(mActivity);
+ !DisplayController.showDesktopTaskbarForFreeformDisplay(mActivity)
+ && DisplayController.showLockedTaskbarOnHome(mActivity);
mTaskbarBackgroundDuration = activity.getResources().getInteger(
R.integer.taskbar_background_duration);
diff --git a/quickstep/src/com/android/quickstep/util/SystemWindowManagerProxy.java b/quickstep/src/com/android/quickstep/util/SystemWindowManagerProxy.java
index 4d56c63..10ae7a3 100644
--- a/quickstep/src/com/android/quickstep/util/SystemWindowManagerProxy.java
+++ b/quickstep/src/com/android/quickstep/util/SystemWindowManagerProxy.java
@@ -33,6 +33,7 @@
import com.android.launcher3.util.window.CachedDisplayInfo;
import com.android.launcher3.util.window.WindowManagerProxy;
import com.android.quickstep.SystemUiProxy;
+import com.android.window.flags.Flags;
import com.android.wm.shell.shared.desktopmode.DesktopModeStatus;
import java.util.List;
@@ -90,6 +91,25 @@
}
@Override
+ public boolean showDesktopTaskbarForFreeformDisplay(Context displayInfoContext) {
+ if (!DesktopModeStatus.canEnterDesktopMode(displayInfoContext)) {
+ return false;
+ }
+
+ if (!DesktopModeStatus.enterDesktopByDefaultOnFreeformDisplay(displayInfoContext)) {
+ return false;
+ }
+
+ if (!Flags.enableDesktopTaskbarOnFreeformDisplays()) {
+ return false;
+ }
+
+ final boolean isFreeformDisplay = displayInfoContext.getResources().getConfiguration()
+ .windowConfiguration.getWindowingMode() == WINDOWING_MODE_FREEFORM;
+ return isFreeformDisplay;
+ }
+
+ @Override
public boolean isHomeVisible(Context context) {
return SystemUiProxy.INSTANCE.get(context).getHomeVisibilityState().isHomeVisible();
}
diff --git a/src/com/android/launcher3/util/DisplayController.java b/src/com/android/launcher3/util/DisplayController.java
index 475dc04..ee1af81 100644
--- a/src/com/android/launcher3/util/DisplayController.java
+++ b/src/com/android/launcher3/util/DisplayController.java
@@ -220,6 +220,14 @@
return INSTANCE.get(context).getInfo().showLockedTaskbarOnHome();
}
+ /**
+ * Returns whether desktop taskbar (pinned taskbar that shows desktop tasks) is to be used
+ * on the display because the display is a freeform display.
+ */
+ public static boolean showDesktopTaskbarForFreeformDisplay(Context context) {
+ return INSTANCE.get(context).getInfo().showDesktopTaskbarForFreeformDisplay();
+ }
+
@Override
public void onDesktopVisibilityChanged(boolean visible) {
notifyConfigChange();
@@ -259,7 +267,9 @@
new PortraitSize(config.screenHeightDp, config.screenWidthDp))
|| mWindowContext.getDisplay().getRotation() != mInfo.rotation
|| mWMProxy.showLockedTaskbarOnHome(mWindowContext)
- != mInfo.showLockedTaskbarOnHome()) {
+ != mInfo.showLockedTaskbarOnHome()
+ || mWMProxy.showDesktopTaskbarForFreeformDisplay(mWindowContext)
+ != mInfo.showDesktopTaskbarForFreeformDisplay()) {
notifyConfigChange();
}
}
@@ -376,6 +386,8 @@
private final boolean mShowLockedTaskbarOnHome;
private final boolean mIsHomeVisible;
+ private final boolean mShowDesktopTaskbarForFreeformDisplay;
+
public Info(Context displayInfoContext) {
/* don't need system overrides for external displays */
this(displayInfoContext, new WindowManagerProxy(), new ArrayMap<>());
@@ -438,6 +450,8 @@
TASKBAR_PINNING_IN_DESKTOP_MODE);
mIsInDesktopMode = wmProxy.isInDesktopMode();
mShowLockedTaskbarOnHome = wmProxy.showLockedTaskbarOnHome(displayInfoContext);
+ mShowDesktopTaskbarForFreeformDisplay = wmProxy.showDesktopTaskbarForFreeformDisplay(
+ displayInfoContext);
mIsHomeVisible = wmProxy.isHomeVisible(displayInfoContext);
}
@@ -455,6 +469,11 @@
return sTransientTaskbarStatusForTests;
}
if (enableTaskbarPinning()) {
+ // If "freeform" display taskbar is enabled, ensure the taskbar is pinned.
+ if (mShowDesktopTaskbarForFreeformDisplay) {
+ return false;
+ }
+
// If Launcher is visible on the freeform display, ensure the taskbar is pinned.
if (mShowLockedTaskbarOnHome && mIsHomeVisible) {
return false;
@@ -533,6 +552,14 @@
public boolean showLockedTaskbarOnHome() {
return mShowLockedTaskbarOnHome;
}
+
+ /**
+ * Returns whether the taskbar should be pinned, and showing desktop tasks, because the
+ * display is a "freeform" display.
+ */
+ public boolean showDesktopTaskbarForFreeformDisplay() {
+ return mShowDesktopTaskbarForFreeformDisplay;
+ }
}
/**
diff --git a/src/com/android/launcher3/util/window/WindowManagerProxy.java b/src/com/android/launcher3/util/window/WindowManagerProxy.java
index e568eed..f511ef2 100644
--- a/src/com/android/launcher3/util/window/WindowManagerProxy.java
+++ b/src/com/android/launcher3/util/window/WindowManagerProxy.java
@@ -121,6 +121,14 @@
}
/**
+ * Returns whether the display is a freeform display for which taskbar should be pinned
+ * and showing desktop tasks.
+ */
+ public boolean showDesktopTaskbarForFreeformDisplay(Context displayInfoContext) {
+ return false;
+ }
+
+ /**
* Returns if the home is visible.
*/
public boolean isHomeVisible(Context context) {
diff --git a/tests/multivalentTests/src/com/android/launcher3/util/DisplayControllerTest.kt b/tests/multivalentTests/src/com/android/launcher3/util/DisplayControllerTest.kt
index 7e76e19..588a668 100644
--- a/tests/multivalentTests/src/com/android/launcher3/util/DisplayControllerTest.kt
+++ b/tests/multivalentTests/src/com/android/launcher3/util/DisplayControllerTest.kt
@@ -32,6 +32,7 @@
import com.android.launcher3.dagger.LauncherAppComponent
import com.android.launcher3.dagger.LauncherAppSingleton
import com.android.launcher3.util.DisplayController.CHANGE_DENSITY
+import com.android.launcher3.util.DisplayController.CHANGE_DESKTOP_MODE
import com.android.launcher3.util.DisplayController.CHANGE_ROTATION
import com.android.launcher3.util.DisplayController.CHANGE_TASKBAR_PINNING
import com.android.launcher3.util.DisplayController.DisplayInfoChangeListener
@@ -229,6 +230,63 @@
.onDisplayInfoChanged(any(), any(), eq(CHANGE_TASKBAR_PINNING))
assertFalse(displayController.getInfo().isTransientTaskbar())
}
+
+ @Test
+ @UiThreadTest
+ fun testTaskbarPinnedForDesktopTaskbar_inDesktopMode() {
+ whenever(windowManagerProxy.showDesktopTaskbarForFreeformDisplay(any())).thenReturn(true)
+ whenever(launcherPrefs.get(TASKBAR_PINNING)).thenReturn(false)
+ whenever(launcherPrefs.get(TASKBAR_PINNING_IN_DESKTOP_MODE)).thenReturn(false)
+ whenever(windowManagerProxy.isInDesktopMode()).thenReturn(true)
+ whenever(windowManagerProxy.isHomeVisible(any())).thenReturn(false)
+ DisplayController.enableTaskbarModePreferenceForTests(true)
+
+ assertTrue(displayController.getInfo().isTransientTaskbar())
+
+ displayController.onConfigurationChanged(configuration)
+
+ verify(displayInfoChangeListener)
+ .onDisplayInfoChanged(any(), any(), eq(CHANGE_TASKBAR_PINNING or CHANGE_DESKTOP_MODE))
+ assertFalse(displayController.getInfo().isTransientTaskbar())
+ }
+
+ @Test
+ @UiThreadTest
+ fun testTaskbarPinnedForDesktopTaskbar_notInDesktopMode() {
+ whenever(windowManagerProxy.showDesktopTaskbarForFreeformDisplay(any())).thenReturn(true)
+ whenever(launcherPrefs.get(TASKBAR_PINNING)).thenReturn(false)
+ whenever(launcherPrefs.get(TASKBAR_PINNING_IN_DESKTOP_MODE)).thenReturn(false)
+ whenever(windowManagerProxy.isInDesktopMode()).thenReturn(false)
+ whenever(windowManagerProxy.isHomeVisible(any())).thenReturn(false)
+ DisplayController.enableTaskbarModePreferenceForTests(true)
+
+ assertTrue(displayController.getInfo().isTransientTaskbar())
+
+ displayController.onConfigurationChanged(configuration)
+
+ verify(displayInfoChangeListener)
+ .onDisplayInfoChanged(any(), any(), eq(CHANGE_TASKBAR_PINNING))
+ assertFalse(displayController.getInfo().isTransientTaskbar())
+ }
+
+ @Test
+ @UiThreadTest
+ fun testTaskbarPinnedForDesktopTaskbar_onHome() {
+ whenever(windowManagerProxy.showDesktopTaskbarForFreeformDisplay(any())).thenReturn(true)
+ whenever(launcherPrefs.get(TASKBAR_PINNING)).thenReturn(false)
+ whenever(launcherPrefs.get(TASKBAR_PINNING_IN_DESKTOP_MODE)).thenReturn(false)
+ whenever(windowManagerProxy.isInDesktopMode()).thenReturn(false)
+ whenever(windowManagerProxy.isHomeVisible(any())).thenReturn(true)
+ DisplayController.enableTaskbarModePreferenceForTests(true)
+
+ assertTrue(displayController.getInfo().isTransientTaskbar())
+
+ displayController.onConfigurationChanged(configuration)
+
+ verify(displayInfoChangeListener)
+ .onDisplayInfoChanged(any(), any(), eq(CHANGE_TASKBAR_PINNING))
+ assertFalse(displayController.getInfo().isTransientTaskbar())
+ }
}
class MyWmProxy : WindowManagerProxy()