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

Commit 677d040e authored by Rob Carr's avatar Rob Carr Committed by Android (Google) Code Review
Browse files

Merge "AttachedSurfaceControl: Add setTouchableRegion API"

parents a4913850 234c2592
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -48489,6 +48489,7 @@ package android.view {
    method @Nullable public android.view.SurfaceControl.Transaction buildReparentTransaction(@NonNull android.view.SurfaceControl);
    method public default int getBufferTransformHint();
    method public default void removeOnBufferTransformHintChangedListener(@NonNull android.view.AttachedSurfaceControl.OnBufferTransformHintChangedListener);
    method public default void setTouchableRegion(@Nullable android.graphics.Region);
  }
  @UiThread public static interface AttachedSurfaceControl.OnBufferTransformHintChangedListener {
+14 −0
Original line number Diff line number Diff line
@@ -17,7 +17,9 @@ package android.view;

import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.SystemApi;
import android.annotation.UiThread;
import android.graphics.Region;
import android.hardware.HardwareBuffer;

/**
@@ -124,4 +126,16 @@ public interface AttachedSurfaceControl {
    default void removeOnBufferTransformHintChangedListener(
            @NonNull OnBufferTransformHintChangedListener listener) {
    }

    /**
     * Sets the touchable region for this SurfaceControl, expressed in surface local
     * coordinates. By default the touchable region is the entire Layer, indicating
     * that if the layer is otherwise eligible to receive touch it receives touch
     * on the entire surface. Setting the touchable region allows the SurfaceControl
     * to receive touch in some regions, while allowing for pass-through in others.
     *
     * @param r The region to use or null to use the entire Layer bounds
     */
    default void setTouchableRegion(@Nullable Region r) {
    }
}
+5 −0
Original line number Diff line number Diff line
@@ -339,4 +339,9 @@ interface IWindowSession {
     * @param callback The {@link IOnBackInvokedCallback} to set.
     */
    oneway void setOnBackInvokedCallback(IWindow window, IOnBackInvokedCallback callback);

    /**
     * Clears a touchable region set by {@link #setInsets}.
     */
    void clearTouchableRegion(IWindow window);
}
+61 −9
Original line number Diff line number Diff line
@@ -52,6 +52,7 @@ import static android.view.ViewRootImplProto.VISIBLE_RECT;
import static android.view.ViewRootImplProto.WIDTH;
import static android.view.ViewRootImplProto.WINDOW_ATTRIBUTES;
import static android.view.ViewRootImplProto.WIN_FRAME;
import static android.view.ViewTreeObserver.InternalInsetsInfo.TOUCHABLE_INSETS_REGION;
import static android.view.WindowCallbacks.RESIZE_MODE_DOCKED_DIVIDER;
import static android.view.WindowCallbacks.RESIZE_MODE_FREEFORM;
import static android.view.WindowInsetsController.APPEARANCE_LIGHT_NAVIGATION_BARS;
@@ -473,6 +474,9 @@ public final class ViewRootImpl implements ViewParent,
    final Region mTransparentRegion;
    final Region mPreviousTransparentRegion;

    Region mTouchableRegion;
    Region mPreviousTouchableRegion;

    @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
    int mWidth;
    @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
@@ -3251,9 +3255,15 @@ public final class ViewRootImpl implements ViewParent,
            mAttachInfo.mTreeObserver.dispatchOnGlobalLayout();
        }

        Rect contentInsets = null;
        Rect visibleInsets = null;
        Region touchableRegion = null;
        int touchableInsetMode = TOUCHABLE_INSETS_REGION;
        boolean computedInternalInsets = false;
        if (computesInternalInsets) {
            // Clear the original insets.
            final ViewTreeObserver.InternalInsetsInfo insets = mAttachInfo.mGivenInternalInsets;

            // Clear the original insets.
            insets.reset();

            // Compute new insets in place.
@@ -3265,9 +3275,6 @@ public final class ViewRootImpl implements ViewParent,
                mLastGivenInsets.set(insets);

                // Translate insets to screen coordinates if needed.
                final Rect contentInsets;
                final Rect visibleInsets;
                final Region touchableRegion;
                if (mTranslator != null) {
                    contentInsets = mTranslator.getTranslatedContentInsets(insets.contentInsets);
                    visibleInsets = mTranslator.getTranslatedVisibleInsets(insets.visibleInsets);
@@ -3277,12 +3284,46 @@ public final class ViewRootImpl implements ViewParent,
                    visibleInsets = insets.visibleInsets;
                    touchableRegion = insets.touchableRegion;
                }

                computedInternalInsets = true;
            }
            touchableInsetMode = insets.mTouchableInsets;
        }
        boolean needsSetInsets = computedInternalInsets;
        needsSetInsets |= !Objects.equals(mPreviousTouchableRegion, mTouchableRegion) &&
            (mTouchableRegion != null);
        if (needsSetInsets) {
            if (mTouchableRegion != null) {
                if (mPreviousTouchableRegion == null) {
                    mPreviousTouchableRegion = new Region();
                }
                mPreviousTouchableRegion.set(mTouchableRegion);
                if (touchableInsetMode != TOUCHABLE_INSETS_REGION) {
                    Log.e(mTag, "Setting touchableInsetMode to non TOUCHABLE_INSETS_REGION" +
                          " from OnComputeInternalInsets, while also using setTouchableRegion" +
                          " causes setTouchableRegion to be ignored");
                }
            } else {
                mPreviousTouchableRegion = null;
            }
            if (contentInsets == null) contentInsets = new Rect(0,0,0,0);
            if (visibleInsets == null) visibleInsets = new Rect(0,0,0,0);
            if (touchableRegion == null) {
                touchableRegion = mTouchableRegion;
            } else if (touchableRegion != null && mTouchableRegion != null) {
                touchableRegion.op(touchableRegion, mTouchableRegion, Region.Op.UNION);
            }
            try {
                    mWindowSession.setInsets(mWindow, insets.mTouchableInsets,
                mWindowSession.setInsets(mWindow, touchableInsetMode,
                                         contentInsets, visibleInsets, touchableRegion);
            } catch (RemoteException e) {
                throw e.rethrowFromSystemServer();
            }
        } else if (mTouchableRegion == null && mPreviousTouchableRegion != null) {
            mPreviousTouchableRegion = null;
            try {
                mWindowSession.clearTouchableRegion(mWindow);
            } catch (RemoteException e) {
                throw e.rethrowFromSystemServer();
            }
        }

@@ -10706,4 +10747,15 @@ public final class ViewRootImpl implements ViewParent,
        }
        return mFallbackOnBackInvokedDispatcher;
    }

    @Override
    public void setTouchableRegion(Region r) {
        if (r != null) {
            mTouchableRegion = new Region(r);
        } else {
            mTouchableRegion = null;
        }
        mLastGivenInsets.reset();
        requestLayout();
    }
}
+5 −0
Original line number Diff line number Diff line
@@ -332,6 +332,11 @@ public class WindowlessWindowManager implements IWindowSession {
        setTouchRegion(window.asBinder(), touchableRegion);
    }

    @Override
    public void clearTouchableRegion(android.view.IWindow window) {
        setTouchRegion(window.asBinder(), null);
    }

    @Override
    public void finishDrawing(android.view.IWindow window,
            android.view.SurfaceControl.Transaction postDrawTransaction) {
Loading