Loading core/java/android/view/ViewRootImpl.java +30 −1 Original line number Diff line number Diff line Loading @@ -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 Loading Loading @@ -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; Loading Loading @@ -1418,6 +1438,7 @@ public final class ViewRootImpl implements ViewParent, if (mHardwareRendererObserver != null) { mAttachInfo.mThreadedRenderer.addObserver(mHardwareRendererObserver); } addPrepareSurfaceControlForWebviewCallback(); addASurfaceTransactionCallback(); mAttachInfo.mThreadedRenderer.setSurfaceControl(mSurfaceControl); } Loading Loading @@ -7743,6 +7764,7 @@ public final class ViewRootImpl implements ViewParent, } } if (mAttachInfo.mThreadedRenderer != null) { addPrepareSurfaceControlForWebviewCallback(); addASurfaceTransactionCallback(); mAttachInfo.mThreadedRenderer.setSurfaceControl(mSurfaceControl); } Loading Loading @@ -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; } Loading graphics/java/android/graphics/HardwareRenderer.java +26 −0 Original line number Diff line number Diff line Loading @@ -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); Loading Loading @@ -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. * Loading Loading @@ -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, Loading libs/hwui/WebViewFunctorManager.cpp +2 −0 Original line number Diff line number Diff line Loading @@ -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); Loading libs/hwui/jni/android_graphics_HardwareRenderer.cpp +34 −0 Original line number Diff line number Diff line Loading @@ -70,6 +70,10 @@ struct { jmethodID onMergeTransaction; } gASurfaceTransactionCallback; struct { jmethodID prepare; } gPrepareSurfaceControlForWebviewCallback; struct { jmethodID onFrameDraw; } gFrameDrawingCallback; Loading Loading @@ -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); Loading Loading @@ -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", Loading Loading @@ -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, Loading libs/hwui/renderthread/CanvasContext.cpp +7 −0 Original line number Diff line number Diff line Loading @@ -193,6 +193,7 @@ void CanvasContext::setSurfaceControl(ASurfaceControl* surfaceControl) { if (surfaceControl == nullptr) { setASurfaceTransactionCallback(nullptr); setPrepareSurfaceControlForWebviewCallback(nullptr); } if (mSurfaceControl != nullptr) { Loading Loading @@ -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
core/java/android/view/ViewRootImpl.java +30 −1 Original line number Diff line number Diff line Loading @@ -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 Loading Loading @@ -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; Loading Loading @@ -1418,6 +1438,7 @@ public final class ViewRootImpl implements ViewParent, if (mHardwareRendererObserver != null) { mAttachInfo.mThreadedRenderer.addObserver(mHardwareRendererObserver); } addPrepareSurfaceControlForWebviewCallback(); addASurfaceTransactionCallback(); mAttachInfo.mThreadedRenderer.setSurfaceControl(mSurfaceControl); } Loading Loading @@ -7743,6 +7764,7 @@ public final class ViewRootImpl implements ViewParent, } } if (mAttachInfo.mThreadedRenderer != null) { addPrepareSurfaceControlForWebviewCallback(); addASurfaceTransactionCallback(); mAttachInfo.mThreadedRenderer.setSurfaceControl(mSurfaceControl); } Loading Loading @@ -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; } Loading
graphics/java/android/graphics/HardwareRenderer.java +26 −0 Original line number Diff line number Diff line Loading @@ -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); Loading Loading @@ -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. * Loading Loading @@ -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, Loading
libs/hwui/WebViewFunctorManager.cpp +2 −0 Original line number Diff line number Diff line Loading @@ -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); Loading
libs/hwui/jni/android_graphics_HardwareRenderer.cpp +34 −0 Original line number Diff line number Diff line Loading @@ -70,6 +70,10 @@ struct { jmethodID onMergeTransaction; } gASurfaceTransactionCallback; struct { jmethodID prepare; } gPrepareSurfaceControlForWebviewCallback; struct { jmethodID onFrameDraw; } gFrameDrawingCallback; Loading Loading @@ -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); Loading Loading @@ -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", Loading Loading @@ -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, Loading
libs/hwui/renderthread/CanvasContext.cpp +7 −0 Original line number Diff line number Diff line Loading @@ -193,6 +193,7 @@ void CanvasContext::setSurfaceControl(ASurfaceControl* surfaceControl) { if (surfaceControl == nullptr) { setASurfaceTransactionCallback(nullptr); setPrepareSurfaceControlForWebviewCallback(nullptr); } if (mSurfaceControl != nullptr) { Loading Loading @@ -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 */