[英]How to create a BlocListener that can listen to all pages in flutter with access to MaterialApp context?
I'm trying to create a BlocListener
that has the ability to listen to all pages/routes throughout the app just like how you can access a Bloc
or a Provider
all throughout the app if they are defined at root-level like in the code below我正在尝试创建一个
BlocListener
,它能够侦听整个应用程序中的所有页面/路由,就像您如何在整个应用程序中访问Bloc
或Provider
一样,如果它们是在根级别定义的,如下面的代码
runApp(
MultiProvider(
providers: [
ChangeNotifierProvider<IdentityTokenProvider>(
create: (_) => IdentityTokenProvider(),
),
],
child: MultiBlocProvider(
providers: [
BlocProvider<AuthBloc>(
create: (_) => AuthBloc(),
),
],
child: MaterialApp(
debugShowCheckedModeBanner: AppConfig.DEBUGGABLE,
theme: ThemeData(
// fontFamily: CustomFontStyle.montserrat,
),
home: AuthListener(
child: Center(
child: const MainApp(),
),
),
),
),
),
);
As you can see, I have providers, blocs, and one listener.如您所见,我有提供者、集团和一名听众。 I have no problem accessing the blocs and providers in other pages.
我在其他页面中访问集团和提供者没有问题。 My problem is the auth listener.
我的问题是身份验证侦听器。 I lose access to the
AuthListener
once I move to a different page (by removing stack), because it is inside the MaterialApp
.一旦我移动到不同的页面(通过删除堆栈),我将无法访问
AuthListener
,因为它位于MaterialApp
内。 However, in this instance, I need that specific listener ( AuthListener
) to be inside a MaterialApp
, because it consists of code that uses page navigations (which doesn't work if the implementation is done outside/above the widget tree of a MaterialApp
), and makes us of the MaterialApp
context for showing dialogs.但是,在这种情况下,我需要特定的侦听器(
AuthListener
)位于MaterialApp
中,因为它包含使用页面导航的代码(如果实现是在MaterialApp
的小部件树之外/之上完成的,则该代码不起作用) ,并使我们使用MaterialApp
上下文来显示对话框。
My implementation of page routing which removes the stack, which is another cause of losing access to the AuthListener
我的页面路由实现删除了堆栈,这是失去对
AuthListener
访问权限的另一个原因
Navigator.pushAndRemoveUntil(
context,
MaterialPageRoute(builder: (_) => route),
(Route<dynamic> route) => false);
Why do I remove the route/page stack when moving to a different page?为什么在移动到不同页面时要删除路由/页面堆栈?
My AuthListener
implementation我的
AuthListener
实现
class AuthListener extends StatefulWidget {
final Widget child;
const AuthListener({Key key, @required this.child}) : super(key: key);
@override
_AuthListenerState createState() => _AuthListenerState();
}
class _AuthListenerState extends State<AuthListener> {
@override
Widget build(BuildContext context) {
return BlocListener<AuthBloc, AuthState>(
listener: (context, state) {
if (state is AuthAuthenticated) {
PageRouterController.pushAndRemoveStack(context, const EcomPage());
} else if (state is AuthUnauthenticated) {
PageRouterController.pushAndRemoveStack(context, const LoginPage());
}
},
child: widget.child,
);
}
}
Is there a different way around this?有没有不同的方法来解决这个问题?
So I ended up defining a所以我最终定义了一个
static final GlobalKey<NavigatorState> navigatorKey = new GlobalKey();
and used it in my MaterialApp并在我的 MaterialApp 中使用它
@override
Widget build(BuildContext context) {
return MaterialApp(
debugShowCheckedModeBanner: App.DEBUGGABLE,
theme: ThemeData(
// fontFamily: CustomFontStyle.montserrat,
),
navigatorKey: App.navigatorKey,
home: Center(
child: const LoginPage(),
),
);
}
So then, whenever I have to navigate in cases where the implementation is outside the MaterialApp (in my case via the AuthListener which is found at root-level, above the MaterialApp), I can navigate via因此,每当我必须在实现位于 MaterialApp 之外的情况下进行导航(在我的情况下,通过在 MaterialApp 上方的根级别找到的 AuthListener),我可以通过
App.navigatorKey.currentState.pushAndRemoveUntil(
MaterialPageRoute(builder: (_) => route),
(Route<dynamic> route) => false);
Which means I can finally have access to the MaterialApp navigator and context even with the listener outside the MaterialApp which allows me to do both navigation and showing of dialogs这意味着我终于可以访问 MaterialApp 导航器和上下文,即使在 MaterialApp 之外的侦听器也允许我进行导航和显示对话框
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.