Loading core/java/android/view/ThreadedRenderer.java +2 −4 Original line number Diff line number Diff line Loading @@ -794,8 +794,7 @@ public final class ThreadedRenderer { } final long[] frameInfo = choreographer.mFrameInfo.mFrameInfo; int syncResult = nSyncAndDrawFrame(mNativeProxy, frameInfo, frameInfo.length, mRootNode.mNativeRenderNode); int syncResult = nSyncAndDrawFrame(mNativeProxy, frameInfo, frameInfo.length); if ((syncResult & SYNC_LOST_SURFACE_REWARD_IF_FOUND) != 0) { setEnabled(false); attachInfo.mViewRootImpl.mSurface.release(); Loading Loading @@ -994,8 +993,7 @@ public final class ThreadedRenderer { private static native void nSetLightCenter(long nativeProxy, float lightX, float lightY, float lightZ); private static native void nSetOpaque(long nativeProxy, boolean opaque); private static native int nSyncAndDrawFrame(long nativeProxy, long[] frameInfo, int size, long rootRenderNode); private static native int nSyncAndDrawFrame(long nativeProxy, long[] frameInfo, int size); private static native void nDestroy(long nativeProxy, long rootRenderNode); private static native void nRegisterAnimatingRenderNode(long rootRenderNode, long animatingNode); Loading core/jni/android_view_RenderNode.cpp +14 −1 Original line number Diff line number Diff line Loading @@ -128,9 +128,22 @@ static void android_view_RenderNode_destroyRenderNode(JNIEnv* env, static void android_view_RenderNode_setDisplayList(JNIEnv* env, jobject clazz, jlong renderNodePtr, jlong displayListPtr) { class RemovedObserver : public TreeObserver { public: virtual void onMaybeRemovedFromTree(RenderNode* node) override { maybeRemovedNodes.insert(sp<RenderNode>(node)); } std::set< sp<RenderNode> > maybeRemovedNodes; }; RenderNode* renderNode = reinterpret_cast<RenderNode*>(renderNodePtr); DisplayList* newData = reinterpret_cast<DisplayList*>(displayListPtr); renderNode->setStagingDisplayList(newData); RemovedObserver observer; renderNode->setStagingDisplayList(newData, &observer); for (auto& node : observer.maybeRemovedNodes) { if (node->hasParents()) continue; onRenderNodeRemoved(env, node.get()); } } // ---------------------------------------------------------------------------- Loading core/jni/android_view_Surface.cpp +1 −1 Original line number Diff line number Diff line Loading @@ -525,7 +525,7 @@ static void draw(JNIEnv* env, jclass clazz, jlong rendererPtr) { UiFrameInfoBuilder(proxy->frameInfo()) .setVsync(vsync, vsync) .addFlag(FrameInfoFlags::SurfaceCanvas); proxy->syncAndDrawFrame(); proxy->syncAndDrawFrame(nullptr); } static void destroy(JNIEnv* env, jclass clazz, jlong rendererPtr) { Loading core/jni/android_view_ThreadedRenderer.cpp +36 −37 Original line number Diff line number Diff line Loading @@ -72,6 +72,31 @@ static JNIEnv* getenv(JavaVM* vm) { return env; } // TODO: Clean this up, it's a bit odd to need to call over to // rendernode's jni layer. Probably means RootRenderNode should be pulled // into HWUI with appropriate callbacks for the various JNI hooks so // that RenderNode's JNI layer can handle its own thing void onRenderNodeRemoved(JNIEnv* env, RenderNode* node); class ScopedRemovedRenderNodeObserver : public TreeObserver { public: ScopedRemovedRenderNodeObserver(JNIEnv* env) : mEnv(env) {} ~ScopedRemovedRenderNodeObserver() { for (auto& node : mMaybeRemovedNodes) { if (node->hasParents()) continue; onRenderNodeRemoved(mEnv, node.get()); } } virtual void onMaybeRemovedFromTree(RenderNode* node) override { mMaybeRemovedNodes.insert(sp<RenderNode>(node)); } private: JNIEnv* mEnv; std::set< sp<RenderNode> > mMaybeRemovedNodes; }; class OnFinishedEvent { public: OnFinishedEvent(BaseRenderNodeAnimator* animator, AnimationListener* listener) Loading Loading @@ -120,13 +145,7 @@ private: std::string mMessage; }; // TODO: Clean this up, it's a bit odd to need to call over to // rendernode's jni layer. Probably means RootRenderNode should be pulled // into HWUI with appropriate callbacks for the various JNI hooks so // that RenderNode's JNI layer can handle its own thing void onRenderNodeRemoved(JNIEnv* env, RenderNode* node); class RootRenderNode : public RenderNode, ErrorHandler, TreeObserver { class RootRenderNode : public RenderNode, ErrorHandler { public: RootRenderNode(JNIEnv* env) : RenderNode() { mLooper = Looper::getForThread(); Loading @@ -143,9 +162,6 @@ public: virtual void prepareTree(TreeInfo& info) override { info.errorHandler = this; if (info.mode == TreeInfo::MODE_FULL) { info.observer = this; } // TODO: This is hacky info.windowInsetLeft = -stagingProperties().getLeft(); info.windowInsetTop = -stagingProperties().getTop(); Loading @@ -155,7 +171,6 @@ public: info.windowInsetLeft = 0; info.windowInsetTop = 0; info.errorHandler = nullptr; info.observer = nullptr; } void sendMessage(const sp<MessageHandler>& handler) { Loading @@ -181,27 +196,10 @@ public: mPendingAnimatingRenderNodes.clear(); } virtual void onMaybeRemovedFromTree(RenderNode* node) override { mMaybeRemovedNodes.insert(sp<RenderNode>(node)); } void processMaybeRemovedNodes(JNIEnv* env) { // We can safely access mMaybeRemovedNodes here because // we will only modify it in prepareTree calls that are // MODE_FULL for (auto& node : mMaybeRemovedNodes) { if (node->hasParents()) continue; onRenderNodeRemoved(env, node.get()); } mMaybeRemovedNodes.clear(); } private: sp<Looper> mLooper; JavaVM* mVm; std::vector< sp<RenderNode> > mPendingAnimatingRenderNodes; std::set< sp<RenderNode> > mMaybeRemovedNodes; }; class AnimationContextBridge : public AnimationContext { Loading Loading @@ -500,24 +498,23 @@ static void android_view_ThreadedRenderer_setOpaque(JNIEnv* env, jobject clazz, } static int android_view_ThreadedRenderer_syncAndDrawFrame(JNIEnv* env, jobject clazz, jlong proxyPtr, jlongArray frameInfo, jint frameInfoSize, jlong rootNodePtr) { jlong proxyPtr, jlongArray frameInfo, jint frameInfoSize) { LOG_ALWAYS_FATAL_IF(frameInfoSize != UI_THREAD_FRAME_INFO_SIZE, "Mismatched size expectations, given %d expected %d", frameInfoSize, UI_THREAD_FRAME_INFO_SIZE); RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr); RootRenderNode* rootRenderNode = reinterpret_cast<RootRenderNode*>(rootNodePtr); ScopedRemovedRenderNodeObserver observer(env); env->GetLongArrayRegion(frameInfo, 0, frameInfoSize, proxy->frameInfo()); int ret = proxy->syncAndDrawFrame(); rootRenderNode->processMaybeRemovedNodes(env); return ret; return proxy->syncAndDrawFrame(&observer); } static void android_view_ThreadedRenderer_destroy(JNIEnv* env, jobject clazz, jlong proxyPtr, jlong rootNodePtr) { ScopedRemovedRenderNodeObserver observer(env); RootRenderNode* rootRenderNode = reinterpret_cast<RootRenderNode*>(rootNodePtr); rootRenderNode->destroy(); RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr); proxy->destroy(); proxy->destroy(&observer); } static void android_view_ThreadedRenderer_registerAnimatingRenderNode(JNIEnv* env, jobject clazz, Loading @@ -542,9 +539,10 @@ static jlong android_view_ThreadedRenderer_createTextureLayer(JNIEnv* env, jobje static void android_view_ThreadedRenderer_buildLayer(JNIEnv* env, jobject clazz, jlong proxyPtr, jlong nodePtr) { ScopedRemovedRenderNodeObserver observer(env); RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr); RenderNode* node = reinterpret_cast<RenderNode*>(nodePtr); proxy->buildLayer(node); proxy->buildLayer(node, &observer); } static jboolean android_view_ThreadedRenderer_copyLayerInto(JNIEnv* env, jobject clazz, Loading Loading @@ -579,8 +577,9 @@ static void android_view_ThreadedRenderer_detachSurfaceTexture(JNIEnv* env, jobj static void android_view_ThreadedRenderer_destroyHardwareResources(JNIEnv* env, jobject clazz, jlong proxyPtr) { ScopedRemovedRenderNodeObserver observer(env); RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr); proxy->destroyHardwareResources(); proxy->destroyHardwareResources(&observer); } static void android_view_ThreadedRenderer_trimMemory(JNIEnv* env, jobject clazz, Loading Loading @@ -736,7 +735,7 @@ static const JNINativeMethod gMethods[] = { { "nSetup", "(JIIFII)V", (void*) android_view_ThreadedRenderer_setup }, { "nSetLightCenter", "(JFFF)V", (void*) android_view_ThreadedRenderer_setLightCenter }, { "nSetOpaque", "(JZ)V", (void*) android_view_ThreadedRenderer_setOpaque }, { "nSyncAndDrawFrame", "(J[JIJ)I", (void*) android_view_ThreadedRenderer_syncAndDrawFrame }, { "nSyncAndDrawFrame", "(J[JI)I", (void*) android_view_ThreadedRenderer_syncAndDrawFrame }, { "nDestroy", "(JJ)V", (void*) android_view_ThreadedRenderer_destroy }, { "nRegisterAnimatingRenderNode", "(JJ)V", (void*) android_view_ThreadedRenderer_registerAnimatingRenderNode }, { "nInvokeFunctor", "(JZ)V", (void*) android_view_ThreadedRenderer_invokeFunctor }, Loading libs/hwui/RenderNode.cpp +2 −2 Original line number Diff line number Diff line Loading @@ -81,14 +81,14 @@ RenderNode::~RenderNode() { #endif } void RenderNode::setStagingDisplayList(DisplayList* displayList) { void RenderNode::setStagingDisplayList(DisplayList* displayList, TreeObserver* observer) { mNeedsDisplayListSync = true; delete mStagingDisplayList; mStagingDisplayList = displayList; // If mParentCount == 0 we are the sole reference to this RenderNode, // so immediately free the old display list if (!mParentCount && !mStagingDisplayList) { deleteDisplayList(nullptr); deleteDisplayList(observer); } } Loading Loading
core/java/android/view/ThreadedRenderer.java +2 −4 Original line number Diff line number Diff line Loading @@ -794,8 +794,7 @@ public final class ThreadedRenderer { } final long[] frameInfo = choreographer.mFrameInfo.mFrameInfo; int syncResult = nSyncAndDrawFrame(mNativeProxy, frameInfo, frameInfo.length, mRootNode.mNativeRenderNode); int syncResult = nSyncAndDrawFrame(mNativeProxy, frameInfo, frameInfo.length); if ((syncResult & SYNC_LOST_SURFACE_REWARD_IF_FOUND) != 0) { setEnabled(false); attachInfo.mViewRootImpl.mSurface.release(); Loading Loading @@ -994,8 +993,7 @@ public final class ThreadedRenderer { private static native void nSetLightCenter(long nativeProxy, float lightX, float lightY, float lightZ); private static native void nSetOpaque(long nativeProxy, boolean opaque); private static native int nSyncAndDrawFrame(long nativeProxy, long[] frameInfo, int size, long rootRenderNode); private static native int nSyncAndDrawFrame(long nativeProxy, long[] frameInfo, int size); private static native void nDestroy(long nativeProxy, long rootRenderNode); private static native void nRegisterAnimatingRenderNode(long rootRenderNode, long animatingNode); Loading
core/jni/android_view_RenderNode.cpp +14 −1 Original line number Diff line number Diff line Loading @@ -128,9 +128,22 @@ static void android_view_RenderNode_destroyRenderNode(JNIEnv* env, static void android_view_RenderNode_setDisplayList(JNIEnv* env, jobject clazz, jlong renderNodePtr, jlong displayListPtr) { class RemovedObserver : public TreeObserver { public: virtual void onMaybeRemovedFromTree(RenderNode* node) override { maybeRemovedNodes.insert(sp<RenderNode>(node)); } std::set< sp<RenderNode> > maybeRemovedNodes; }; RenderNode* renderNode = reinterpret_cast<RenderNode*>(renderNodePtr); DisplayList* newData = reinterpret_cast<DisplayList*>(displayListPtr); renderNode->setStagingDisplayList(newData); RemovedObserver observer; renderNode->setStagingDisplayList(newData, &observer); for (auto& node : observer.maybeRemovedNodes) { if (node->hasParents()) continue; onRenderNodeRemoved(env, node.get()); } } // ---------------------------------------------------------------------------- Loading
core/jni/android_view_Surface.cpp +1 −1 Original line number Diff line number Diff line Loading @@ -525,7 +525,7 @@ static void draw(JNIEnv* env, jclass clazz, jlong rendererPtr) { UiFrameInfoBuilder(proxy->frameInfo()) .setVsync(vsync, vsync) .addFlag(FrameInfoFlags::SurfaceCanvas); proxy->syncAndDrawFrame(); proxy->syncAndDrawFrame(nullptr); } static void destroy(JNIEnv* env, jclass clazz, jlong rendererPtr) { Loading
core/jni/android_view_ThreadedRenderer.cpp +36 −37 Original line number Diff line number Diff line Loading @@ -72,6 +72,31 @@ static JNIEnv* getenv(JavaVM* vm) { return env; } // TODO: Clean this up, it's a bit odd to need to call over to // rendernode's jni layer. Probably means RootRenderNode should be pulled // into HWUI with appropriate callbacks for the various JNI hooks so // that RenderNode's JNI layer can handle its own thing void onRenderNodeRemoved(JNIEnv* env, RenderNode* node); class ScopedRemovedRenderNodeObserver : public TreeObserver { public: ScopedRemovedRenderNodeObserver(JNIEnv* env) : mEnv(env) {} ~ScopedRemovedRenderNodeObserver() { for (auto& node : mMaybeRemovedNodes) { if (node->hasParents()) continue; onRenderNodeRemoved(mEnv, node.get()); } } virtual void onMaybeRemovedFromTree(RenderNode* node) override { mMaybeRemovedNodes.insert(sp<RenderNode>(node)); } private: JNIEnv* mEnv; std::set< sp<RenderNode> > mMaybeRemovedNodes; }; class OnFinishedEvent { public: OnFinishedEvent(BaseRenderNodeAnimator* animator, AnimationListener* listener) Loading Loading @@ -120,13 +145,7 @@ private: std::string mMessage; }; // TODO: Clean this up, it's a bit odd to need to call over to // rendernode's jni layer. Probably means RootRenderNode should be pulled // into HWUI with appropriate callbacks for the various JNI hooks so // that RenderNode's JNI layer can handle its own thing void onRenderNodeRemoved(JNIEnv* env, RenderNode* node); class RootRenderNode : public RenderNode, ErrorHandler, TreeObserver { class RootRenderNode : public RenderNode, ErrorHandler { public: RootRenderNode(JNIEnv* env) : RenderNode() { mLooper = Looper::getForThread(); Loading @@ -143,9 +162,6 @@ public: virtual void prepareTree(TreeInfo& info) override { info.errorHandler = this; if (info.mode == TreeInfo::MODE_FULL) { info.observer = this; } // TODO: This is hacky info.windowInsetLeft = -stagingProperties().getLeft(); info.windowInsetTop = -stagingProperties().getTop(); Loading @@ -155,7 +171,6 @@ public: info.windowInsetLeft = 0; info.windowInsetTop = 0; info.errorHandler = nullptr; info.observer = nullptr; } void sendMessage(const sp<MessageHandler>& handler) { Loading @@ -181,27 +196,10 @@ public: mPendingAnimatingRenderNodes.clear(); } virtual void onMaybeRemovedFromTree(RenderNode* node) override { mMaybeRemovedNodes.insert(sp<RenderNode>(node)); } void processMaybeRemovedNodes(JNIEnv* env) { // We can safely access mMaybeRemovedNodes here because // we will only modify it in prepareTree calls that are // MODE_FULL for (auto& node : mMaybeRemovedNodes) { if (node->hasParents()) continue; onRenderNodeRemoved(env, node.get()); } mMaybeRemovedNodes.clear(); } private: sp<Looper> mLooper; JavaVM* mVm; std::vector< sp<RenderNode> > mPendingAnimatingRenderNodes; std::set< sp<RenderNode> > mMaybeRemovedNodes; }; class AnimationContextBridge : public AnimationContext { Loading Loading @@ -500,24 +498,23 @@ static void android_view_ThreadedRenderer_setOpaque(JNIEnv* env, jobject clazz, } static int android_view_ThreadedRenderer_syncAndDrawFrame(JNIEnv* env, jobject clazz, jlong proxyPtr, jlongArray frameInfo, jint frameInfoSize, jlong rootNodePtr) { jlong proxyPtr, jlongArray frameInfo, jint frameInfoSize) { LOG_ALWAYS_FATAL_IF(frameInfoSize != UI_THREAD_FRAME_INFO_SIZE, "Mismatched size expectations, given %d expected %d", frameInfoSize, UI_THREAD_FRAME_INFO_SIZE); RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr); RootRenderNode* rootRenderNode = reinterpret_cast<RootRenderNode*>(rootNodePtr); ScopedRemovedRenderNodeObserver observer(env); env->GetLongArrayRegion(frameInfo, 0, frameInfoSize, proxy->frameInfo()); int ret = proxy->syncAndDrawFrame(); rootRenderNode->processMaybeRemovedNodes(env); return ret; return proxy->syncAndDrawFrame(&observer); } static void android_view_ThreadedRenderer_destroy(JNIEnv* env, jobject clazz, jlong proxyPtr, jlong rootNodePtr) { ScopedRemovedRenderNodeObserver observer(env); RootRenderNode* rootRenderNode = reinterpret_cast<RootRenderNode*>(rootNodePtr); rootRenderNode->destroy(); RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr); proxy->destroy(); proxy->destroy(&observer); } static void android_view_ThreadedRenderer_registerAnimatingRenderNode(JNIEnv* env, jobject clazz, Loading @@ -542,9 +539,10 @@ static jlong android_view_ThreadedRenderer_createTextureLayer(JNIEnv* env, jobje static void android_view_ThreadedRenderer_buildLayer(JNIEnv* env, jobject clazz, jlong proxyPtr, jlong nodePtr) { ScopedRemovedRenderNodeObserver observer(env); RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr); RenderNode* node = reinterpret_cast<RenderNode*>(nodePtr); proxy->buildLayer(node); proxy->buildLayer(node, &observer); } static jboolean android_view_ThreadedRenderer_copyLayerInto(JNIEnv* env, jobject clazz, Loading Loading @@ -579,8 +577,9 @@ static void android_view_ThreadedRenderer_detachSurfaceTexture(JNIEnv* env, jobj static void android_view_ThreadedRenderer_destroyHardwareResources(JNIEnv* env, jobject clazz, jlong proxyPtr) { ScopedRemovedRenderNodeObserver observer(env); RenderProxy* proxy = reinterpret_cast<RenderProxy*>(proxyPtr); proxy->destroyHardwareResources(); proxy->destroyHardwareResources(&observer); } static void android_view_ThreadedRenderer_trimMemory(JNIEnv* env, jobject clazz, Loading Loading @@ -736,7 +735,7 @@ static const JNINativeMethod gMethods[] = { { "nSetup", "(JIIFII)V", (void*) android_view_ThreadedRenderer_setup }, { "nSetLightCenter", "(JFFF)V", (void*) android_view_ThreadedRenderer_setLightCenter }, { "nSetOpaque", "(JZ)V", (void*) android_view_ThreadedRenderer_setOpaque }, { "nSyncAndDrawFrame", "(J[JIJ)I", (void*) android_view_ThreadedRenderer_syncAndDrawFrame }, { "nSyncAndDrawFrame", "(J[JI)I", (void*) android_view_ThreadedRenderer_syncAndDrawFrame }, { "nDestroy", "(JJ)V", (void*) android_view_ThreadedRenderer_destroy }, { "nRegisterAnimatingRenderNode", "(JJ)V", (void*) android_view_ThreadedRenderer_registerAnimatingRenderNode }, { "nInvokeFunctor", "(JZ)V", (void*) android_view_ThreadedRenderer_invokeFunctor }, Loading
libs/hwui/RenderNode.cpp +2 −2 Original line number Diff line number Diff line Loading @@ -81,14 +81,14 @@ RenderNode::~RenderNode() { #endif } void RenderNode::setStagingDisplayList(DisplayList* displayList) { void RenderNode::setStagingDisplayList(DisplayList* displayList, TreeObserver* observer) { mNeedsDisplayListSync = true; delete mStagingDisplayList; mStagingDisplayList = displayList; // If mParentCount == 0 we are the sole reference to this RenderNode, // so immediately free the old display list if (!mParentCount && !mStagingDisplayList) { deleteDisplayList(nullptr); deleteDisplayList(observer); } } Loading