Merge "Destroy saved surfaces if one of the last visible windows gets removed" into nyc-dev

am: 15818e1156

* commit '15818e1156101f1d3a01009e7bc223d8ae88546d':
  Destroy saved surfaces if one of the last visible windows gets removed

Change-Id: I143743940263578e7111ae41eb7b88c005be18a6
This commit is contained in:
Chong Zhang
2016-05-25 17:42:33 +00:00
committed by android-build-merger
4 changed files with 36 additions and 17 deletions

View File

@@ -451,6 +451,16 @@ class AppWindowToken extends WindowToken {
destroySurfaces();
}
void markSavedSurfaceExiting() {
for (int i = allAppWindows.size() - 1; i >= 0; i--) {
final WindowState w = allAppWindows.get(i);
if (w.isAnimatingInvisibleWithSavedSurface()) {
w.mAnimatingExit = true;
w.mWinAnimator.mAnimating = true;
}
}
}
void restoreSavedSurfaces() {
if (!canRestoreSurfaces()) {
clearVisibleBeforeClientHidden();

View File

@@ -2277,6 +2277,19 @@ public class WindowManagerService extends IWindowManager.Stub
}
}
private void setupWindowForRemoveOnExit(WindowState win) {
win.mRemoveOnExit = true;
win.setDisplayLayoutNeeded();
// Request a focus update as this window's input channel is already gone. Otherwise
// we could have no focused window in input manager.
final boolean focusChanged = updateFocusedWindowLocked(
UPDATE_FOCUS_WILL_PLACE_SURFACES, false /*updateInputWindows*/);
mWindowPlacerLocked.performSurfacePlacement();
if (focusChanged) {
mInputMonitor.updateInputWindowsLw(false /*force*/);
}
}
public void removeWindow(Session session, IWindow client) {
synchronized(mWindowMap) {
WindowState win = windowForClientLocked(session, client, false);
@@ -2358,14 +2371,7 @@ public class WindowManagerService extends IWindowManager.Stub
// Do not set mAnimatingExit to true here, it will cause the surface to be hidden
// immediately after the enter animation is done. If the app is not yet drawn then
// it will show up as a flicker.
win.mRemoveOnExit = true;
// Request a focus update as this window's input channel is already gone. Otherwise
// we could have no focused window in input manager.
final boolean focusChanged = updateFocusedWindowLocked(
UPDATE_FOCUS_WILL_PLACE_SURFACES, false /*updateInputWindows*/);
if (focusChanged) {
mInputMonitor.updateInputWindowsLw(false /*force*/);
}
setupWindowForRemoveOnExit(win);
Binder.restoreCallingIdentity(origId);
return;
}
@@ -2417,17 +2423,10 @@ public class WindowManagerService extends IWindowManager.Stub
// The exit animation is running or should run... wait for it!
if (DEBUG_ADD_REMOVE) Slog.v(TAG_WM,
"Not removing " + win + " due to exit animation ");
win.mRemoveOnExit = true;
win.setDisplayLayoutNeeded();
final boolean focusChanged = updateFocusedWindowLocked(
UPDATE_FOCUS_WILL_PLACE_SURFACES, false /*updateInputWindows*/);
mWindowPlacerLocked.performSurfacePlacement();
setupWindowForRemoveOnExit(win);
if (appToken != null) {
appToken.updateReportedVisibilityLocked();
}
if (focusChanged) {
mInputMonitor.updateInputWindowsLw(false /*force*/);
}
Binder.restoreCallingIdentity(origId);
return;
}

View File

@@ -2111,7 +2111,9 @@ final class WindowState implements WindowManagerPolicy.WindowState {
void clearHasSavedSurface() {
mSurfaceSaved = false;
mAnimatingWithSavedSurface = false;
mWasVisibleBeforeClientHidden = false;
if (mWasVisibleBeforeClientHidden) {
mAppToken.destroySavedSurfaces();
}
}
boolean clearAnimatingWithSavedSurface() {

View File

@@ -1301,6 +1301,14 @@ class WindowSurfacePlacer {
appsCount = mService.mClosingApps.size();
for (int i = 0; i < appsCount; i++) {
AppWindowToken wtoken = mService.mClosingApps.valueAt(i);
// If we still have some windows animating with saved surfaces that's
// either invisible or already removed, mark them exiting so that they
// are disposed of after the exit animation. These are not supposed to
// be shown, or are delayed removal until app is actually drawn (in which
// case the window will be removed after the animation).
wtoken.markSavedSurfaceExiting();
final AppWindowAnimator appAnimator = wtoken.mAppAnimator;
if (DEBUG_APP_TRANSITIONS) Slog.v(TAG, "Now closing app " + wtoken);
appAnimator.clearThumbnail();