【问题标题】:How to deselect the already selected item after tap on another item ListView in Flutter?在 Flutter 中点击另一个项目 ListView 后如何取消选择已选择的项目?
【发布时间】:2019-09-30 11:06:35
【问题描述】:

我想让用户从列表中只选择一个选项,如果他一个接一个地选择,那么只有最后一个选项应该被认为是选中的。

在当前代码中,用户可以从列表中选择多个我想避免的选项。

尝试过的代码:

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return new MaterialApp(
      title: 'Test App',
      theme: new ThemeData(
        primarySwatch: Colors.red,
      ),
      home: new MyHomePage(),
    );
  }
}

class MyHomePage extends StatefulWidget {
  @override
  _MyHomePageState createState() => new _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  List<int> indexList = new List();
  }

  @override
  Widget build(BuildContext context) {
    return new Scaffold(
      appBar: new AppBar(
        title: new Text('Selected ${indexList.length}  ' + indexList.toString()),
      ),
      body: new ListView.builder(
        itemCount: 3,    
        itemBuilder: (context, index) {
          return new CustomWidget(  
            index: index,
            callback: () {
              if (indexList.isNotEmpty) {
                indexList.clear();
              } 

            },
          );
        },
      ),
    );
  }
}

class CustomWidget extends StatefulWidget {
  final int index;
  final VoidCallback callback;

  const CustomWidget({Key key, this.index, this.callback}) : super(key: key);

  @override
  _CustomWidgetState createState() => new _CustomWidgetState();
}


class _CustomWidgetState extends State<CustomWidget> {
  bool selected = false;
  CustomWidget lastSelectedWidget;

  @override
  Widget build(BuildContext context) {
    return new GestureDetector(
      onTap: () {
          setState(() {
            lastSelectedWidget = widget;
            print(lastSelectedWidget.key);
            selected = !selected;
          });
          widget.callback();
      },
      child: new Container(
        margin: new EdgeInsets.all(5.0),
        child: new ListTile(
          title: new Text("Title ${widget.index}"),
          subtitle: new Text("Description ${widget.index}"),
        ),
        decoration: selected
            ? new BoxDecoration(color: Colors.black38, border: new Border.all(color: Colors.black))
            : new BoxDecoration(),
      ),
    );
  }
}

我正在实现一种列表样式的单选按钮。

【问题讨论】:

    标签: flutter flutter-listview


    【解决方案1】:

    您不能将定义选择哪个CustomWidget 的责任分配给自己的CustomWidgetCustomWidget 一定不知道其他CustomWidgets 的存在,也不知道他们持有的信息。

    鉴于此,您的CustomWidget 应该是这样的:

    class CustomWidget extends StatefulWidget {
      final int index;
      final bool isSelected;
      final VoidCallback onSelect;
    
      const CustomWidget({
        Key key,
        @required this.index,
        @required this.isSelected,
        @required this.onSelect,
      })  : assert(index != null),
            assert(isSelected != null),
            assert(onSelect != null),
            super(key: key);
    
      @override
      _CustomWidgetState createState() => _CustomWidgetState();
    }
    
    class _CustomWidgetState extends State<CustomWidget> {
      @override
      Widget build(BuildContext context) {
        return GestureDetector(
          onTap: widget.onSelect,
          child: Container(
            margin: EdgeInsets.all(5.0),
            child: ListTile(
              title: Text("Title ${widget.index}"),
              subtitle: Text("Description ${widget.index}"),
            ),
            decoration: widget.isSelected
                ? BoxDecoration(color: Colors.black38, border: Border.all(color: Colors.black))
                : BoxDecoration(),
          ),
        );
      }
    }
    

    以及使用CustomWidget的小部件:

    class MyHomePage extends StatefulWidget {
      @override
      _MyHomePageState createState() => _MyHomePageState();
    }
    
    class _MyHomePageState extends State<MyHomePage> {
      int currentSelectedIndex;
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(
            title: Text('Selected index is $currentSelectedIndex'),
          ),
          body: ListView.builder(
            itemCount: 3,
            itemBuilder: (context, index) {
              return CustomWidget(
                index: index,
                isSelected: currentSelectedIndex == index,
                onSelect: () {
                  setState(() {
                    currentSelectedIndex = index;
                  });
                },
              );
            },
          ),
        );
      }
    }
    

    【讨论】:

      猜你喜欢
      • 2021-11-13
      • 2012-10-13
      • 2011-02-01
      • 1970-01-01
      • 2015-10-19
      • 1970-01-01
      • 2013-07-19
      • 1970-01-01
      • 2014-06-30
      相关资源
      最近更新 更多