Flutter中RefreshIndicator显示加载状态但未执行刷新操作问题求助
Flutter RefreshIndicator嵌套FutureBuilder无法触发刷新的解决方案
问题原因
- FutureBuilder的
future参数直接绑定buildList()调用,未存储为State的成员变量,刷新操作执行后无法触发组件重建拉取新数据 onRefresh回调执行完成后未调用setState更新状态,接口返回的新数据无法同步到界面buildList方法中未对refresh异步操作加await,接口数据还未写入本地SQFlite数据库就提前执行查库逻辑,返回的仍是旧数据- 若列表内容不足一屏,ListView默认无滚动能力,无法触发RefreshIndicator的下拉回调
修复后完整代码
class _MyTasksListViewState extends State<MyTasksListView> { // 定义成员变量存储Future,避免每次build重复创建 late Future<List<OT>> _listFuture; @override void initState() { super.initState(); // 初始化时首次加载数据 _listFuture = buildList(); } @override Widget build(BuildContext context) { return FutureBuilder<List<OT>>( // 绑定成员变量的Future,不要直接调用buildList() future: _listFuture, builder: (context, snapshot) { if (snapshot.hasData) { return RefreshIndicator( child: ListView( // 强制列表可滚动,解决内容不足一屏无法触发刷新的问题 physics: const AlwaysScrollableScrollPhysics(), children: snapshot.data! .map((ot) => ListTile( title: Text("Numero de OT: " + ot.ot.toString()), subtitle: Text("OT Original: " + ot.otOriginal), onTap: () { Navigator.of(context) .pushNamed('/Tareas', arguments: { 'Tareas': ot.tareas, }); }, )) .toList(), ), onRefresh: () async { // 等待新数据加载完成 final newList = await buildList(); // 调用setState更新Future,触发FutureBuilder重建刷新界面 setState(() { _listFuture = Future.value(newList); }); }); } else { return const Center(child: CircularProgressIndicator()); } }, ); } Future<List<OT>> buildList() async { // 加await等待refresh把接口数据写入数据库后再查库 await refresh(context); List<OT> lista = []; Database database = await initDB(); var otFromDB = await database.rawQuery("SELECT * FROM 'ots'"); var tareasFromDB = await database.rawQuery("SELECT * FROM 'tareas'"); for (var i in otFromDB) { OT ot = OT.fromArray(i); for (var tarea in tareasFromDB) { if (tarea['otID'] == ot.ot) { ot.tareas.add(Tarea.fromArray(tarea)); } } lista.add(ot); } return lista; } }
核心修改说明
- 新增State成员变量
_listFuture存储加载数据的Future,避免FutureBuilder每次build都重复执行加载逻辑 - 重写
initState方法做首次数据加载初始化 - 修改
onRefresh回调逻辑,加载完新数据后调用setState更新_listFuture触发界面刷新 - 给
buildList方法中的refresh调用加await,确保接口数据写入数据库完成后再执行查库逻辑 - 给ListView添加
AlwaysScrollableScrollPhysics滚动特性,解决内容不满一屏无法下拉触发刷新的问题
内容的提问来源于stack exchange,提问作者Ignacio Nacho Parravicini
相关产品推荐
相关产品推荐

