当前位置:网站首页>BlocProvider为什么感觉和Provider很相似?
BlocProvider为什么感觉和Provider很相似?
2022-07-01 23:31:00 【岛上码农@公众号同名】
前言
上一篇Flutter 入门与实战(八十六):不到40行代码手撸一个BlocProvider,我们只用了不到40行代码手撸了一个 SimpleBlocProvider
,用起来感觉也还可以,这就是 Bloc 的优势之一,你可以基于 Bloc
这种模式自己做扩展,形成自己的状态管理组件。我们这一篇来看看官方 flutter_bloc 插件提供的 BlocProvider
怎么样。
Provider 的模仿者?
我们先来看 BlocProvider
实现的计数器示例代码:
class BlocCounterWrapper extends StatelessWidget {
@override
Widget build(BuildContext context) {
return BlocProvider(
create: (_) => CounterCubit(),
child: BlocCounterPage(),
);
}
}
class BlocCounterPage extends StatelessWidget {
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('Bloc 计数器'),
),
body: Center(
child: BlocBuilder<CounterCubit, int>(
builder: (context, count) => Text(
'$count',
style: TextStyle(
fontSize: 32,
color: Colors.blue,
),
),
),
),
floatingActionButton: FloatingActionButton(
onPressed: () {
context.read<CounterCubit>().increment();
},
tooltip: '点击增加',
child: Icon(Icons.add),
),
);
}
}
这代码是不是十分熟悉?如果回顾我们之前的 Provider
状态管理,感觉是十分相似啊!比如:
Widget build(BuildContext context) {
return BlocProvider(
create: (_) => CounterCubit(),
child: BlocCounterPage(),
);
}
在 Provider
里实现就是下面这样。
Widget build(BuildContext context) {
return Provider(
create: (_) => CounterCubit(),
child: BlocCounterPage(),
);
}
而在 FloatingActionButton
里的 context.read
用法也和 Provider
里的一样。所以,如果要从 Provider
迁移到 Bloc 也是十分简单的。实际从源码逐层向上,你会发现里面就有 provider 的代码。
library flutter_bloc;
export 'package:bloc/bloc.dart';
export 'package:provider/provider.dart'
show ProviderNotFoundException, ReadContext, SelectContext, WatchContext;
而从 Provider
和 bloc
的GitHub源码贡献者中我们也发现 Provider
的代码贡献者Felix Angelov 就是 bloc 代码的发起者。。 所以这就不奇怪 Bloc 中使用 Provider 了。
与 Provider 的异同
BlocProvider
和 Provider
一样,通过组件树为子组件提供状态数据。也就是我们可以像使用 Provider
一样使用 BlocProvider
,比如使用已有的状态对象时的哟用法和 Provider
一样使用 value
参数赋值:
final counter = CounterCubit();
//...
BlocProvider.value(
value: counter,
child: SomeWidget(),
);
在比如可以在子组件中使用 context.read
和 context.watch
。以及使用 select 方法监听状态数据的部分变化。
final isPositive = context.select((CounterBloc b) => b.state >= 0);
还有 MultiBlocProvider
来向子组件树传递多个Bloc状态对象。
MultiBlocProvider(
providers: [
BlocProvider<BlocA>(
create: (BuildContext context) => BlocA(),
),
BlocProvider<BlocB>(
create: (BuildContext context) => BlocB(),
),
BlocProvider<BlocC>(
create: (BuildContext context) => BlocC(),
),
],
child: ChildA(),
)
可以说,如果之前你用 Provider
状态管理的话,可以无缝迁移到 BlocProvider
。当然,状态对象类还是需要改一下的。这也是 BlocProvider
和 Provider
的区别。比如状态对象不需要实现 ChangeNotifier
接口,在状态数据改变的时候也无需调用 notifyListeners
来通知刷新。实际我们从 BlocProvider
的源码扒出了一段监听状态对象实现的方法,这里其实也是使用我们在 SimpleBlocProvider
中使用的 Stream.listen
方法来实现的。
static VoidCallback _startListening(
InheritedContext<BlocBase?> e,
BlocBase value,
) {
final subscription = value.stream.listen(
(dynamic _) => e.markNeedsNotifyDependents(),
);
return subscription.cancel;
}
而其他部分的代码基本就是复用 Provider
的代码。所以 BlocProvider
可以看成是使用了 Stream.listen
监听状态数据的方式替换 ChangeNotifer
的 Provider
的变种。因此,如果想从 Provider
切换到 BlocProvider
,可以大胆地切换,代码修改工作量很低。而且无需在状态对象里反复调用 notifyListeners
来通知界面刷新了。
总结
本篇介绍了 BlocProvider
的使用,从写法上来看,感觉不到太多的优势,个人估计这是作者想让 Provider
的用户可以直接切换到 BlocProvider
才提供了这么一个 Provider
的替代品。不过,这只是冰山一脚,实际上,flutter_bloc 还提供了很多其他的选择,我们接下来会一一介绍。
边栏推荐
猜你喜欢
Matplotlib常用設置
Three development trends of enterprise application from the perspective of the third technological revolution
Huisheng Huiying 2022 intelligent, fast and simple video editing software
Redis AOF日志
安全协议重点
Notes to problems - file /usr/share/mysql/charsets/readme from install of mysql-server-5.1.73-1 glibc23.x86_ 64 c
为什么PHP叫超文本预处理器
【.Net Core】程序相关各种全局文件
Why is PHP called hypertext preprocessor
Win 10 mstsc connect RemoteApp
随机推荐
2022 examination questions and online simulation examination for safety management personnel of hazardous chemical business units
[LeetCode] 最后一个单词的长度【58】
【必会】BM41 输出二叉树的右视图【中等+】
Daily three questions 6.30
Postgresql随手记(10)动态执行EXECUTING语法解析过程
What are the common types of points mall games?
Redis RDB快照
JS - use of arguments
物联网技术应用属于什么专业分类
[micro service sentinel] sentinelresourceaspect details
Y53. Chapter III kubernetes from introduction to mastery -- ingress (26)
y53.第三章 Kubernetes从入门到精通 -- ingress(二六)
Future trend and development of neural network Internet of things
ADO.NET之SqlDataAdpter对象
JPA handwritten SQL, received with user-defined entity classes
每日三题 6.30
每日三题 6.30(2)
Door level modeling - after class exercises
notBlank 和 notEmpty
Three development trends of enterprise application from the perspective of the third technological revolution