Prevent SurfaceView from drawing over parent surface insets
Parent SurfaceView to a bounds layer that enforces a crop preventing it from drawing over the surface insets. The bounds layer crop is set to the surface insets and updated when the parent surface size changes or the parent surface insets change. If the SurfaceView children are reparented to another client surface then ensure the SurfaceView relative layer info is updated correctly. Bug: 132205507 Test: go/wm-smoke Test: test preserve surfaces codepath with split screen and ensure relative z is preserved Test: test surfaceview apps, youtube, maps & camera. Test: try to repro maps pip issue described in bug Change-Id: I14c2f7603345ad89f0af4db48150b05d8ada602a
This commit is contained in:
@@ -105,7 +105,7 @@ public abstract class WallpaperService extends Service {
|
||||
|
||||
static final String TAG = "WallpaperService";
|
||||
static final boolean DEBUG = false;
|
||||
|
||||
|
||||
private static final int DO_ATTACH = 10;
|
||||
private static final int DO_DETACH = 20;
|
||||
private static final int DO_SET_DESIRED_SIZE = 30;
|
||||
@@ -126,7 +126,7 @@ public abstract class WallpaperService extends Service {
|
||||
|
||||
private final ArrayList<Engine> mActiveEngines
|
||||
= new ArrayList<Engine>();
|
||||
|
||||
|
||||
static final class WallpaperCommand {
|
||||
String action;
|
||||
int x;
|
||||
@@ -145,7 +145,7 @@ public abstract class WallpaperService extends Service {
|
||||
*/
|
||||
public class Engine {
|
||||
IWallpaperEngineWrapper mIWallpaperEngine;
|
||||
|
||||
|
||||
// Copies from mIWallpaperEngine.
|
||||
HandlerCaller mCaller;
|
||||
IWallpaperConnection mConnection;
|
||||
@@ -155,7 +155,7 @@ public abstract class WallpaperService extends Service {
|
||||
boolean mVisible;
|
||||
boolean mReportedVisible;
|
||||
boolean mDestroyed;
|
||||
|
||||
|
||||
// Current window state.
|
||||
boolean mCreated;
|
||||
boolean mSurfaceCreated;
|
||||
@@ -258,7 +258,7 @@ public abstract class WallpaperService extends Service {
|
||||
}
|
||||
super.setFixedSize(width, height);
|
||||
}
|
||||
|
||||
|
||||
public void setKeepScreenOn(boolean screenOn) {
|
||||
throw new UnsupportedOperationException(
|
||||
"Wallpapers do not support keep screen on");
|
||||
@@ -403,14 +403,14 @@ public abstract class WallpaperService extends Service {
|
||||
mClockFunction = clockFunction;
|
||||
mHandler = handler;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Provides access to the surface in which this wallpaper is drawn.
|
||||
*/
|
||||
public SurfaceHolder getSurfaceHolder() {
|
||||
return mSurfaceHolder;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Convenience for {@link WallpaperManager#getDesiredMinimumWidth()
|
||||
* WallpaperManager.getDesiredMinimumWidth()}, returning the width
|
||||
@@ -419,7 +419,7 @@ public abstract class WallpaperService extends Service {
|
||||
public int getDesiredMinimumWidth() {
|
||||
return mIWallpaperEngine.mReqWidth;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Convenience for {@link WallpaperManager#getDesiredMinimumHeight()
|
||||
* WallpaperManager.getDesiredMinimumHeight()}, returning the height
|
||||
@@ -437,7 +437,7 @@ public abstract class WallpaperService extends Service {
|
||||
public boolean isVisible() {
|
||||
return mReportedVisible;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Returns true if this engine is running in preview mode -- that is,
|
||||
* it is being shown to the user before they select it as the actual
|
||||
@@ -456,7 +456,7 @@ public abstract class WallpaperService extends Service {
|
||||
public boolean isInAmbientMode() {
|
||||
return mIsInAmbientMode;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Control whether this wallpaper will receive raw touch events
|
||||
* from the window manager as the user interacts with the window
|
||||
@@ -557,7 +557,7 @@ public abstract class WallpaperService extends Service {
|
||||
* {@link WallpaperManager#sendWallpaperCommand}.
|
||||
* The default implementation does nothing, and always returns null
|
||||
* as the result.
|
||||
*
|
||||
*
|
||||
* @param action The name of the command to perform. This tells you
|
||||
* what to do and how to interpret the rest of the arguments.
|
||||
* @param x Generic integer parameter.
|
||||
@@ -794,7 +794,7 @@ public abstract class WallpaperService extends Service {
|
||||
}
|
||||
|
||||
mLayout.format = mFormat;
|
||||
|
||||
|
||||
mCurWindowFlags = mWindowFlags;
|
||||
mLayout.flags = mWindowFlags
|
||||
| WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS
|
||||
@@ -1020,7 +1020,7 @@ public abstract class WallpaperService extends Service {
|
||||
mIsCreating = false;
|
||||
mSurfaceCreated = true;
|
||||
if (redrawNeeded) {
|
||||
mSession.finishDrawing(mWindow);
|
||||
mSession.finishDrawing(mWindow, null /* postDrawTransaction */);
|
||||
}
|
||||
mIWallpaperEngine.reportShown();
|
||||
}
|
||||
@@ -1045,7 +1045,7 @@ public abstract class WallpaperService extends Service {
|
||||
mSurfaceHolder.setSizeFromLayout();
|
||||
mInitializing = true;
|
||||
mSession = WindowManagerGlobal.getWindowSession();
|
||||
|
||||
|
||||
mWindow.setSession(mSession);
|
||||
|
||||
mLayout.packageName = getPackageName();
|
||||
@@ -1149,7 +1149,7 @@ public abstract class WallpaperService extends Service {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void doOffsetsChanged(boolean always) {
|
||||
if (mDestroyed) {
|
||||
return;
|
||||
@@ -1187,7 +1187,7 @@ public abstract class WallpaperService extends Service {
|
||||
mOffsetsChanged = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (sync) {
|
||||
try {
|
||||
if (DEBUG) Log.v(TAG, "Reporting offsets change complete");
|
||||
@@ -1196,7 +1196,7 @@ public abstract class WallpaperService extends Service {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void doCommand(WallpaperCommand cmd) {
|
||||
Bundle result;
|
||||
if (!mDestroyed) {
|
||||
@@ -1213,7 +1213,7 @@ public abstract class WallpaperService extends Service {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void reportSurfaceDestroyed() {
|
||||
if (mSurfaceCreated) {
|
||||
mSurfaceCreated = false;
|
||||
@@ -1229,12 +1229,12 @@ public abstract class WallpaperService extends Service {
|
||||
onSurfaceDestroyed(mSurfaceHolder);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void detach() {
|
||||
if (mDestroyed) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
mDestroyed = true;
|
||||
|
||||
if (mIWallpaperEngine.mDisplayManager != null) {
|
||||
@@ -1246,9 +1246,9 @@ public abstract class WallpaperService extends Service {
|
||||
if (DEBUG) Log.v(TAG, "onVisibilityChanged(false): " + this);
|
||||
onVisibilityChanged(false);
|
||||
}
|
||||
|
||||
|
||||
reportSurfaceDestroyed();
|
||||
|
||||
|
||||
if (DEBUG) Log.v(TAG, "onDestroy(): " + this);
|
||||
onDestroy();
|
||||
|
||||
@@ -1256,18 +1256,18 @@ public abstract class WallpaperService extends Service {
|
||||
try {
|
||||
if (DEBUG) Log.v(TAG, "Removing window and destroying surface "
|
||||
+ mSurfaceHolder.getSurface() + " of: " + this);
|
||||
|
||||
|
||||
if (mInputEventReceiver != null) {
|
||||
mInputEventReceiver.dispose();
|
||||
mInputEventReceiver = null;
|
||||
}
|
||||
|
||||
|
||||
mSession.remove(mWindow);
|
||||
} catch (RemoteException e) {
|
||||
}
|
||||
mSurfaceHolder.mSurface.release();
|
||||
mCreated = false;
|
||||
|
||||
|
||||
// Dispose the input channel after removing the window so the Window Manager
|
||||
// doesn't interpret the input channel being closed as an abnormal termination.
|
||||
if (mInputChannel != null) {
|
||||
|
||||
@@ -2,15 +2,15 @@
|
||||
**
|
||||
** Copyright 2006, The Android Open Source Project
|
||||
**
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
** you may not use this file except in compliance with the License.
|
||||
** You may obtain a copy of the License at
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
** you may not use this file except in compliance with the License.
|
||||
** You may obtain a copy of the License at
|
||||
**
|
||||
** http://www.apache.org/licenses/LICENSE-2.0
|
||||
** http://www.apache.org/licenses/LICENSE-2.0
|
||||
**
|
||||
** Unless required by applicable law or agreed to in writing, software
|
||||
** distributed under the License is distributed on an "AS IS" BASIS,
|
||||
** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
** Unless required by applicable law or agreed to in writing, software
|
||||
** distributed under the License is distributed on an "AS IS" BASIS,
|
||||
** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
** See the License for the specific language governing permissions and
|
||||
** limitations under the License.
|
||||
*/
|
||||
@@ -31,6 +31,7 @@ import android.view.WindowManager;
|
||||
import android.view.InsetsState;
|
||||
import android.view.Surface;
|
||||
import android.view.SurfaceControl;
|
||||
import android.view.Transaction;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@@ -57,7 +58,7 @@ interface IWindowSession {
|
||||
* position should be ignored) and surface of the window. The surface
|
||||
* will be invalid if the window is currently hidden, else you can use it
|
||||
* to draw the window's contents.
|
||||
*
|
||||
*
|
||||
* @param window The window being modified.
|
||||
* @param seq Ordering sequence number.
|
||||
* @param attrs If non-null, new attributes to apply to the window.
|
||||
@@ -147,8 +148,15 @@ interface IWindowSession {
|
||||
*/
|
||||
void getDisplayFrame(IWindow window, out Rect outDisplayFrame);
|
||||
|
||||
/**
|
||||
* Called when the client has finished drawing the surface, if needed.
|
||||
*
|
||||
* @param postDrawTransaction transaction filled by the client that can be
|
||||
* used to synchronize any post draw transactions with the server. Transaction
|
||||
* is null if there is no sync required.
|
||||
*/
|
||||
@UnsupportedAppUsage
|
||||
void finishDrawing(IWindow window);
|
||||
void finishDrawing(IWindow window, in Transaction postDrawTransaction);
|
||||
|
||||
@UnsupportedAppUsage
|
||||
void setInTouchMode(boolean showFocus);
|
||||
|
||||
@@ -2693,6 +2693,14 @@ public final class SurfaceControl implements Parcelable {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Writes the transaction to parcel, clearing the transaction as if it had been applied so
|
||||
* it can be used to store future transactions. It's the responsibility of the parcel
|
||||
* reader to apply the original transaction.
|
||||
*
|
||||
* @param dest parcel to write the transaction to
|
||||
* @param flags
|
||||
*/
|
||||
@Override
|
||||
public void writeToParcel(@NonNull Parcel dest, @WriteFlags int flags) {
|
||||
if (mNativeObject == 0) {
|
||||
|
||||
@@ -98,7 +98,8 @@ import java.util.concurrent.locks.ReentrantLock;
|
||||
* artifacts may occur on previous versions of the platform when its window is
|
||||
* positioned asynchronously.</p>
|
||||
*/
|
||||
public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallback {
|
||||
public class SurfaceView extends View
|
||||
implements ViewRootImpl.WindowStoppedCallback, ViewRootImpl.SurfaceChangedCallback {
|
||||
private static final String TAG = "SurfaceView";
|
||||
private static final boolean DEBUG = false;
|
||||
|
||||
@@ -120,7 +121,7 @@ public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallb
|
||||
boolean mDrawFinished = false;
|
||||
|
||||
final Rect mScreenRect = new Rect();
|
||||
SurfaceSession mSurfaceSession;
|
||||
final SurfaceSession mSurfaceSession = new SurfaceSession();
|
||||
|
||||
SurfaceControl mSurfaceControl;
|
||||
// In the case of format changes we switch out the surface in-place
|
||||
@@ -266,11 +267,22 @@ public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallb
|
||||
updateSurface();
|
||||
}
|
||||
|
||||
/** @hide */
|
||||
@Override
|
||||
public void surfaceChangedCallback(SurfaceControl.Transaction transaction) {
|
||||
if (getViewRootImpl() != null && mBackgroundControl != null && mSurfaceControl != null) {
|
||||
SurfaceControl sc = getViewRootImpl().getSurfaceControl();
|
||||
transaction.setRelativeLayer(mBackgroundControl, sc, Integer.MIN_VALUE);
|
||||
transaction.setRelativeLayer(mSurfaceControl, sc, mSubLayer);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttachedToWindow() {
|
||||
super.onAttachedToWindow();
|
||||
|
||||
getViewRootImpl().addWindowStoppedCallback(this);
|
||||
getViewRootImpl().addSurfaceChangedCallback(this);
|
||||
mWindowStopped = false;
|
||||
|
||||
mViewVisibility = getVisibility() == VISIBLE;
|
||||
@@ -356,6 +368,7 @@ public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallb
|
||||
// the SurfaceHolder forward, most live wallpapers do it.
|
||||
if (viewRoot != null) {
|
||||
viewRoot.removeWindowStoppedCallback(this);
|
||||
viewRoot.removeSurfaceChangedCallback(this);
|
||||
}
|
||||
|
||||
mAttachedToWindow = false;
|
||||
@@ -637,21 +650,34 @@ public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallb
|
||||
mScreenRect.offset(surfaceInsets.left, surfaceInsets.top);
|
||||
|
||||
if (creating) {
|
||||
viewRoot.createBoundsSurface(mSubLayer);
|
||||
mSurfaceSession = new SurfaceSession();
|
||||
mDeferredDestroySurfaceControl = mSurfaceControl;
|
||||
|
||||
updateOpaqueFlag();
|
||||
// SurfaceView hierarchy
|
||||
// ViewRootImpl surface
|
||||
// - bounds layer (crops all child surfaces to parent surface insets)
|
||||
// - SurfaceView surface (drawn relative to ViewRootImpl surface)
|
||||
// - Background color layer (drawn behind all SurfaceView surfaces)
|
||||
//
|
||||
// The bounds layer is used to crop the surface view so it does not draw into
|
||||
// the parent surface inset region. Since there can be multiple surface views
|
||||
// below or above the parent surface, one option is to create multiple bounds
|
||||
// layer for each z order. The other option, the one implement is to create
|
||||
// a single bounds layer and set z order for each child surface relative to the
|
||||
// parent surface.
|
||||
// When creating the surface view, we parent it to the bounds layer and then
|
||||
// set the relative z order. When the parent surface changes, we have to
|
||||
// make sure to update the relative z via ViewRootImpl.SurfaceChangedCallback.
|
||||
final String name = "SurfaceView - " + viewRoot.getTitle().toString();
|
||||
|
||||
mSurfaceControl = new SurfaceControl.Builder(mSurfaceSession)
|
||||
.setName(name)
|
||||
.setOpaque((mSurfaceFlags & SurfaceControl.OPAQUE) != 0)
|
||||
.setBufferSize(mSurfaceWidth, mSurfaceHeight)
|
||||
.setFormat(mFormat)
|
||||
.setParent(viewRoot.getSurfaceControl())
|
||||
.setFlags(mSurfaceFlags)
|
||||
.build();
|
||||
mSurfaceControl =
|
||||
new SurfaceControl.Builder(mSurfaceSession)
|
||||
.setName(name)
|
||||
.setOpaque((mSurfaceFlags & SurfaceControl.OPAQUE) != 0)
|
||||
.setBufferSize(mSurfaceWidth, mSurfaceHeight)
|
||||
.setFormat(mFormat)
|
||||
.setParent(viewRoot.getBoundsLayer())
|
||||
.setFlags(mSurfaceFlags)
|
||||
.build();
|
||||
mBackgroundControl = new SurfaceControl.Builder(mSurfaceSession)
|
||||
.setName("Background for -" + name)
|
||||
.setOpaque(true)
|
||||
@@ -674,7 +700,7 @@ public class SurfaceView extends View implements ViewRootImpl.WindowStoppedCallb
|
||||
|
||||
SurfaceControl.openTransaction();
|
||||
try {
|
||||
mSurfaceControl.setLayer(mSubLayer);
|
||||
mSurfaceControl.setRelativeLayer(viewRoot.getSurfaceControl(), mSubLayer);
|
||||
|
||||
if (mViewVisibility) {
|
||||
mSurfaceControl.show();
|
||||
|
||||
@@ -68,6 +68,7 @@ import android.os.Build;
|
||||
import android.os.Bundle;
|
||||
import android.os.Debug;
|
||||
import android.os.Handler;
|
||||
import android.os.IBinder;
|
||||
import android.os.Looper;
|
||||
import android.os.Message;
|
||||
import android.os.ParcelFileDescriptor;
|
||||
@@ -476,17 +477,19 @@ public final class ViewRootImpl implements ViewParent,
|
||||
@UnsupportedAppUsage
|
||||
public final Surface mSurface = new Surface();
|
||||
private final SurfaceControl mSurfaceControl = new SurfaceControl();
|
||||
private IBinder mPreviousSurfaceControlHandle = null;
|
||||
|
||||
private final Transaction mChangeSurfaceTransaction = new Transaction();
|
||||
private final SurfaceSession mSurfaceSession = new SurfaceSession();
|
||||
|
||||
/**
|
||||
* Child surface of {@code mSurface} with the same bounds as its parent, and crop bounds
|
||||
* are set to the parent's bounds adjusted for surface insets. This surface is created when
|
||||
* {@link ViewRootImpl#createBoundsSurface(int)} is called.
|
||||
* By parenting to this bounds surface, child surfaces can ensure they do not draw into the
|
||||
* surface inset regions set by the parent window.
|
||||
* Child container layer of {@code mSurface} with the same bounds as its parent, and cropped to
|
||||
* the surface insets. This surface is created only if a client requests it via {@link
|
||||
* #getBoundsLayer()}. By parenting to this bounds surface, child surfaces can ensure they do
|
||||
* not draw into the surface inset regions set by the parent window.
|
||||
*/
|
||||
public final Surface mBoundsSurface = new Surface();
|
||||
private SurfaceSession mSurfaceSession;
|
||||
private SurfaceControl mBoundsSurfaceControl;
|
||||
private SurfaceControl mBoundsLayer;
|
||||
|
||||
private final Transaction mTransaction = new Transaction();
|
||||
|
||||
@UnsupportedAppUsage
|
||||
@@ -1576,65 +1579,76 @@ public final class ViewRootImpl implements ViewParent,
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a surface as a child of {@code mSurface} with the same bounds as its parent and
|
||||
* crop bounds set to the parent's bounds adjusted for surface insets.
|
||||
*
|
||||
* @param zOrderLayer Z order relative to the parent surface.
|
||||
*/
|
||||
public void createBoundsSurface(int zOrderLayer) {
|
||||
if (mSurfaceSession == null) {
|
||||
mSurfaceSession = new SurfaceSession();
|
||||
}
|
||||
if (mBoundsSurfaceControl != null && mBoundsSurface.isValid()) {
|
||||
return; // surface control for bounds surface already exists.
|
||||
}
|
||||
/** Register callback to be notified when the ViewRootImpl surface changes. */
|
||||
interface SurfaceChangedCallback {
|
||||
void surfaceChangedCallback(SurfaceControl.Transaction transaction);
|
||||
}
|
||||
|
||||
mBoundsSurfaceControl = new SurfaceControl.Builder(mSurfaceSession)
|
||||
private final ArrayList<SurfaceChangedCallback> mSurfaceChangedCallbacks = new ArrayList<>();
|
||||
void addSurfaceChangedCallback(SurfaceChangedCallback c) {
|
||||
mSurfaceChangedCallbacks.add(c);
|
||||
}
|
||||
|
||||
void removeSurfaceChangedCallback(SurfaceChangedCallback c) {
|
||||
mSurfaceChangedCallbacks.remove(c);
|
||||
}
|
||||
|
||||
private void notifySurfaceChanged(SurfaceControl.Transaction transaction) {
|
||||
for (int i = 0; i < mSurfaceChangedCallbacks.size(); i++) {
|
||||
mSurfaceChangedCallbacks.get(i).surfaceChangedCallback(transaction);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a child layer with the same bounds as its parent {@code mSurface} and cropped to the
|
||||
* surface insets. If the layer does not exist, it is created.
|
||||
*
|
||||
* <p>Parenting to this layer will ensure that its children are cropped by the view's surface
|
||||
* insets.
|
||||
*/
|
||||
public SurfaceControl getBoundsLayer() {
|
||||
if (mBoundsLayer == null) {
|
||||
mBoundsLayer = new SurfaceControl.Builder(mSurfaceSession)
|
||||
.setContainerLayer()
|
||||
.setName("Bounds for - " + getTitle().toString())
|
||||
.setParent(mSurfaceControl)
|
||||
.build();
|
||||
|
||||
setBoundsSurfaceCrop();
|
||||
mTransaction.setLayer(mBoundsSurfaceControl, zOrderLayer)
|
||||
.show(mBoundsSurfaceControl)
|
||||
.apply();
|
||||
mBoundsSurface.copyFrom(mBoundsSurfaceControl);
|
||||
setBoundsLayerCrop(mTransaction);
|
||||
mTransaction.show(mBoundsLayer).apply();
|
||||
}
|
||||
return mBoundsLayer;
|
||||
}
|
||||
|
||||
private void setBoundsSurfaceCrop() {
|
||||
private void setBoundsLayerCrop(Transaction t) {
|
||||
// mWinFrame is already adjusted for surface insets. So offset it and use it as
|
||||
// the cropping bounds.
|
||||
mTempBoundsRect.set(mWinFrame);
|
||||
mTempBoundsRect.offsetTo(mWindowAttributes.surfaceInsets.left,
|
||||
mWindowAttributes.surfaceInsets.top);
|
||||
mTransaction.setWindowCrop(mBoundsSurfaceControl, mTempBoundsRect);
|
||||
t.setWindowCrop(mBoundsLayer, mTempBoundsRect);
|
||||
}
|
||||
|
||||
/**
|
||||
* Called after window layout to update the bounds surface. If the surface insets have
|
||||
* changed or the surface has resized, update the bounds surface.
|
||||
* Called after window layout to update the bounds surface. If the surface insets have changed
|
||||
* or the surface has resized, update the bounds surface.
|
||||
*/
|
||||
private void updateBoundsSurface() {
|
||||
if (mBoundsSurfaceControl != null && mSurface.isValid()) {
|
||||
setBoundsSurfaceCrop();
|
||||
mTransaction.deferTransactionUntilSurface(mBoundsSurfaceControl,
|
||||
private void updateBoundsLayer() {
|
||||
if (mBoundsLayer != null) {
|
||||
setBoundsLayerCrop(mTransaction);
|
||||
mTransaction.deferTransactionUntilSurface(mBoundsLayer,
|
||||
mSurface, mSurface.getNextFrameNumber())
|
||||
.apply();
|
||||
}
|
||||
}
|
||||
|
||||
private void destroySurface() {
|
||||
if (mBoundsLayer != null) {
|
||||
mBoundsLayer.release();
|
||||
mBoundsLayer = null;
|
||||
}
|
||||
mSurface.release();
|
||||
mSurfaceControl.release();
|
||||
|
||||
mSurfaceSession = null;
|
||||
|
||||
if (mBoundsSurfaceControl != null) {
|
||||
mBoundsSurfaceControl.remove();
|
||||
mBoundsSurface.release();
|
||||
mBoundsSurfaceControl = null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -2598,7 +2612,7 @@ public final class ViewRootImpl implements ViewParent,
|
||||
}
|
||||
|
||||
if (surfaceSizeChanged) {
|
||||
updateBoundsSurface();
|
||||
updateBoundsLayer();
|
||||
}
|
||||
|
||||
final boolean didLayout = layoutRequested && (!mStopped || mReportNextDraw);
|
||||
@@ -3438,7 +3452,9 @@ public final class ViewRootImpl implements ViewParent,
|
||||
private void reportDrawFinished() {
|
||||
try {
|
||||
mDrawsNeededToReport = 0;
|
||||
mWindowSession.finishDrawing(mWindow);
|
||||
if (mSurfaceControl.isValid()) {
|
||||
mWindowSession.finishDrawing(mWindow, mChangeSurfaceTransaction);
|
||||
}
|
||||
} catch (RemoteException e) {
|
||||
// Have fun!
|
||||
}
|
||||
@@ -7089,6 +7105,9 @@ public final class ViewRootImpl implements ViewParent,
|
||||
frameNumber = mSurface.getNextFrameNumber();
|
||||
}
|
||||
|
||||
mPreviousSurfaceControlHandle = mSurfaceControl.isValid()
|
||||
? mSurfaceControl.getHandle() : null;
|
||||
|
||||
int relayoutResult = mWindowSession.relayout(mWindow, mSeq, params,
|
||||
(int) (mView.getMeasuredWidth() * appScale + 0.5f),
|
||||
(int) (mView.getMeasuredHeight() * appScale + 0.5f), viewVisibility,
|
||||
@@ -7102,6 +7121,11 @@ public final class ViewRootImpl implements ViewParent,
|
||||
destroySurface();
|
||||
}
|
||||
|
||||
if (mPreviousSurfaceControlHandle != null && mSurfaceControl.isValid()
|
||||
&& mPreviousSurfaceControlHandle != mSurfaceControl.getHandle()) {
|
||||
notifySurfaceChanged(mChangeSurfaceTransaction);
|
||||
}
|
||||
|
||||
mPendingAlwaysConsumeSystemBars =
|
||||
(relayoutResult & WindowManagerGlobal.RELAYOUT_RES_CONSUME_ALWAYS_SYSTEM_BARS) != 0;
|
||||
|
||||
@@ -7326,7 +7350,8 @@ public final class ViewRootImpl implements ViewParent,
|
||||
try {
|
||||
if ((relayoutWindow(mWindowAttributes, viewVisibility, false)
|
||||
& WindowManagerGlobal.RELAYOUT_RES_FIRST_TIME) != 0) {
|
||||
mWindowSession.finishDrawing(mWindow);
|
||||
mWindowSession.finishDrawing(
|
||||
mWindow, null /* postDrawTransaction */);
|
||||
}
|
||||
} catch (RemoteException e) {
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user