Flutter应用抽屉点击报错:build期间调用setState/markNeedsBuild求助
问题原因与解决方案
核心错误点
你代码里的onTap: tapHandler()是立即执行了传入的导航函数,而非将函数作为点击回调传递。这会导致Drawer构建过程中就触发Navigator.pushNamed操作,此时Flutter框架正在构建UI,导航操作会引发框架状态冲突,进而抛出setState() or markNeedsBuild() called during build错误,同时造成应用卡顿。
修复代码
只需修改buildListTile方法里的onTap赋值,将tapHandler()改为tapHandler(或用箭头函数包裹),确保函数在点击时才执行:
import 'package:flutter/material.dart'; import 'package:meals_recipes/screens/filters_screen.dart'; class MainDrawer extends StatelessWidget { Widget buildListTile(String title, IconData icon, Function tapHandler) { return ListTile( leading: Icon( icon, size: 24, ), title: Text( title, style: TextStyle( fontFamily: "RobotoCondensed", fontWeight: FontWeight.w700, fontSize: 22), ), // 修复:去掉括号,传递函数引用而非立即执行 onTap: tapHandler, ); } @override Widget build(BuildContext context) { return Drawer( child: Column( children: <Widget>[ Container( height: 100, width: double.infinity, padding: const EdgeInsets.all(20), alignment: Alignment.centerLeft, color: Theme.of(context).colorScheme.secondary, child: Text( 'Cooking Up!', style: TextStyle( fontSize: 30, fontWeight: FontWeight.w900, color: Theme.of(context).primaryColor), ), ), const SizedBox( height: 20, ), buildListTile('Meals', Icons.restaurant, () { Navigator.of(context).pushNamed('/'); }), buildListTile('Filters', Icons.filter, () { Navigator.of(context).pushNamed(FiltersScreen.routeName); }), ], ), ); } }
补充说明
如果tapHandler需要接收参数,可改用箭头函数包裹,示例:
onTap: () => tapHandler(yourParameter),
这种写法同样能保证函数在点击事件触发时才执行,避免构建过程中触发状态更新。
内容的提问来源于stack exchange,提问作者Tooraj rezaei
相关产品推荐
相关产品推荐

