1. Flutter 原理与优势
在开始之前,先简单了解一下 Flutter:
我们可以看到 Flutter 框架包括 Framework 和 Engine,他们运行在各自的 Platform 上。其中,Freamwork 是 Dart 实现的,其提供了基础 Widgets 与 渲染、动画、绘制、手势等能力,开发者可以基于此实现各种 Widgets;而 Engine 是 C++ 实现的,包括 Skia 二位图形库、Dart VM、Text 文本渲染等。实际上,Flutter 的上层能力都是由 Engine 提供的,Flutter 正是通过 Engine 将各个 Platform 的差异化抹平,从而保证多端一致性。接下来,我们自上而下逐一分析 Flutter 的优势。
1.1 Framework (Dart)
首先,我们看看 Framework。其实,Flutter 选用 Dart 语言作为上层语言也是绝妙的选择。
在语言设计上,Dart 的设计目标应该是同时借鉴了 Java 和 JavaScript。Dart 在静态语法方面和 Java 非常相似,如类型定义、函数声明、泛型等,而在动态特性方面又和 JavaScript 很像,如函数式特性、异步支持等。并且 Dart 又各自取长补短从而完善自身,语言特性上丰富且优雅。
并且 Dart 运行时和编译器支持 Flutter 的两个关键特性的组合:
- 基于JIT的快速开发周期:Flutter在开发阶段采用,采用 JIT 模式,这样就避免了每次改动都要进行编译,极大的节省了开发时间;(注:这一点客户端开发同学应该深有体会,手 Q iOS 开发同学和我说改动一行手Q代码都要编译40分钟才能看到效果)
- 基于AOT的发布包: Flutter 在发布时可以通过 AOT 生成高效的 ARM 代码以保证应用性能。而 JavaScript 则不具有这个能力。
至于 Dart VM 的性能方面,我想我们也不需要太过担心,虽然没有找到相关测试数据,但毕竟 Google 在 Go(没用 VM 但有 GC)、JavaScript(V8)、Dalvik(Android 上的 Java VM)上已经有了很多技术积淀,事实上 Dart 开发团队的很多成员都是来自 Chrome 团队的。
1.2 Engine(C++)
其次,我们看看 Flutter Engine 的优势。之前我们无论是开发 React Native 还是 Hippy 的混编项目,UI 组件的渲染实际上都是交由 Native 侧负责渲染的,这就会导致可能存在的多端不一致性。下面分别 Hippy iOS 工程的代码结构、Hippy 与 Native 的通信原理与 UI 组件渲染过程图(出处:@dahonglin 同学的 《iOS Hippy 实践》分享,React Native 原理图与 Hippy 一致,此处不赘述),Hippy 侧调用某组件,实际上通过 JS Bridge 是向 Native 请求渲染 Native 提供的组件,渲染工作由 Native 自己完成,而非 Flutter Engine 直接提供 Render 能力来抹平多端的差异性。
1.3 Platform(Native)
最后,这一层我们主要来关注一下 Flutter Plugin 与 Native 的通信。Flutter Plugin 可以提供通过 MethodChannel 调起客户端 API 从而使 Flutter 获取客户端能力,原理如下所示:
比如我们可以封装一个获取剩余电脑的 Plugin,在 Dart 侧直接使用两端封装好的 API 即可。
综上所述,Flutter 是 Google 使用 Dart 语言开发的一套移动应用开发框架,它不同于其他开发框架:
- Flutter 使用 AOT 预编译代码为机器码,所以它的运行效率更高**,**且运行时采用 JIT 模式,支持 Hot Reload。
- Flutter 的 UI 控件并没有使用底层的原生控件,而是使用 Skia 渲染引擎绘制而成,因为不依赖底层控件,所以多端一致性非常好。
- 开发者可以通过 Plugin 与 Native 进行通信,扩展性也非常强。