Flutter BlocListener中能否调用异步方法?如何获取页面跳转返回值?
Flutter Bloc 6.1.3:BlocListener异步等待页面返回值的解决办法
你的代码没法正常运行,大概率是这几个问题:
CustomerCreateSuccessState没做相等性判断,导致状态重复触发listener,多次执行跳转- 直接把
Navigator.pushNamed的返回值赋值给bool,但它的返回类型是dynamic,类型不匹配会报错 - 所用的context可能找不到路由栈,导致Navigator无法正常跳转
具体解决步骤
1. 让状态只触发一次
给CustomerCreateSuccessState加上Equatable的支持(需要先添加equatable依赖),这样只有状态真的变化时,listener才会触发:
class CustomerCreateSuccessState extends CustomerState with EquatableMixin { @override List<Object> get props => []; // 如果状态里有自定义参数,把参数放到这个列表里 }
2. 修正异步回调的返回值处理
修改listener里的代码,先判断返回值的类型,再赋值使用:
BlocListener<CustomerBloc, CustomerState>( listener: (context, state) async { if (state is CustomerCreateSuccessState) { final result = await Navigator.pushNamed(context, '/Card'); // 先校验类型,避免报错 if (result is bool) { bool res = result; // 这里写拿到返回值后的逻辑,比如更新状态、提示用户等 } } }, )
3. 确保上下文能访问到Navigator
如果BlocListener嵌套在Scaffold或者其他widget里面,可能会出现context找不到路由的情况,这时候可以用Builder包裹子widget,拿到正确的context:
BlocListener<CustomerBloc, CustomerState>( listener: (context, state) async { if (state is CustomerCreateSuccessState) { final result = await Navigator.pushNamed(context, '/Card'); if (result is bool) { // 处理逻辑 } } }, child: Builder( builder: (context) => // 这里放你的页面内容 ), )
额外小技巧
如果需要在页面返回后更新Bloc的状态,可以在拿到返回值后发送事件:
if (result is bool) { context.read<CustomerBloc>().add(CustomerUpdateEvent(result)); }
内容的提问来源于stack exchange,提问作者unice
相关产品推荐
相关产品推荐

