From b2e37802995e710c4a4d7b28e35c0b584ad2be7a Mon Sep 17 00:00:00 2001 From: Andrii Kulian Date: Wed, 11 Jan 2017 00:36:44 -0800 Subject: [PATCH] Relayout window when rotated landscape <-> seascape When 180 degree rotation happens there is no real configuration change, so an application window could miss an update, which caused visual artifacts. In this CL layout is forced when rotation changes. Test: Unit tests in ag/1778638. Bug: 33607506 Change-Id: Ia1e3375212bade9061d6e1d9679604e67c50da20 --- core/java/android/view/ViewRootImpl.java | 3 ++- .../server/wm/WindowManagerService.java | 2 +- .../com/android/server/wm/WindowState.java | 27 ++++++++++++++----- 3 files changed, 23 insertions(+), 9 deletions(-) diff --git a/core/java/android/view/ViewRootImpl.java b/core/java/android/view/ViewRootImpl.java index b42f7695c3de5..36825dd179353 100644 --- a/core/java/android/view/ViewRootImpl.java +++ b/core/java/android/view/ViewRootImpl.java @@ -1724,6 +1724,7 @@ public final class ViewRootImpl implements ViewParent, final int surfaceGenerationId = mSurface.getGenerationId(); final boolean isViewVisible = viewVisibility == View.VISIBLE; + final boolean windowRelayoutWasForced = mForceNextWindowRelayout; if (mFirst || windowShouldResize || insetsChanged || viewVisibilityChanged || params != null || mForceNextWindowRelayout) { mForceNextWindowRelayout = false; @@ -1888,7 +1889,7 @@ public final class ViewRootImpl implements ViewParent, mAttachInfo.mThreadedRenderer.destroy(); } } else if ((surfaceGenerationId != mSurface.getGenerationId() - || surfaceSizeChanged) + || surfaceSizeChanged || windowRelayoutWasForced) && mSurfaceHolder == null && mAttachInfo.mThreadedRenderer != null) { mFullRedrawNeeded = true; diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java index 38cb54320a1b7..332a9b91d5f91 100644 --- a/services/core/java/com/android/server/wm/WindowManagerService.java +++ b/services/core/java/com/android/server/wm/WindowManagerService.java @@ -4465,7 +4465,7 @@ public class WindowManagerService extends IWindowManager.Stub mRoot.mOrientationChangeComplete = false; w.mLastFreezeDuration = 0; } - + w.mReportOrientationChanged = true; }, true /* traverseTopToBottom */); if (rotateSeamlessly) { diff --git a/services/core/java/com/android/server/wm/WindowState.java b/services/core/java/com/android/server/wm/WindowState.java index 3daad4373d069..3816d5d0bf977 100644 --- a/services/core/java/com/android/server/wm/WindowState.java +++ b/services/core/java/com/android/server/wm/WindowState.java @@ -428,6 +428,11 @@ class WindowState extends WindowContainer implements WindowManagerP */ int mLastVisibleLayoutRotation = -1; + /** + * Set when we need to report the orientation change to client to trigger a relayout. + */ + boolean mReportOrientationChanged; + /** * How long we last kept the screen frozen. */ @@ -1093,7 +1098,8 @@ class WindowState extends WindowContainer implements WindowManagerP || mFrameSizeChanged || configChanged || dragResizingChanged - || !isResizedWhileNotDragResizingReported()) { + || !isResizedWhileNotDragResizingReported() + || mReportOrientationChanged) { if (DEBUG_RESIZE || DEBUG_ORIENTATION) { Slog.v(TAG_WM, "Resize reasons for w=" + this + ": " + " contentInsetsChanged=" + mContentInsetsChanged @@ -1108,7 +1114,8 @@ class WindowState extends WindowContainer implements WindowManagerP + " configChanged=" + configChanged + " dragResizingChanged=" + dragResizingChanged + " resizedWhileNotDragResizingReported=" - + isResizedWhileNotDragResizingReported()); + + isResizedWhileNotDragResizingReported() + + " reportOrientationChanged=" + mReportOrientationChanged); } // If it's a dead window left on screen, and the configuration changed, there is nothing @@ -3004,6 +3011,7 @@ class WindowState extends WindowContainer implements WindowManagerP final Rect stableInsets = mLastStableInsets; final Rect outsets = mLastOutsets; final boolean reportDraw = mWinAnimator.mDrawState == DRAW_PENDING; + final boolean reportOrientation = mReportOrientationChanged; if (mAttrs.type != WindowManager.LayoutParams.TYPE_APPLICATION_STARTING && mClient instanceof IWindow.Stub) { // To prevent deadlock simulate one-way call if win.mClient is a local object. @@ -3012,7 +3020,8 @@ class WindowState extends WindowContainer implements WindowManagerP public void run() { try { dispatchResized(frame, overscanInsets, contentInsets, visibleInsets, - stableInsets, outsets, reportDraw, newConfig); + stableInsets, outsets, reportDraw, newConfig, + reportOrientation); } catch (RemoteException e) { // Not a remote call, RemoteException won't be raised. } @@ -3020,7 +3029,7 @@ class WindowState extends WindowContainer implements WindowManagerP }); } else { dispatchResized(frame, overscanInsets, contentInsets, visibleInsets, stableInsets, - outsets, reportDraw, newConfig); + outsets, reportDraw, newConfig, reportOrientation); } //TODO (multidisplay): Accessibility supported only for the default display. @@ -3036,6 +3045,7 @@ class WindowState extends WindowContainer implements WindowManagerP mFrameSizeChanged = false; mResizedWhileNotDragResizingReported = true; mWinAnimator.mSurfaceResized = false; + mReportOrientationChanged = false; } catch (RemoteException e) { mOrientationChanging = false; mLastFreezeDuration = (int)(SystemClock.elapsedRealtime() @@ -3076,8 +3086,9 @@ class WindowState extends WindowContainer implements WindowManagerP private void dispatchResized(Rect frame, Rect overscanInsets, Rect contentInsets, Rect visibleInsets, Rect stableInsets, Rect outsets, boolean reportDraw, - Configuration newConfig) throws RemoteException { - final boolean forceRelayout = isDragResizeChanged() || mResizedWhileNotDragResizing; + Configuration newConfig, boolean reportOrientation) throws RemoteException { + final boolean forceRelayout = isDragResizeChanged() || mResizedWhileNotDragResizing + || reportOrientation; mClient.resized(frame, overscanInsets, contentInsets, visibleInsets, stableInsets, outsets, reportDraw, newConfig, getBackdropFrame(frame), @@ -3370,11 +3381,13 @@ class WindowState extends WindowContainer implements WindowManagerP pw.print(" mDestroying="); pw.print(mDestroying); pw.print(" mRemoved="); pw.println(mRemoved); } - if (mOrientationChanging || mAppFreezing || mTurnOnScreen) { + if (mOrientationChanging || mAppFreezing || mTurnOnScreen + || mReportOrientationChanged) { pw.print(prefix); pw.print("mOrientationChanging="); pw.print(mOrientationChanging); pw.print(" mAppFreezing="); pw.print(mAppFreezing); pw.print(" mTurnOnScreen="); pw.println(mTurnOnScreen); + pw.print(" mReportOrientationChanged="); pw.println(mReportOrientationChanged); } if (mLastFreezeDuration != 0) { pw.print(prefix); pw.print("mLastFreezeDuration=");