Flutter的组件渲染方式参考了RN的渲染方式,通过虚拟Dom和diff计算来达到性能的优化。在Flutter中左右的东西都是有Widget组成,这里我们不讨论简单的StalessWidgtet,因为其使用和渲染都很简单,主要以有实际意义的StafulWidget为探讨对象。与RN的渲染一样,可以将Flutter组件渲染分成三个阶段
- 初始化(插入渲染树)
- 状态改变(更新渲染树组件)
- 销毁(移除渲染树)
1. 初始化
初始化的时候会依次调用initState->didChangedDependencies->build方法。
initState是在构造函数之后调用的,整个组件的生命周期阶段只会调用一次,值得注意的是在我们更新组件的时候,组件是会重新创建的,但State在销毁之前一直都是同一个,并且重新绑定到新的组件上,在里面我们可以初始化一些全局要用到的东西。
didChangedDependencies方法会在initState后调用,在这方法回调里,我们可以使用InheritedWidget获取父级传递共享的资源。整个生命周期didChangedDependencies会调用多次,至少1次,并且在某些更新阶段也会调用。
2. 更新
更新分为两种更新:
一种是组件本身或者其父组件调用setState触发的更新,这种更新走的生命周期是:didUpdateWidget->build。
这没什么说的,我们可以在didUpdateWidget重新绑定一些组件的监听或者重置状态。
另一种是依赖的InheritedWidget发生变化的时候,会触发didChangedDependencies。
3.销毁
销毁阶段,主要执行的方法有两个:deactivate->dispose。
deactivate方法标志组件为无效状态,紧跟着会进入dispose,
dispose是组件完全销毁时回调,主要在里面做一些移除监听的操作
两个页面时的生命周期
简单了解生命周期还不够,要知道我们有多个页面时生命周期是如何运作的这对我们开发来很重要。
假设有两个页面A、B,当我们新打开页面时,初始化阶段很简单
A:initState -> didChangedDependences ->build
这时候,我们开启新的B页面:
B:initState -> didChangedDependences ->build
A:deactivate->build
你没有看错,我们B页面初始化阶段结束后,A页面会进入不可用状态,并重新build(但不会绘制),A页面不会卸载。
最后,我们从B页面按返回键返回A页面:
A:deactivate->build
B:deactivate->dispose
此时A页面进入运行状态,B页面移除