summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Jorim Jaggi <jjaggi@google.com> 2016-02-19 19:54:39 -0800
committer Jorim Jaggi <jjaggi@google.com> 2016-02-23 10:50:34 -0500
commit8fa4522b24065d15535e17eed7cd5370b878a4c5 (patch)
tree1f8ae9531a481ff54121b4894e99266d6921a819
parent5060bd891068b78bcbe72e1d8b61efac2da02c20 (diff)
Recents transition fixes
- Make sure to destroy the saved surfaces while we resize a task. The usual destroying mechanism doesn't work here because we don't add the windows to WMS.mResizingWindows. - Make sure not to save the surface when a resize happened after the window has been marked as gone (exiting). In this case, we resize the task, so we add the window to mResizingWindows, but then when we don't layout the window because win.isGoneForLayout() == true, so it would save a surface that has the wrong size. - Ensure the configuration of the top task when dismissing the docked stack. First, this speeds up when the user navigates to it in the fullscreen stack. Second, it fixes some other weirdness with saving surfaces. - Only exclude windows from layout when hidden is requested, so when transitioning from hidden -> shown, the app immediately gets the updated size when the task was resized when the window was hidden. Bug: 27276087 Change-Id: I6faf016724136d984b259d184af58d41684f3425
-rw-r--r--services/core/java/com/android/server/am/ActivityManagerService.java56
-rw-r--r--services/core/java/com/android/server/am/ActivityStackSupervisor.java2
-rw-r--r--services/core/java/com/android/server/wm/Task.java14
-rw-r--r--services/core/java/com/android/server/wm/WindowManagerService.java3
-rw-r--r--services/core/java/com/android/server/wm/WindowState.java13
5 files changed, 59 insertions, 29 deletions
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index 49503d9e901d..6f2d843345f4 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -17768,36 +17768,42 @@ public final class ActivityManagerService extends ActivityManagerNative
final long origId = Binder.clearCallingIdentity();
final ActivityStack stack = mStackSupervisor.getStack(fromStackId);
if (stack != null) {
- if (fromStackId == DOCKED_STACK_ID) {
-
- // We are moving all tasks from the docked stack to the fullscreen stack, which
- // is dismissing the docked stack, so resize all other stacks to fullscreen here
- // already so we don't end up with resize trashing.
- for (int i = FIRST_STATIC_STACK_ID; i <= LAST_STATIC_STACK_ID; i++) {
- if (StackId.isResizeableByDockedStack(i)) {
- ActivityStack otherStack = mStackSupervisor.getStack(i);
- if (otherStack != null) {
- mStackSupervisor.resizeStackLocked(i,
- null, null, null, PRESERVE_WINDOWS,
- true /* allowResizeInDockedMode */);
+ mWindowManager.deferSurfaceLayout();
+ try {
+ if (fromStackId == DOCKED_STACK_ID) {
+
+ // We are moving all tasks from the docked stack to the fullscreen stack,
+ // which is dismissing the docked stack, so resize all other stacks to
+ // fullscreen here already so we don't end up with resize trashing.
+ for (int i = FIRST_STATIC_STACK_ID; i <= LAST_STATIC_STACK_ID; i++) {
+ if (StackId.isResizeableByDockedStack(i)) {
+ ActivityStack otherStack = mStackSupervisor.getStack(i);
+ if (otherStack != null) {
+ mStackSupervisor.resizeStackLocked(i,
+ null, null, null, PRESERVE_WINDOWS,
+ true /* allowResizeInDockedMode */);
+ }
}
}
}
- }
- final ArrayList<TaskRecord> tasks = stack.getAllTasks();
- final int size = tasks.size();
- if (onTop) {
- for (int i = 0; i < size; i++) {
- mStackSupervisor.moveTaskToStackLocked(tasks.get(i).taskId,
- FULLSCREEN_WORKSPACE_STACK_ID, ON_TOP, !FORCE_FOCUS,
- "moveTasksToFullscreenStack", ANIMATE);
- }
- } else {
- for (int i = size - 1; i >= 0; i--) {
- mStackSupervisor.positionTaskInStackLocked(tasks.get(i).taskId,
- FULLSCREEN_WORKSPACE_STACK_ID, 0);
+ final ArrayList<TaskRecord> tasks = stack.getAllTasks();
+ final int size = tasks.size();
+ if (onTop) {
+ for (int i = 0; i < size; i++) {
+ mStackSupervisor.moveTaskToStackLocked(tasks.get(i).taskId,
+ FULLSCREEN_WORKSPACE_STACK_ID, onTop, !FORCE_FOCUS,
+ "moveTasksToFullscreenStack", ANIMATE);
+ }
+ } else {
+ for (int i = size - 1; i >= 0; i--) {
+ mStackSupervisor.positionTaskInStackLocked(tasks.get(i).taskId,
+ FULLSCREEN_WORKSPACE_STACK_ID, 0);
+ }
}
+ } finally {
+ mWindowManager.continueSurfaceLayout();
}
+
}
Binder.restoreCallingIdentity(origId);
}
diff --git a/services/core/java/com/android/server/am/ActivityStackSupervisor.java b/services/core/java/com/android/server/am/ActivityStackSupervisor.java
index c143474ce0c8..648c2387d2b5 100644
--- a/services/core/java/com/android/server/am/ActivityStackSupervisor.java
+++ b/services/core/java/com/android/server/am/ActivityStackSupervisor.java
@@ -2396,6 +2396,8 @@ public final class ActivityStackSupervisor implements DisplayListener {
stack.positionTask(task, position);
// The task might have already been running and its visibility needs to be synchronized with
// the visibility of the stack / windows.
+ stack.ensureActivityConfigurationLocked(task.topRunningActivityLocked(), 0,
+ !PRESERVE_WINDOWS);
stack.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
resumeFocusedStackTopActivityLocked();
}
diff --git a/services/core/java/com/android/server/wm/Task.java b/services/core/java/com/android/server/wm/Task.java
index 325005bb2206..807355202f90 100644
--- a/services/core/java/com/android/server/wm/Task.java
+++ b/services/core/java/com/android/server/wm/Task.java
@@ -247,7 +247,7 @@ class Task implements DimLayer.DimLayerUser {
mStack.removeTask(this);
}
stack.positionTask(this, position, showForAllUsers());
- setBounds(bounds, config);
+ resizeLocked(bounds, config, false /* force */);
}
boolean removeAppToken(AppWindowToken wtoken) {
@@ -272,7 +272,7 @@ class Task implements DimLayer.DimLayerUser {
}
/** Set the task bounds. Passing in null sets the bounds to fullscreen. */
- int setBounds(Rect bounds, Configuration config) {
+ private int setBounds(Rect bounds, Configuration config) {
if (config == null) {
config = Configuration.EMPTY;
}
@@ -598,13 +598,21 @@ class Task implements DimLayer.DimLayerUser {
void resizeWindows() {
final ArrayList<WindowState> resizingWindows = mService.mResizingWindows;
for (int activityNdx = mAppTokens.size() - 1; activityNdx >= 0; --activityNdx) {
- final ArrayList<WindowState> windows = mAppTokens.get(activityNdx).allAppWindows;
+ final AppWindowToken atoken = mAppTokens.get(activityNdx);
+
+ // Some windows won't go through the resizing process, if they don't have a surface, so
+ // destroy all saved surfaces here.
+ atoken.destroySavedSurfaces();
+ final ArrayList<WindowState> windows = atoken.allAppWindows;
for (int winNdx = windows.size() - 1; winNdx >= 0; --winNdx) {
final WindowState win = windows.get(winNdx);
if (win.mHasSurface && !resizingWindows.contains(win)) {
if (DEBUG_RESIZE) Slog.d(TAG, "resizeWindows: Resizing " + win);
resizingWindows.add(win);
}
+ if (win.isGoneForLayoutLw()) {
+ win.mResizedWhileGone = true;
+ }
}
}
}
diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java
index b5444fce8d52..cc97e68b6876 100644
--- a/services/core/java/com/android/server/wm/WindowManagerService.java
+++ b/services/core/java/com/android/server/wm/WindowManagerService.java
@@ -2758,6 +2758,9 @@ public class WindowManagerService extends IWindowManager.Stub
winAnimator.mReportSurfaceResized = false;
result |= WindowManagerGlobal.RELAYOUT_RES_SURFACE_RESIZED;
}
+ if (!win.isGoneForLayoutLw()) {
+ win.mResizedWhileGone = false;
+ }
outFrame.set(win.mCompatFrame);
outOverscanInsets.set(win.mOverscanInsets);
outContentInsets.set(win.mContentInsets);
diff --git a/services/core/java/com/android/server/wm/WindowState.java b/services/core/java/com/android/server/wm/WindowState.java
index f30c8d3f751b..8ad8ea0e420a 100644
--- a/services/core/java/com/android/server/wm/WindowState.java
+++ b/services/core/java/com/android/server/wm/WindowState.java
@@ -448,6 +448,11 @@ final class WindowState implements WindowManagerPolicy.WindowState {
final private Rect mTmpRect = new Rect();
+ /**
+ * Whether the window was resized by us while it was gone for layout.
+ */
+ boolean mResizedWhileGone = false;
+
WindowState(WindowManagerService service, Session s, IWindow c, WindowToken token,
WindowState attachedWindow, int appOp, int seq, WindowManager.LayoutParams a,
int viewVisibility, final DisplayContent displayContent) {
@@ -1235,7 +1240,7 @@ final class WindowState implements WindowManagerPolicy.WindowState {
return mViewVisibility == View.GONE
|| !mRelayoutCalled
|| (atoken == null && mRootToken.hidden)
- || (atoken != null && (atoken.hiddenRequested || atoken.hidden))
+ || (atoken != null && atoken.hiddenRequested)
|| mAttachedHidden
|| (mAnimatingExit && !isAnimatingLw())
|| mDestroying;
@@ -1836,6 +1841,12 @@ final class WindowState implements WindowManagerPolicy.WindowState {
return false;
}
+ if (mResizedWhileGone) {
+ // Somebody resized our window while we were gone for layout, which means that the
+ // client got an old size, so we have an outdated surface here.
+ return false;
+ }
+
if (DEBUG_DISABLE_SAVING_SURFACES) {
return false;
}