Flutter Cubit With BlocListener:如何根据状态导航用户?
Flutter Cubit With BlocListener: How can I Navigate the user according to state?
我有一个basic auth cubit,在状态下,它只有一个变量。
@freezed
class AuthState with _$AuthState {
const AuthState._();
const factory AuthState({
required bool isUserSignedIn,
}) = _AuthState;
factory AuthState.initial() => const AuthState(isUserSignedIn: false);
}
在 cubit 部分,我可以通过调试控制台中的 FirebaseAuth.instance.authStateChanges().listen((User? user))
方法轻松检查用户是否登录。
现在,问题从着陆页部分开始。有些事情会产生问题。
首先,您可以看到下面的着陆页代码。在这里,我有初始的 initState(当 App 启动时,它首先工作),然后,我 return BlocListener 用于监听 cubit 的状态。
当我单击登录按钮和注销按钮时,它工作正常(我可以在调试控制台中看到它,我可以注销但相同的屏幕继续停留,在我重新加载应用程序后,我可以看到我有已经退出)。
在 BlocListener 部分,我尝试打印一些文本,但它们不起作用,我的意思是我在调试控制台中看不到它们。
class LandingPage extends StatefulWidget {
const LandingPage({Key? key}) : super(key: key);
@override
State<LandingPage> createState() => _LandingPageState();
}
class _LandingPageState extends State<LandingPage> {
@override
void initState() {
WidgetsBinding.instance!.addPostFrameCallback((_) {
final bool isUserSignedIn =
context.read<AuthCubit>().state.isUserSignedIn;
if (isUserSignedIn) {
AutoRouter.of(context).replace(const HomeRoute());
} else if (!isUserSignedIn) {
AutoRouter.of(context).replace(const SignInRoute());
}
});
super.initState();
}
@override
Widget build(BuildContext context) {
return BlocListener<AuthCubit, AuthState>(
listenWhen: (p, c) => p.isUserSignedIn != c.isUserSignedIn,
listener: (context, state) {
final bool isUserSignedIn =
context.read<AuthCubit>().state.isUserSignedIn;
if (isUserSignedIn) {
print("blocblocbloc1");
AutoRouter.of(context).replace(const HomeRoute());
} else {
print("blocblocbloc2");
AutoRouter.of(context).root.popUntilRoot();
}
},
child: const Scaffold(
body: Center(
child: CircularProgressIndicator(color: Colors.white),
),
),
);
}
}
除此之外,我使用自动路由进行轮换(因为我不想看到直接的小部件,所以我想根据用户的登录状态来导航用户)。一开始我想也许 AutoRouter 不起作用,但打印语句也不起作用。
这里我也分享我的main.dart档案。
class AppWidget extends StatelessWidget {
const AppWidget({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
final _appRouter = AppRouter();
return BlocProvider(
lazy: true,
create: (context) => AuthCubit(),
child: MaterialApp.router(
routeInformationParser: _appRouter.defaultRouteParser(),
routerDelegate: _appRouter.delegate(),
debugShowCheckedModeBanner: false,
),
);
}
}
最后,我的路由器页面在这里。
@MaterialAutoRouter(
replaceInRouteName: 'Page,Route',
routes: <AutoRoute>[
AutoRoute(page: LandingPage, initial: true),
AutoRoute(
page: HomePage,
),
AutoRoute(
page: SignInPage,
),
],
)
class $AppRouter {}
解决方案:使用flow_builder根据状态导航用户
我有一个basic auth cubit,在状态下,它只有一个变量。
@freezed
class AuthState with _$AuthState {
const AuthState._();
const factory AuthState({
required bool isUserSignedIn,
}) = _AuthState;
factory AuthState.initial() => const AuthState(isUserSignedIn: false);
}
在 cubit 部分,我可以通过调试控制台中的 FirebaseAuth.instance.authStateChanges().listen((User? user))
方法轻松检查用户是否登录。
现在,问题从着陆页部分开始。有些事情会产生问题。
首先,您可以看到下面的着陆页代码。在这里,我有初始的 initState(当 App 启动时,它首先工作),然后,我 return BlocListener 用于监听 cubit 的状态。 当我单击登录按钮和注销按钮时,它工作正常(我可以在调试控制台中看到它,我可以注销但相同的屏幕继续停留,在我重新加载应用程序后,我可以看到我有已经退出)。
在 BlocListener 部分,我尝试打印一些文本,但它们不起作用,我的意思是我在调试控制台中看不到它们。
class LandingPage extends StatefulWidget {
const LandingPage({Key? key}) : super(key: key);
@override
State<LandingPage> createState() => _LandingPageState();
}
class _LandingPageState extends State<LandingPage> {
@override
void initState() {
WidgetsBinding.instance!.addPostFrameCallback((_) {
final bool isUserSignedIn =
context.read<AuthCubit>().state.isUserSignedIn;
if (isUserSignedIn) {
AutoRouter.of(context).replace(const HomeRoute());
} else if (!isUserSignedIn) {
AutoRouter.of(context).replace(const SignInRoute());
}
});
super.initState();
}
@override
Widget build(BuildContext context) {
return BlocListener<AuthCubit, AuthState>(
listenWhen: (p, c) => p.isUserSignedIn != c.isUserSignedIn,
listener: (context, state) {
final bool isUserSignedIn =
context.read<AuthCubit>().state.isUserSignedIn;
if (isUserSignedIn) {
print("blocblocbloc1");
AutoRouter.of(context).replace(const HomeRoute());
} else {
print("blocblocbloc2");
AutoRouter.of(context).root.popUntilRoot();
}
},
child: const Scaffold(
body: Center(
child: CircularProgressIndicator(color: Colors.white),
),
),
);
}
}
除此之外,我使用自动路由进行轮换(因为我不想看到直接的小部件,所以我想根据用户的登录状态来导航用户)。一开始我想也许 AutoRouter 不起作用,但打印语句也不起作用。
这里我也分享我的main.dart档案。
class AppWidget extends StatelessWidget {
const AppWidget({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
final _appRouter = AppRouter();
return BlocProvider(
lazy: true,
create: (context) => AuthCubit(),
child: MaterialApp.router(
routeInformationParser: _appRouter.defaultRouteParser(),
routerDelegate: _appRouter.delegate(),
debugShowCheckedModeBanner: false,
),
);
}
}
最后,我的路由器页面在这里。
@MaterialAutoRouter(
replaceInRouteName: 'Page,Route',
routes: <AutoRoute>[
AutoRoute(page: LandingPage, initial: true),
AutoRoute(
page: HomePage,
),
AutoRoute(
page: SignInPage,
),
],
)
class $AppRouter {}
解决方案:使用flow_builder根据状态导航用户