Introduce TaskOrganizer
A first take at the TaskOrganizer API for allowing SysUI to control task presentation.
In this CL we introduce the first two primitives:
1. The interface itself for implementation by SysUI
2. Support for organizing a given windowing mode (but atm really only PIP)
We include a sample app that manages the PIP from an APPLICATION_OVERLAY window.
Bug: 139371701
Test: wmtests/TaskOrganizerTests. TaskOrganizerPipTest
Change-Id: I44a8ed311bc5f06285bba2c6ff3b37a7d19a9190
diff --git a/services/core/java/com/android/server/wm/ActivityTaskManagerService.java b/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
index 76c0e4e..3548918 100644
--- a/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
+++ b/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
@@ -226,6 +226,7 @@
import android.util.TimeUtils;
import android.util.proto.ProtoOutputStream;
import android.view.IRecentsAnimationRunner;
+import android.view.ITaskOrganizer;
import android.view.RemoteAnimationAdapter;
import android.view.RemoteAnimationDefinition;
import android.view.WindowContainerTransaction;
@@ -662,6 +663,12 @@
private FontScaleSettingObserver mFontScaleSettingObserver;
+ /**
+ * Stores the registration and state of TaskOrganizers in use.
+ */
+ TaskOrganizerController mTaskOrganizerController =
+ new TaskOrganizerController(this, mGlobalLock);
+
private int mDeviceOwnerUid = Process.INVALID_UID;
private final class FontScaleSettingObserver extends ContentObserver {
@@ -1271,6 +1278,14 @@
.execute();
}
+ @Override
+ public final void registerTaskOrganizer(ITaskOrganizer organizer, int windowingMode) {
+ enforceCallerIsRecentsOrHasPermission(
+ MANAGE_ACTIVITY_STACKS, "registerTaskOrganizer()");
+ synchronized (mGlobalLock) {
+ mTaskOrganizerController.registerTaskOrganizer(organizer, windowingMode);
+ }
+ }
@Override
public IBinder requestStartActivityPermissionToken(IBinder delegatorToken) {
@@ -3319,6 +3334,18 @@
}
}
+ private void applyWindowContainerChange(ConfigurationContainer cc,
+ WindowContainerTransaction.Change c) {
+ sanitizeAndApplyConfigChange(cc, c);
+
+ Rect enterPipBounds = c.getEnterPipBounds();
+ if (enterPipBounds != null) {
+ Task tr = (Task) cc;
+ mStackSupervisor.updatePictureInPictureMode(tr,
+ enterPipBounds, true);
+ }
+ }
+
@Override
public void applyContainerTransaction(WindowContainerTransaction t) {
mAmInternal.enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "applyContainerTransaction()");
@@ -3335,7 +3362,7 @@
entries.next();
final ConfigurationContainer cc = ConfigurationContainer.RemoteToken.fromBinder(
entry.getKey()).getContainer();
- sanitizeAndApplyConfigChange(cc, entry.getValue());
+ applyWindowContainerChange(cc, entry.getValue());
}
}
} finally {
@@ -4057,7 +4084,11 @@
throw new IllegalArgumentException("Stack: " + stack
+ " doesn't support animated resize.");
}
- if (animate) {
+ /**
+ * TODO(b/146594635): Remove all PIP animation code from WM
+ * once SysUI handles animation. Don't even try to animate TaskOrganized tasks.
+ */
+ if (animate && !stack.isControlledByTaskOrganizer()) {
stack.animateResizePinnedStack(null /* destBounds */,
null /* sourceHintBounds */, animationDuration,
false /* fromFullscreen */);