Loading services/core/java/com/android/server/wm/ActivityStarter.java +6 −6 Original line number Diff line number Diff line Loading @@ -2607,11 +2607,6 @@ class ActivityStarter { final Task launchStack = getLaunchStack(mStartActivity, mLaunchFlags, intentTask, mOptions); if (launchStack == null || launchStack == mTargetStack) { // Do not set mMovedToFront to true below for split-screen-top stack, or // START_TASK_TO_FRONT will be returned and trigger unexpected animations when a // new intent has delivered. final boolean isSplitScreenTopStack = mTargetStack.isTopSplitScreenStack(); // TODO(b/151572268): Figure out a better way to move tasks in above 2-levels // tasks hierarchies. if (mTargetStack != intentTask Loading @@ -2620,6 +2615,11 @@ class ActivityStarter { false /* includingParents */); intentTask = intentTask.getParent().asTask(); } // If the task is in multi-windowing mode, the activity may already be on // the top (visible to user but not the global top), then the result code // should be START_DELIVERED_TO_TOP instead of START_TASK_TO_FRONT. final boolean wasTopOfVisibleRootTask = intentActivity.mVisibleRequested && intentActivity == mTargetStack.topRunningActivity(); // We only want to move to the front, if we aren't going to launch on a // different stack. If we launch on a different stack, we will put the // task on top there. Loading @@ -2628,7 +2628,7 @@ class ActivityStarter { mTargetStack.moveTaskToFront(intentTask, mNoAnimation, mOptions, mStartActivity.appTimeTracker, DEFER_RESUME, "bringingFoundTaskToFront"); mMovedToFront = !isSplitScreenTopStack; mMovedToFront = !wasTopOfVisibleRootTask; } else { intentTask.reparent(launchStack, ON_TOP, REPARENT_MOVE_ROOT_TASK_TO_FRONT, ANIMATE, DEFER_RESUME, "reparentToTargetStack"); Loading services/tests/wmtests/src/com/android/server/wm/ActivityStarterTests.java +29 −26 Original line number Diff line number Diff line Loading @@ -33,7 +33,6 @@ import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD; import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN; import static android.app.WindowConfiguration.WINDOWING_MODE_PINNED; import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMARY; import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY; import static android.content.Intent.FLAG_ACTIVITY_LAUNCH_ADJACENT; import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK; import static android.content.Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED; Loading Loading @@ -84,6 +83,7 @@ import android.os.Process; import android.os.RemoteException; import android.platform.test.annotations.Presubmit; import android.service.voice.IVoiceInteractionSession; import android.util.Pair; import android.view.Gravity; import androidx.test.filters.SmallTest; Loading Loading @@ -434,17 +434,12 @@ public class ActivityStarterTests extends WindowTestsBase { final ActivityStarter starter = prepareStarter( FLAG_ACTIVITY_RESET_TASK_IF_NEEDED | FLAG_ACTIVITY_SINGLE_TOP, false /* mockGetLaunchStack */); final ActivityRecord splitPrimaryFocusActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); final ActivityRecord splitSecondReusableActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); splitPrimaryFocusActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY); splitSecondReusableActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_SECONDARY); final Pair<ActivityRecord, ActivityRecord> activities = createActivitiesInSplit(); final ActivityRecord splitPrimaryFocusActivity = activities.first; final ActivityRecord splitSecondReusableActivity = activities.second; // Set focus back to primary. splitPrimaryFocusActivity.getRootTask().moveToFront("testSplitScreenDeliverToTop"); splitPrimaryFocusActivity.moveFocusableActivityToTop("testSplitScreenDeliverToTop"); // Start activity and delivered new intent. starter.getIntent().setComponent(splitSecondReusableActivity.mActivityComponent); Loading @@ -463,24 +458,15 @@ public class ActivityStarterTests extends WindowTestsBase { public void testSplitScreenTaskToFront() { final ActivityStarter starter = prepareStarter( FLAG_ACTIVITY_RESET_TASK_IF_NEEDED | FLAG_ACTIVITY_SINGLE_TOP, false); final ActivityRecord splitSecondReusableActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); final ActivityRecord splitSecondTopActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); final ActivityRecord splitPrimaryFocusActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); splitPrimaryFocusActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY); splitSecondReusableActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_SECONDARY); splitSecondTopActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_SECONDARY); // Make it on top of split-screen-secondary. splitSecondTopActivity.getRootTask().moveToFront("testSplitScreenTaskToFront"); final Pair<ActivityRecord, ActivityRecord> activities = createActivitiesInSplit(); final ActivityRecord splitPrimaryFocusActivity = activities.first; final ActivityRecord splitSecondReusableActivity = activities.second; final ActivityRecord splitSecondTopActivity = new ActivityBuilder(mAtm).setCreateTask(true) .setParentTask(splitSecondReusableActivity.getRootTask()).build(); assertTrue(splitSecondTopActivity.inSplitScreenSecondaryWindowingMode()); // Let primary stack has focus. splitPrimaryFocusActivity.getRootTask().moveToFront("testSplitScreenTaskToFront"); splitPrimaryFocusActivity.moveFocusableActivityToTop("testSplitScreenTaskToFront"); // Start activity and delivered new intent. starter.getIntent().setComponent(splitSecondReusableActivity.mActivityComponent); Loading @@ -491,6 +477,23 @@ public class ActivityStarterTests extends WindowTestsBase { assertEquals(START_TASK_TO_FRONT, result); } /** Returns 2 activities. The first is in primary and the second is in secondary. */ private Pair<ActivityRecord, ActivityRecord> createActivitiesInSplit() { final TestSplitOrganizer splitOrg = new TestSplitOrganizer(mAtm); // The fullscreen windowing mode activity will be moved to split-secondary by // TestSplitOrganizer when a split-primary task appears. final ActivityRecord splitSecondActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); final ActivityRecord splitPrimaryActivity = new TaskBuilder(mSupervisor) .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY).setCreateActivity(true) .build().getTopMostActivity(); splitPrimaryActivity.mVisibleRequested = splitSecondActivity.mVisibleRequested = true; assertEquals(splitOrg.mPrimary, splitPrimaryActivity.getRootTask()); assertEquals(splitOrg.mSecondary, splitSecondActivity.getRootTask()); return Pair.create(splitPrimaryActivity, splitSecondActivity); } /** * Tests activity is cleaned up properly in a task mode violation. */ Loading services/tests/wmtests/src/com/android/server/wm/WindowTestsBase.java +3 −0 Original line number Diff line number Diff line Loading @@ -1045,6 +1045,9 @@ class WindowTestsBase extends SystemServiceTestsBase { spyOn(task); task.mUserId = mUserId; Task rootTask = task.getRootTask(); if (task != rootTask && !Mockito.mockingDetails(rootTask).isSpy()) { spyOn(rootTask); } doNothing().when(rootTask).startActivityLocked( any(), any(), anyBoolean(), anyBoolean(), any()); Loading Loading
services/core/java/com/android/server/wm/ActivityStarter.java +6 −6 Original line number Diff line number Diff line Loading @@ -2607,11 +2607,6 @@ class ActivityStarter { final Task launchStack = getLaunchStack(mStartActivity, mLaunchFlags, intentTask, mOptions); if (launchStack == null || launchStack == mTargetStack) { // Do not set mMovedToFront to true below for split-screen-top stack, or // START_TASK_TO_FRONT will be returned and trigger unexpected animations when a // new intent has delivered. final boolean isSplitScreenTopStack = mTargetStack.isTopSplitScreenStack(); // TODO(b/151572268): Figure out a better way to move tasks in above 2-levels // tasks hierarchies. if (mTargetStack != intentTask Loading @@ -2620,6 +2615,11 @@ class ActivityStarter { false /* includingParents */); intentTask = intentTask.getParent().asTask(); } // If the task is in multi-windowing mode, the activity may already be on // the top (visible to user but not the global top), then the result code // should be START_DELIVERED_TO_TOP instead of START_TASK_TO_FRONT. final boolean wasTopOfVisibleRootTask = intentActivity.mVisibleRequested && intentActivity == mTargetStack.topRunningActivity(); // We only want to move to the front, if we aren't going to launch on a // different stack. If we launch on a different stack, we will put the // task on top there. Loading @@ -2628,7 +2628,7 @@ class ActivityStarter { mTargetStack.moveTaskToFront(intentTask, mNoAnimation, mOptions, mStartActivity.appTimeTracker, DEFER_RESUME, "bringingFoundTaskToFront"); mMovedToFront = !isSplitScreenTopStack; mMovedToFront = !wasTopOfVisibleRootTask; } else { intentTask.reparent(launchStack, ON_TOP, REPARENT_MOVE_ROOT_TASK_TO_FRONT, ANIMATE, DEFER_RESUME, "reparentToTargetStack"); Loading
services/tests/wmtests/src/com/android/server/wm/ActivityStarterTests.java +29 −26 Original line number Diff line number Diff line Loading @@ -33,7 +33,6 @@ import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD; import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN; import static android.app.WindowConfiguration.WINDOWING_MODE_PINNED; import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMARY; import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY; import static android.content.Intent.FLAG_ACTIVITY_LAUNCH_ADJACENT; import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK; import static android.content.Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED; Loading Loading @@ -84,6 +83,7 @@ import android.os.Process; import android.os.RemoteException; import android.platform.test.annotations.Presubmit; import android.service.voice.IVoiceInteractionSession; import android.util.Pair; import android.view.Gravity; import androidx.test.filters.SmallTest; Loading Loading @@ -434,17 +434,12 @@ public class ActivityStarterTests extends WindowTestsBase { final ActivityStarter starter = prepareStarter( FLAG_ACTIVITY_RESET_TASK_IF_NEEDED | FLAG_ACTIVITY_SINGLE_TOP, false /* mockGetLaunchStack */); final ActivityRecord splitPrimaryFocusActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); final ActivityRecord splitSecondReusableActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); splitPrimaryFocusActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY); splitSecondReusableActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_SECONDARY); final Pair<ActivityRecord, ActivityRecord> activities = createActivitiesInSplit(); final ActivityRecord splitPrimaryFocusActivity = activities.first; final ActivityRecord splitSecondReusableActivity = activities.second; // Set focus back to primary. splitPrimaryFocusActivity.getRootTask().moveToFront("testSplitScreenDeliverToTop"); splitPrimaryFocusActivity.moveFocusableActivityToTop("testSplitScreenDeliverToTop"); // Start activity and delivered new intent. starter.getIntent().setComponent(splitSecondReusableActivity.mActivityComponent); Loading @@ -463,24 +458,15 @@ public class ActivityStarterTests extends WindowTestsBase { public void testSplitScreenTaskToFront() { final ActivityStarter starter = prepareStarter( FLAG_ACTIVITY_RESET_TASK_IF_NEEDED | FLAG_ACTIVITY_SINGLE_TOP, false); final ActivityRecord splitSecondReusableActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); final ActivityRecord splitSecondTopActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); final ActivityRecord splitPrimaryFocusActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); splitPrimaryFocusActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY); splitSecondReusableActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_SECONDARY); splitSecondTopActivity.getRootTask() .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_SECONDARY); // Make it on top of split-screen-secondary. splitSecondTopActivity.getRootTask().moveToFront("testSplitScreenTaskToFront"); final Pair<ActivityRecord, ActivityRecord> activities = createActivitiesInSplit(); final ActivityRecord splitPrimaryFocusActivity = activities.first; final ActivityRecord splitSecondReusableActivity = activities.second; final ActivityRecord splitSecondTopActivity = new ActivityBuilder(mAtm).setCreateTask(true) .setParentTask(splitSecondReusableActivity.getRootTask()).build(); assertTrue(splitSecondTopActivity.inSplitScreenSecondaryWindowingMode()); // Let primary stack has focus. splitPrimaryFocusActivity.getRootTask().moveToFront("testSplitScreenTaskToFront"); splitPrimaryFocusActivity.moveFocusableActivityToTop("testSplitScreenTaskToFront"); // Start activity and delivered new intent. starter.getIntent().setComponent(splitSecondReusableActivity.mActivityComponent); Loading @@ -491,6 +477,23 @@ public class ActivityStarterTests extends WindowTestsBase { assertEquals(START_TASK_TO_FRONT, result); } /** Returns 2 activities. The first is in primary and the second is in secondary. */ private Pair<ActivityRecord, ActivityRecord> createActivitiesInSplit() { final TestSplitOrganizer splitOrg = new TestSplitOrganizer(mAtm); // The fullscreen windowing mode activity will be moved to split-secondary by // TestSplitOrganizer when a split-primary task appears. final ActivityRecord splitSecondActivity = new ActivityBuilder(mAtm).setCreateTask(true).build(); final ActivityRecord splitPrimaryActivity = new TaskBuilder(mSupervisor) .setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY).setCreateActivity(true) .build().getTopMostActivity(); splitPrimaryActivity.mVisibleRequested = splitSecondActivity.mVisibleRequested = true; assertEquals(splitOrg.mPrimary, splitPrimaryActivity.getRootTask()); assertEquals(splitOrg.mSecondary, splitSecondActivity.getRootTask()); return Pair.create(splitPrimaryActivity, splitSecondActivity); } /** * Tests activity is cleaned up properly in a task mode violation. */ Loading
services/tests/wmtests/src/com/android/server/wm/WindowTestsBase.java +3 −0 Original line number Diff line number Diff line Loading @@ -1045,6 +1045,9 @@ class WindowTestsBase extends SystemServiceTestsBase { spyOn(task); task.mUserId = mUserId; Task rootTask = task.getRootTask(); if (task != rootTask && !Mockito.mockingDetails(rootTask).isSpy()) { spyOn(rootTask); } doNothing().when(rootTask).startActivityLocked( any(), any(), anyBoolean(), anyBoolean(), any()); Loading