Flutter中TextField的onChanged无法更新SongModel列表问题
问题原因及解决方案
核心问题
- filterSongs定义位置错误:你在
build方法里声明filterSongs,每次调用setState触发build时,这个变量都会被重新初始化为空列表,之前的过滤结果会被直接清空。 - 参数传递导致引用失效:
getSearch函数中接收的filterSongs是局部参数,Dart中列表作为参数传递时是引用的副本,你在函数里对filterSongs赋值,只是修改了局部变量的指向,完全不会影响外层build方法里的原变量。
修复步骤
1. 将变量移至State类成员
把songs和filterSongs定义为State类的成员变量,避免build时被重复初始化:
class YourPageState extends State<YourPage> { List<SongModel>? songs; List<SongModel> filterSongs = []; final TextEditingController searchController = TextEditingController(); @override void didChangeDependencies() { super.didChangeDependencies(); // 根据实际场景调整songs的初始化方式,这里假设从路由参数获取item final item = ModalRoute.of(context)?.settings.arguments as YourItemType; songs = item.data!; filterSongs = List.from(songs!); // 初始化为全部歌曲 } // ...其他页面代码 }
2. 修改getSearch函数逻辑
无需传递songs和filterSongs作为参数,直接使用类成员变量,简化搜索逻辑:
void getSearch() { final searchText = searchController.text.toLowerCase(); setState(() { if (searchText.isEmpty) { filterSongs = List.from(songs!); } else { filterSongs = songs!.where((song) => song.title.toLowerCase().contains(searchText) ).toList(); } }); }
3. 更新TextField的onChanged调用
直接调用无参的getSearch即可:
TextField( keyboardType: TextInputType.text, controller: searchController, onChanged: (value) => getSearch(), decoration: InputDecoration(/* 你的装饰配置 */), )
额外说明
- 使用
List.from(songs!)而非直接赋值songs!,是为了创建新列表副本,避免后续操作意外修改原列表数据。 - 搜索时统一转小写,确保大小写不敏感的匹配逻辑准确。
内容的提问来源于stack exchange,提问作者HARSH J.
相关产品推荐
相关产品推荐

