From 6dd73e98d77af599253ae26a2076abceaa44a78c Mon Sep 17 00:00:00 2001 From: Winson Chung Date: Thu, 5 Nov 2020 15:57:36 -0800 Subject: [PATCH] 6/ Fix some flakey issues with dragging to split - Ensure that the task info activity type always matches the actual task activity type (can be different than the window configuration type) - Ensure that the targets hit rects respect the insets, and that dragging out of all targets (but still within the window) will hide the last target - Work around race with launching secondary task when splitting, wait until the split screen task org has moved existing tasks to secondary split root before starting the new task, and also update the home task position when going home (b/172686383) - Add a timeout to clean up drag surfaces if SysUI crashes while mid-drag - Clean up some other calls to get activity type/win mode Bug: 169894807 Test: atest DragDropControllerTests Test: atest DragAndDropPolicyTest Test: atest SplitScreenTests Change-Id: I7ae11cc38b1e927d955798ef1056e17c9e435758 --- .../android/wm/shell/ShellTaskOrganizer.java | 8 +-- .../shell/draganddrop/DragAndDropPolicy.java | 59 +++++++++++++------ .../wm/shell/draganddrop/DragLayout.java | 18 ++++-- .../wm/shell/pip/phone/PipController.java | 3 +- .../wm/shell/pip/tv/PipController.java | 3 +- .../wm/shell/splitscreen/SplitScreen.java | 3 + .../splitscreen/SplitScreenController.java | 22 +++++-- .../splitscreen/SplitScreenTaskListener.java | 19 +++++- .../shell/splitscreen/WindowManagerProxy.java | 7 +-- .../draganddrop/DragAndDropPolicyTest.java | 10 ++++ .../android/server/wm/DragDropController.java | 9 +++ .../java/com/android/server/wm/DragState.java | 5 ++ .../core/java/com/android/server/wm/Task.java | 4 ++ 13 files changed, 124 insertions(+), 46 deletions(-) diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/ShellTaskOrganizer.java b/libs/WindowManager/Shell/src/com/android/wm/shell/ShellTaskOrganizer.java index 51ddb17daa009..2d20feeb0832b 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/ShellTaskOrganizer.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/ShellTaskOrganizer.java @@ -346,15 +346,9 @@ public class ShellTaskOrganizer extends TaskOrganizer { return mTaskListeners.get(taskListenerType); } - @WindowingMode - public static int getWindowingMode(RunningTaskInfo taskInfo) { - return taskInfo.configuration.windowConfiguration.getWindowingMode(); - } - @VisibleForTesting static @TaskListenerType int taskInfoToTaskListenerType(RunningTaskInfo runningTaskInfo) { - final int windowingMode = getWindowingMode(runningTaskInfo); - switch (windowingMode) { + switch (runningTaskInfo.getWindowingMode()) { case WINDOWING_MODE_FULLSCREEN: return runningTaskInfo.letterboxActivityBounds != null ? TASK_LISTENER_TYPE_LETTERBOX diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/draganddrop/DragAndDropPolicy.java b/libs/WindowManager/Shell/src/com/android/wm/shell/draganddrop/DragAndDropPolicy.java index 25890bc31b3c5..8a547b4477fd9 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/draganddrop/DragAndDropPolicy.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/draganddrop/DragAndDropPolicy.java @@ -18,6 +18,7 @@ package com.android.wm.shell.draganddrop; import static android.app.ActivityTaskManager.INVALID_TASK_ID; import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD; +import static android.app.WindowConfiguration.ACTIVITY_TYPE_UNDEFINED; import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN; import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED; import static android.content.ClipDescription.EXTRA_ACTIVITY_OPTIONS; @@ -67,6 +68,7 @@ import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.util.ArrayList; import java.util.List; +import java.util.function.Consumer; /** * The policy for handling drag and drop operations to shell. @@ -133,20 +135,20 @@ public class DragAndDropPolicy { // TODO(b/169894807): For now, only allow splitting to the right/bottom until we // have split pairs mTargets.add(new Target(TYPE_FULLSCREEN, - new Rect(0, 0, w, h / 2), + new Rect(l, t, l + iw, t + ih / 2), new Rect(l, t, l + iw, t + ih), new Rect(0, 0, w, h))); mTargets.add(new Target(TYPE_SPLIT_BOTTOM, - new Rect(0, h / 2, w, h), + new Rect(l, t + ih / 2, l + iw, t + ih), new Rect(l, t + ih / 2, l + iw, t + ih), new Rect(0, h / 2, w, h))); } else { mTargets.add(new Target(TYPE_FULLSCREEN, - new Rect(0, 0, w / 2, h), + new Rect(l, t, l + iw / 2, t + ih), new Rect(l, t, l + iw, t + ih), new Rect(0, 0, w, h))); mTargets.add(new Target(TYPE_SPLIT_RIGHT, - new Rect(w / 2, 0, w, h), + new Rect(l + iw / 2, t, l + iw, t + ih), new Rect(l + iw / 2, t, l + iw, t + ih), new Rect(w / 2, 0, w, h))); } @@ -162,12 +164,12 @@ public class DragAndDropPolicy { secondarySplitBounds.intersect(new Rect(l, t, l + iw, t + ih)); if (isVerticalSplit) { mTargets.add(new Target(TYPE_FULLSCREEN, - new Rect(0, 0, w, secondarySplitRawBounds.top), + new Rect(l, t, l + iw, secondarySplitRawBounds.top), new Rect(l, t, l + iw, t + ih), new Rect(0, 0, w, secondarySplitRawBounds.top))); } else { mTargets.add(new Target(TYPE_FULLSCREEN, - new Rect(0, 0, secondarySplitRawBounds.left, h), + new Rect(l, t, secondarySplitRawBounds.left, t + ih), new Rect(l, t, l + iw, t + ih), new Rect(0, 0, w, h))); } @@ -178,7 +180,7 @@ public class DragAndDropPolicy { } else { // Otherwise only show the fullscreen target mTargets.add(new Target(TYPE_FULLSCREEN, - new Rect(0, 0, w, h), + new Rect(l, t, l + iw, t + ih), new Rect(l, t, l + iw, t + ih), new Rect(0, 0, w, h))); } @@ -210,6 +212,7 @@ public class DragAndDropPolicy { final boolean isShortcut = description.hasMimeType(MIMETYPE_APPLICATION_SHORTCUT); final Intent dragData = mSession.dragData; + boolean deferAppLaunchUntilSplit = false; if (target.type == TYPE_FULLSCREEN) { if (mSplitScreen != null && mSplitScreen.isDividerVisible()) { // If in split, remove split and launch fullscreen @@ -226,20 +229,40 @@ public class DragAndDropPolicy { // Not in split, enter split now mStarter.enterSplitScreen(mSession.runningTaskId, target.type == TYPE_SPLIT_LEFT || target.type == TYPE_SPLIT_TOP); + deferAppLaunchUntilSplit = true; } } - Bundle opts = dragData.hasExtra(EXTRA_ACTIVITY_OPTIONS) - ? dragData.getBundleExtra(EXTRA_ACTIVITY_OPTIONS) - : null; - if (isTask) { - mStarter.startTask(dragData.getIntExtra(EXTRA_TASK_ID, INVALID_TASK_ID), opts); - } else if (isShortcut) { - mStarter.startShortcut(dragData.getStringExtra(EXTRA_PACKAGE_NAME), - dragData.getStringExtra(EXTRA_SHORTCUT_ID), - opts, dragData.getParcelableExtra(EXTRA_USER)); + final Runnable startAppRunnable = () -> { + Bundle opts = dragData.hasExtra(EXTRA_ACTIVITY_OPTIONS) + ? dragData.getBundleExtra(EXTRA_ACTIVITY_OPTIONS) + : null; + if (isTask) { + mStarter.startTask(dragData.getIntExtra(EXTRA_TASK_ID, INVALID_TASK_ID), opts); + } else if (isShortcut) { + mStarter.startShortcut(dragData.getStringExtra(EXTRA_PACKAGE_NAME), + dragData.getStringExtra(EXTRA_SHORTCUT_ID), + opts, dragData.getParcelableExtra(EXTRA_USER)); + } else { + mStarter.startIntent(dragData.getParcelableExtra(EXTRA_PENDING_INTENT), opts); + } + }; + if (deferAppLaunchUntilSplit) { + // TODO(b/169894807): The enterSplitScreen() call above will trigger the current task + // into split, and we should wait for home and other tasks to be moved to + // split-secondary before trying to launch the new secondary task. This can be removed + // once we have app-pairs. + mSplitScreen.registerInSplitScreenListener(new Consumer() { + @Override + public void accept(Boolean inSplit) { + if (inSplit) { + startAppRunnable.run(); + mSplitScreen.unregisterInSplitScreenListener(this); + } + } + }); } else { - mStarter.startIntent(dragData.getParcelableExtra(EXTRA_PENDING_INTENT), opts); + startAppRunnable.run(); } } @@ -274,7 +297,7 @@ public class DragAndDropPolicy { * Updates the session data based on the current state of the system. */ void update() { - final ClipDescription description = mInitialDragData.getDescription(); + try { List tasks = mIActivityTaskManager.getFilteredTasks(1, diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/draganddrop/DragLayout.java b/libs/WindowManager/Shell/src/com/android/wm/shell/draganddrop/DragLayout.java index fa857cdd174c3..5b7531c09a7b7 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/draganddrop/DragLayout.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/draganddrop/DragLayout.java @@ -135,17 +135,25 @@ public class DragLayout extends View { // visibility of the current region DragAndDropPolicy.Target target = mPolicy.getTargetAtLocation( (int) event.getX(), (int) event.getY()); - if (target != null && mCurrentTarget != target) { + if (mCurrentTarget != target) { ProtoLog.v(ShellProtoLogGroup.WM_SHELL_DRAG_AND_DROP, "Current target: %s", target); - Interpolator boundsInterpolator = FAST_OUT_SLOW_IN; - if (mCurrentTarget == null) { + if (target == null) { + // Animating to no target + mDropOutline.startVisibilityAnimation(false, LINEAR); + Rect finalBounds = new Rect(mCurrentTarget.drawRegion); + finalBounds.inset(mDisplayMargin, mDisplayMargin); + mDropOutline.startBoundsAnimation(finalBounds, FAST_OUT_LINEAR_IN); + } else if (mCurrentTarget == null) { + // Animating to first target mDropOutline.startVisibilityAnimation(true, LINEAR); Rect initialBounds = new Rect(target.drawRegion); initialBounds.inset(mDisplayMargin, mDisplayMargin); mDropOutline.setRegionBounds(initialBounds); - boundsInterpolator = LINEAR_OUT_SLOW_IN; + mDropOutline.startBoundsAnimation(target.drawRegion, LINEAR_OUT_SLOW_IN); + } else { + // Bounds change + mDropOutline.startBoundsAnimation(target.drawRegion, FAST_OUT_SLOW_IN); } - mDropOutline.startBoundsAnimation(target.drawRegion, boundsInterpolator); mCurrentTarget = target; } } diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipController.java b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipController.java index 251f8d4722459..854096c1d12f1 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipController.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipController.java @@ -324,8 +324,7 @@ public class PipController implements Pip, PipTaskOrganizer.PipTransitionCallbac @Override public void onActivityRestartAttempt(ActivityManager.RunningTaskInfo task, boolean homeTaskVisible, boolean clearedTask, boolean wasVisible) { - if (task.configuration.windowConfiguration.getWindowingMode() - != WINDOWING_MODE_PINNED) { + if (task.getWindowingMode() != WINDOWING_MODE_PINNED) { return; } mTouchHandler.getMotionHelper().expandLeavePip( diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/tv/PipController.java b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/tv/PipController.java index 70b5446213298..402d79c6fbd1b 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/tv/PipController.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/tv/PipController.java @@ -398,8 +398,7 @@ public class PipController implements Pip, PipTaskOrganizer.PipTransitionCallbac private void onActivityRestartAttempt(ActivityManager.RunningTaskInfo task, boolean clearedTask) { - if (task.configuration.windowConfiguration.getWindowingMode() - != WINDOWING_MODE_PINNED) { + if (task.getWindowingMode() != WINDOWING_MODE_PINNED) { return; } if (DEBUG) Log.d(TAG, "onPinnedActivityRestartAttempt()"); diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreen.java b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreen.java index cfe9b9157eaa1..e55f065c1bb21 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreen.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreen.java @@ -57,6 +57,9 @@ public interface SplitScreen { /** Registers listener that gets called whenever the existence of the divider changes. */ void registerInSplitScreenListener(Consumer listener); + /** Unregisters listener that gets called whenever the existence of the divider changes. */ + void unregisterInSplitScreenListener(Consumer listener); + /** Registers listener that gets called whenever the split screen bounds changes. */ void registerBoundsChangeListener(BiConsumer listener); diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenController.java b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenController.java index 49f11592a7fa6..07af289c4f352 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenController.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenController.java @@ -58,6 +58,7 @@ import java.io.PrintWriter; import java.lang.ref.WeakReference; import java.util.ArrayList; import java.util.List; +import java.util.concurrent.CopyOnWriteArrayList; import java.util.function.BiConsumer; import java.util.function.Consumer; @@ -85,8 +86,8 @@ public class SplitScreenController implements SplitScreen, private final WindowManagerProxy mWindowManagerProxy; private final TaskOrganizer mTaskOrganizer; - private final ArrayList>> mDockedStackExistsListeners = - new ArrayList<>(); + private final CopyOnWriteArrayList>> mDockedStackExistsListeners + = new CopyOnWriteArrayList<>(); private final ArrayList>> mBoundsChangedListeners = new ArrayList<>(); @@ -173,7 +174,7 @@ public class SplitScreenController implements SplitScreen, @Override public void onActivityRestartAttempt(ActivityManager.RunningTaskInfo task, boolean homeTaskVisible, boolean clearedTask, boolean wasVisible) { - if (!wasVisible || task.configuration.windowConfiguration.getWindowingMode() + if (!wasVisible || task.getWindowingMode() != WINDOWING_MODE_SPLIT_SCREEN_PRIMARY || !mSplits.isSplitScreenSupported()) { return; @@ -477,6 +478,17 @@ public class SplitScreenController implements SplitScreen, } } + @Override + public void unregisterInSplitScreenListener(Consumer listener) { + synchronized (mDockedStackExistsListeners) { + for (int i = mDockedStackExistsListeners.size() - 1; i >= 0; i--) { + if (mDockedStackExistsListeners.get(i) == listener) { + mDockedStackExistsListeners.remove(i); + } + } + } + } + @Override public void registerBoundsChangeListener(BiConsumer listener) { synchronized (mBoundsChangedListeners) { @@ -500,9 +512,7 @@ public class SplitScreenController implements SplitScreen, } // Note: The set of running tasks from the system is ordered by recency. final RunningTaskInfo topRunningTask = runningTasks.get(0); - - final int activityType = topRunningTask.configuration.windowConfiguration - .getActivityType(); + final int activityType = topRunningTask.getActivityType(); if (activityType == ACTIVITY_TYPE_HOME || activityType == ACTIVITY_TYPE_RECENTS) { return false; } diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenTaskListener.java b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenTaskListener.java index 64e9d66183900..5b2b38ba81899 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenTaskListener.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenTaskListener.java @@ -23,7 +23,6 @@ import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMAR import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY; import static android.view.Display.DEFAULT_DISPLAY; -import static com.android.wm.shell.ShellTaskOrganizer.getWindowingMode; import static com.android.wm.shell.protolog.ShellProtoLogGroup.WM_SHELL_TASK_ORG; import android.app.ActivityManager.RunningTaskInfo; @@ -42,6 +41,7 @@ import com.android.wm.shell.Transitions; import com.android.wm.shell.common.SyncTransactionQueue; import java.io.PrintWriter; +import java.util.ArrayList; class SplitScreenTaskListener implements ShellTaskOrganizer.TaskListener { private static final String TAG = "SplitScreenTaskListener"; @@ -106,7 +106,7 @@ class SplitScreenTaskListener implements ShellTaskOrganizer.TaskListener { return; } - final int winMode = getWindowingMode(taskInfo); + final int winMode = taskInfo.getWindowingMode(); if (winMode == WINDOWING_MODE_SPLIT_SCREEN_PRIMARY) { ProtoLog.v(WM_SHELL_TASK_ORG, "%s onTaskAppeared Primary taskId=%d", TAG, taskInfo.taskId); @@ -283,6 +283,21 @@ class SplitScreenTaskListener implements ShellTaskOrganizer.TaskListener { mSplitScreenController.startEnterSplit(); } } else if (secondaryImpliesMinimize) { + // Workaround for b/172686383, we can't rely on the sync bounds change transaction for + // the home task to finish before the last updateChildTaskSurface() call even if it's + // queued on the sync transaction queue, so ensure that the home task surface is updated + // again before we minimize + final ArrayList tasks = new ArrayList<>(); + mSplitScreenController.getWmProxy().getHomeAndRecentsTasks(tasks, + mSplitScreenController.getSecondaryRoot()); + for (int i = 0; i < tasks.size(); i++) { + final RunningTaskInfo taskInfo = tasks.get(i); + final SurfaceControl leash = mLeashByTaskId.get(taskInfo.taskId); + if (leash != null) { + updateChildTaskSurface(taskInfo, leash, false /* firstAppeared */); + } + } + // Both splits are populated but the secondary split has a home/recents stack on top, // so enter minimized mode. mSplitScreenController.ensureMinimizedSplit(); diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/WindowManagerProxy.java b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/WindowManagerProxy.java index c51bbeb7b6c28..0307206e2defa 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/WindowManagerProxy.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/WindowManagerProxy.java @@ -120,7 +120,7 @@ class WindowManagerProxy { new WindowOrganizer().applyTransaction(t); } - private boolean getHomeAndRecentsTasks(List out, + boolean getHomeAndRecentsTasks(List out, WindowContainerToken parent) { boolean resizable = false; List rootTasks = parent == null @@ -209,8 +209,7 @@ class WindowManagerProxy { continue; } // Only move fullscreen tasks to split secondary. - if (rootTask.configuration.windowConfiguration.getWindowingMode() - != WINDOWING_MODE_FULLSCREEN) { + if (rootTask.getWindowingMode() != WINDOWING_MODE_FULLSCREEN) { continue; } // Since this iterates from bottom to top, update topHomeTask for every fullscreen task @@ -232,7 +231,7 @@ class WindowManagerProxy { } boolean isHomeOrRecentTask(ActivityManager.RunningTaskInfo ti) { - final int atype = ti.configuration.windowConfiguration.getActivityType(); + final int atype = ti.getActivityType(); return atype == ACTIVITY_TYPE_HOME || atype == ACTIVITY_TYPE_RECENTS; } diff --git a/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/draganddrop/DragAndDropPolicyTest.java b/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/draganddrop/DragAndDropPolicyTest.java index affd7367f4729..fad1f057267ab 100644 --- a/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/draganddrop/DragAndDropPolicyTest.java +++ b/libs/WindowManager/Shell/tests/unittest/src/com/android/wm/shell/draganddrop/DragAndDropPolicyTest.java @@ -35,6 +35,7 @@ import static org.mockito.ArgumentMatchers.any; import static org.mockito.ArgumentMatchers.anyBoolean; import static org.mockito.ArgumentMatchers.anyInt; import static org.mockito.ArgumentMatchers.eq; +import static org.mockito.Mockito.doAnswer; import static org.mockito.Mockito.doReturn; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.reset; @@ -68,10 +69,13 @@ import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.Mock; import org.mockito.MockitoAnnotations; +import org.mockito.invocation.InvocationOnMock; +import org.mockito.stubbing.Answer; import java.util.ArrayList; import java.util.Collections; import java.util.HashSet; +import java.util.function.Consumer; /** * Tests for the drag and drop policy. @@ -124,6 +128,12 @@ public class DragAndDropPolicyTest { doReturn(new Rect(50, 0, 100, 100)).when(divider) .getNonMinimizedSplitScreenSecondaryBounds(); + doAnswer((Answer) invocation -> { + Consumer callback = invocation.getArgument(0); + callback.accept(true); + return null; + }).when(mSplitScreen).registerInSplitScreenListener(any()); + mPolicy = new DragAndDropPolicy(mContext, mIActivityTaskManager, mSplitScreen, mStarter); mActivityClipData = createClipData(MIMETYPE_APPLICATION_ACTIVITY); mNonResizeableActivityClipData = createClipData(MIMETYPE_APPLICATION_ACTIVITY); diff --git a/services/core/java/com/android/server/wm/DragDropController.java b/services/core/java/com/android/server/wm/DragDropController.java index 3eac1be3ebeed..627af9149fe52 100644 --- a/services/core/java/com/android/server/wm/DragDropController.java +++ b/services/core/java/com/android/server/wm/DragDropController.java @@ -49,6 +49,7 @@ class DragDropController { static final int MSG_DRAG_END_TIMEOUT = 0; static final int MSG_TEAR_DOWN_DRAG_AND_DROP_INPUT = 1; static final int MSG_ANIMATION_END = 2; + static final int MSG_REMOVE_DRAG_SURFACE_TIMEOUT = 3; /** * Drag state per operation. @@ -384,6 +385,14 @@ class DragDropController { } break; } + + case MSG_REMOVE_DRAG_SURFACE_TIMEOUT: { + synchronized (mService.mGlobalLock) { + mService.mTransactionFactory.get() + .reparent((SurfaceControl) msg.obj, null).apply(); + } + break; + } } } } diff --git a/services/core/java/com/android/server/wm/DragState.java b/services/core/java/com/android/server/wm/DragState.java index 8c80205a9e457..e7d8ad690bc4c 100644 --- a/services/core/java/com/android/server/wm/DragState.java +++ b/services/core/java/com/android/server/wm/DragState.java @@ -23,6 +23,7 @@ import static com.android.internal.protolog.ProtoLogGroup.WM_DEBUG_ORIENTATION; import static com.android.internal.protolog.ProtoLogGroup.WM_SHOW_TRANSACTIONS; import static com.android.server.wm.DragDropController.MSG_ANIMATION_END; import static com.android.server.wm.DragDropController.MSG_DRAG_END_TIMEOUT; +import static com.android.server.wm.DragDropController.MSG_REMOVE_DRAG_SURFACE_TIMEOUT; import static com.android.server.wm.DragDropController.MSG_TEAR_DOWN_DRAG_AND_DROP_INPUT; import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_DRAG; import static com.android.server.wm.WindowManagerDebugConfig.SHOW_LIGHT_TRANSACTIONS; @@ -59,6 +60,7 @@ import android.view.WindowManager; import android.view.animation.DecelerateInterpolator; import android.view.animation.Interpolator; +import com.android.internal.os.SomeArgs; import com.android.internal.protolog.common.ProtoLog; import com.android.internal.view.IDragAndDropPermissions; import com.android.server.LocalServices; @@ -248,6 +250,9 @@ class DragState { if (mSurfaceControl != null) { if (!mRelinquishDragSurface) { mTransaction.reparent(mSurfaceControl, null).apply(); + } else { + mDragDropController.sendTimeoutMessage(MSG_REMOVE_DRAG_SURFACE_TIMEOUT, + mSurfaceControl); } mSurfaceControl = null; } diff --git a/services/core/java/com/android/server/wm/Task.java b/services/core/java/com/android/server/wm/Task.java index 0b2ba8727abe5..3290282791266 100644 --- a/services/core/java/com/android/server/wm/Task.java +++ b/services/core/java/com/android/server/wm/Task.java @@ -4072,6 +4072,10 @@ class Task extends WindowContainer { info.taskDescription = new ActivityManager.TaskDescription(getTaskDescription()); info.supportsSplitScreenMultiWindow = supportsSplitScreenWindowingMode(); info.configuration.setTo(getConfiguration()); + // Update to the task's current activity type and windowing mode which may differ from the + // window configuration + info.configuration.windowConfiguration.setActivityType(getActivityType()); + info.configuration.windowConfiguration.setWindowingMode(getWindowingMode()); info.token = mRemoteToken.toWindowContainerToken(); //TODO (AM refactor): Just use local once updateEffectiveIntent is run during all child