使用 Provider 向整个 Flutter 模块全局提供 BLoC
Posted
技术标签:
【中文标题】使用 Provider 向整个 Flutter 模块全局提供 BLoC【英文标题】:Use Provider to provide BLoCs globally to whole flutter module 【发布时间】:2020-06-11 16:10:02 【问题描述】:https://pub.dev/packages/provider
在没有 MaterialApp 的情况下,我可以使用 Provider 为树下的所有小部件全局提供块吗?我尝试向页面提供 BLoC,但是当我导航到下一页时,找不到 BloC。那么我应该在导航到新页面时提供它,还是有解决方案可以在没有 MaterialApp 的情况下在全球范围内提供它?
目前我正在这样做
Provider
|_MaterialApp
|_MyPage1 (from which you can navigate to MyPage2...3)
这种方法有效,所有页面都可以访问提供的 BLoC。
但是如果使用这种方法
Provider
|_MyPage1 (from which you can navigate to MyPage2...3)
MyPage2、MyPage3 找不到提供的 BLoC。 BLoC 只能在 MyPage1 上找到
【问题讨论】:
【参考方案1】:您可以通过使用MaterialApp
的builder
属性来实现此目的。
lib/main.dart
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
class SomeBloc
final String someValue;
SomeBloc(this.someValue);
void dispose()
void main()
runApp(MyApp());
class MyApp extends StatelessWidget
SomeBloc _someBloc = SomeBloc("someValue");
@override
Widget build(BuildContext context)
return MaterialApp(
builder: (context, widget) => Provider<SomeBloc>(
create: (_) => _someBloc,
dispose: (_, bloc) => bloc.dispose(),
child: widget,
),
initialRoute: '/first-page',
routes: <String, WidgetBuilder>
'/first-page': (context) => FirstPage(),
'/second-page': (context) => SecondPage(),
,
);
class FirstPage extends StatelessWidget
@override
Widget build(BuildContext context)
SomeBloc _someBloc = Provider.of<SomeBloc>(context);
return Scaffold(
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(_someBloc.someValue),
RaisedButton(
child: Text("Open second page"),
onPressed: () => Navigator.push(
context,
MaterialPageRoute(
builder: (_) => SecondPage(),
),
),
)
],
),
),
);
class SecondPage extends StatelessWidget
@override
Widget build(BuildContext context)
SomeBloc _someBloc = Provider.of<SomeBloc>(context);
return Scaffold(
body: Center(
child: Text(_someBloc.someValue),
),
);
根据文档,
首页
使用 home 和使用 builder 的区别在于 home 子树被插入到应用程序下面导航器中。
建造者
...从构建器返回的小部件插入上方应用的导航器(如果有)。
如果您希望在所有路线上提供您的“区块”,则必须在 Navigator
小部件上方提供这些。
这就是为什么这很简单:
return Provider(
create: (_) => _someBloc,
child: MaterialApp(
home: FirstPage(),
),
);
在上述设置中,Provider
位于 Navigator
小部件之上。
这不是:
return MaterialApp(
home: Provider(
create: (_) => _someBloc,
child: FirstPage(),
),
);
_someBloc
只能由 FirstPage
小部件访问。
希望这会有所帮助。
【讨论】:
以上是关于使用 Provider 向整个 Flutter 模块全局提供 BLoC的主要内容,如果未能解决你的问题,请参考以下文章
Flutter 应用程序 Multi Provider 和相互依赖的 Stream Providers