如何解决Flutter:小部件列表中的自定义多项选择行
我正在尝试从Container窗口小部件列表构建一个多选行(包装在GestureDetector中,用于onTap)。当用户单击“行”中的“容器”小部件之一时,该“容器”小部件会更改颜色(变为蓝色)以反映用户的选择。如果用户然后在“行”中点击另一个“容器”窗口小部件,则该窗口小部件会更改颜色以反映用户的选择,而所有其他窗口小部件都将重置为初始颜色(白色)。此外,用户的选择(索引?)必须是可检索的。
到目前为止,我所能做的就是创建一排“容器行”窗口小部件,这些窗口小部件可以在点击时改变颜色,但是彼此独立地起作用。也就是说,用户可能单击多个选择,这很不好。我需要一些有关如何突破功能的新建议,在该功能下,只能选择一个容器,而所选的值将被传递出去。
干杯, T
//choice button
class ChoiceButton extends StatefulWidget {
final String label;
final bool ispressed;
const ChoiceButton({
Key key,this.ispressed = false,this.label,}) : super(key: key);
@override
_ChoiceButtonState createState() => _ChoiceButtonState();
}
class _ChoiceButtonState extends State<ChoiceButton> {
bool _ispressed;
@override
void initState() {
super.initState();
_ispressed = widget.ispressed;
}
@override
Widget build(BuildContext context) {
return GestureDetector(
onTap: () {
setState(() {
_ispressed = !_ispressed;
});
},child: Container(
height: 80,width: 80,decoration: Boxdecoration(
color: _ispressed ? Colors.blue : Colors.transparent,border: Border.all(
color: Colors.blue,width: 80 * 0.05,),child: Center(
child: Text(
widget.label,style: TextStyle(
fontSize: 12,fontWeight: FontWeight.bold,color: _ispressed ? Colors.white : Colors.blue,textAlign: TextAlign.center,);
}
}
//choice row
class ChoiceRow extends StatefulWidget {
@override
_ChoiceRowState createState() => _ChoiceRowState();
}
class _ChoiceRowState extends State<ChoiceRow> {
bool ispressed = false;
String classChoice = '';
@override
Widget build(BuildContext context) {
return Row(
mainAxisAlignment: MainAxisAlignment.start,children: \[
SizedBox(width: 30),ChoiceButton(
ispressed: ispressed,label: 'A',SizedBox(width: 10),label: 'B',label: 'C',\],);
}
}
解决方法
我为此提供了两个答案...。请使用您喜欢的任何一个。
- 简单的 :
因此Flutter提供了一个名为 ToggleButton 的小部件,该小部件可以满足上述所有需求。请遵循this文档,以获取有关此小部件的更多信息。
您可以在切换按钮的小部件列表中添加自定义的ChoiceButton设计,并且进行一些调整后,您也可以实现ChioceRow设计。
- 现在,如果您是一个喜欢从头开始做所有事情的人(例如:P) ,那么我对您在上面提供的代码中做了一些更改,这些更改将满足您所有的需求。下面是编辑后的代码。
class ChoiceRow extends StatefulWidget {
@override
_ChoiceRowState createState() => _ChoiceRowState();
}
class _ChoiceRowState extends State<ChoiceRow> {
List<bool> isPressedList = [false,false,false];
String classChoice = '';
@override
Widget build(BuildContext context) {
print("Status L $isPressedList");
return Row(
mainAxisAlignment: MainAxisAlignment.start,children: [
SizedBox(width: 30),GestureDetector(
onTap: (){
print("Hello");
setState(() {
isPressedList[0] = true;
isPressedList[1] = false;
isPressedList[2] = false;
});
},child: ChoiceButton(
isPressed: isPressedList[0],label: 'A',),SizedBox(width: 10),GestureDetector(
onTap: (){
setState(() {
isPressedList[0] = false;
isPressedList[1] = true;
isPressedList[2] = false;
});
},child: ChoiceButton(
isPressed: isPressedList[1],label: 'B',GestureDetector(
onTap: (){
setState(() {
isPressedList[0] = false;
isPressedList[1] = false;
isPressedList[2] = true;
});
},child: ChoiceButton(
isPressed: isPressedList[2],label: 'C',],);
}
}
class ChoiceButton extends StatelessWidget {
final String label;
final bool isPressed;
ChoiceButton({this.label,this.isPressed});
@override
Widget build(BuildContext context) {
return Container(
height: 80,width: 80,decoration: BoxDecoration(
color: isPressed ? Colors.blue : Colors.transparent,border: Border.all(
color: Colors.blue,width: 80 * 0.05,child: Center(
child: Text(
label,style: TextStyle(
fontSize: 12,fontWeight: FontWeight.bold,color: isPressed ? Colors.white : Colors.blue,textAlign: TextAlign.center,);
}
}
更改:
-
我创建了一个列表(onPressedList),该列表可以跟踪切换按钮的当前状态(例如打开和关闭的其他状态)。
-
我在ChoiceRow类的按钮上移动了GestureDetector包装。这是因为很难将onTap结果从ChoiceButton传递到ChoiceRow。 (现在,如果您希望在Button类本身中使用手势检测器,则可以使列表成为全局列表,或者使列表成为完全不同的静态值,以便可以正确访问该列表)
-
我使ChoiceButton类成为无状态的,因为现在无需使其保持有状态。
我所做的两件事是添加一个列表,该列表跟踪切换按钮的当前状态,并且当一个切换按钮处于活动状态时,所有其他按钮都将被停用。
现在它可以按照您上面提到的那样工作,并且您还可以通过“ isPressedList”来跟踪所有按钮的当前状态。
GLHF:)
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。