当前位置:网站首页>使用 RepositoryProvider简化父子组件的传值
使用 RepositoryProvider简化父子组件的传值
2022-07-05 19:29:00 【InfoQ】
前言
- 构造函数传值:父组件将子组件需要的对象通过构造函数传递给子组件;
- 单例对象:构建单例对象,使得父子组件使用的是同一个对象;
- 容器:将对象存入容器中,父子组件使用的时候直接从容器中获取。
RepositoryProvider
Provider
RepositoryProvider定义
Repository
Provider
Provider
Bloc
Bloc
RepositoryProvider
create
value
create
value
RepositoryProvider
class RepositoryProvider<T> extends Provider<T>
with RepositoryProviderSingleChildWidget {
RepositoryProvider({
Key? key,
required Create<T> create,
Widget? child,
bool? lazy,
}) : super(
key: key,
create: create,
dispose: (_, __) {},
child: child,
lazy: lazy,
);
RepositoryProvider.value({
Key? key,
required T value,
Widget? child,
}) : super.value(
key: key,
value: value,
child: child,
);
static T of<T>(BuildContext context, {bool listen = false}) {
try {
return Provider.of<T>(context, listen: listen);
} on ProviderNotFoundException catch (e) {
if (e.valueType != T) rethrow;
throw FlutterError(
'''
RepositoryProvider.of() called with a context that does not contain a repository of type $T.
No ancestor could be found starting from the context that was passed to RepositoryProvider.of<$T>().
This can happen if the context you used comes from a widget above the RepositoryProvider.
The context used was: $context
''',
);
}
}
}
mixin RepositoryProviderSingleChildWidget on SingleChildWidget {}
MultiRepositoryProvider
RepositoryProvider
RepositoryProvider
Provider
of
listen
false
// 方式1
context.read<T>()
// 方式2
RepositoryProvider.of<T>(context)
MultiRepositoryProvider
MultiRepositoryProvider(
providers: [
RepositoryProvider<RepositoryA>(
create: (context) => RepositoryA(),
),
RepositoryProvider<RepositoryB>(
create: (context) => RepositoryB(),
),
RepositoryProvider<RepositoryC>(
create: (context) => RepositoryC(),
),
],
child: ChildA(),
)
RepositoryProvider 应用
- 头像及背景图:
_getBannerWithAvatar
;
- 个人资料:
_getPersonalProfile
;
- 个人数据统计:
_getPersonalStatistic
。

PersonalEntity personalProfile = personalResponse.personalProfile!;
return Stack(
children: [
CustomScrollView(
slivers: [
_getBannerWithAvatar(context, personalProfile),
_getPersonalProfile(personalProfile),
_getPersonalStatistic(personalProfile),
],
),
// ...
],
);
},
//...
personalProfile

personalProfile
RepositoryProvider.value(
child: CustomScrollView(
slivers: [
const BannerWithAvatar(),
const PersonalProfile(),
const PersonalStatistic(),
],
),
value: personalProfile,
),
// ...
value
personalProfile
personalProfile
context.read<PersonalEntity>()
RepositoryProvider
personalProfile
class BannerWithAvatar extends StatelessWidget {
final double bannerHeight = 230;
final double imageHeight = 180;
final double avatarRadius = 45;
final double avatarBorderSize = 4;
const BannerWithAvatar({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return SliverToBoxAdapter(
child: Container(
height: bannerHeight,
color: Colors.white70,
alignment: Alignment.topLeft,
child: Stack(
children: [
Container(
height: bannerHeight,
),
Positioned(
top: 0,
left: 0,
child: CachedNetworkImage(
imageUrl:
'https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=688497718,308119011&fm=26&gp=0.jpg',
height: imageHeight,
width: MediaQuery.of(context).size.width,
fit: BoxFit.fill,
),
),
Positioned(
left: 20,
top: imageHeight - avatarRadius - avatarBorderSize,
child: _getAvatar(
context.read<PersonalEntity>().avatar,
avatarRadius * 2,
avatarBorderSize,
),
),
],
),
),
);
}
Widget _getAvatar(String avatarUrl, double size, double borderSize) {
return Stack(alignment: Alignment.center, children: [
Container(
width: size + borderSize * 2,
height: size + borderSize * 2,
clipBehavior: Clip.antiAlias,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(size / 2 + borderSize),
),
),
Container(
width: size,
height: size,
clipBehavior: Clip.antiAlias,
decoration: BoxDecoration(
color: Colors.black,
borderRadius: BorderRadius.circular(size / 2),
),
child: CachedNetworkImage(
imageUrl: avatarUrl,
height: size,
width: size,
fit: BoxFit.fill,
),
),
]);
}
}
总结
RepositoryProvider
RepositoryProvider
Provider
RepositoryProvider
context
RepositoryProvider.of

边栏推荐
- Xaas trap: all things serve (possible) is not what it really needs
- 爬虫练习题(二)
- Teach you to deal with JS reverse picture camouflage hand in hand
- 通过POI追加数据到excel中小案例
- PHP uses ueditor to upload pictures and add watermarks
- Debezium系列之:IDEA集成词法和语法分析ANTLR,查看debezium支持的ddl、dml等语句
- Fuzor 2020软件安装包下载及安装教程
- MMO项目学习一:预热
- Advanced application of C # language
- Information / data
猜你喜欢
大厂面试必备技能,2022Android不死我不倒
使用easyexcel模板导出的两个坑(Map空数据列错乱和不支持嵌套对象)
基于FPGA的超声波测距
【AI 框架基础技术】自动求导机制 (Autograd)
Can Leica capture the high-end market offered by Huawei for Xiaomi 12s?
Oracle fault handling: ora-10873:file * needs to be either taken out of backup or media recovered
Xaas trap: all things serve (possible) is not what it really needs
Advanced application of C # language
Millimeter wave radar human body sensor, intelligent perception of static presence, human presence detection application
UWB ultra wideband positioning technology, real-time centimeter level high-precision positioning application, ultra wideband transmission technology
随机推荐
Postman核心功能解析-参数化和测试报告
【FAQ】华为帐号服务报错 907135701的常见原因总结和解决方法
Debezium系列之:解析默认值字符集
IFD-x 微型红外成像仪(模块)关于温度测量和成像精度的关系
acm入门day1
Microwave radar induction module technology, real-time intelligent detection of human existence, static micro motion and static perception
Can Leica capture the high-end market offered by Huawei for Xiaomi 12s?
Postman core function analysis - parameterization and test report
Django使用mysqlclient服务连接并写入数据库的操作过程
[performance test] jmeter+grafana+influxdb deployment practice
毫米波雷达人体感应器,智能感知静止存在,人体存在检测应用
数学分析_笔记_第9章:曲线积分与曲面积分
618“低调”谢幕,百秋尚美如何携手品牌跨越“不确定时代”?
[Collection - industry solutions] how to build a high-performance data acceleration and data editing platform
C#应用程序界面开发基础——窗体控制(6)——菜单栏、工具栏和状态栏控件
#夏日挑战赛# HarmonyOS - 实现消息通知功能
不愧是大佬,字节大牛耗时八个月又一力作
Zhongang Mining: analysis of the current market supply situation of the global fluorite industry in 2022
word如何转换成pdf?word转pdf简单的方法分享!
【AI 框架基础技术】自动求导机制 (Autograd)