Flutter中Provider三元运算符判断始终返回False问题求助
问题:三元判断始终返回'Blackout',即使blackoutStatus[1]显示为'0'
预期Text组件在RxStatus Provider的blackoutStatus[1]值为'0'时显示Normal,其他值显示Blackout,但实际无论该值显示为'0'还是'2',三元判断始终返回Blackout。已通过额外Text组件确认blackoutStatus[1]确实在'0'和'2'之间切换,但判断逻辑不生效。
相关代码
问题代码片段
Container( child: Text( Provider.of<RxStatus>(context,listen:true).blackoutStatus[int.parse('1')] == '0' ? 'Normal':'BlackOut', style: TextStyle(color: Colors.red), ), )
Vault组件核心代码
class Vault extends StatefulWidget { const Vault({Key? key}) : super(key: key); @override _VaultState createState() => _VaultState(); } class _VaultState extends State<Vault> { late Timer _timer; @override initState() { _timer = Timer.periodic(const Duration(seconds: 5), (timer) { Provider.of<RxStatus>(context,listen: false).getFeedback("vault"); print('vault'); }); print("vault initState Called"); } void dispose() { print('dispose vault'); _timer?.cancel(); super.dispose(); } Widget build(BuildContext context) { var screenSize = MediaQuery.of(context).size; return Stack( children:[ Row( mainAxisAlignment: MainAxisAlignment.center, children: [ //Right Wall Column( mainAxisAlignment: MainAxisAlignment.center, children: [ RotatedBox(quarterTurns:1 , child: ProDsxRx(rxLabel: 'Vault 7', rxId: '7')), RotatedBox(quarterTurns:1 , child: ProDsxRx(rxLabel: 'Vault 8', rxId: '8')), RotatedBox(quarterTurns:1 , child: ProDsxRx(rxLabel: 'Vault 9', rxId: '9')), Container( child: Text( Provider.of<RxStatus>(context,listen: true).blackoutStatus[int.parse('1')] , style: TextStyle(color: Colors.red), ), ), Container( child: Text( Provider.of<RxStatus>(context,listen: true).blackoutStatus[int.parse('1')] == '0' ? 'Normal': 'BlackOut', style: TextStyle(color: Colors.red), ), ) ], ) ], ), ProdsxFloatingMenuButton() ], ); } }
RxStatus Provider核心代码
class RxStatus extends ChangeNotifier { List rxIDs = [ 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12,13, 14, 15, 16, 19, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46 ]; final List rxIDs_bank = [ 10, 11, 12,13, 14, 15,19, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46 ]; final List rxIDs_vault = [ 1, 2, 3, 4, 5, 6, 7, 8, 9,16, ]; Map blackoutStatus = { 1:'0',2:'0',3:'0',4:'0',5:'0', 6:'0',7:'0',8:'0',9:'0',10:'0', 11:'0',12:'0',13:'0',14:'0', 15:'0', 16:'0', 23:'0', 24:'0', 25:'0', 26:'0', 27:'0', 28:'0', 29:'0', 30:'0', 31:'0', 32:'0', 33:'0', 34:'0', 35:'0', 36:'0', 37:'0', 38:'0', 39:'0', 40:'0', 41:'0', 42:'0', 43:'0', 44:'0', 45:'0', 46:'0', }; getFeedback(_bank_vault) async { if(_bank_vault == 'bank'){ rxIDs = [...rxIDs_bank]; }else if(_bank_vault =='vault'){ rxIDs = [...rxIDs_vault]; } rxIDs.asMap().forEach((index, item) async { try { print('blackout status${item}'); // Check blackout var response = await http.get(Uri.parse('http://172.31.3.${item}/cgi-bin/query.cgi?cmd=cat /sys/devices/platform/videoip/pause')); blackoutStatus[item] = response.body; print(blackoutStatus); notifyListeners(); }catch (error) { blackoutStatus[item] = 'Error'; notifyListeners(); } }); } }
问题原因
核心问题是HTTP请求返回的response.body可能包含多余的空白字符(比如换行符\n、空格)。虽然UI显示时看不到这些空白,但字符串严格比较时,'0\n' == '0'会返回false,导致三元判断始终触发Blackout分支。
解决方案
1. 处理HTTP返回值(推荐)
在RxStatus的getFeedback方法中,对response.body调用trim()去除首尾空白字符:
blackoutStatus[item] = response.body.trim();
2. 在判断时处理字符串
如果不想修改Provider逻辑,也可以在UI判断时直接对取值做trim处理,同时优化int.parse('1')为直接使用1:
Container( child: Text( Provider.of<RxStatus>(context,listen: true).blackoutStatus[1]?.trim() == '0' ? 'Normal': 'BlackOut', style: TextStyle(color: Colors.red), ), )
额外优化
原代码中rxIDs.asMap().forEach搭配async会导致多个异步请求同时触发,notifyListeners()被频繁调用。可以改用Future.wait批量处理异步请求,统一更新状态:
getFeedback(_bank_vault) async { if(_bank_vault == 'bank'){ rxIDs = [...rxIDs_bank]; }else if(_bank_vault =='vault'){ rxIDs = [...rxIDs_vault]; } // 批量处理异步请求 await Future.wait(rxIDs.map((item) async { try { print('blackout status${item}'); var response = await http.get(Uri.parse('http://172.31.3.${item}/cgi-bin/query.cgi?cmd=cat /sys/devices/platform/videoip/pause')); blackoutStatus[item] = response.body.trim(); } catch (error) { blackoutStatus[item] = 'Error'; } })); // 所有请求完成后统一通知状态更新 notifyListeners(); }
内容的提问来源于stack exchange,提问作者sou pen su
相关产品推荐
相关产品推荐

