StatefulBuilder内部的RadioListTile不取消选择RadioListTile内部的其他选项 [英] RadioListTile Inside StatefulBuilder not deselecting other options inside RadioListTile
问题描述
我创建了一个函数,其中在该函数中创建了不同的小部件,我为问题中每个单选类型的答案创建了一个radioListTile.(遍历所有答案,并为每个答案创建radioListTile).
I created a function in which I am creating different widgets in that function I am creating a radioListTile for each answer of type radio inside a question. (looping through all the answers and created radioListTile for each answer).
我已将此radioListtile包裹在statefulBuilder中,以使其不会重新创建或影响整个屏幕,并使用setstate方法更改/设置值.
I have wrapped this radioListtile inside a statefulBuilder so that it don't recreates or effect the whole screen and used setstate method to change/set the value.
问题是当我在radioListTile中选择任何其他选项/值时,它不会取消选择先前的选项(意味着我可以在radioListTile中选择所有选项).
the problem is when I select any other option/value inside this radioListTile it does not deselects the previous option (means I can select all the options inside the radioListTile).
请在下面检查我的代码以创建小部件.
List<Widget> getAnswerWidget(Question objQuestion) {
// list of all answers inside a question
List<Answer> answerList = objQuestion.answers;
// list of widgets for each question
List<Widget> answerWidget = [];
// fetching answer type for switch case inside generating answers method
var answerType = answerList[0].answerType.toUpperCase();
switch (answerType) {
case ("TEXT"): // if answer type is equal to text
var index = listAnswers
.indexWhere((pair) => pair['Key'] == objQuestion.questionId);
answerWidget.add(StatefulBuilder(
builder: (BuildContext context, StateSetter setState) {
return Container(
child: Padding(
padding: EdgeInsets.all(10.0),
child: new Theme(
data: new ThemeData(
primaryColor: Color.fromRGBO(223, 0, 61, 1),
primaryColorDark: Color.fromRGBO(223, 0, 61, 1),
),
child: TextField(
decoration: new InputDecoration(
border: new OutlineInputBorder(
borderSide: new BorderSide(
color: Color.fromRGBO(223, 0, 61, 1))),
hintText: 'This is a question hint',
helperText: 'this is a helper text.',
labelText: 'Enter text',
prefixIcon: const Icon(
Icons.question_answer,
color: Color.fromRGBO(223, 0, 61, 1),
),
prefixText: ' ',
suffixText: 'suffix',
suffixStyle: const TextStyle(
color: Color.fromRGBO(223, 0, 61, 1))),
),
),
),
);
}));
return answerWidget;
break;
case ("CHECKBOX"): // if answer type is equal to checkbox
for (Answer ans in objQuestion.answers) {
var index =
listAnswers.indexWhere((pair) => pair['Key'] == ans.answerId);
answerWidget.add(StatefulBuilder(
builder: (BuildContext context, StateSetter setState) {
return Container(
child: Padding(
padding: EdgeInsets.all(10.0),
child: CheckboxListTile(
title: Text(ans.answerText),
value: listAnswers[index]['value'],
onChanged: (val) {
setState(() {
listAnswers[index]['value'] = val;
print(listAnswers[index]['value']);
});
},
secondary: const Icon(Icons.check),
),
));
}));
}
return answerWidget;
break;
case ("RADIO"): // if answer type is equal to radio (majority of answers are radio)
var index = listAnswers
.indexWhere((pair) => pair['Key'] == objQuestion.questionId);
for (Answer ans in objQuestion.answers) {
answerWidget.add(StatefulBuilder(
builder: (BuildContext context, StateSetter setState) {
return Container(
child: Padding(
padding: EdgeInsets.all(10.0),
child: RadioListTile(
groupValue: listAnswers[index]['value'],
title: Text(ans.answerText),
value: ans.answerId,
onChanged: (val) {
setState(() {
listAnswers[index]['value'] = val;
// debug
print(
'listValue: ' + listAnswers[index]['value'].toString());
print('index: ' + index.toString());
});
},
selected: listAnswers[index]['value'] == ans.answerId,
secondary: const Icon(Icons.child_care),
),
));
}));
}
return answerWidget;
break;
case ("OPTION"): // if answer type is equal to dropdown/select
var index = listAnswers
.indexWhere((pair) => pair['Key'] == objQuestion.questionId);
List<DropdownMenuItem> _dropdownItems = [];
for (var i = 0; i < answerList.length; i++) {
_dropdownItems.add(DropdownMenuItem(
value: answerList[i].answerId,
child: Text(answerList[i].answerText)));
}
answerWidget.add(StatefulBuilder(
builder: (BuildContext context, StateSetter setState) {
return Container(
child: Padding(
padding: EdgeInsets.all(10.0),
child: DropdownButton(
hint: Text('Please Select'),
items: _dropdownItems,
onChanged: (value) {
setState(() {
listAnswers[index]['value'] = value;
print('value:' + value.toString());
});
}),
),
);
}));
return answerWidget;
break;
case ("DATE"): // if answer type is equal to date
var index = listAnswers
.indexWhere((pair) => pair['Key'] == objQuestion.questionId);
answerWidget.add(StatefulBuilder(
builder: (BuildContext context, StateSetter setState) {
return Container(
child: Padding(
padding: EdgeInsets.all(10.0),
child: MyTextFieldDatePicker(
// custom widget inside utils folder
labelText: "Date",
prefixIcon: Icon(Icons.date_range),
suffixIcon: Icon(Icons.arrow_drop_down),
lastDate: DateTime.now().add(Duration(days: 366)),
firstDate: DateTime.now().add(Duration(days: -366)),
initialDate: DateTime.now().add(Duration(days: 1)),
onDateChanged: (selectedDate) {
listAnswers[index]['value'] = selectedDate;
})));
}));
return answerWidget;
break;
} // end switch answer type cases
return answerWidget;
}
生成地图的代码(将此作为我存储答案/选择的位置)
void generateAnswers(List<Question> objQuestions) {
for (int i = 0; i < objQuestions.length; i++) {
if (objQuestions[i].answers[0].answerType.toUpperCase() == 'CHECKBOX') {
for (Answer ans in objQuestions[i].answers) {
var keyPair = {
'Key': ans.answerId,
'value': false,
};
listAnswers.add(keyPair);
}
} else if (objQuestions[i].answers[0].answerType.toUpperCase() ==
'RADIO') {
var keyPair = {
'Key': objQuestions[i].questionId,
'value': 0,
};
listAnswers.add(keyPair);
} else if (objQuestions[i].answers[0].answerType.toUpperCase() ==
'TEXT') {
var keyPair = {
'Key': objQuestions[i].questionId,
'value': "",
};
listAnswers.add(keyPair);
} else if (objQuestions[i].answers[0].answerType.toUpperCase() ==
'OPTION') {
var keyPair = {
'Key': objQuestions[i].questionId,
'value': null,
};
listAnswers.add(keyPair);
} else if (objQuestions[i].answers[0].answerType.toUpperCase() ==
'DATE') {
var keyPair = {
'Key': objQuestions[i].questionId,
'value': TimeOfDay.now(),
};
listAnswers.add(keyPair);
}
}
}
注意:如果我删除answerWidget.add(StatefulBuilder(...)),它将使整个屏幕得以重建(它确实解决了我的选择问题).如果从最后一个问题中选择一个选项,它将再次出现在顶部.
推荐答案
创建用于处理无线电图块状态的单独方法,并将该状态作为参数传递给此方法,例如
Create a separate method for handling radio tile state and pass the state as parameter to this method e.g
List<RadioListTile> generateRadioTile(var objQuestion, StateSetter setState){
List<RadioListTile> radioList = [];
for (Answer ans in objQuestion.answers) {
var index = listAnswers.indexWhere((pair) => pair['key'] == objQuestion.questionId);
// fetching answer index
var ansIndex = listAnswers[index]['answer'].indexWhere((pair) => pair['key'] == ans.answerId);
radioList.add(RadioListTile(
// key: _key,
title: Text(ans.answerText),
value: listAnswers[index]['answer'][ansIndex]['key'],
groupValue: listAnswers[index]['selectedValue'],
onChanged: (val) {
setState(() {
// making all other answer option selected value to false
listAnswers[index]['answer'].asMap().forEach(
(index, keyPair) => keyPair['value'] = false);
// making current answer option selected value to true
listAnswers[index]['answer'][ansIndex]['value'] =
true;
// setting current selected value to selected answer answerId which is key value
listAnswers[index]['selectedValue'] = val;
// printing value for debugging
print('val: ' + val.toString());
print('ans_index: ' + ansIndex.toString());
print('value: ' +
listAnswers[index]['answer'][ansIndex]['value']
.toString());
print('Answer array values :-');
listAnswers[index]['answer'].asMap().forEach(
(index, keyPair) => print(keyPair['value']));
// working with the visibility
processAnswerLogic(ans.answerLogic);
});
},
secondary: const Icon(Icons.check),
activeColor: Color.fromRGBO(223, 0, 61, 1),
));
}
return radioList;}
并在switch语句中更改您的代码,如下所示:
and in switch statement change your code as below:
case ("RADIO"): // if answer type is equal to radio (majority of answers are radio)
answerWidget.add(StatefulBuilder(
builder: (BuildContext context, StateSetter setState) {
return Container(
child: Padding(
padding: EdgeInsets.all(10.0),
child: Column(
children: generateRadioTile(objQuestion, setState),
)));
}));
return answerWidget;
break;
这篇关于StatefulBuilder内部的RadioListTile不取消选择RadioListTile内部的其他选项的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!