如何解决-在使用TextField搜索之前,直到在Flutter中键入任何内容时,列表中最初没有显示任何项目?

时间:2019-07-29 17:59:08

标签: flutter dart

在我的flutter项目中,我通过API调用获得了一些价值。我在 initState 函数内部调用该函数,然后将结果保存在列表中。

然后,我添加了一个 TextField 以在列表中进行搜索。搜索工作正常,但问题是-最初列表中没有显示任何项目。如果我输入了某些内容或在输入后删除了这些文本,则该文本有效

这是我的代码-

在类中,我添加了以下变量-

  List<ModelAllNotes> _allNotes = List<ModelAllNotes>();
  TextEditingController editingController = TextEditingController();
  var items = List<ModelAllNotes>();

initState 函数内部,我称为函数-

  @override
  void initState() {
    setState(() {
      _getAllNotes();
      items.addAll(_allNotes);
    });
  }

_getAllNotes()函数内部,我完成了API调用部分-

  void _getAllNotes() {
    Webservice().load(ModelAllNotes.allNotes).then( (allNotes) => {
      setState(()=>{
        _allNotes = allNotes

      })
     });
  }

要过滤,该列表在搜索时我为此创建了一个功能-

 void filterSearchResults(String query) {
    List<ModelAllNotes> dummySearchList = List<ModelAllNotes>();
    dummySearchList.addAll(_allNotes);
    if(query.isNotEmpty) {
      List<ModelAllNotes> dummyListData = List<ModelAllNotes>();
      dummySearchList.forEach((item) {
        if(item.title.contains(query)) {
          dummyListData.add(item);
        }
      });
      setState(() {
        items.clear();
        items.addAll(dummyListData);
      });
      return;
    } else {
      setState(() {
        items.clear();
        items.addAll(_allNotes);
      });
    }

  }

然后在构建函数中,我完成了显示如下方式的列表-

  @override
  Widget build(BuildContext context) {
    return new Scaffold(
      body: Column(
        children: <Widget>[
          Padding(
            padding: const EdgeInsets.all(8.0),
            child: TextField(
              onChanged: (value) {
                filterSearchResults(value);
              },
              controller: editingController,
              decoration: InputDecoration(
                  labelText: "Search",
                  hintText: "Search",
                  prefixIcon: Icon(Icons.search),
                  border: OutlineInputBorder(
                  borderRadius: BorderRadius.all(Radius.circular(25.0)))),
            ),
          ),

          Expanded (
            child: Container(
              child: new ListView.builder(
                  itemCount: items.length,
                  itemBuilder: (BuildContext ctxt, int index) {
                    return new Padding(
                        padding: const EdgeInsets.all(8.0),
                        child: GestureDetector(
                          child: Container(
                            child: showCard(index),
                          ),
                          onTap: (){
                            print('Card pressed');
                            Navigator.pushNamed(ctxt, '/DetailsNotes', arguments: items[index]).then((val)=>{_getAllNotes()});
                          },

                        ),
                      )

                    );

                  }
              ),

            ),
          )

        ],

      )
    );

完成所有这些操作后,最初将显示空白屏幕。当我在搜索TextField中输入内容时,它会显示列表。因此,我需要一种解决方案来在屏幕出现时显示列表。

1 个答案:

答案 0 :(得分:0)

您无需两次致电setState(一个在initState上,另一个在您致电_getAllNotes的那一次)

这篇文章解释了为什么你不应该这么做  称它为您的工作方式:https://stackoverflow.com/a/53373017/4902078

但是我认为问题在于您在initState上致电

_getAllNotes();
items.addAll(_allNotes);

然后在_getAllNotes内调用服务器,并在then语句中更新_allNotes。调用than内容时,items.addAll(_allNotes);可能已经运行,并添加了一个空列表。如果您将items.addAll(_allNotes);添加到setState内的_getAllNotes内,则可能会起作用。