【问题标题】:navigation using bloc 8 and auto_route 3.2.0使用 bloc 8 和 auto_route 3.2.0 进行导航
【发布时间】:2022-10-30 19:17:41
【问题描述】:

我正在尝试使用 auto_route 显示屏幕,基于使用 bloc 的状态。我有两个目标:

  1. 点击按钮时导航(例如登录)
  2. 如果在任何时候状态发生变化,请再次导航到正确的屏幕(例如会话到期)

    对于用例 1,我有一个按钮:

                   child: ElevatedButton(
                    onPressed: () {
                      final sessionBloc = BlocProvider.of<SessionBloc>(context);
                      sessionBloc.add(SignInEvent());
                    },
                    child: const Text('Login'),
                  ),
    

    这委托给我的会话组,该会话组具有定义为的处理程序:

        emit(
          SignedIn(
            const User(
                displayName: 'displayName',
                phoneNumber: 'phoneNumber',
                idNumber: 'idNumber',
                photoUrl: 'photoUrl'),
          ),
        );
    

    我正在尝试使用定义为的 authguard:

    class AuthGuard extends AutoRouteGuard {
    
      AuthGuard({required Stream<SessionState> sessionBloc}) {
        sessionBloc.listen((state) {
          print('['+state.toString()+']');
          _authenticated = state is SignedIn;
        });
      }
    
      bool _authenticated = true;
    
      @override
      void onNavigation(NavigationResolver resolver, StackRouter router) {
        if (!_authenticated) {
          router.push(
            LoginRouter(),
          );
        }
        resolver.next(true);
      }
    }
    

    每次按下按钮时,我都能看到打印语句,所以效果很好(不足为奇)。

    问题是按下按钮时我没有导航到另一个屏幕。我只能假设这是因为虽然我正在更新状态并且 authguard 知道新状态,但在我们实际尝试导航之前它什么都不做,即调用 onNavigate。

    那么我该怎么做,我如何/在哪里触发导航?

【问题讨论】:

  • 作为一种解决方法; ElevatedButton( onPressed: () async { BlocProvider.of<SessionBloc>(context).add(SignoutEvent()); ///原来 add 本质上是异步的,因此下面的等待 ///在我可以手动导航之前等待 BlocProvider。 of<SessionBloc>(context).stream.first; context.navigateTo(HomeRoute()); }, child: Text('Sign Out'), ),

标签: flutter navigation bloc


【解决方案1】:

我会使用 BlocConsumer 或 BlocListner 并在 listen 方法中导航到所需的屏幕。并确保在身份验证后要导航到的路由上有路由保护。

        BlocListener<SessionBloc, SessionState>(
      listener: (context, state) {
        if(state is SignedIn){
          //TODO: route to the page you want to go to
          
        }
      },
      child: ElevatedButton(
        onPressed: () {
          final sessionBloc = BlocProvider.of<SessionBloc>(context);
          sessionBloc.add(SignInEvent());
        },
        child: const Text('Login'),
      ),
    );

【讨论】:

    猜你喜欢
    • 2019-06-04
    • 2020-05-06
    • 2019-07-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-12-31
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多