Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 6979344d authored by Vishnu Nair's avatar Vishnu Nair Committed by Android (Google) Code Review
Browse files

Merge changes I0ccbdb5a,I0f5d57e5 into sc-dev

* changes:
  Use surface size instead of frame size when adjusting layer bounds
  Fix SurfaceView background layer leaks
parents 3dba81df 127b0e6f
Loading
Loading
Loading
Loading
+59 −30
Original line number Diff line number Diff line
@@ -1083,7 +1083,12 @@ public class SurfaceView extends View implements ViewRootImpl.SurfaceChangedCall

                if (creating) {
                    updateOpaqueFlag();
                    mDeferredDestroySurfaceControl = createSurfaceControls(viewRoot);
                    final String name = "SurfaceView[" + viewRoot.getTitle().toString() + "]";
                    if (mUseBlastAdapter) {
                        createBlastSurfaceControls(viewRoot, name);
                    } else {
                        mDeferredDestroySurfaceControl = createSurfaceControls(viewRoot, name);
                    }
                } else if (mSurfaceControl == null) {
                    return;
                }
@@ -1220,53 +1225,77 @@ public class SurfaceView extends View implements ViewRootImpl.SurfaceChangedCall
     * out, the old surface can be persevered until the new one has drawn by keeping the reference
     * of the old SurfaceControl alive.
     */
    private SurfaceControl createSurfaceControls(ViewRootImpl viewRoot) {
        final String name = "SurfaceView[" + viewRoot.getTitle().toString() + "]";

        SurfaceControl.Builder builder = new SurfaceControl.Builder(mSurfaceSession)
    private SurfaceControl createSurfaceControls(ViewRootImpl viewRoot, String name) {
        final SurfaceControl previousSurfaceControl = mSurfaceControl;
        mSurfaceControl = new SurfaceControl.Builder(mSurfaceSession)
                .setName(name)
                .setLocalOwnerView(this)
                .setParent(viewRoot.getBoundsLayer())
                .setCallsite("SurfaceView.updateSurface");
                .setCallsite("SurfaceView.updateSurface")
                .setBufferSize(mSurfaceWidth, mSurfaceHeight)
                .setFlags(mSurfaceFlags)
                .setFormat(mFormat)
                .build();
        mBackgroundControl = createBackgroundControl(name);
        return previousSurfaceControl;
    }

        final SurfaceControl previousSurfaceControl;
        if (mUseBlastAdapter) {
            mSurfaceControl = builder
    private SurfaceControl createBackgroundControl(String name) {
        return new SurfaceControl.Builder(mSurfaceSession)
        .setName("Background for " + name)
        .setLocalOwnerView(this)
        .setOpaque(true)
        .setColorLayer()
        .setParent(mSurfaceControl)
        .setCallsite("SurfaceView.updateSurface")
        .build();
    }

    // We don't recreate the surface controls but only recreate the adapter. Since the blast layer
    // is still alive, the old buffers will continue to be presented until replaced by buffers from
    // the new adapter. This means we do not need to track the old surface control and destroy it
    // after the client has drawn to avoid any flickers.
    private void createBlastSurfaceControls(ViewRootImpl viewRoot, String name) {
        if (mSurfaceControl == null) {
            mSurfaceControl = new SurfaceControl.Builder(mSurfaceSession)
                    .setName(name)
                    .setLocalOwnerView(this)
                    .setParent(viewRoot.getBoundsLayer())
                    .setCallsite("SurfaceView.updateSurface")
                    .setContainerLayer()
                    .build();
            previousSurfaceControl = mBlastSurfaceControl;
        }

        if (mBlastSurfaceControl == null) {
            mBlastSurfaceControl = new SurfaceControl.Builder(mSurfaceSession)
                    .setName(name + "(BLAST)")
                    .setLocalOwnerView(this)
                    .setBufferSize(mSurfaceWidth, mSurfaceHeight)
                    .setParent(mSurfaceControl)
                    .setFlags(mSurfaceFlags)
                    .setHidden(false)
                    .setBLASTLayer()
                    .setCallsite("SurfaceView.updateSurface")
                    .build();
            mBlastBufferQueue = new BLASTBufferQueue(name, mBlastSurfaceControl, mSurfaceWidth,
                    mSurfaceHeight, mFormat, true /* TODO */);
        } else {
            previousSurfaceControl = mSurfaceControl;
            mSurfaceControl = builder
                    .setBufferSize(mSurfaceWidth, mSurfaceHeight)
                    .setFlags(mSurfaceFlags)
                    .setFormat(mFormat)
                    .build();
            mBlastSurfaceControl = null;
            mBlastBufferQueue = null;
            // update blast layer
            mTmpTransaction
                    .setOpaque(mBlastSurfaceControl, (mSurfaceFlags & SurfaceControl.OPAQUE) != 0)
                    .setSecure(mBlastSurfaceControl, (mSurfaceFlags & SurfaceControl.SECURE) != 0)
                    .show(mBlastSurfaceControl)
                    .apply();
        }
        mBackgroundControl = new SurfaceControl.Builder(mSurfaceSession)
            .setName("Background for " + name)
            .setLocalOwnerView(this)
            .setOpaque(true)
            .setColorLayer()
            .setParent(mSurfaceControl)
            .setCallsite("SurfaceView.updateSurface")
            .build();

        return previousSurfaceControl;
        if (mBackgroundControl == null) {
            mBackgroundControl = createBackgroundControl(name);
        }

        // Always recreate the IGBP for compatibility. This can be optimized in the future but
        // the behavior change will need to be gated by SDK version.
        if (mBlastBufferQueue != null) {
            mBlastBufferQueue.destroy();
        }
        mBlastBufferQueue = new BLASTBufferQueue(name, mBlastSurfaceControl, mSurfaceWidth,
                mSurfaceHeight, mFormat, true /* TODO */);
    }

    private void onDrawFinished() {
+6 −5
Original line number Diff line number Diff line
@@ -1898,11 +1898,12 @@ public final class ViewRootImpl implements ViewParent,
    }

    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);
        // Adjust of insets and update the bounds layer so child surfaces do not draw into
        // the surface inset region.
        mTempBoundsRect.set(0, 0, mSurfaceSize.x, mSurfaceSize.y);
        mTempBoundsRect.inset(mWindowAttributes.surfaceInsets.left,
                mWindowAttributes.surfaceInsets.top,
                mWindowAttributes.surfaceInsets.right, mWindowAttributes.surfaceInsets.bottom);
        t.setWindowCrop(mBoundsLayer, mTempBoundsRect);
    }