Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit ef25cfa0 authored by Riddle Hsu's avatar Riddle Hsu
Browse files

Prevent new pip task from being added to recents

When swiping an auto-pip task with multiple activities,
the path to recents is from
r.reparent(rootTask...
 > ActivityRecord#onParentChanged
  > TaskFragment#setResumedActivity
   > ActivitTaskSupervisor$#updateTopResumedActivityIfNeeded
    > ATMS#setLastResumedActivityUncheckLocked
     > RecentTasks#add
Because the current implementation preserve fullscreen mode of
the activity until the transition finishes, the activity is
focusable temporarily.

By making the pip task non-focusable only for reparent,
updateTopResumedActivityIfNeeded won't detect a focus change
and it will early return without changing states.

Though the toggle of focusable might not be needed if
isPip2ExperimentEnabled is turned on (because the activity will be
pinned mode immediately), it won't affect the result so it should
be safe as a general logic.

Fix: 309120043
Test: RootWindowContainerTests#testMultipleActivitiesTaskEnterPip

Change-Id: Ia5c00ea3b62271cc4eb552e99b64eb9000fb4394
parent cf01f294
Loading
Loading
Loading
Loading
+5 −1
Original line number Diff line number Diff line
@@ -2171,12 +2171,16 @@ class RootWindowContainer extends WindowContainer<DisplayContent>
                    // now, it will take focus briefly which confuses the RecentTasks tracker.
                    rootTask.setWindowingMode(WINDOWING_MODE_PINNED);
                }

                // Temporarily disable focus when reparenting to avoid intermediate focus change
                // (because the task is on top and the activity is resumed), which could cause the
                // task to be added in recents task list unexpectedly.
                rootTask.setFocusable(false);
                // There are multiple activities in the task and moving the top activity should
                // reveal/leave the other activities in their original task.
                // On the other hand, ActivityRecord#onParentChanged takes care of setting the
                // up-to-dated root pinned task information on this newly created root task.
                r.reparent(rootTask, MAX_VALUE, reason);
                rootTask.setFocusable(true);

                // Ensure the leash of new task is in sync with its current bounds after reparent.
                rootTask.maybeApplyLastRecentsAnimationTransaction();
+25 −0
Original line number Diff line number Diff line
@@ -317,6 +317,31 @@ public class RootWindowContainerTests extends WindowTestsBase {
        assertTrue(firstActivity.mRequestForceTransition);
    }

    @Test
    public void testMultipleActivitiesTaskEnterPip() {
        // Enable shell transition because the order of setting windowing mode is different.
        registerTestTransitionPlayer();
        final ActivityRecord transientActivity = new ActivityBuilder(mAtm)
                .setCreateTask(true).build();
        final ActivityRecord activity1 = new ActivityBuilder(mAtm).setCreateTask(true).build();
        final ActivityRecord activity2 = new ActivityBuilder(mAtm)
                .setTask(activity1.getTask()).build();
        activity2.setState(RESUMED, "test");

        // Assume the top activity switches to a transient-launch, e.g. recents.
        transientActivity.setState(RESUMED, "test");
        transientActivity.getTask().moveToFront("test");

        mRootWindowContainer.moveActivityToPinnedRootTask(activity2,
                null /* launchIntoPipHostActivity */, "test");
        assertEquals("Created PiP task must not change focus", transientActivity.getTask(),
                mRootWindowContainer.getTopDisplayFocusedRootTask());
        final Task newPipTask = activity2.getTask();
        assertEquals(newPipTask, mDisplayContent.getDefaultTaskDisplayArea().getRootPinnedTask());
        assertNotEquals(newPipTask, activity1.getTask());
        assertFalse("Created PiP task must not be in recents", newPipTask.inRecents);
    }

    /**
     * When there is only one activity in the Task, and the activity is requesting to enter PIP, the
     * whole Task should enter PIP.