Reputation: 61
I am trying to create a gender selection functionality that contains 3 radio buttons. I have done this code but it is not working as I want it.
Radio button container
final _radio_colume_container = Container(
margin: const EdgeInsets.fromLTRB(50, 15, 50, 00),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Text(
'Gender*',
),
Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
add_radio_button(0, 'Male'),
add_radio_button(1, 'Female'),
add_radio_button(2, 'Others'),
],
),
],
),
);
add_radio_button Method
Row add_radio_button(int btnValue, String title) {
return Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
Radio(
activeColor: Colors.green,
value: btnValue,
groupValue: -1,
onChanged: _handleradiobutton,
),
Text(title)
],
);
}
I am achieving this
I want to achieve this.
Upvotes: 2
Views: 14187
Reputation: 1
Padding(
padding: EdgeInsets.only(left: 5, right: 5),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
"Gender",
style: TextStyle(fontSize: 19),
),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Expanded(
child: ListTile(
title: const Text('M'),
leading: Radio<Gender>(
fillColor:
MaterialStateColor.resolveWith(
(states) => Colors.blue),
value: Gender.male,
groupValue: _gen,
onChanged: (Gender? value) {
setState(() {
_gen = value;
});
},
),
),
),
Expanded(
child: ListTile(
title: const Text('F'),
leading: Radio<Gender>(
fillColor:
MaterialStateColor.resolveWith(
(states) => Colors.blue),
value: Gender.female,
groupValue: _gen,
onChanged: (Gender? value) {
setState(() {
_gen = value;
});
},
),
),
),
Expanded(
child: ListTile(
title: const Text('O'),
leading: Radio<Gender>(
fillColor:
MaterialStateColor.resolveWith(
(states) => Colors.blue),
value: Gender.other,
groupValue: _gen,
onChanged: (Gender? value) {
setState(() {
_gen = value;
});
},
),
),
),
])
])),
Upvotes: 0
Reputation: 809
After applying some refactoring from @Shubham's answer, presenting a generalized version of the code for multiple purposes.
import 'package:flutter/material.dart';
/// Requires a list of string ['Male','Female','Other'] only once.
class GenderField extends StatelessWidget {
final List<String> genderList;
GenderField(this.genderList);
@override
Widget build(BuildContext context) {
String select;
Map<int, String> mappedGender = genderList.asMap();
return StatefulBuilder(
builder: (_, StateSetter setState) => Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
mainAxisSize: MainAxisSize.min,
children: [
Text(
'Gender : ',
style: TextStyle(fontWeight: FontWeight.w400),
),
...mappedGender.entries.map(
(MapEntry<int, String> mapEntry) => Row(
mainAxisAlignment: MainAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
children: [
Radio(
activeColor: Theme.of(context).primaryColor,
groupValue: select,
value: genderList[mapEntry.key],
onChanged: (value) => setState(() => select = value),
),
Text(mapEntry.value)
]),
),
],
),
);
}
}
In the main.dart, this widget can be called as
// Some code
Padding(
padding: EdgeInsets.only(bottom: 10),
child: GenderField(['Male','Female','Other'])
)
Upvotes: 0
Reputation: 61
List gender=["Male","Female","Other"];
String select;
Row addRadioButton(int btnValue, String title) {
return Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
Radio(
activeColor: Theme.of(context).primaryColor,
value: gender[btnValue],
groupValue: select,
onChanged: (value){
setState(() {
print(value);
select=value;
});
},
),
Text(title)
],
);
}
//Use the above widget where you want the radio button
child: Row(
children: <Widget>[
addRadioButton(0, 'Male'),
addRadioButton(1, 'Female'),
addRadioButton(2, 'Others'),
],
),
Upvotes: 6
Reputation: 7869
You should take a look at RadioListTile
as it provides a dense
property which will help reduce the padding between the button and its title.
Upvotes: 1