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

Commit 17410b66 authored by Huihong Luo's avatar Huihong Luo Committed by Android (Google) Code Review
Browse files

Merge "Fix z-order for webview surface control" into sc-dev

parents e5a810e1 34f42fde
Loading
Loading
Loading
Loading
+30 −1
Original line number Diff line number Diff line
@@ -461,6 +461,9 @@ public final class ViewRootImpl implements ViewParent,
    protected final ViewFrameInfo mViewFrameInfo = new ViewFrameInfo();
    private final InputEventAssigner mInputEventAssigner = new InputEventAssigner();

    // Set to true if mSurfaceControl is used for Webview Overlay
    private boolean mIsForWebviewOverlay;

    /**
     * Update the Choreographer's FrameInfo object with the timing information for the current
     * ViewRootImpl instance. Erase the data in the current ViewFrameInfo to prepare for the next
@@ -1374,6 +1377,23 @@ public final class ViewRootImpl implements ViewParent,
        mAttachInfo.mThreadedRenderer.setASurfaceTransactionCallback(callback);
    }

    /**
     * Register a callback to be executed when Webview overlay needs a surface control.
     * This callback will be executed on RenderThread worker thread, and released inside native code
     * when CanvasContext is destroyed.
     */
    private void addPrepareSurfaceControlForWebviewCallback() {
        HardwareRenderer.PrepareSurfaceControlForWebviewCallback callback = () -> {
            // make mSurfaceControl transparent, so child surface controls are visible
            if (mIsForWebviewOverlay) return;
            synchronized (ViewRootImpl.this) {
                mIsForWebviewOverlay = true;
            }
            mTransaction.setOpaque(mSurfaceControl, false).apply();
        };
        mAttachInfo.mThreadedRenderer.setPrepareSurfaceControlForWebviewCallback(callback);
    }

    @UnsupportedAppUsage
    private void enableHardwareAcceleration(WindowManager.LayoutParams attrs) {
        mAttachInfo.mHardwareAccelerated = false;
@@ -1418,6 +1438,7 @@ public final class ViewRootImpl implements ViewParent,
                    if (mHardwareRendererObserver != null) {
                        mAttachInfo.mThreadedRenderer.addObserver(mHardwareRendererObserver);
                    }
                    addPrepareSurfaceControlForWebviewCallback();
                    addASurfaceTransactionCallback();
                    mAttachInfo.mThreadedRenderer.setSurfaceControl(mSurfaceControl);
                }
@@ -7743,6 +7764,7 @@ public final class ViewRootImpl implements ViewParent,
                }
            }
            if (mAttachInfo.mThreadedRenderer != null) {
                addPrepareSurfaceControlForWebviewCallback();
                addASurfaceTransactionCallback();
                mAttachInfo.mThreadedRenderer.setSurfaceControl(mSurfaceControl);
            }
@@ -7790,7 +7812,14 @@ public final class ViewRootImpl implements ViewParent,
            return;
        }

        synchronized (this) {
            if (mIsForWebviewOverlay) {
                mIsSurfaceOpaque = false;
                return;
            }
            mTransaction.setOpaque(mSurfaceControl, opaque).apply();
        }

        mIsSurfaceOpaque = opaque;
    }

