Loading libs/WindowManager/Shell/multivalentTests/src/com/android/wm/shell/bubbles/BubbleTaskStackListenerTest.kt +25 −0 Original line number Diff line number Diff line Loading @@ -195,4 +195,29 @@ class BubbleTaskStackListenerTest { verifyNoInteractions(taskOrganizer) verifyNoInteractions(taskViewTaskController) } @Test @EnableFlags( FLAG_ENABLE_CREATE_ANY_BUBBLE, FLAG_ENABLE_BUBBLE_ANYTHING, FLAG_EXCLUDE_TASK_FROM_RECENTS, FLAG_ENABLE_BUBBLE_APP_COMPAT_FIXES, ) fun onTaskMovedToFront_inStackAppBubbleToFullscreen_notifiesTaskRemoval() { task.configuration.windowConfiguration.windowingMode = WINDOWING_MODE_FULLSCREEN bubbleData.stub { on { getBubbleInStackWithTaskId(bubbleTaskId) } doReturn bubble } bubbleTaskStackListener.onTaskMovedToFront(task) val taskViewTaskController = bubble.taskView.controller val taskOrganizer = taskViewTaskController.taskOrganizer val wct = argumentCaptor<WindowContainerTransaction>().let { wctCaptor -> verify(taskOrganizer).applyTransaction(wctCaptor.capture()) wctCaptor.lastValue } verifyExitBubbleTransaction(wct, bubbleTaskToken.asBinder()) verify(taskViewTaskController).notifyTaskRemovalStarted(task) } } libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleTaskStackListener.kt +20 −18 Original line number Diff line number Diff line Loading @@ -34,11 +34,12 @@ import dagger.Lazy import java.util.Optional /** * Listens for task stack changes and handles bubble interactions when activities are restarted. * Listens for task stack changes to manage associated bubble interactions. * * This class monitors task stack events to determine how bubbles should behave when their * associated activities are restarted. It handles scenarios where bubbles should be expanded * or moved to fullscreen based on the task's windowing mode. * This class monitors task stack events, including task restarts and movements to the front, * to determine how bubbles should behave. It handles scenarios where bubbles should be expanded * or moved to fullscreen based on the task's windowing mode. This includes skipping split * task restarts, as they are handled by the split screen controller. * * @property bubbleController The [BubbleController] to manage bubble promotions and expansions. * @property bubbleData The [BubbleData] to access and update bubble information. Loading @@ -55,11 +56,11 @@ class BubbleTaskStackListener( clearedTask: Boolean, wasVisible: Boolean, ) { val taskId = task.taskId ProtoLog.d( WM_SHELL_BUBBLES_NOISY, "BubbleTaskStackListener.onActivityRestartAttempt(): taskId=%d", task.taskId) val taskId = task.taskId taskId) bubbleData.getBubbleInStackWithTaskId(taskId)?.let { bubble -> when { isBubbleToFullscreen(task) -> moveCollapsedInStackBubbleToFullscreen(bubble, task) Loading @@ -69,6 +70,19 @@ class BubbleTaskStackListener( } } override fun onTaskMovedToFront(task: ActivityManager.RunningTaskInfo) { val taskId = task.taskId ProtoLog.d( WM_SHELL_BUBBLES_NOISY, "BubbleTaskStackListener.onTaskMovedToFront(): taskId=%d", taskId) bubbleData.getBubbleInStackWithTaskId(taskId)?.let { bubble -> when { isBubbleToFullscreen(task) -> moveCollapsedInStackBubbleToFullscreen(bubble, task) } } } private fun isBubbleToSplit(task: ActivityManager.RunningTaskInfo): Boolean { return task.hasParentTask() && splitScreenController.get() .map { it.isTaskRootOrStageRoot(task.parentTaskId) } Loading Loading @@ -112,18 +126,6 @@ class BubbleTaskStackListener( task.taskId, bubble.key ) collapsedBubbleToFullscreenInternal(bubble, task) } /** Internal function to move a collapsed bubble to fullscreen task. */ private fun collapsedBubbleToFullscreenInternal( bubble: Bubble, task: ActivityManager.RunningTaskInfo, ) { ProtoLog.d( WM_SHELL_BUBBLES_NOISY, "BubbleTaskStackListener.collapsedBubbleToFullscreenInternal(): taskId=%d", task.taskId) val taskViewTaskController: TaskViewTaskController = bubble.taskView.controller val taskOrganizer: ShellTaskOrganizer = taskViewTaskController.taskOrganizer Loading libs/WindowManager/Shell/tests/util/src/com/android/wm/shell/bubbles/util/BubbleTestUtils.kt +3 −1 Original line number Diff line number Diff line Loading @@ -75,7 +75,9 @@ object BubbleTestUtils { /** Verifies the [WindowContainerTransaction] to exit Bubble. */ @JvmStatic fun verifyExitBubbleTransaction( wct: WindowContainerTransaction, taskToken: IBinder, captionInsetsOwner: IBinder? wct: WindowContainerTransaction, taskToken: IBinder, captionInsetsOwner: IBinder? = null, ) { // Verify hierarchy ops Loading Loading
libs/WindowManager/Shell/multivalentTests/src/com/android/wm/shell/bubbles/BubbleTaskStackListenerTest.kt +25 −0 Original line number Diff line number Diff line Loading @@ -195,4 +195,29 @@ class BubbleTaskStackListenerTest { verifyNoInteractions(taskOrganizer) verifyNoInteractions(taskViewTaskController) } @Test @EnableFlags( FLAG_ENABLE_CREATE_ANY_BUBBLE, FLAG_ENABLE_BUBBLE_ANYTHING, FLAG_EXCLUDE_TASK_FROM_RECENTS, FLAG_ENABLE_BUBBLE_APP_COMPAT_FIXES, ) fun onTaskMovedToFront_inStackAppBubbleToFullscreen_notifiesTaskRemoval() { task.configuration.windowConfiguration.windowingMode = WINDOWING_MODE_FULLSCREEN bubbleData.stub { on { getBubbleInStackWithTaskId(bubbleTaskId) } doReturn bubble } bubbleTaskStackListener.onTaskMovedToFront(task) val taskViewTaskController = bubble.taskView.controller val taskOrganizer = taskViewTaskController.taskOrganizer val wct = argumentCaptor<WindowContainerTransaction>().let { wctCaptor -> verify(taskOrganizer).applyTransaction(wctCaptor.capture()) wctCaptor.lastValue } verifyExitBubbleTransaction(wct, bubbleTaskToken.asBinder()) verify(taskViewTaskController).notifyTaskRemovalStarted(task) } }
libs/WindowManager/Shell/src/com/android/wm/shell/bubbles/BubbleTaskStackListener.kt +20 −18 Original line number Diff line number Diff line Loading @@ -34,11 +34,12 @@ import dagger.Lazy import java.util.Optional /** * Listens for task stack changes and handles bubble interactions when activities are restarted. * Listens for task stack changes to manage associated bubble interactions. * * This class monitors task stack events to determine how bubbles should behave when their * associated activities are restarted. It handles scenarios where bubbles should be expanded * or moved to fullscreen based on the task's windowing mode. * This class monitors task stack events, including task restarts and movements to the front, * to determine how bubbles should behave. It handles scenarios where bubbles should be expanded * or moved to fullscreen based on the task's windowing mode. This includes skipping split * task restarts, as they are handled by the split screen controller. * * @property bubbleController The [BubbleController] to manage bubble promotions and expansions. * @property bubbleData The [BubbleData] to access and update bubble information. Loading @@ -55,11 +56,11 @@ class BubbleTaskStackListener( clearedTask: Boolean, wasVisible: Boolean, ) { val taskId = task.taskId ProtoLog.d( WM_SHELL_BUBBLES_NOISY, "BubbleTaskStackListener.onActivityRestartAttempt(): taskId=%d", task.taskId) val taskId = task.taskId taskId) bubbleData.getBubbleInStackWithTaskId(taskId)?.let { bubble -> when { isBubbleToFullscreen(task) -> moveCollapsedInStackBubbleToFullscreen(bubble, task) Loading @@ -69,6 +70,19 @@ class BubbleTaskStackListener( } } override fun onTaskMovedToFront(task: ActivityManager.RunningTaskInfo) { val taskId = task.taskId ProtoLog.d( WM_SHELL_BUBBLES_NOISY, "BubbleTaskStackListener.onTaskMovedToFront(): taskId=%d", taskId) bubbleData.getBubbleInStackWithTaskId(taskId)?.let { bubble -> when { isBubbleToFullscreen(task) -> moveCollapsedInStackBubbleToFullscreen(bubble, task) } } } private fun isBubbleToSplit(task: ActivityManager.RunningTaskInfo): Boolean { return task.hasParentTask() && splitScreenController.get() .map { it.isTaskRootOrStageRoot(task.parentTaskId) } Loading Loading @@ -112,18 +126,6 @@ class BubbleTaskStackListener( task.taskId, bubble.key ) collapsedBubbleToFullscreenInternal(bubble, task) } /** Internal function to move a collapsed bubble to fullscreen task. */ private fun collapsedBubbleToFullscreenInternal( bubble: Bubble, task: ActivityManager.RunningTaskInfo, ) { ProtoLog.d( WM_SHELL_BUBBLES_NOISY, "BubbleTaskStackListener.collapsedBubbleToFullscreenInternal(): taskId=%d", task.taskId) val taskViewTaskController: TaskViewTaskController = bubble.taskView.controller val taskOrganizer: ShellTaskOrganizer = taskViewTaskController.taskOrganizer Loading
libs/WindowManager/Shell/tests/util/src/com/android/wm/shell/bubbles/util/BubbleTestUtils.kt +3 −1 Original line number Diff line number Diff line Loading @@ -75,7 +75,9 @@ object BubbleTestUtils { /** Verifies the [WindowContainerTransaction] to exit Bubble. */ @JvmStatic fun verifyExitBubbleTransaction( wct: WindowContainerTransaction, taskToken: IBinder, captionInsetsOwner: IBinder? wct: WindowContainerTransaction, taskToken: IBinder, captionInsetsOwner: IBinder? = null, ) { // Verify hierarchy ops Loading