Loading core/java/android/window/ITaskFragmentOrganizerController.aidl +14 −0 Original line number Diff line number Diff line Loading @@ -16,6 +16,7 @@ package android.window; import android.view.RemoteAnimationDefinition; import android.window.ITaskFragmentOrganizer; /** @hide */ Loading @@ -30,4 +31,17 @@ interface ITaskFragmentOrganizerController { * Unregisters a previously registered TaskFragmentOrganizer. */ void unregisterOrganizer(in ITaskFragmentOrganizer organizer); /** * Registers remote animations per transition type for the organizer. It will override the * animations if the transition only contains windows that belong to the organized * TaskFragments. */ void registerRemoteAnimations(in ITaskFragmentOrganizer organizer, in RemoteAnimationDefinition definition); /** * Unregisters remote animations per transition type for the organizer. */ void unregisterRemoteAnimations(in ITaskFragmentOrganizer organizer); } core/java/android/window/TaskFragmentOrganizer.java +29 −0 Original line number Diff line number Diff line Loading @@ -23,6 +23,7 @@ import android.content.res.Configuration; import android.os.Bundle; import android.os.IBinder; import android.os.RemoteException; import android.view.RemoteAnimationDefinition; import java.util.concurrent.Executor; Loading Loading @@ -90,6 +91,34 @@ public class TaskFragmentOrganizer extends WindowOrganizer { } } /** * Registers remote animations per transition type for the organizer. It will override the * animations if the transition only contains windows that belong to the organized * TaskFragments. * @hide */ @CallSuper public void registerRemoteAnimations(@NonNull RemoteAnimationDefinition definition) { try { getController().registerRemoteAnimations(mInterface, definition); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } } /** * Unregisters remote animations per transition type for the organizer. * @hide */ @CallSuper public void unregisterRemoteAnimations() { try { getController().unregisterRemoteAnimations(mInterface); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } } /** Called when a TaskFragment is created and organized by this organizer. */ public void onTaskFragmentAppeared( @NonNull TaskFragmentAppearedInfo taskFragmentAppearedInfo) {} Loading data/etc/services.core.protolog.json +18 −0 Original line number Diff line number Diff line Loading @@ -1261,6 +1261,12 @@ "group": "WM_DEBUG_WINDOW_TRANSITIONS", "at": "com\/android\/server\/wm\/Transition.java" }, "-702650156": { "message": "Override with TaskFragment remote animation for transit=%s", "level": "VERBOSE", "group": "WM_DEBUG_APP_TRANSITIONS", "at": "com\/android\/server\/wm\/AppTransitionController.java" }, "-701167286": { "message": "applyAnimation: transit=%s, enter=%b, wc=%s", "level": "VERBOSE", Loading Loading @@ -1789,6 +1795,12 @@ "group": "WM_DEBUG_STATES", "at": "com\/android\/server\/wm\/TaskFragment.java" }, "-70719599": { "message": "Unregister remote animations for organizer=%s uid=%d pid=%d", "level": "VERBOSE", "group": "WM_DEBUG_WINDOW_ORGANIZER", "at": "com\/android\/server\/wm\/TaskFragmentOrganizerController.java" }, "-55185509": { "message": "setFocusedTask: taskId=%d touchedActivity=%s", "level": "DEBUG", Loading Loading @@ -2941,6 +2953,12 @@ "group": "WM_ERROR", "at": "com\/android\/server\/wm\/WindowManagerService.java" }, "1210037962": { "message": "Register remote animations for organizer=%s uid=%d pid=%d", "level": "VERBOSE", "group": "WM_DEBUG_WINDOW_ORGANIZER", "at": "com\/android\/server\/wm\/TaskFragmentOrganizerController.java" }, "1219600119": { "message": "addWindow: win=%s Callers=%s", "level": "DEBUG", Loading services/core/java/com/android/server/wm/ActivityRecord.java +7 −0 Original line number Diff line number Diff line Loading @@ -2595,6 +2595,13 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A return task != null ? task.getOrganizedTask() : null; } /** Returns the organized parent {@link TaskFragment}. */ @Nullable TaskFragment getOrganizedTaskFragment() { final TaskFragment parent = getTaskFragment(); return parent != null ? parent.getOrganizedTaskFragment() : null; } @Override @Nullable TaskDisplayArea getDisplayArea() { Loading services/core/java/com/android/server/wm/AppTransitionController.java +65 −3 Original line number Diff line number Diff line Loading @@ -86,6 +86,7 @@ import android.view.WindowManager.TransitionFlags; import android.view.WindowManager.TransitionOldType; import android.view.WindowManager.TransitionType; import android.view.animation.Animation; import android.window.ITaskFragmentOrganizer; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.protolog.common.ProtoLog; Loading Loading @@ -233,7 +234,11 @@ public class AppTransitionController { final ActivityRecord topChangingApp = getTopApp(mDisplayContent.mChangingContainers, false /* ignoreHidden */); final WindowManager.LayoutParams animLp = getAnimLp(animLpActivity); // Check if there is any override if (!overrideWithTaskFragmentRemoteAnimation(transit, activityTypes)) { overrideWithRemoteAnimationIfSet(animLpActivity, transit, activityTypes); } final boolean voiceInteraction = containsVoiceInteraction(mDisplayContent.mOpeningApps) || containsVoiceInteraction(mDisplayContent.mOpeningApps); Loading Loading @@ -483,6 +488,7 @@ public class AppTransitionController { return TYPE_NONE; } @Nullable private static WindowManager.LayoutParams getAnimLp(ActivityRecord activity) { final WindowState mainWindow = activity != null ? activity.findMainWindow() : null; return mainWindow != null ? mainWindow.mAttrs : null; Loading @@ -505,6 +511,61 @@ public class AppTransitionController { : null; } /** * Overrides the pending transition with the remote animation defined by the * {@link ITaskFragmentOrganizer} if all windows in the transition are children of * {@link TaskFragment} that are organized by the same organizer. * * @return {@code true} if the transition is overridden. */ @VisibleForTesting boolean overrideWithTaskFragmentRemoteAnimation(@TransitionOldType int transit, ArraySet<Integer> activityTypes) { final ArrayList<WindowContainer> allWindows = new ArrayList<>(); allWindows.addAll(mDisplayContent.mClosingApps); allWindows.addAll(mDisplayContent.mOpeningApps); allWindows.addAll(mDisplayContent.mChangingContainers); // Find the common TaskFragmentOrganizer of all windows. ITaskFragmentOrganizer organizer = null; for (int i = allWindows.size() - 1; i >= 0; i--) { final ActivityRecord r = getAppFromContainer(allWindows.get(i)); if (r == null) { return false; } final TaskFragment organizedTaskFragment = r.getOrganizedTaskFragment(); final ITaskFragmentOrganizer curOrganizer = organizedTaskFragment != null ? organizedTaskFragment.getTaskFragmentOrganizer() : null; if (curOrganizer == null) { // All windows must below an organized TaskFragment. return false; } if (organizer == null) { organizer = curOrganizer; } else if (!organizer.asBinder().equals(curOrganizer.asBinder())) { // They must be controlled by the same organizer. return false; } } final RemoteAnimationDefinition definition = organizer != null ? mDisplayContent.mAtmService.mTaskFragmentOrganizerController .getRemoteAnimationDefinition(organizer) : null; final RemoteAnimationAdapter adapter = definition != null ? definition.getAdapter(transit, activityTypes) : null; if (adapter == null) { return false; } mDisplayContent.mAppTransition.overridePendingAppTransitionRemote(adapter); ProtoLog.v(WM_DEBUG_APP_TRANSITIONS, "Override with TaskFragment remote animation for transit=%s", AppTransition.appTransitionOldToString(transit)); return true; } /** * Overrides the pending transition with the remote animation defined for the transition in the * set of defined remote animations in the app window token. Loading @@ -524,13 +585,14 @@ public class AppTransitionController { } static ActivityRecord getAppFromContainer(WindowContainer wc) { return wc.asTask() != null ? wc.asTask().getTopNonFinishingActivity() return wc.asTaskFragment() != null ? wc.asTaskFragment().getTopNonFinishingActivity() : wc.asActivityRecord(); } /** * @return The window token that determines the animation theme. */ @Nullable private ActivityRecord findAnimLayoutParamsToken(@TransitionOldType int transit, ArraySet<Integer> activityTypes) { ActivityRecord result; Loading @@ -543,7 +605,7 @@ public class AppTransitionController { w -> w.getRemoteAnimationDefinition() != null && w.getRemoteAnimationDefinition().hasTransition(transit, activityTypes)); if (result != null) { return getAppFromContainer(result); return result; } result = lookForHighestTokenWithFilter(closingApps, openingApps, changingApps, w -> w.fillsParent() && w.findMainWindow() != null); Loading Loading
core/java/android/window/ITaskFragmentOrganizerController.aidl +14 −0 Original line number Diff line number Diff line Loading @@ -16,6 +16,7 @@ package android.window; import android.view.RemoteAnimationDefinition; import android.window.ITaskFragmentOrganizer; /** @hide */ Loading @@ -30,4 +31,17 @@ interface ITaskFragmentOrganizerController { * Unregisters a previously registered TaskFragmentOrganizer. */ void unregisterOrganizer(in ITaskFragmentOrganizer organizer); /** * Registers remote animations per transition type for the organizer. It will override the * animations if the transition only contains windows that belong to the organized * TaskFragments. */ void registerRemoteAnimations(in ITaskFragmentOrganizer organizer, in RemoteAnimationDefinition definition); /** * Unregisters remote animations per transition type for the organizer. */ void unregisterRemoteAnimations(in ITaskFragmentOrganizer organizer); }
core/java/android/window/TaskFragmentOrganizer.java +29 −0 Original line number Diff line number Diff line Loading @@ -23,6 +23,7 @@ import android.content.res.Configuration; import android.os.Bundle; import android.os.IBinder; import android.os.RemoteException; import android.view.RemoteAnimationDefinition; import java.util.concurrent.Executor; Loading Loading @@ -90,6 +91,34 @@ public class TaskFragmentOrganizer extends WindowOrganizer { } } /** * Registers remote animations per transition type for the organizer. It will override the * animations if the transition only contains windows that belong to the organized * TaskFragments. * @hide */ @CallSuper public void registerRemoteAnimations(@NonNull RemoteAnimationDefinition definition) { try { getController().registerRemoteAnimations(mInterface, definition); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } } /** * Unregisters remote animations per transition type for the organizer. * @hide */ @CallSuper public void unregisterRemoteAnimations() { try { getController().unregisterRemoteAnimations(mInterface); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } } /** Called when a TaskFragment is created and organized by this organizer. */ public void onTaskFragmentAppeared( @NonNull TaskFragmentAppearedInfo taskFragmentAppearedInfo) {} Loading
data/etc/services.core.protolog.json +18 −0 Original line number Diff line number Diff line Loading @@ -1261,6 +1261,12 @@ "group": "WM_DEBUG_WINDOW_TRANSITIONS", "at": "com\/android\/server\/wm\/Transition.java" }, "-702650156": { "message": "Override with TaskFragment remote animation for transit=%s", "level": "VERBOSE", "group": "WM_DEBUG_APP_TRANSITIONS", "at": "com\/android\/server\/wm\/AppTransitionController.java" }, "-701167286": { "message": "applyAnimation: transit=%s, enter=%b, wc=%s", "level": "VERBOSE", Loading Loading @@ -1789,6 +1795,12 @@ "group": "WM_DEBUG_STATES", "at": "com\/android\/server\/wm\/TaskFragment.java" }, "-70719599": { "message": "Unregister remote animations for organizer=%s uid=%d pid=%d", "level": "VERBOSE", "group": "WM_DEBUG_WINDOW_ORGANIZER", "at": "com\/android\/server\/wm\/TaskFragmentOrganizerController.java" }, "-55185509": { "message": "setFocusedTask: taskId=%d touchedActivity=%s", "level": "DEBUG", Loading Loading @@ -2941,6 +2953,12 @@ "group": "WM_ERROR", "at": "com\/android\/server\/wm\/WindowManagerService.java" }, "1210037962": { "message": "Register remote animations for organizer=%s uid=%d pid=%d", "level": "VERBOSE", "group": "WM_DEBUG_WINDOW_ORGANIZER", "at": "com\/android\/server\/wm\/TaskFragmentOrganizerController.java" }, "1219600119": { "message": "addWindow: win=%s Callers=%s", "level": "DEBUG", Loading
services/core/java/com/android/server/wm/ActivityRecord.java +7 −0 Original line number Diff line number Diff line Loading @@ -2595,6 +2595,13 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A return task != null ? task.getOrganizedTask() : null; } /** Returns the organized parent {@link TaskFragment}. */ @Nullable TaskFragment getOrganizedTaskFragment() { final TaskFragment parent = getTaskFragment(); return parent != null ? parent.getOrganizedTaskFragment() : null; } @Override @Nullable TaskDisplayArea getDisplayArea() { Loading
services/core/java/com/android/server/wm/AppTransitionController.java +65 −3 Original line number Diff line number Diff line Loading @@ -86,6 +86,7 @@ import android.view.WindowManager.TransitionFlags; import android.view.WindowManager.TransitionOldType; import android.view.WindowManager.TransitionType; import android.view.animation.Animation; import android.window.ITaskFragmentOrganizer; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.protolog.common.ProtoLog; Loading Loading @@ -233,7 +234,11 @@ public class AppTransitionController { final ActivityRecord topChangingApp = getTopApp(mDisplayContent.mChangingContainers, false /* ignoreHidden */); final WindowManager.LayoutParams animLp = getAnimLp(animLpActivity); // Check if there is any override if (!overrideWithTaskFragmentRemoteAnimation(transit, activityTypes)) { overrideWithRemoteAnimationIfSet(animLpActivity, transit, activityTypes); } final boolean voiceInteraction = containsVoiceInteraction(mDisplayContent.mOpeningApps) || containsVoiceInteraction(mDisplayContent.mOpeningApps); Loading Loading @@ -483,6 +488,7 @@ public class AppTransitionController { return TYPE_NONE; } @Nullable private static WindowManager.LayoutParams getAnimLp(ActivityRecord activity) { final WindowState mainWindow = activity != null ? activity.findMainWindow() : null; return mainWindow != null ? mainWindow.mAttrs : null; Loading @@ -505,6 +511,61 @@ public class AppTransitionController { : null; } /** * Overrides the pending transition with the remote animation defined by the * {@link ITaskFragmentOrganizer} if all windows in the transition are children of * {@link TaskFragment} that are organized by the same organizer. * * @return {@code true} if the transition is overridden. */ @VisibleForTesting boolean overrideWithTaskFragmentRemoteAnimation(@TransitionOldType int transit, ArraySet<Integer> activityTypes) { final ArrayList<WindowContainer> allWindows = new ArrayList<>(); allWindows.addAll(mDisplayContent.mClosingApps); allWindows.addAll(mDisplayContent.mOpeningApps); allWindows.addAll(mDisplayContent.mChangingContainers); // Find the common TaskFragmentOrganizer of all windows. ITaskFragmentOrganizer organizer = null; for (int i = allWindows.size() - 1; i >= 0; i--) { final ActivityRecord r = getAppFromContainer(allWindows.get(i)); if (r == null) { return false; } final TaskFragment organizedTaskFragment = r.getOrganizedTaskFragment(); final ITaskFragmentOrganizer curOrganizer = organizedTaskFragment != null ? organizedTaskFragment.getTaskFragmentOrganizer() : null; if (curOrganizer == null) { // All windows must below an organized TaskFragment. return false; } if (organizer == null) { organizer = curOrganizer; } else if (!organizer.asBinder().equals(curOrganizer.asBinder())) { // They must be controlled by the same organizer. return false; } } final RemoteAnimationDefinition definition = organizer != null ? mDisplayContent.mAtmService.mTaskFragmentOrganizerController .getRemoteAnimationDefinition(organizer) : null; final RemoteAnimationAdapter adapter = definition != null ? definition.getAdapter(transit, activityTypes) : null; if (adapter == null) { return false; } mDisplayContent.mAppTransition.overridePendingAppTransitionRemote(adapter); ProtoLog.v(WM_DEBUG_APP_TRANSITIONS, "Override with TaskFragment remote animation for transit=%s", AppTransition.appTransitionOldToString(transit)); return true; } /** * Overrides the pending transition with the remote animation defined for the transition in the * set of defined remote animations in the app window token. Loading @@ -524,13 +585,14 @@ public class AppTransitionController { } static ActivityRecord getAppFromContainer(WindowContainer wc) { return wc.asTask() != null ? wc.asTask().getTopNonFinishingActivity() return wc.asTaskFragment() != null ? wc.asTaskFragment().getTopNonFinishingActivity() : wc.asActivityRecord(); } /** * @return The window token that determines the animation theme. */ @Nullable private ActivityRecord findAnimLayoutParamsToken(@TransitionOldType int transit, ArraySet<Integer> activityTypes) { ActivityRecord result; Loading @@ -543,7 +605,7 @@ public class AppTransitionController { w -> w.getRemoteAnimationDefinition() != null && w.getRemoteAnimationDefinition().hasTransition(transit, activityTypes)); if (result != null) { return getAppFromContainer(result); return result; } result = lookForHighestTokenWithFilter(closingApps, openingApps, changingApps, w -> w.fillsParent() && w.findMainWindow() != null); Loading