+26 −0
Original line number Diff line number Diff line
@@ -762,6 +762,16 @@ public class HardwareRenderer {
        nSetASurfaceTransactionCallback(mNativeProxy, callback);
    }

    private PrepareSurfaceControlForWebviewCallback mAPrepareSurfaceControlForWebviewCallback;

    /** @hide */
    public void setPrepareSurfaceControlForWebviewCallback(
            PrepareSurfaceControlForWebviewCallback callback) {
        // ensure callback is kept alive on the java side since weak ref is used in native code
        mAPrepareSurfaceControlForWebviewCallback = callback;
        nSetPrepareSurfaceControlForWebviewCallback(mNativeProxy, callback);
    }

    /** @hide */
    public void setFrameCallback(FrameDrawingCallback callback) {
        nSetFrameCallback(mNativeProxy, callback);
@@ -876,6 +886,19 @@ public class HardwareRenderer {
        session.close();
    }

   /**
     * Interface used to receive callbacks when Webview requests a surface control.
     *
     * @hide
     */
    public interface PrepareSurfaceControlForWebviewCallback {
        /**
         * Invoked when Webview calls to get a surface control.
         *
         */
        void prepare();
    }

    /**
     * Interface used to receive callbacks when a transaction needs to be merged.
     *
@@ -1374,6 +1397,9 @@ public class HardwareRenderer {
    private static native void nSetASurfaceTransactionCallback(long nativeProxy,
            ASurfaceTransactionCallback callback);

    private static native void nSetPrepareSurfaceControlForWebviewCallback(long nativeProxy,
            PrepareSurfaceControlForWebviewCallback callback);

    private static native void nSetFrameCallback(long nativeProxy, FrameDrawingCallback callback);

    private static native void nSetFrameCompleteCallback(long nativeProxy,
+2 −0
Original line number Diff line number Diff line
@@ -197,6 +197,8 @@ ASurfaceControl* WebViewFunctor::getSurfaceControl() {
    auto funcs = renderthread::RenderThread::getInstance().getASurfaceControlFunctions();
    mSurfaceControl = funcs.createFunc(rootSurfaceControl, "Webview Overlay SurfaceControl");
    ASurfaceTransaction* transaction = funcs.transactionCreateFunc();
    activeContext->prepareSurfaceControlForWebview();
    funcs.transactionSetZOrderFunc(transaction, mSurfaceControl, -1);
    funcs.transactionSetVisibilityFunc(transaction, mSurfaceControl,
                                       ASURFACE_TRANSACTION_VISIBILITY_SHOW);
    funcs.transactionApplyFunc(transaction);
+34 −0
Original line number Diff line number Diff line
@@ -70,6 +70,10 @@ struct {
    jmethodID onMergeTransaction;
} gASurfaceTransactionCallback;

struct {
    jmethodID prepare;
} gPrepareSurfaceControlForWebviewCallback;

struct {
    jmethodID onFrameDraw;
} gFrameDrawingCallback;
@@ -672,6 +676,28 @@ static void android_view_ThreadedRenderer_setASurfaceTransactionCallback(
    }
}

static void android_view_ThreadedRenderer_setPrepareSurfaceControlForWebviewCallback(
        JNIEnv* env, jobject clazz, jlong proxyPtr, jobject callback) {
    RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr);
    if (!callback) {
        proxy->setPrepareSurfaceControlForWebviewCallback(nullptr);
    } else {
        JavaVM* vm = nullptr;
        LOG_ALWAYS_FATAL_IF(env->GetJavaVM(&vm) != JNI_OK, "Unable to get Java VM");
        auto globalCallbackRef =
                std::make_shared<JWeakGlobalRefHolder>(vm, callback);
        proxy->setPrepareSurfaceControlForWebviewCallback([globalCallbackRef]() {
            JNIEnv* env = getenv(globalCallbackRef->vm());
            jobject localref = env->NewLocalRef(globalCallbackRef->ref());
            if (CC_UNLIKELY(!localref)) {
                return;
            }
            env->CallVoidMethod(localref, gPrepareSurfaceControlForWebviewCallback.prepare);
            env->DeleteLocalRef(localref);
        });
    }
}

static void android_view_ThreadedRenderer_setFrameCallback(JNIEnv* env,
        jobject clazz, jlong proxyPtr, jobject frameCallback) {
    RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr);
@@ -970,6 +996,9 @@ static const JNINativeMethod gMethods[] = {
        {"nSetASurfaceTransactionCallback",
         "(JLandroid/graphics/HardwareRenderer$ASurfaceTransactionCallback;)V",
         (void*)android_view_ThreadedRenderer_setASurfaceTransactionCallback},
        {"nSetPrepareSurfaceControlForWebviewCallback",
         "(JLandroid/graphics/HardwareRenderer$PrepareSurfaceControlForWebviewCallback;)V",
         (void*)android_view_ThreadedRenderer_setPrepareSurfaceControlForWebviewCallback},
        {"nSetFrameCallback", "(JLandroid/graphics/HardwareRenderer$FrameDrawingCallback;)V",
         (void*)android_view_ThreadedRenderer_setFrameCallback},
        {"nSetFrameCompleteCallback",
@@ -1037,6 +1066,11 @@ int register_android_view_ThreadedRenderer(JNIEnv* env) {
    gASurfaceTransactionCallback.onMergeTransaction =
            GetMethodIDOrDie(env, aSurfaceTransactionCallbackClass, "onMergeTransaction", "(JJJ)V");

    jclass prepareSurfaceControlForWebviewCallbackClass = FindClassOrDie(
            env, "android/graphics/HardwareRenderer$PrepareSurfaceControlForWebviewCallback");
    gPrepareSurfaceControlForWebviewCallback.prepare =
            GetMethodIDOrDie(env, prepareSurfaceControlForWebviewCallbackClass, "prepare", "()V");

    jclass frameCallbackClass = FindClassOrDie(env,
            "android/graphics/HardwareRenderer$FrameDrawingCallback");
    gFrameDrawingCallback.onFrameDraw = GetMethodIDOrDie(env, frameCallbackClass,
+7 −0
Original line number Diff line number Diff line
@@ -193,6 +193,7 @@ void CanvasContext::setSurfaceControl(ASurfaceControl* surfaceControl) {

    if (surfaceControl == nullptr) {
        setASurfaceTransactionCallback(nullptr);
        setPrepareSurfaceControlForWebviewCallback(nullptr);
    }

    if (mSurfaceControl != nullptr) {
@@ -914,6 +915,12 @@ bool CanvasContext::mergeTransaction(ASurfaceTransaction* transaction, ASurfaceC
    return true;
}

void CanvasContext::prepareSurfaceControlForWebview() {
    if (mPrepareSurfaceControlForWebviewCallback) {
        std::invoke(mPrepareSurfaceControlForWebviewCallback);
    }
}

} /* namespace renderthread */
} /* namespace uirenderer */
} /* namespace android */
Loading