Flutter 中 Provider 基本使用
前言:
Provider.of<XXX>(context).数据
Provider.of<XXX>(context).方法
ChangeNotifier:这个是真正数据(状态)存放的地方。我们自己创建的provider 是混入ChangeNotifier 的。
一 安装
在pub.dev 上搜索provider
二 在main中设置
三 使用
1 > 创建一个count_provider 类
import 'package:flutter/foundation.dart';// 实现基于ChangeNotifier的类 内部维护一个计数
// 当计数有变化的时候,同时感知所有的监听者
class CountProvider with ChangeNotifier {int _count = 0;int get count => _count;void increment() {_count++;// 这里一定要通知变化notifyListeners();}void reset() {_count = 0;notifyListeners();}
}
2> 在 Widget build(BuildContext context) 中获取provider ,需要传入context
_countProvider = Provider.of<CountProvider>(context);
3>可以调用 操作数据
this._countProvider.increment();
this._countProvider.reset();
4 在依赖数据的widget 使用数据 数据怎会
// 现获取
_countProvider = Provider.of<CountProvider>(context);
// 再去使用
Text("${this._countProvider.count}"),
四 什么是Consumer?
使用Consumer 的话,Widget build 方法不会多次build,改变只需要改变的,实现了局部刷新。
class _ProviderSonWidgetState extends State<ProviderSonWidget> {// var _countProvider;@overrideWidget build(BuildContext context) {print("计数改变了,ProviderSonWidgetState 调用了build");// _countProvider = Provider.of<CountProvider>(context);return Consumer<CountProvider>(builder: (context, cntProvider, child) {return Container(child: Text("${cntProvider.count}"),);},);}
}
Consumer 这里的builder 方法会被多次的调用,其实这样很不好,因为其内部本身不依赖provider的数据,只是改变了provider的数据,所以没有必要重新
// 这里的按钮点击之后 子组件进行加1操作floatingActionButton: Consumer<CountProvider>(builder: (context, cntPorvider, child) {print("Consumer->builder被调用了");return FloatingActionButton(onPressed: () {// 调用加+1操作cntPorvider.increment();},child: Icon(Icons.add),);
另外还有 Consumer2 Consumer3 Consumer4 Consumer5 Consumer6
是什么意思呢
意思是 当你Builder里面的代码依赖多个provider 提供的数据时候,可以选择对应的Consumer
class Consumer3<A, B, C> extends SingleChildStatelessWidget
return Consumer2<CountProvider, UserInfoProvider>(builder: (context, cntProvider, userProvider, child) {return Container(child: Text("${cntProvider.count}---${userProvider.getUsername()}"),);},);
五 Selector
Selector 也有多个 Selector2 Selector3 Selector4 Selector5 Selector6
使用selector 第一个作用可以对原有的数据进行转换 第二个作用可以设置要不要重新构建,执行builder 方法
// 这里的按钮点击之后 子组件进行加1操作floatingActionButton: Selector<CountProvider, CountProvider>(// 这里如果return false 的话,下面的builder 就不会再次的执行 shouldRebuild: (previous, next) => false,builder: (context, cntPorvider, child) {print("Consumer->builder被调用了111");return FloatingActionButton(onPressed: () {// 调用加+1操作cntPorvider.increment();},child: Icon(Icons.add),);},selector: (ctx, cntPorvider) {return cntPorvider;},)