SetState没有更新listview。

4

我正在尝试使搜索按钮按下后创建一个列表项。它可以工作,但是为了让它出现,我必须单击按钮,然后重新构建应用程序。我查看了一些其他帖子,但是找不到任何有效的解决方案。需要注意的主要部分是我有一个添加列表项的函数。我有一个带有on press的按钮来创建该列表项。并且我在底部的容器的子元素中拥有已创建的列表项列表。

class Home extends StatefulWidget {
  const Home({Key? key}) : super(key: key);

  @override
  State<Home> createState() => _HomeState();
}

class _HomeState extends State<Home> {

  List<Widget> _listOfWidgets = [];

  @override
  Widget build(BuildContext context) {

    _addItemToList() {
      List<Widget> tempList =
          _listOfWidgets; // defining a new temporary list which will be equal to our other list
      tempList.add(ListTile(
          key: UniqueKey(),
          leading: Icon(Icons.list),
          trailing: FlatButton(
            onPressed: () async {},
            //Download Link
            child: Text(
              "Download",
              style: TextStyle(color: Colors.green, fontSize: 15),
            ),
          ),
          title: Text("")));
      this.setState(() {
        _listOfWidgets =
            tempList; // this will trigger a rebuild of the ENTIRE widget, therefore adding our new item to the list!
      });
    }

    return MaterialApp(
        theme: ThemeData.light(),
        darkTheme: ThemeData.dark(),
        themeMode: currentTheme.currentTheme(),
        home: Scaffold(
            appBar: AppBar(
              actions: [
                IconButton(
                  onPressed: () {
                    setState(() {
                      currentTheme.switchTheme();
                    });
                  },
                  icon: Icon(Icons.wb_sunny),
                ),
                IconButton(
                  onPressed: () async {
                    await FirebaseAuth.instance.signOut();
                  },
                  icon: Icon(Icons.exit_to_app),
                ),
              ],
              backgroundColor: Colors.blue,
              title: Text("Home"),
            ),
            body: ListView(
              children: [
                ListTile(
                  leading: SizedBox(
                    width: 300,
                    child: TextField(
                      controller: search,
                      decoration: InputDecoration(
                        labelText: "Enter Manga Name",
                      ),
                    ),
                  ),
                  trailing: ElevatedButton(
                      onPressed: () async {
                        _addItemToList();
                      },
                      child: Text("Search")),
                ),
                Container(
                    margin: EdgeInsets.all(15),
                    width: 100,
                    height: 515,
                    color: Colors.black12,
                    child: ListView(
                      children: _listOfWidgets,
                    ))
              ],
            )));
  }
}

你需要将 _addItemToList() 方法从 build 方法中移出,它应该是类作用域方法。 - ישו אוהב אותך
3个回答

0
onPressed: () {
    setState(() {
        _addItemToList();
    });    
},

问题的解决方案是:
      List<Widget> tempList = <Widget>[];

    _addItemToList() {

  tempList.addAll(
          _listOfWidgets); // defining a new temporary list which will be equal to our other list
      tempList.add(ListTile(
          key: UniqueKey(),
          leading: Icon(Icons.list),
          trailing: FlatButton(
            onPressed: () async {},
            //Download Link
            child: Text(
              "Download",
              style: TextStyle(color: Colors.green, fontSize: 15),
            ),
          ),
          title: Text("")));
      this.setState(() {
        _listOfWidgets =
            tempList; // this will trigger a rebuild of the ENTIRE widget, therefore adding our new item to the list!
      });
    }

0

尝试添加下面的代码:

如果你更新状态,你需要使用setState()

更好的状态管理方式是使用BLoC或Provider包。


...

onPressed: () {
    setState(() {
        _addItemToList();
    });    
},

...

这在第一次按钮按下时有效,但之后它会回到我必须重建的状态。 - EFTPMC
重新构建状态,请在 -> didChangeAppLifecycleState() 函数内调用该函数。这是内置函数。 - Rakesh Saini
如果重新绘制UI,则需要调用setState()。您需要在每个需要更改UI的按钮的onPressed()中调用setState() - TwoGirls

0

调试了一下之后终于解决了。我的ListView中的键应该是唯一的,因此我需要添加 key: UniqueKey()。我之前在ListTiles中添加了键,而不是真正的ListView。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接