Flutter组件生命周期和App生命周期示例解析

作者:顾安 时间:2022-07-18 23:15:59 

引言

在Flutter开发中,所有的组件和页面都继承自Widget,所以探索页面的生命周期其实就是Widget的生命周期。 在 Flutter 中一切皆 组件,而组件又分为 StatefulWidget(有状态) 和 StatelessWidget(无状态)组件

无状态组件(StatelessWidget)

无状态组件,可以理解为将外部传入的数据转化为界面展示的内容,只会渲染一次。

有状态组件(StatefulWidget)

有状态组件,是定义交互逻辑和业务数据,可以理解为具有动态可交互的内容界面,会根据数据的变化进行多次渲染。

Flutter组件生命周期和App生命周期示例解析

StatefulWidget生命周期详细分析

1. createState

当StatefulWidget被创建时立即执行createState。createState 函数执行完毕后表示当前组件已经在 Widget 树中,此时有一个非常重要的属性mounted设置为true。

2. initState

该函数为 State 初始化调用,只会被调用一次。因此,通常会在该回调中做一些一次性的操作,如执行 State 各变量的初始赋值,获取服务端数据等。

3. didChangeDependencies

该函数是在该组件依赖的 State 发生变化时会被调用。didChangeDependencies 方法调用后,组件的状态变为 dirty,立即调用 build 方法。

4. build

主要是在方法中创建各种组件,绘制到屏幕上,由于 build 会被调用多次,因此在该函数中只能做返回 Widget 相关逻辑,避免因为执行多次而导致状态异常。因此此方法可以在每一帧中调用,此方法中应该只包含构建组件的代码,不应该包含其他额外的功能,尤其是耗时任务。

5. didUpdateWidget

该函数主要是在组件重新构建,比如说热重载,父组件发生 build 的情况下,子组件该方法才会被调用,其次该方法调用之后一定会再调用本组件中的 build 方法。此方法中通常会用当前组件与前组件进行对比。Framework 调用完此方法后,会将组件设置为 dirty 状态,然后调用 build 方法,因此无需在此方法中调用 setState 方法。

6. deactivate

在组件被移除节点后会被调用,在某些情况下,框架将重新插入 State 对象到树的其他位置(例如,如果包含该树的子树 State 对象从树中的一个位置移植到另一位置),框架将会调用 build 方法来提供 State 对象适应其在树中的新位置。

7. dispose

永久移除组件,并释放组件资源。调用完 dispose后,mounted 属性被设置为 false,也代表组件生命周期的结束,此时再调用 setState 方法将会抛出异常。

8. reassemble

主要在开发阶段使用,在 debug 模式下,每次热重载都会调用该函数,因此在 debug 阶段可以在此期间增加一些 debug 代码,来检查代码问题。

App生命周期

App的生命周期的监听,在Flutter中需要通过 * WidgetsBindingObserver * 中的AppLifecycleState方法来是实现。

