You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter实现搜索栏无搜索效果,无法正常查询JSON数据源内容

现有代码核心问题

  • 全量数据源newData是FutureBuilder回调内的局部变量,搜索逻辑无法持久访问完整原始数据,且每次FutureBuilder重建都会重复向notesForDisplay添加数据导致条目重复
  • 搜索逻辑中出现未定义的index变量,note[index]['VERB']写法错误,应该直接取当前遍历项的VERB字段
  • ListView的itemBuilder直接使用原始newData的下标取值,未使用过滤后的notesForDisplay,导致过滤结果不会生效
  • AppBar初始化时JSON数据还未加载完成,传入_searchBar的newData是空值,搜索功能无可用数据源
  • 未处理FutureBuilder的加载状态,数据加载完成前会出现空指针报错

修正实现方案

第一步:在State类中定义成员变量存储数据源

class _YourPageState extends State<YourPage> {
  // 存储全量原始JSON数据
  List _allNotes = [];
  // 存储当前需要展示的过滤后数据
  List _notesForDisplay = [];
  // 你的原有变量
  List<String> savedWords = [];

  // 后面是你的其他方法
}

第二步:调整build方法逻辑

@override
Widget build(BuildContext context) {
  return MaterialApp(
    home: Scaffold(
      appBar: AppBar(
        automaticallyImplyLeading: true,
        title: _searchBar(),
      ),
      body: Container(
        decoration: BoxDecoration(
          image: DecorationImage(
            image: AssetImage('images/gradient_blue.jpg'),
            fit: BoxFit.cover
          )
        ),
        child: FutureBuilder(
          future: DefaultAssetBundle.of(context).loadString('files/myfile.json'),
          builder: (context, snapshot) {
            // 先处理加载状态
            if (snapshot.connectionState == ConnectionState.waiting) {
              return const Center(child: CircularProgressIndicator());
            }
            if (snapshot.hasError) {
              return const Center(child: Text("数据加载失败"));
            }
            // 仅第一次加载完成时赋值全量数据,避免重复添加
            if (_allNotes.isEmpty) {
              _allNotes = json.decode(snapshot.data.toString());
              _notesForDisplay = List.from(_allNotes);
            }

            return ListView.builder(
              itemBuilder: (BuildContext context, int index){
                // 所有取值从过滤后的_notesForDisplay取
                String word = _notesForDisplay[index]['VERB'];
                String meaning = _notesForDisplay[index]['MEANING'];
                bool isSaved = savedWords.contains(word);
                return _listItem(index, isSaved, word, meaning);
              },
              itemCount: _notesForDisplay.length
            );
          },
        ),
      )
    )
  );
}

第三步:修正搜索栏逻辑

Widget _searchBar() {
  return Padding(
    padding: const EdgeInsets.all(8.0),
    child: TextField(
      decoration: InputDecoration(hintText: 'Search..'),
      onChanged: (text) {
        text = text.toLowerCase();
        setState(() {
          if (text.isEmpty) {
            // 搜索内容为空时重置展示全部数据
            _notesForDisplay = List.from(_allNotes);
            return;
          }
          // 基于全量数据源过滤,移除错误的index引用
          _notesForDisplay = _allNotes.where((note) {
            var noteTitle = note['VERB'].toLowerCase();
            return noteTitle.contains(text);
          }).toList();
        });
      },
    ),
  );
}

第四步:调整列表项方法参数

Widget _listItem(int index, bool isSaved, String word, String meaning) {
  return Card(
    children: <Widget>[
      Column(
        children: <Widget>[
          InkWell(
            child: RichText(
              text: TextSpan(
                children: [
                  TextSpan(
                    text: word,
                    // 你的其他样式配置
                  )
                ]
              )
            )
          )
        ]
      )
    ]
  );
}

内容的提问来源于stack exchange,提问作者Lash

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.02 16:54:04