Framework层 由Dart编写,开发者接触到顶层,用于应用层开发
Engine 层,由C/C++编写,主要进行图形渲染
Embedder层,由植入层语言编写,如iOS使用Objective-C/swift,Android使用java
flutter::EngineLayer --> ui.EngineLayer flutter::FrameInfo --> ui.FrameInfo flutter::CanvasImage --> ui.Image flutter::SceneBuilder --> ui.SceneBuilder flutter::Scene --> ui.Scene
Dart层渲染过程是配置的layer渲染树,并且提交到c++层进行渲染的过程。ui.SceneBuilder便是这颗渲染树的容器
Dart代码调用构造函数 ui.SceneBuilder()时,调用c++方法 SceneBuilder_constructor
调用 flutter::SceneBuilder的构造方法并生成c++实例sceneBuilder
因 flutter::SceneBuilder 继承自内存计数对象 RefCountedDartWrappable,对象生成后会内存计数加1
将生成c++实例sceneBuilder使用Dart的API生成一个 WeakPersitentHandle,注入到Dart上下中。在这里之后,Dart便可使用这个 builder对象,便可操作这个c++的 flutter::SceneBuilder实例。
程序运行许久后,当Dart虚拟机判断Dart 对象builder没有被任何其他对象引用时(例如简单的情况是被置空builder=null,也称为无可达性),对象就会被垃圾回收器(Garbage Collection)回收释放,内存计数将会减一
当内存计数为0时,会触发c++的析构函数,最终c++实例指向的内存块被回收
我们这种从渲染树的角度去探寻flutter内存泄漏的方法,可以推广到所以其他Dart不同类型的对象。
开发者在编写代码时,需要时刻注意异步调用,以及时刻注意操纵的Element会否被引用而导致无法释放。
✿ 拓展阅读
作者|萧湘
编辑|橙子君
出品|阿里巴巴新零售淘系技术