Merge "Embedded Activities in TaskFragments" into sc-v2-dev
This commit is contained in:
@@ -20,7 +20,6 @@ import static android.app.WindowConfiguration.WindowingMode;
|
||||
|
||||
import android.annotation.NonNull;
|
||||
import android.annotation.Nullable;
|
||||
import android.content.ComponentName;
|
||||
import android.content.res.Configuration;
|
||||
import android.os.IBinder;
|
||||
import android.os.Parcel;
|
||||
@@ -39,13 +38,6 @@ public final class TaskFragmentInfo implements Parcelable {
|
||||
@NonNull
|
||||
private final IBinder mFragmentToken;
|
||||
|
||||
/**
|
||||
* The component name of the initial root activity of this TaskFragment, which will be used
|
||||
* to configure the relationships for TaskFragments.
|
||||
*/
|
||||
@NonNull
|
||||
private final ComponentName mInitialComponentName;
|
||||
|
||||
@NonNull
|
||||
private final WindowContainerToken mToken;
|
||||
|
||||
@@ -59,14 +51,12 @@ public final class TaskFragmentInfo implements Parcelable {
|
||||
private final boolean mIsVisible;
|
||||
|
||||
public TaskFragmentInfo(
|
||||
@NonNull IBinder fragmentToken, @NonNull ComponentName initialComponentName,
|
||||
@NonNull WindowContainerToken token, @NonNull Configuration configuration,
|
||||
boolean isEmpty, boolean isVisible) {
|
||||
if (fragmentToken == null || initialComponentName == null) {
|
||||
@NonNull IBinder fragmentToken, @NonNull WindowContainerToken token,
|
||||
@NonNull Configuration configuration, boolean isEmpty, boolean isVisible) {
|
||||
if (fragmentToken == null) {
|
||||
throw new IllegalArgumentException("Invalid TaskFragmentInfo.");
|
||||
}
|
||||
mFragmentToken = fragmentToken;
|
||||
mInitialComponentName = initialComponentName;
|
||||
mToken = token;
|
||||
mConfiguration.setTo(configuration);
|
||||
mIsEmpty = isEmpty;
|
||||
@@ -77,10 +67,6 @@ public final class TaskFragmentInfo implements Parcelable {
|
||||
return mFragmentToken;
|
||||
}
|
||||
|
||||
public ComponentName getInitialComponentName() {
|
||||
return mInitialComponentName;
|
||||
}
|
||||
|
||||
public WindowContainerToken getToken() {
|
||||
return mToken;
|
||||
}
|
||||
@@ -112,7 +98,6 @@ public final class TaskFragmentInfo implements Parcelable {
|
||||
}
|
||||
|
||||
return mFragmentToken.equals(that.mFragmentToken)
|
||||
&& mInitialComponentName.equals(that.mInitialComponentName)
|
||||
&& mToken.equals(that.mToken)
|
||||
&& mIsEmpty == that.mIsEmpty
|
||||
&& mIsVisible == that.mIsVisible
|
||||
@@ -121,7 +106,6 @@ public final class TaskFragmentInfo implements Parcelable {
|
||||
|
||||
private TaskFragmentInfo(Parcel in) {
|
||||
mFragmentToken = in.readStrongBinder();
|
||||
mInitialComponentName = in.readTypedObject(ComponentName.CREATOR);
|
||||
mToken = in.readTypedObject(WindowContainerToken.CREATOR);
|
||||
mConfiguration.readFromParcel(in);
|
||||
mIsEmpty = in.readBoolean();
|
||||
@@ -131,7 +115,6 @@ public final class TaskFragmentInfo implements Parcelable {
|
||||
@Override
|
||||
public void writeToParcel(@NonNull Parcel dest, int flags) {
|
||||
dest.writeStrongBinder(mFragmentToken);
|
||||
dest.writeTypedObject(mInitialComponentName, flags);
|
||||
dest.writeTypedObject(mToken, flags);
|
||||
mConfiguration.writeToParcel(dest, flags);
|
||||
dest.writeBoolean(mIsEmpty);
|
||||
@@ -156,7 +139,6 @@ public final class TaskFragmentInfo implements Parcelable {
|
||||
public String toString() {
|
||||
return "TaskFragmentInfo{"
|
||||
+ " fragmentToken=" + mFragmentToken
|
||||
+ " initialComponentName=" + mInitialComponentName
|
||||
+ " token=" + mToken
|
||||
+ " isEmpty=" + mIsEmpty
|
||||
+ " isVisible=" + mIsVisible
|
||||
|
||||
@@ -27,6 +27,7 @@ import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_ATM;
|
||||
import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_WITH_CLASS_NAME;
|
||||
import static com.android.server.wm.ActivityTaskSupervisor.ON_TOP;
|
||||
|
||||
import android.annotation.NonNull;
|
||||
import android.annotation.Nullable;
|
||||
import android.app.ActivityOptions;
|
||||
import android.app.IApplicationThread;
|
||||
@@ -38,6 +39,7 @@ import android.content.pm.ApplicationInfo;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.content.pm.ResolveInfo;
|
||||
import android.os.Binder;
|
||||
import android.os.Bundle;
|
||||
import android.os.IBinder;
|
||||
import android.os.UserHandle;
|
||||
import android.provider.Settings;
|
||||
@@ -488,6 +490,16 @@ public class ActivityStartController {
|
||||
return START_SUCCESS;
|
||||
}
|
||||
|
||||
void startActivityInTaskFragment(@NonNull TaskFragment taskFragment,
|
||||
@NonNull Intent activityIntent, @Nullable Bundle activityOptions) {
|
||||
obtainStarter(activityIntent, "startActivityInTaskFragment")
|
||||
.setActivityOptions(activityOptions)
|
||||
.setInTaskFragment(taskFragment)
|
||||
.setCallingUid(Binder.getCallingUid())
|
||||
.setCallingPid(Binder.getCallingPid())
|
||||
.execute();
|
||||
}
|
||||
|
||||
void registerRemoteAnimationForNextActivityStart(String packageName,
|
||||
RemoteAnimationAdapter adapter) {
|
||||
mPendingRemoteAnimationRegistry.addPendingAnimation(packageName, adapter);
|
||||
|
||||
@@ -177,6 +177,7 @@ class ActivityStarter {
|
||||
private int mPreferredWindowingMode;
|
||||
|
||||
private Task mInTask;
|
||||
private TaskFragment mInTaskFragment;
|
||||
@VisibleForTesting
|
||||
boolean mAddingToTask;
|
||||
private Task mReuseTask;
|
||||
@@ -342,6 +343,7 @@ class ActivityStarter {
|
||||
boolean avoidMoveToFront;
|
||||
ActivityRecord[] outActivity;
|
||||
Task inTask;
|
||||
TaskFragment inTaskFragment;
|
||||
String reason;
|
||||
ProfilerInfo profilerInfo;
|
||||
Configuration globalConfig;
|
||||
@@ -392,6 +394,7 @@ class ActivityStarter {
|
||||
componentSpecified = false;
|
||||
outActivity = null;
|
||||
inTask = null;
|
||||
inTaskFragment = null;
|
||||
reason = null;
|
||||
profilerInfo = null;
|
||||
globalConfig = null;
|
||||
@@ -407,7 +410,7 @@ class ActivityStarter {
|
||||
/**
|
||||
* Adopts all values from passed in request.
|
||||
*/
|
||||
void set(Request request) {
|
||||
void set(@NonNull Request request) {
|
||||
caller = request.caller;
|
||||
intent = request.intent;
|
||||
intentGrants = request.intentGrants;
|
||||
@@ -432,6 +435,7 @@ class ActivityStarter {
|
||||
componentSpecified = request.componentSpecified;
|
||||
outActivity = request.outActivity;
|
||||
inTask = request.inTask;
|
||||
inTaskFragment = request.inTaskFragment;
|
||||
reason = request.reason;
|
||||
profilerInfo = request.profilerInfo;
|
||||
globalConfig = request.globalConfig;
|
||||
@@ -574,6 +578,7 @@ class ActivityStarter {
|
||||
mPreferredWindowingMode = starter.mPreferredWindowingMode;
|
||||
|
||||
mInTask = starter.mInTask;
|
||||
mInTaskFragment = starter.mInTaskFragment;
|
||||
mAddingToTask = starter.mAddingToTask;
|
||||
mReuseTask = starter.mReuseTask;
|
||||
|
||||
@@ -835,6 +840,7 @@ class ActivityStarter {
|
||||
final int startFlags = request.startFlags;
|
||||
final SafeActivityOptions options = request.activityOptions;
|
||||
Task inTask = request.inTask;
|
||||
mInTaskFragment = request.inTaskFragment;
|
||||
|
||||
int err = ActivityManager.START_SUCCESS;
|
||||
// Pull the optional Ephemeral Installer-only bundle out of the options early.
|
||||
@@ -2204,6 +2210,7 @@ class ActivityStarter {
|
||||
mPreferredWindowingMode = WINDOWING_MODE_UNDEFINED;
|
||||
|
||||
mInTask = null;
|
||||
mInTaskFragment = null;
|
||||
mAddingToTask = false;
|
||||
mReuseTask = null;
|
||||
|
||||
@@ -2691,11 +2698,23 @@ class ActivityStarter {
|
||||
mIntentDelivered = true;
|
||||
}
|
||||
|
||||
private void addOrReparentStartingActivity(Task parent, String reason) {
|
||||
if (mStartActivity.getTask() == null || mStartActivity.getTask() == parent) {
|
||||
parent.addChild(mStartActivity);
|
||||
private void addOrReparentStartingActivity(@NonNull Task task, String reason) {
|
||||
TaskFragment newParent = task;
|
||||
if (mInTaskFragment != null) {
|
||||
// mInTaskFragment is created and added to the leaf task by task fragment organizer's
|
||||
// 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);
|
||||
} else {
|
||||
newParent = mInTaskFragment;
|
||||
}
|
||||
}
|
||||
if (mStartActivity.getTaskFragment() == null
|
||||
|| mStartActivity.getTaskFragment() == newParent) {
|
||||
newParent.addChild(mStartActivity, POSITION_TOP);
|
||||
} else {
|
||||
mStartActivity.reparent(parent, parent.getChildCount() /* top */, reason);
|
||||
mStartActivity.reparent(newParent, newParent.getChildCount() /* top */, reason);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2927,6 +2946,11 @@ class ActivityStarter {
|
||||
return this;
|
||||
}
|
||||
|
||||
ActivityStarter setInTaskFragment(TaskFragment taskFragment) {
|
||||
mRequest.inTaskFragment = taskFragment;
|
||||
return this;
|
||||
}
|
||||
|
||||
ActivityStarter setWaitResult(WaitResult result) {
|
||||
mRequest.waitResult = result;
|
||||
return this;
|
||||
@@ -3010,5 +3034,7 @@ class ActivityStarter {
|
||||
pw.print(mDoResume);
|
||||
pw.print(" mAddingToTask=");
|
||||
pw.println(mAddingToTask);
|
||||
pw.print(" mInTaskFragment=");
|
||||
pw.println(mInTaskFragment);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -629,7 +629,7 @@ class Task extends TaskFragment {
|
||||
IVoiceInteractionSession _voiceSession, IVoiceInteractor _voiceInteractor,
|
||||
boolean _createdByOrganizer, IBinder _launchCookie, boolean _deferTaskAppear,
|
||||
boolean _removeWithTaskOrganizer) {
|
||||
super(atmService, _createdByOrganizer);
|
||||
super(atmService, null /* fragmentToken */, _createdByOrganizer);
|
||||
|
||||
mTaskId = _taskId;
|
||||
mUserId = _userId;
|
||||
@@ -643,7 +643,6 @@ class Task extends TaskFragment {
|
||||
: new PersistedTaskSnapshotData();
|
||||
// Tasks have no set orientation value (including SCREEN_ORIENTATION_UNSPECIFIED).
|
||||
setOrientation(SCREEN_ORIENTATION_UNSET);
|
||||
mRemoteToken = new RemoteToken(this);
|
||||
affinityIntent = _affinityIntent;
|
||||
affinity = _affinity;
|
||||
rootAffinity = _rootAffinity;
|
||||
@@ -4976,7 +4975,6 @@ class Task extends TaskFragment {
|
||||
// Slot the activity into the history root task and proceed
|
||||
ProtoLog.i(WM_DEBUG_ADD_REMOVE, "Adding activity %s to task %s "
|
||||
+ "callers: %s", r, task, new RuntimeException("here").fillInStackTrace());
|
||||
task.positionChildAtTop(r);
|
||||
|
||||
// The transition animation and starting window are not needed if {@code allowMoveToFront}
|
||||
// is false, because the activity won't be visible.
|
||||
|
||||
@@ -74,7 +74,6 @@ import android.app.servertransaction.ClientTransaction;
|
||||
import android.app.servertransaction.NewIntentItem;
|
||||
import android.app.servertransaction.PauseActivityItem;
|
||||
import android.app.servertransaction.ResumeActivityItem;
|
||||
import android.content.ComponentName;
|
||||
import android.content.res.Configuration;
|
||||
import android.graphics.Rect;
|
||||
import android.os.IBinder;
|
||||
@@ -155,6 +154,9 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
*/
|
||||
int mMinHeight;
|
||||
|
||||
/** Avoid reentrant of {@link #removeImmediately()}. */
|
||||
private boolean mRemoving;
|
||||
|
||||
// The TaskFragment that adjacent to this one.
|
||||
private TaskFragment mAdjacentTaskFragment;
|
||||
|
||||
@@ -196,23 +198,13 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
boolean mCreatedByOrganizer;
|
||||
|
||||
/** Organizer that organizing this TaskFragment. */
|
||||
// TODO(b/190433129) set the value when creating TaskFragment from WCT.
|
||||
@Nullable
|
||||
private ITaskFragmentOrganizer mTaskFragmentOrganizer;
|
||||
|
||||
/** Client assigned unique token for this TaskFragment if this is created by an organizer. */
|
||||
// TODO(b/190433129) set the value when creating TaskFragment from WCT.
|
||||
@Nullable
|
||||
private IBinder mFragmentToken;
|
||||
|
||||
/**
|
||||
* The component name of the root activity that initiated this TaskFragment, which will be used
|
||||
* to configure the relationships for TaskFragments.
|
||||
*/
|
||||
// TODO(b/190433129) set the value when creating TaskFragment from WCT.
|
||||
@Nullable
|
||||
private ComponentName mInitialComponentName;
|
||||
|
||||
private final Rect mTmpInsets = new Rect();
|
||||
private final Rect mTmpBounds = new Rect();
|
||||
private final Rect mTmpFullBounds = new Rect();
|
||||
@@ -260,15 +252,18 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
}
|
||||
}
|
||||
|
||||
TaskFragment(ActivityTaskManagerService atmService, boolean createdByOrganizer) {
|
||||
TaskFragment(ActivityTaskManagerService atmService, IBinder fragmentToken,
|
||||
boolean createdByOrganizer) {
|
||||
super(atmService.mWindowManager);
|
||||
|
||||
mAtmService = atmService;
|
||||
mTaskSupervisor = atmService.mTaskSupervisor;
|
||||
mTaskSupervisor = mAtmService.mTaskSupervisor;
|
||||
mRootWindowContainer = mAtmService.mRootWindowContainer;
|
||||
mCreatedByOrganizer = createdByOrganizer;
|
||||
mTaskFragmentOrganizerController =
|
||||
mAtmService.mWindowOrganizerController.mTaskFragmentOrganizerController;
|
||||
mFragmentToken = fragmentToken;
|
||||
mRemoteToken = new RemoteToken(this);
|
||||
}
|
||||
|
||||
void setAdjacentTaskFragment(TaskFragment taskFragment) {
|
||||
@@ -276,6 +271,10 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
taskFragment.mAdjacentTaskFragment = this;
|
||||
}
|
||||
|
||||
void setTaskFragmentOrganizer(ITaskFragmentOrganizer organizer) {
|
||||
mTaskFragmentOrganizer = organizer;
|
||||
}
|
||||
|
||||
TaskFragment getAdjacentTaskFragment() {
|
||||
return mAdjacentTaskFragment;
|
||||
}
|
||||
@@ -1981,7 +1980,6 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
}
|
||||
}
|
||||
|
||||
// TODO(b/190433129) call when TaskFragment is removed from WCT#deleteTaskFragment
|
||||
private void sendTaskFragmentVanished() {
|
||||
if (mTaskFragmentOrganizer != null) {
|
||||
mTaskFragmentOrganizerController.onTaskFragmentVanished(mTaskFragmentOrganizer, this);
|
||||
@@ -1995,7 +1993,6 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
TaskFragmentInfo getTaskFragmentInfo() {
|
||||
return new TaskFragmentInfo(
|
||||
mFragmentToken,
|
||||
mInitialComponentName,
|
||||
mRemoteToken.toWindowContainerToken(),
|
||||
getConfiguration(),
|
||||
getChildCount() == 0,
|
||||
@@ -2026,6 +2023,17 @@ class TaskFragment extends WindowContainer<WindowContainer> {
|
||||
mMinHeight = minHeight;
|
||||
}
|
||||
|
||||
@Override
|
||||
void removeImmediately() {
|
||||
if (mRemoving) {
|
||||
return;
|
||||
}
|
||||
mRemoving = true;
|
||||
super.removeImmediately();
|
||||
sendTaskFragmentVanished();
|
||||
mRemoving = false;
|
||||
}
|
||||
|
||||
boolean dump(String prefix, FileDescriptor fd, PrintWriter pw, boolean dumpAll,
|
||||
boolean dumpClient, String dumpPackage, final boolean needSep, Runnable header) {
|
||||
boolean printed = false;
|
||||
|
||||
@@ -48,6 +48,7 @@ import android.os.Bundle;
|
||||
import android.os.IBinder;
|
||||
import android.os.Parcel;
|
||||
import android.os.RemoteException;
|
||||
import android.util.ArrayMap;
|
||||
import android.util.ArraySet;
|
||||
import android.util.Slog;
|
||||
import android.view.SurfaceControl;
|
||||
@@ -106,6 +107,11 @@ class WindowOrganizerController extends IWindowOrganizerController.Stub
|
||||
final TaskFragmentOrganizerController mTaskFragmentOrganizerController;
|
||||
|
||||
final TransitionController mTransitionController;
|
||||
/**
|
||||
* A Map which manages the relationship between
|
||||
* {@link TaskFragmentCreationParams.mFragmentToken fragmentToken} and {@link TaskFragment}
|
||||
*/
|
||||
private final ArrayMap<IBinder, TaskFragment> mLaunchTaskFragments = new ArrayMap<>();
|
||||
|
||||
WindowOrganizerController(ActivityTaskManagerService atm) {
|
||||
mService = atm;
|
||||
@@ -558,12 +564,12 @@ class WindowOrganizerController extends IWindowOrganizerController.Stub
|
||||
case HIERARCHY_OP_TYPE_CREATE_TASK_FRAGMENT:
|
||||
final TaskFragmentCreationParams taskFragmentCreationOptions =
|
||||
hop.getTaskFragmentCreationOptions();
|
||||
// TODO(b/190433129) add actual implementation on WM Core
|
||||
createTaskFragment(taskFragmentCreationOptions);
|
||||
break;
|
||||
case HIERARCHY_OP_TYPE_DELETE_TASK_FRAGMENT:
|
||||
wc = WindowContainer.fromBinder(hop.getContainer());
|
||||
if (wc == null || !wc.isAttached()) {
|
||||
Slog.e(TAG, "Attempt to operate on detached container: " + wc);
|
||||
Slog.e(TAG, "Attempt to operate on unknown or detached container: " + wc);
|
||||
break;
|
||||
}
|
||||
final TaskFragment taskFragment = wc.asTaskFragment();
|
||||
@@ -571,23 +577,40 @@ class WindowOrganizerController extends IWindowOrganizerController.Stub
|
||||
throw new IllegalArgumentException(
|
||||
"Can only delete organized TaskFragment, but not Task.");
|
||||
}
|
||||
// TODO(b/190433129) add actual implementation on WM Core
|
||||
deleteTaskFragment(taskFragment);
|
||||
break;
|
||||
case HIERARCHY_OP_TYPE_START_ACTIVITY_IN_TASK_FRAGMENT:
|
||||
fragmentToken = hop.getContainer();
|
||||
if (!mLaunchTaskFragments.containsKey(fragmentToken)) {
|
||||
throw new IllegalArgumentException(
|
||||
"Not allowed to operate with invalid fragment token");
|
||||
}
|
||||
final Intent activityIntent = hop.getActivityIntent();
|
||||
final Bundle activityOptions = hop.getLaunchOptions();
|
||||
// TODO(b/190433129) add actual implementation on WM Core
|
||||
mService.getActivityStartController()
|
||||
.startActivityInTaskFragment(mLaunchTaskFragments.get(fragmentToken),
|
||||
activityIntent, activityOptions);
|
||||
// TODO(b/189385246) : report the failure back to the organizer if the activity
|
||||
// start failed
|
||||
break;
|
||||
case HIERARCHY_OP_TYPE_REPARENT_ACTIVITY_TO_TASK_FRAGMENT:
|
||||
fragmentToken = hop.getNewParent();
|
||||
final ActivityRecord activity = ActivityRecord.forTokenLocked(hop.getContainer());
|
||||
// TODO(b/190433129) add actual implementation on WM Core
|
||||
if (!mLaunchTaskFragments.containsKey(fragmentToken) || activity == null) {
|
||||
throw new IllegalArgumentException(
|
||||
"Not allowed to operate with invalid fragment token or activity.");
|
||||
}
|
||||
activity.reparent(mLaunchTaskFragments.get(fragmentToken), POSITION_TOP);
|
||||
break;
|
||||
case HIERARCHY_OP_TYPE_REPARENT_CHILDREN:
|
||||
final WindowContainer oldParent = WindowContainer.fromBinder(hop.getContainer());
|
||||
final WindowContainer newParent = WindowContainer.fromBinder(hop.getNewParent());
|
||||
// TODO(b/190433129) add actual implementation on WM Core
|
||||
if (oldParent == null || !oldParent.isAttached()) {
|
||||
Slog.e(TAG, "Attempt to operate on unknown or detached container: "
|
||||
+ oldParent);
|
||||
break;
|
||||
}
|
||||
reparentTaskFragment(oldParent, newParent);
|
||||
break;
|
||||
}
|
||||
return effects;
|
||||
@@ -866,4 +889,51 @@ class WindowOrganizerController extends IWindowOrganizerController.Stub
|
||||
private void enforceTaskPermission(String func) {
|
||||
mService.enforceTaskPermission(func);
|
||||
}
|
||||
|
||||
void createTaskFragment(@NonNull TaskFragmentCreationParams creationParams) {
|
||||
final ActivityRecord ownerActivity =
|
||||
ActivityRecord.forTokenLocked(creationParams.getOwnerToken());
|
||||
if (ownerActivity == null || ownerActivity.getTask() == null) {
|
||||
// TODO(b/189385246) : report the failure back to the organizer
|
||||
return;
|
||||
}
|
||||
// The ownerActivity has to belong to the same app as the root Activity of the target Task.
|
||||
final ActivityRecord rootActivity = ownerActivity.getTask().getRootActivity();
|
||||
if (rootActivity.getUid() != ownerActivity.getUid()) {
|
||||
// TODO(b/189385246) : report the failure back to the organizer
|
||||
return;
|
||||
}
|
||||
final TaskFragment taskFragment = new TaskFragment(mService,
|
||||
creationParams.getFragmentToken(), true /* createdByOrganizer */);
|
||||
ownerActivity.getTask().addChild(taskFragment, POSITION_TOP);
|
||||
taskFragment.setWindowingMode(creationParams.getWindowingMode());
|
||||
taskFragment.setBounds(creationParams.getInitialBounds());
|
||||
taskFragment.setTaskFragmentOrganizer(creationParams.getOrganizer());
|
||||
mLaunchTaskFragments.put(creationParams.getFragmentToken(), taskFragment);
|
||||
}
|
||||
|
||||
void reparentTaskFragment(@NonNull WindowContainer oldParent,
|
||||
@Nullable WindowContainer newParent) {
|
||||
WindowContainer parent = newParent;
|
||||
if (parent == null && oldParent.asTaskFragment() != null) {
|
||||
parent = oldParent.asTaskFragment().getTask();
|
||||
}
|
||||
if (parent == null) {
|
||||
// TODO(b/189385246) : report the failure back to the organizer
|
||||
return;
|
||||
}
|
||||
while (oldParent.hasChild()) {
|
||||
oldParent.getChildAt(0).reparent(parent, POSITION_TOP);
|
||||
}
|
||||
}
|
||||
|
||||
void deleteTaskFragment(@NonNull TaskFragment taskFragment) {
|
||||
final int index = mLaunchTaskFragments.indexOfValue(taskFragment);
|
||||
if (index < 0) {
|
||||
throw new IllegalArgumentException(
|
||||
"Not allowed to operate with invalid taskFragment");
|
||||
}
|
||||
mLaunchTaskFragments.removeAt(index);
|
||||
taskFragment.removeImmediately();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1729,6 +1729,10 @@ class WindowState extends WindowContainer<WindowState> implements WindowManagerP
|
||||
return mActivityRecord != null ? mActivityRecord.getTask() : null;
|
||||
}
|
||||
|
||||
@Nullable TaskFragment getTaskFragment() {
|
||||
return mActivityRecord != null ? mActivityRecord.getTaskFragment() : null;
|
||||
}
|
||||
|
||||
@Nullable Task getRootTask() {
|
||||
final Task task = getTask();
|
||||
if (task != null) {
|
||||
@@ -2908,9 +2912,14 @@ class WindowState extends WindowContainer<WindowState> implements WindowManagerP
|
||||
// means we need to intercept touches outside of that window. The dim layer
|
||||
// user associated with the window (task or root task) will give us the good
|
||||
// bounds, as they would be used to display the dim layer.
|
||||
final Task task = getTask();
|
||||
if (task != null) {
|
||||
task.getDimBounds(mTmpRect);
|
||||
final TaskFragment taskFragment = getTaskFragment();
|
||||
if (taskFragment != null) {
|
||||
final Task task = taskFragment.asTask();
|
||||
if (task != null) {
|
||||
task.getDimBounds(mTmpRect);
|
||||
} else {
|
||||
mTmpRect.set(taskFragment.getBounds());
|
||||
}
|
||||
} else if (getRootTask() != null) {
|
||||
getRootTask().getDimBounds(mTmpRect);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user