一、状态管理
1.概念
Flutter是一种响应式编程框架,能根据数据或状态变化自动更新用户界面。状态(State)指的是某个时间点上,应用中的所有变量和数据的当前值或配置,比如用户登录信息、表单数据、页面显示内容、网络请求的结果等。状态管理涉及如何追踪、更新和同步应用程序的状态,确保在数据变化时,用户界面能够正确更新。
2.方式
-
父 Widget 管理子 Widget 的状态:适用于跟用户数据相关的状态管理
-
Widget 管理自己的状态:适用于组件私有的状态,比如UI样式
-
父 Widget 和子 Widget混合管理:既涉及数据也涉及UI样式
-
全局状态管理:需要同步跨组件状态
-
事件通知+setState:Flutter 框架重新调用 build 方法,对比新的和旧的 widget 树,重建发生了变化的部分
-
InheritedWidget:在整个组件树中传递数据,通知依赖它的子树,当数据发生变化时重新构建
-
二、setState
只能在 StatefulWidget 中使用,适用于局部状态更新
-
源码
@protected
void setState(VoidCallback fn) { //传入一个回调函数,更新有变化的状态变量
assert(fn != null); //断言检查有传入的回调函数
assert(() { //断言检查调用 setState 时的生命周期正确
if (_debugLifecycleState == _StateLifecycle.defunct) { //检查 State 对象是否已被销毁
throw FlutterError.fromParts(<DiagnosticsNode>[
ErrorSummary('setState() called after dispose(): $this'),
ErrorDescription(
'This error happens if you call setState() on a State object for a widget that '
'no longer appears in the widget tree (e.g., whose parent widget no longer '
'includes the widget in its build). This error can occur when code calls '
'setState() from a timer or an animation callback.',
),
ErrorHint(
'The preferred solution is '
'to cancel the timer or stop listening to the animation in the dispose() '
'callback. Another solution is to check the "mounted" property of this '
'object before calling setState() to ensure the object is still in the '
'tree.',
),
ErrorHint(
'This error might indicate a memory leak if setState() is being called '
'because another object is retaining a reference to this State object '
'after it has been removed from the tree. To avoid memory leaks, '
'consider breaking the reference to this object during dispose().',
),
]);
}
if (_debugLifecycleState == _StateLifecycle.created && !mounted) { //检查 State 对象是否刚被创建尚未插入 Widget 树中
throw FlutterError.fromParts(<DiagnosticsNode>[
ErrorSummary('setState() called in constructor: $this'),