class AppLifePage extends StatefulWidget {
 CEAppLifePage({Key key}) : super(key: key);
 @override
 _AppLifePageState createState() => _AppLifePageState();
}
//  实现WidgetsBindingObserver观察者
class _AppLifePageState extends State<AppLifePage> with WidgetsBindingObserver{
 @override
 void initState() {
   super.initState();
   WidgetsBinding.instance.addObserver(this); //添加观察者
 }
 @override
 Widget build(BuildContext context) {
   return Scaffold(
     appBar: AppBar(title: Text("App生命周期"),),
     body: Text('Flutter App 生命周期'),
   );
 }
 @override
 void didChangeAppLifecycleState(AppLifecycleState state) {
   super.didChangeAppLifecycleState(state);
   print("didChangeAppLifecycleState: $state");
   switch (state) {
       case AppLifecycleState.resumed:
         print('应用程序可见且响应用户输入。');
         break;
       case AppLifecycleState.paused:
         print('应用程序不可见且无法响应用户输入,运行在后台。');
         break;
       case AppLifecycleState.inactive:
         print('应用程序处于非激活状态,无法响应用户输入。');
         break;
       case AppLifecycleState.detached:
         print('应用程序仍寄存在Flutter引擎上,但与平台 View 分离。');
         break;
     }
 }
 //  当前系统改变了一些访问性活动的回调
 @override
 void didChangeAccessibilityFeatures() {
   super.didChangeAccessibilityFeatures();
   print("didChangeAccessibilityFeatures");
 }
 //  低内存回调
 @override
 void didHaveMemoryPressure() {
   super.didHaveMemoryPressure();
   print("didHaveMemoryPressure");
 }
 //  用户本地设置变化时调用,如系统语言改变
 @override
 void didChangeLocales(List<Locale> locale) {
   super.didChangeLocales(locale);
   print("didChangeLocales");
 }
 //  应用尺寸改变时回调,例如旋转
 @override
 void didChangeMetrics() {
   super.didChangeMetrics();
   Size size = WidgetsBinding.instance.window.physicalSize;
   print("didChangeMetrics  :宽:${size.width} 高:${size.height}");
 }
 //  系统切换主题时回调
 @override
 void didChangePlatformBrightness() {
   super.didChangePlatformBrightness();
   print("didChangePlatformBrightness");
 }
 //  文字系数变化
 @override
 void didChangeTextScaleFactor() {
   super.didChangeTextScaleFactor();
   print(
       "didChangeTextScaleFactor  :${WidgetsBinding.instance.window.textScaleFactor}");
 }
 @override
 void dispose() {
   super.dispose();
   WidgetsBinding.instance.removeObserver(this); //  销毁观察者
 }
}

重点是重写 didChangeAppLifecycleState 方法,AppLifecycleState 中的状态包括:resumed、inactive、paused、detached。

resumed:应用程序可见且响应用户输入。

inactive:应用程序处于非激活状态,无法响应用户输入。在iOS上,打电话、响应TouchID请求、进入应用程序切换器或控制中心都处于此状态。在Android上,分屏应用,打电话,弹出系统对话框或其他窗口等。

pause:应用程序不可见且无法响应用户输入,运行在后台。处于此状态时,引擎将不会调用 Window.onBeginFrame 和 Window.onDrawFrame。

detached:应用程序仍寄存在Flutter引擎上,但与平台 View 分离。处于此状态的时机:引擎首次加载到附加 到一个平台 View的过程中,或者由于执行 Navigator pop ,view 被销毁。

结束语

来源:https://juejin.cn/post/7168709152808648735

标签:Flutter,组件,APP,生命周期
0
投稿

猜你喜欢

  • 常用的Java数据结构知识点汇总

    2022-09-09 02:26:02
  • 详解Springboot配置文件的使用

    2022-02-26 09:02:26
  • 浅谈android @id和@+id的区别

    2021-10-28 06:06:09
  • Android自定义控件实现UC浏览器语音搜索效果

    2022-06-01 06:59:40
  • SpringBoot异步调用方法并接收返回值

    2023-08-16 22:33:49
  • Android实现启动页倒计时效果

    2021-07-26 20:50:14
  • C++编程异常处理中try和throw以及catch语句的用法

    2023-04-08 15:29:41
  • Mybatis-Plus分页的使用与注意事项

    2022-08-14 22:00:56
  • Java对List进行排序的两种实现方法

    2022-10-31 13:40:06
  • Java 程序员掌握 Spring Boot非常有必要

    2021-06-27 19:06:52
  • Java使用线程池实现socket编程的方法详解

    2022-12-17 22:05:12
  • SpringAOP+RabbitMQ+WebSocket实战详解

    2023-01-01 18:40:25
  • android中RecyclerView自定义分割线实现

    2023-08-03 17:37:47
  • Android中使用Kotlin实现一个简单的登录界面

    2023-01-29 13:51:37
  • spring Bean创建的完整过程记录

    2022-04-14 03:57:51
  • SpringBoot+easypoi实现数据的Excel导出

    2023-04-05 12:27:19
  • Java泛型与数据库应用实例详解

    2023-08-14 09:37:15
  • C#开发WinForm之DataGridView开发详解

    2023-06-25 06:31:35
  • Linux下动静态库的打包与使用指南(C/C++)

    2023-06-21 20:22:11
  • C#将Word转换成PDF方法汇总(基于Office和WPS)

    2021-09-12 22:52:58
  • asp之家 软件编程 m.aspxhome.com