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

Commit 5916e506 authored by Chavi Weingarten's avatar Chavi Weingarten
Browse files

Revert "Remove WindowlessWindowLayout"

This reverts commit 6b204587.

Reason for revert: Breaks bounds computation for windowless windows by computing inset values

Change-Id: I11a4b8a16a905ab46b26b783f67bd1b3f2939e43
parent 12917797
Loading
Loading
Loading
Loading
+2 −2
Original line number Diff line number Diff line
@@ -292,7 +292,7 @@ public class SurfaceControlViewHost {
    public SurfaceControlViewHost(@NonNull Context c, @NonNull Display d,
            @NonNull WindowlessWindowManager wwm) {
        mWm = wwm;
        mViewRoot = new ViewRootImpl(c, d, mWm);
        mViewRoot = new ViewRootImpl(c, d, mWm, new WindowlessWindowLayout());
        addConfigCallback(c, d);

        WindowManagerGlobal.getInstance().addWindowlessRoot(mViewRoot);
@@ -322,7 +322,7 @@ public class SurfaceControlViewHost {
        mWm = new WindowlessWindowManager(context.getResources().getConfiguration(),
                mSurfaceControl, hostToken);

        mViewRoot = new ViewRootImpl(context, display, mWm);
        mViewRoot = new ViewRootImpl(context, display, mWm, new WindowlessWindowLayout());
        addConfigCallback(context, display);

        WindowManagerGlobal.getInstance().addWindowlessRoot(mViewRoot);
+4 −3
Original line number Diff line number Diff line
@@ -922,13 +922,14 @@ public final class ViewRootImpl implements ViewParent,
    private String mTag = TAG;

    public ViewRootImpl(Context context, Display display) {
        this(context, display, WindowManagerGlobal.getWindowSession());
        this(context, display, WindowManagerGlobal.getWindowSession(), new WindowLayout());
    }

    public ViewRootImpl(@UiContext Context context, Display display, IWindowSession session) {
    public ViewRootImpl(@UiContext Context context, Display display, IWindowSession session,
            WindowLayout windowLayout) {
        mContext = context;
        mWindowSession = session;
        mWindowLayout = new WindowLayout();
        mWindowLayout = windowLayout;
        mDisplay = display;
        mBasePackageName = context.getBasePackageName();
        mThread = Thread.currentThread();
+2 −1
Original line number Diff line number Diff line
@@ -388,7 +388,8 @@ public final class WindowManagerGlobal {
            if (windowlessSession == null) {
                root = new ViewRootImpl(view.getContext(), display);
            } else {
                root = new ViewRootImpl(view.getContext(), display, windowlessSession);
                root = new ViewRootImpl(view.getContext(), display,
                        windowlessSession, new WindowlessWindowLayout());
            }

            view.setLayoutParams(wparams);
+71 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2022 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
 *
 *      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.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package android.view;

import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT;

import android.app.WindowConfiguration.WindowingMode;
import android.graphics.Rect;
import android.view.WindowInsets.Type.InsetsType;
import android.window.ClientWindowFrames;

/**
 * Computes window frames for the windowless window.
 *
 * This can't be replaced with the regular WindowLayout because WindowLayout computes bounds
 * with insets and cutout values. Since windowless windows aren't affected by insets and
 * instead are bound by their parent, it will compute incorrect bounds for them if insets are used.
 *
 * @hide
 */
public class WindowlessWindowLayout extends WindowLayout {

    @Override
    public void computeFrames(WindowManager.LayoutParams attrs, InsetsState state,
            Rect displayCutoutSafe, Rect windowBounds, @WindowingMode int windowingMode,
            int requestedWidth, int requestedHeight, @InsetsType int requestedVisibleTypes,
            float compatScale, ClientWindowFrames frames) {
        if (frames.attachedFrame == null) {
            frames.frame.set(0, 0, attrs.width, attrs.height);
            frames.parentFrame.set(frames.frame);
            frames.displayFrame.set(frames.frame);
            return;
        }

        final int height = calculateLength(attrs.height, requestedHeight,
                frames.attachedFrame.height());
        final int width = calculateLength(attrs.width, requestedWidth,
                frames.attachedFrame.width());
        Gravity.apply(attrs.gravity, width, height, frames.attachedFrame,
                (int) (attrs.x + attrs.horizontalMargin),
                (int) (attrs.y + attrs.verticalMargin),
                frames.frame);
        frames.displayFrame.set(frames.frame);
        frames.parentFrame.set(frames.attachedFrame);
    }

    private static int calculateLength(int attrLength, int requestedLength, int parentLength) {
        if (attrLength == MATCH_PARENT) {
            return parentLength;
        }
        if (attrLength == WRAP_CONTENT) {
            return requestedLength;
        }
        return attrLength;
    }
}
+12 −20
Original line number Diff line number Diff line
@@ -94,10 +94,7 @@ public class WindowlessWindowManager implements IWindowSession {
    private InsetsState mInsetsState;
    private final ClientWindowFrames mTmpFrames = new ClientWindowFrames();
    private final MergedConfiguration mTmpConfig = new MergedConfiguration();
    private final InsetsState mTmpInsetsState = new InsetsState();
    private final Rect mTmpDisplayCutoutSafe = new Rect();
    private final Rect mTmpWindowBounds = new Rect();
    private final WindowLayout mLayout = new WindowLayout();
    private final WindowlessWindowLayout mLayout = new WindowlessWindowLayout();

    public WindowlessWindowManager(Configuration c, SurfaceControl rootSurface,
            IBinder hostInputToken) {
@@ -349,27 +346,22 @@ public class WindowlessWindowManager implements IWindowSession {
        }
        WindowManager.LayoutParams attrs = state.mParams;

        mTmpFrames.attachedFrame = state.mAttachedFrame;
        ClientWindowFrames frames = new ClientWindowFrames();
        frames.attachedFrame = state.mAttachedFrame;

        if (state.mAttachedFrame == null) {
            mTmpWindowBounds.set(0, 0, requestedWidth, requestedHeight);
        } else {
            mTmpWindowBounds.set(state.mAttachedFrame);
        }

        mLayout.computeFrames(attrs, mTmpInsetsState, mTmpDisplayCutoutSafe, mTmpWindowBounds,
                WindowConfiguration.WINDOWING_MODE_UNDEFINED, requestedWidth, requestedHeight, 0,
                1f, mTmpFrames);
        mLayout.computeFrames(attrs, null, null, null, WindowConfiguration.WINDOWING_MODE_UNDEFINED,
                requestedWidth, requestedHeight, 0, 0,
                frames);

        state.mFrame.set(mTmpFrames.frame);
        state.mFrame.set(frames.frame);
        if (outFrames != null) {
            outFrames.frame.set(mTmpFrames.frame);
            outFrames.parentFrame.set(mTmpFrames.parentFrame);
            outFrames.displayFrame.set(mTmpFrames.displayFrame);
            outFrames.frame.set(frames.frame);
            outFrames.parentFrame.set(frames.parentFrame);
            outFrames.displayFrame.set(frames.displayFrame);
        }

        t.setPosition(leash, mTmpFrames.frame.left, mTmpFrames.frame.top);
        t.setWindowCrop(leash, mTmpFrames.frame.width(), mTmpFrames.frame.height());
        t.setPosition(leash, frames.frame.left, frames.frame.top);
        t.setWindowCrop(leash, frames.frame.width(), frames.frame.height());

        if (viewFlags == View.VISIBLE) {
            // TODO(b/262892794) ViewRootImpl modifies the app's rendering SurfaceControl