Fixes some issues for embedded Task
1. Don't compute minimum dimensions for embeddedTask in TaskFragment
2. Consider TaskFragment containing ActivityRecord and embedded Task in
Task#getTopResumed(Pausing)Activity
3. Add support to start Activity on top of existing embedded Task in
TaskFragment
Test: SplitActivityLifecycleTest
Bug: 192442647
Change-Id: I8c0988e5070053c6a3b336184aa0a9ebd79adfda
diff --git a/services/core/java/com/android/server/wm/ActivityStarter.java b/services/core/java/com/android/server/wm/ActivityStarter.java
index 3b43e48..d1f50f3 100644
--- a/services/core/java/com/android/server/wm/ActivityStarter.java
+++ b/services/core/java/com/android/server/wm/ActivityStarter.java
@@ -2778,7 +2778,9 @@
// request. If the task was resolved and different than mInTaskFragment, reparent the
// task to mInTaskFragment for embedding.
if (mInTaskFragment.getTask() != task) {
- task.reparent(mInTaskFragment, POSITION_TOP);
+ if (shouldReparentInTaskFragment(task)) {
+ task.reparent(mInTaskFragment, POSITION_TOP);
+ }
} else {
newParent = mInTaskFragment;
}
@@ -2797,6 +2799,18 @@
}
}
+ private boolean shouldReparentInTaskFragment(Task task) {
+ // The task has not been embedded. We should reparent the task to TaskFragment.
+ if (!task.isEmbedded()) {
+ return true;
+ }
+ WindowContainer<?> parent = task.getParent();
+ // If the Activity is going to launch on top of embedded Task in the same TaskFragment,
+ // we don't need to reparent the Task. Otherwise, the embedded Task should reparent to
+ // another TaskFragment.
+ return parent.asTaskFragment() != mInTaskFragment;
+ }
+
private int adjustLaunchFlagsToDocumentMode(ActivityRecord r, boolean launchSingleInstance,
boolean launchSingleTask, int launchFlags) {
if ((launchFlags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0 &&
diff --git a/services/core/java/com/android/server/wm/Task.java b/services/core/java/com/android/server/wm/Task.java
index 424a5aa..ef3065e 100644
--- a/services/core/java/com/android/server/wm/Task.java
+++ b/services/core/java/com/android/server/wm/Task.java
@@ -1226,7 +1226,7 @@
mRootWindowContainer.updateUIDsPresentOnDisplay();
}
- /** Returns the currently topmost resumed activity. */
+ @Override
@Nullable
ActivityRecord getTopResumedActivity() {
if (!isLeafTask()) {
@@ -1243,15 +1243,7 @@
for (int i = mChildren.size() - 1; i >= 0; --i) {
final WindowContainer child = mChildren.get(i);
if (child.asTaskFragment() != null) {
- final ActivityRecord[] resumedActivity = new ActivityRecord[1];
- child.asTaskFragment().forAllLeafTaskFragments(fragment -> {
- if (fragment.getResumedActivity() != null) {
- resumedActivity[0] = fragment.getResumedActivity();
- return true;
- }
- return false;
- });
- topResumedActivity = resumedActivity[0];
+ topResumedActivity = child.asTaskFragment().getTopResumedActivity();
} else if (taskResumedActivity != null
&& child.asActivityRecord() == taskResumedActivity) {
topResumedActivity = taskResumedActivity;
@@ -1263,9 +1255,7 @@
return null;
}
- /**
- * Returns the currently topmost pausing activity.
- */
+ @Override
@Nullable
ActivityRecord getTopPausingActivity() {
if (!isLeafTask()) {
@@ -1282,15 +1272,7 @@
for (int i = mChildren.size() - 1; i >= 0; --i) {
final WindowContainer child = mChildren.get(i);
if (child.asTaskFragment() != null) {
- final ActivityRecord[] pausingActivity = new ActivityRecord[1];
- child.asTaskFragment().forAllLeafTaskFragments(fragment -> {
- if (fragment.getPausingActivity() != null) {
- pausingActivity[0] = fragment.getPausingActivity();
- return true;
- }
- return false;
- });
- topPausingActivity = pausingActivity[0];
+ topPausingActivity = child.asTaskFragment().getTopPausingActivity();
} else if (taskPausingActivity != null
&& child.asActivityRecord() == taskPausingActivity) {
topPausingActivity = taskPausingActivity;
diff --git a/services/core/java/com/android/server/wm/TaskFragment.java b/services/core/java/com/android/server/wm/TaskFragment.java
index ca1d83e..3cebd73 100644
--- a/services/core/java/com/android/server/wm/TaskFragment.java
+++ b/services/core/java/com/android/server/wm/TaskFragment.java
@@ -352,7 +352,29 @@
return mAdjacentTaskFragment;
}
- /** @return the currently resumed activity. */
+ /** Returns the currently topmost resumed activity. */
+ @Nullable
+ ActivityRecord getTopResumedActivity() {
+ final ActivityRecord taskFragResumedActivity = getResumedActivity();
+ for (int i = getChildCount() - 1; i >= 0; --i) {
+ WindowContainer<?> child = getChildAt(i);
+ ActivityRecord topResumedActivity = null;
+ if (taskFragResumedActivity != null && child == taskFragResumedActivity) {
+ topResumedActivity = child.asActivityRecord();
+ } else if (child.asTaskFragment() != null) {
+ topResumedActivity = child.asTaskFragment().getTopResumedActivity();
+ }
+ if (topResumedActivity != null) {
+ return topResumedActivity;
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Returns the currently resumed activity in this TaskFragment's
+ * {@link #mChildren direct children}
+ */
ActivityRecord getResumedActivity() {
return mResumedActivity;
}
@@ -376,6 +398,25 @@
mPausingActivity = pausing;
}
+ /** Returns the currently topmost pausing activity. */
+ @Nullable
+ ActivityRecord getTopPausingActivity() {
+ final ActivityRecord taskFragPausingActivity = getPausingActivity();
+ for (int i = getChildCount() - 1; i >= 0; --i) {
+ WindowContainer<?> child = getChildAt(i);
+ ActivityRecord topPausingActivity = null;
+ if (taskFragPausingActivity != null && child == taskFragPausingActivity) {
+ topPausingActivity = child.asActivityRecord();
+ } else if (child.asTaskFragment() != null) {
+ topPausingActivity = child.asTaskFragment().getTopPausingActivity();
+ }
+ if (topPausingActivity != null) {
+ return topPausingActivity;
+ }
+ }
+ return null;
+ }
+
ActivityRecord getPausingActivity() {
return mPausingActivity;
}
@@ -1673,7 +1714,9 @@
}
final Task thisTask = asTask();
- if (thisTask != null) {
+ // Embedded Task's configuration should go with parent TaskFragment, so we don't re-compute
+ // configuration here.
+ if (thisTask != null && !thisTask.isEmbedded()) {
thisTask.resolveLeafTaskOnlyOverrideConfigs(newParentConfig,
mTmpBounds /* previousBounds */);
}