diff options
6 files changed, 77 insertions, 7 deletions
diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/common/split/SplitWindowManager.java b/libs/WindowManager/Shell/src/com/android/wm/shell/common/split/SplitWindowManager.java index 8fb9bda539a0..5d121c23c6e1 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/common/split/SplitWindowManager.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/common/split/SplitWindowManager.java @@ -143,6 +143,8 @@ public final class SplitWindowManager extends WindowlessWindowManager { /** * Releases the surface control of the current {@link DividerView} and tear down the view * hierarchy. + * @param t If supplied, the surface removal will be bundled with this Transaction. If + * called with null, removes the surface immediately. */ void release(@Nullable SurfaceControl.Transaction t) { if (mDividerView != null) { diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/StageCoordinator.java b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/StageCoordinator.java index 53463a7fe593..c85da526b062 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/StageCoordinator.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/StageCoordinator.java @@ -1825,7 +1825,7 @@ public class StageCoordinator implements SplitLayout.SplitLayoutHandler, void finishEnterSplitScreen(SurfaceControl.Transaction finishT) { ProtoLog.d(WM_SHELL_SPLIT_SCREEN, "finishEnterSplitScreen"); - mSplitLayout.update(finishT, true /* resetImePosition */); + mSplitLayout.update(null, true /* resetImePosition */); mMainStage.getSplitDecorManager().inflate(mContext, mMainStage.mRootLeash, getMainStageBounds()); mSideStage.getSplitDecorManager().inflate(mContext, mSideStage.mRootLeash, diff --git a/packages/SystemUI/res/values/config.xml b/packages/SystemUI/res/values/config.xml index 45243eeb9007..3127cbd6760f 100644 --- a/packages/SystemUI/res/values/config.xml +++ b/packages/SystemUI/res/values/config.xml @@ -37,6 +37,9 @@ <item>400</item> </integer-array> + <!-- Whether to use deadzone with nav bar --> + <bool name="config_useDeadZone">true</bool> + <!-- decay duration (from size_max -> size), in ms --> <integer name="navigation_bar_deadzone_hold">333</integer> <integer name="navigation_bar_deadzone_decay">333</integer> diff --git a/packages/SystemUI/src/com/android/systemui/mediaprojection/appselector/data/RecentTaskListProvider.kt b/packages/SystemUI/src/com/android/systemui/mediaprojection/appselector/data/RecentTaskListProvider.kt index 5dde14bf0867..6e16c6eacfff 100644 --- a/packages/SystemUI/src/com/android/systemui/mediaprojection/appselector/data/RecentTaskListProvider.kt +++ b/packages/SystemUI/src/com/android/systemui/mediaprojection/appselector/data/RecentTaskListProvider.kt @@ -50,8 +50,13 @@ constructor( withContext(coroutineDispatcher) { val groupedTasks: List<GroupedRecentTaskInfo> = recents?.getTasks() ?: emptyList() // Note: the returned task list is from the most-recent to least-recent order. - // The last foreground task is at index 1, because at index 0 will be our app selector. - val foregroundGroup = groupedTasks.elementAtOrNull(1) + // When opening the app selector in full screen, index 0 will be just the app selector + // activity and a null second task, so the foreground task will be index 1, but when + // opening the app selector in split screen mode, the foreground task will be the second + // task in index 0. + val foregroundGroup = + if (groupedTasks.elementAtOrNull(0)?.splitBounds != null) groupedTasks.first() + else groupedTasks.elementAtOrNull(1) val foregroundTaskId1 = foregroundGroup?.taskInfo1?.taskId val foregroundTaskId2 = foregroundGroup?.taskInfo2?.taskId val foregroundTaskIds = listOfNotNull(foregroundTaskId1, foregroundTaskId2) diff --git a/packages/SystemUI/src/com/android/systemui/navigationbar/buttons/DeadZone.java b/packages/SystemUI/src/com/android/systemui/navigationbar/buttons/DeadZone.java index bd3a0c1b0efa..d024d00f9eac 100644 --- a/packages/SystemUI/src/com/android/systemui/navigationbar/buttons/DeadZone.java +++ b/packages/SystemUI/src/com/android/systemui/navigationbar/buttons/DeadZone.java @@ -61,6 +61,7 @@ public class DeadZone { } }; + private final boolean mUseDeadZone; private final NavigationBarController mNavBarController; private final NavigationBarView mNavigationBarView; @@ -86,9 +87,12 @@ public class DeadZone { @Inject public DeadZone(NavigationBarView view) { + mUseDeadZone = view.getResources().getBoolean(R.bool.config_useDeadZone); + mNavigationBarView = view; mNavBarController = Dependency.get(NavigationBarController.class); mDisplayId = view.getContext().getDisplayId(); + onConfigurationChanged(HORIZONTAL); } @@ -108,12 +112,20 @@ public class DeadZone { } public void setFlashOnTouchCapture(boolean dbg) { + if (!mUseDeadZone) { + return; + } + mShouldFlash = dbg; mFlashFrac = 0f; mNavigationBarView.postInvalidate(); } public void onConfigurationChanged(int rotation) { + if (!mUseDeadZone) { + return; + } + mDisplayRotation = rotation; final Resources res = mNavigationBarView.getResources(); @@ -134,6 +146,10 @@ public class DeadZone { // I made you a touch event... public boolean onTouchEvent(MotionEvent event) { + if (!mUseDeadZone) { + return false; + } + if (DEBUG) { Slog.v(TAG, this + " onTouch: " + MotionEvent.actionToString(event.getAction())); } @@ -187,17 +203,17 @@ public class DeadZone { if (mShouldFlash) mNavigationBarView.postInvalidate(); } - public void setFlash(float f) { + private void setFlash(float f) { mFlashFrac = f; mNavigationBarView.postInvalidate(); } - public float getFlash() { + private float getFlash() { return mFlashFrac; } public void onDraw(Canvas can) { - if (!mShouldFlash || mFlashFrac <= 0f) { + if (!mUseDeadZone || !mShouldFlash || mFlashFrac <= 0f) { return; } diff --git a/packages/SystemUI/tests/src/com/android/systemui/mediaprojection/appselector/data/ShellRecentTaskListProviderTest.kt b/packages/SystemUI/tests/src/com/android/systemui/mediaprojection/appselector/data/ShellRecentTaskListProviderTest.kt index b593def283ae..6568175b151d 100644 --- a/packages/SystemUI/tests/src/com/android/systemui/mediaprojection/appselector/data/ShellRecentTaskListProviderTest.kt +++ b/packages/SystemUI/tests/src/com/android/systemui/mediaprojection/appselector/data/ShellRecentTaskListProviderTest.kt @@ -1,6 +1,7 @@ package com.android.systemui.mediaprojection.appselector.data import android.app.ActivityManager.RecentTaskInfo +import android.graphics.Rect import android.testing.AndroidTestingRunner import androidx.test.filters.SmallTest import com.android.systemui.SysuiTestCase @@ -8,8 +9,10 @@ import com.android.systemui.settings.UserTracker import com.android.systemui.util.mockito.any import com.android.systemui.util.mockito.mock import com.android.systemui.util.mockito.whenever +import com.android.wm.shell.common.split.SplitScreenConstants import com.android.wm.shell.recents.RecentTasks import com.android.wm.shell.util.GroupedRecentTaskInfo +import com.android.wm.shell.util.SplitBounds import com.google.common.truth.Truth.assertThat import java.util.Optional import java.util.function.Consumer @@ -90,6 +93,17 @@ class ShellRecentTaskListProviderTest : SysuiTestCase() { } @Test + fun loadRecentTasks_singleTaskPair_returnsTasksAsForeground() { + givenRecentTasks( + createTaskPair(taskId1 = 2, taskId2 = 3, isVisible = true), + ) + + val result = runBlocking { recentTaskListProvider.loadRecentTasks() } + + assertThat(result[0].isForegroundTask).isTrue() + } + + @Test fun loadRecentTasks_multipleTasks_returnsSecondVisibleTaskAsForegroundTask() { givenRecentTasks( createSingleTask(taskId = 1), @@ -133,6 +147,21 @@ class ShellRecentTaskListProviderTest : SysuiTestCase() { } @Test + fun loadRecentTasks_firstTaskIsGroupedAndVisible_marksBothGroupedTasksAsForeground() { + givenRecentTasks( + createTaskPair(taskId1 = 1, taskId2 = 2, isVisible = true), + createSingleTask(taskId = 3), + createSingleTask(taskId = 4), + ) + + val result = runBlocking { recentTaskListProvider.loadRecentTasks() } + + assertThat(result.map { it.isForegroundTask }) + .containsExactly(true, true, false, false) + .inOrder() + } + + @Test fun loadRecentTasks_secondTaskIsGroupedAndInvisible_marksBothGroupedTasksAsNotForeground() { givenRecentTasks( createSingleTask(taskId = 1), @@ -147,6 +176,21 @@ class ShellRecentTaskListProviderTest : SysuiTestCase() { .inOrder() } + @Test + fun loadRecentTasks_firstTaskIsGroupedAndInvisible_marksBothGroupedTasksAsNotForeground() { + givenRecentTasks( + createTaskPair(taskId1 = 1, taskId2 = 2, isVisible = false), + createSingleTask(taskId = 3), + createSingleTask(taskId = 4), + ) + + val result = runBlocking { recentTaskListProvider.loadRecentTasks() } + + assertThat(result.map { it.isForegroundTask }) + .containsExactly(false, false, false, false) + .inOrder() + } + @Suppress("UNCHECKED_CAST") private fun givenRecentTasks(vararg tasks: GroupedRecentTaskInfo) { whenever(recentTasks.getRecentTasks(any(), any(), any(), any(), any())).thenAnswer { @@ -177,7 +221,7 @@ class ShellRecentTaskListProviderTest : SysuiTestCase() { GroupedRecentTaskInfo.forSplitTasks( createTaskInfo(taskId1, isVisible), createTaskInfo(taskId2, isVisible), - null + SplitBounds(Rect(), Rect(), taskId1, taskId2, SplitScreenConstants.SNAP_TO_50_50) ) private fun createTaskInfo(taskId: Int, isVisible: Boolean = false) = |