【问题标题】:Update Flutter ListTile with tap not working用水龙头更新 Flutter ListTile 不起作用
【发布时间】:2020-08-07 18:38:24
【问题描述】:

目标是在点击时将 ListTile leadingsubtitle 的值更改为 null。点击正在切换 _act 布尔值,但 ListTile 的前导:和副标题:值不会从它们的初始状态改变。我的 ListView 代码如下。请帮忙。

        return new ListView(
          children: querySnapShot.data.documents.map((DocumentSnapshot document) {
            bool _act = false;
            return new ListTile(
              leading: _act != false ? const Icon(Icons.remove_red_eye, color: Color(0xff00caff), size: 40) : null,
              title: new Text((DBProvider.db.idDeHasher(document['exampleid'], key) ?? 'fallback'), style: TextStyle(color: secondaryColor)),
              subtitle: _act != false ? new Text((document['exampleString']  ?? 'fallbackString'), style: TextStyle(color: secondaryColor)) : null,
              onTap: () { 
                _act = !_act;
                print(_act.toString());
                }
            );
          }).toList(),
        );

【问题讨论】:

  • 使用setState更改_act
  • _act 变量在每个 setState 上都被重置为 false,因为它的实例化位于 ListView 小部件中。在状态类本身中实例化 _act 变量将提供更新并更改值,但列表视图中的每一行都将被更新,而不是被点击的单行,因为它们都将使用相同的 _act 值。 @Mobina
  • 如果不更新状态,您希望发生什么?什么都不会改变。您可以存储acts 的列表。

标签: flutter listview dart boolean dart-pub


【解决方案1】:

您需要将您的小部件设为Stateful Widget,并在ListTile 上点击时调用setState

根据docs

调用 setState 会通知框架此对象的内部状态已发生更改,可能会影响此子树中的用户界面,这会导致框架为此 State 对象安排构建。

因此,如果小部件的状态发生变化您必须调用setState 来触发视图的重建并立即看到新状态所暗示的变化。

我以你的代码为例添加了一个演示:

     // define a list of acts
        List _acts = [];
         return new ListView(
          children: querySnapShot.data.documents.asMap().entries.map((entry) {
          // declare all entries of the list to false
          acts.add(false);
          // access the index 
          int index = entry.key;
          // access the document
          DocumentSnapshot document = entry.value;
          // DocumentSnapshot document = entry
            return new ListTile(
              leading: _acts[index] != false ? const Icon(Icons.remove_red_eye, color: Color(0xff00caff), size: 40) : null,
              title: new Text((DBProvider.db.idDeHasher(entry.val['exampleid'], key) ?? 'fallback'), style: TextStyle(color: secondaryColor)),
              subtitle: _acts[index] != false ? new Text((document['exampleString']  ?? 'fallbackString'), style: TextStyle(color: secondaryColor)) : null,
              onTap: () { 
               // call setstate
              setState(() { // new line
              // change the bool variable based on the index
               _acts[index] = !_acts[index];
                print(_acts[index].toString());
              });
                }
            );
          }).toList(),
        );

【讨论】:

  • 我以前试过这个。 _act 变量在每个 setState 上都被重置为 false,因为它的实例化位于 ListView 小部件内。在状态类本身中实例化 _act 变量将提供更新并更改值,但列表视图中的每一行都将被更新,而不是被点击的单行,因为它们都将使用相同的 _act 值。
  • 试图让这个工作。在第一行和每个索引上出现错误。 “缺少选择器,例如 '.identifier' 或 '[0]'。请尝试添加选择器。”和“此表达式的类型为 'void',因此无法使用它的值。尝试检查您是否使用了正确的 API;可能有一个函数或调用返回您未预料到的 void。此外检查也可能为 void 的类型参数和变量。”
  • 代码出错了,你现在可以检查一下。
  • 这成功了!只需将 entry.val 更改为文档并实例化 List _acts = [];在州级。谢谢:)
【解决方案2】:
onTap: () { 
setState((){
                _act = !_act;
                print(_act.toString());
                }
});

复制粘贴即可。

【讨论】:

  • 我以前试过这个。 _act 变量在每个 setState 上都被重置为 false,因为它的实例化位于 ListView 小部件内。在状态类本身中实例化 _act 变量将提供更新并更改值,但列表视图中的每一行都将被更新,而不是被点击的单行,因为它们都将使用相同的 _act 值。
【解决方案3】:

在下面替换bool _act = false;

class _SomeClass extends State<SomeClass> { 并用setState({});包围

【讨论】:

    猜你喜欢
    • 2011-01-02
    • 1970-01-01
    • 1970-01-01
    • 2021-11-28
    • 1970-01-01
    • 1970-01-01
    • 2021-08-23
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多