this is my code
Padding(
padding: EdgeInsets.symmetric(vertical: 10.h),
child: DropdownButtonFormField(
decoration: InputDecoration(
labelText: "countries",
labelStyle: TextStyle(fontSize: 16.sp),
border: OutlineInputBorder(
borderRadius: BorderRadius.circular(10))),
items: const [
DropdownMenuItem(child: Text("USA"), value: "USA"),
DropdownMenuItem(
child: Text("Canada"), value: "Canada"),
DropdownMenuItem(
child: Text("Brazil"), value: "Brazil"),
DropdownMenuItem(
child: Text("England"), value: "England"),
],
),
),
when i click on DropDownButtonFormField the items does not appear .
A common mistake when it is not updating is to use DropdownButtonFormField in a StatelessWidget rather than a StatefulWidget. but hard to say as you did not share that part of the code
Seems you are also missing other code in your DropdownButtonFormField
DropdownButtonFormField(
value: myVariable,
onChanged: (value) {
setState(() {
myVariable= value;
});
},
Let me know if this does not help.
Anything with an interaction with user must be inside StatefulWidget.
There is another ways like changenotifier using notifyListeners() inside void function.
https://medium.com/#aruny3/how-to-use-changenotifier-in-flutter-440371617b8c
Related
I am using DropdownButtonFormField with Getx, when I'm updating item-list of dropdown in controller. Anyone have solution?
My requirement is: a dropdown(showing stats) should be dependent on other dropdown(showing country).
child: Obx(
() =>
DropdownButtonFormField<String>(
decoration: InputDecoration(
enabledBorder: UnderlineInputBorder(
borderSide: BorderSide(color: Colors.white)),
),
hint: Text('Choose'),
items: controller.myItemList.map((Item value) {
return DropdownMenuItem<String>(
value: value.id.toString(),
child: new Text(value.Name??""),
);
}).toList(),
onChanged: (String? newValue) {
print("selected: " + newValue);
},
),
),
I got the perfect solution for this problem,
Before updating myItemList which is in controller, we need to reset dropdownButtonFormField using it's key,
example:
final GlobalKey<FormFieldState> _key_dropdown = l̥GlobalKey<FormFieldState>(); //<- add this
child: Obx(
() =>
DropdownButtonFormField<String>(
key: _key_dropdown, //<------ added this line
decoration: InputDecoration(
enabledBorder: UnderlineInputBorder(
borderSide: BorderSide(color: Colors.white)),
),
hint: Text('Choose'),
items: controller.myItemList.map((Item value) {
return DropdownMenuItem<String>(
value: value.id.toString(),
child: new Text(value.Name??""),
);
}).toList(),
onChanged: (String? newValue) {
print("selected: " + newValue);
},
),
),
and before updating the myItemList just need to reset the dropDown using key:
_key_dropdown.currentState!.reset(); // reset the dropdown.
Im trying to use a dropDownButton instead of a dropDownButtonFormField because i run thru alot of bugs that i see in the dropDownButtonFormField widget. One problem is that in dropDownButtonFormField the clickable area to open the items is only over the hint text and not a cm under it, witch in my case created bad ux. The second problem is that in the dropDownButtonFormField, if an item is a long text and the user presses it when it displays on the main part of the dropdown, the text doesnt create a new line so the user can see the text, the same thing doesnt happen to the dropDownButton widget. Im using dropDownButtonFormField only to use the validator. This is with using DropDownButton Widget.
And this is using the dropDownButtonFormField Widget while having a long text.
Center locationDropDown() {
return Center(
child: Container(
margin: const EdgeInsets.all(10),
padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 4),
decoration: BoxDecoration(
color: Colors.grey.shade200,
borderRadius: BorderRadius.circular(12),
),
child: DropdownButtonFormField<String>(
validator: (value) {
if (value == null || value.isEmpty) {
return 'Please select a location';
}
return null;
},
decoration: const InputDecoration(
enabledBorder: UnderlineInputBorder(
borderSide: BorderSide(color: Colors.transparent),
),
),
value: chooseLocation,
hint: const Text('Select a location'),
isExpanded: true,
items: workingData!.map((some) {
return DropdownMenuItem(
child: Text(
some.name + ' (${some.location})',
),
value: some.id,
);
}).toList(),
onChanged: (String? displayedValue) {
setState(
() {
chooseLocation = displayedValue!;
},
);
},
),
),
);
}
isDense: false,
Add isDense value false in DropdownButtonFormField.
I m new to flutter, need help to set the value of the DropdownButton programmatically.
The value is from textfield. Once i click it, it will set the value at the dropdownbutton automatically.
Widget _districtListContainer() {
return Container(
width: 360.0,
child: new InputDecorator(
decoration: InputDecoration(
suffixIcon: new Icon(
Icons.search,
color: Colors.blue[700],
),
labelText: 'Select District',
labelStyle: TextStyle(fontSize: 12.0)),
isEmpty: _selectedDistrict == null,
child: new DropdownButtonHideUnderline(
child: new DropdownButton<District>(
value: _selectedDistrict,
isDense: true,
isExpanded: false,
onChanged: (District newValue) {
setState(() {
_selectedDistrict = newValue;
});
},
items: _listDistrict?.map((District value) {
return new DropdownMenuItem<District>(
value: value,
child: new Text(
value.district != null ? value.district : '',
style: new TextStyle(fontSize: 11.0),
),
);
})?.toList() ??
[],
),
),
),
margin: EdgeInsets.only(bottom: 10.0));
}
thanks
First Of All, Add the data into the list[] From the TextFormfield then retrieve the list into DropDownButton item.
Also, Make Sure, DropDown Button List Display Textformfield data insert activity could not be able to update simultaneously.
I am using FutureBuilder in flutter to fill up a drop down menu DropdownButtonFormField, i have the method
onChanged: (String? newValue) {
setState(() {
dropdownBrokers = newValue!;
});
},
Which allows the widget to rebuild and then assign the new value selected from the dropdown list. However, i am now experiencing a problem from my research stating that whenever the setState() is called, the future builder runs again, which makes my dropdown menu populate again. This is the full code snippet
FutureBuilder <List<Broker>>(
future: brokerData,
builder: (context, snapshot){
if(snapshot.hasData){
//do what needs to be done here
List<Broker>? data = snapshot.data;
for(var i = 0; i< data!.length; i++){
_brokers.add(data[i].firmName);
print(data[i].firmName);
}
return Container(
padding: EdgeInsets.all(10),
child: InputDecorator(
decoration: InputDecoration(
labelStyle: TextStyle(
color: Colors.grey
),
isDense: true,
contentPadding: EdgeInsets.all(7.0),
errorStyle: TextStyle(color: Colors.redAccent, fontSize: 16.0),
hintText: 'Select Broker',
border: OutlineInputBorder(borderRadius: BorderRadius.circular(5.0))),
child: DropdownButtonHideUnderline(
child: DropdownButtonFormField<String>(
alignment: Alignment.center,
value: dropdownBrokers,
icon: const Icon(Icons.arrow_downward),
iconSize: 24,
elevation: 16,
style: const TextStyle(color: Colors.indigo),
onChanged: (String? newValue) {
setState(() {
dropdownBrokers = newValue!;
});
},
items: _brokers.map<DropdownMenuItem<String>>((String value) {
return DropdownMenuItem<String>(
value: value,
child: Text(value),
);
}).toList(),
),
),
),
),
);
Also i get an error when i reselect an item.
How do i prevent the FutureBuilder from running twice
FutureBuilder will always be rendered once unless recreated in the build method. So the solution to this can be done in two ways:
1: Only calling brokerData in the FutureBuilder method or
2: Only calling brokerData in the initState override.
You can not do both.
And I assume the data to be populated in the dropdown comes from the future builder. Then use snapshot.data of the future instead of an already created value in this case:
items: _brokers.map<DropdownMenuItem<String>>((String value) {
return DropdownMenuItem<String>(
value: value,
child: Text(value),
);
Change to:
items: snapshot.data.map<DropdownMenuItem<String>>((String value) {
return DropdownMenuItem<String>(
value: value,
child: Text(value),
);
I am looking for a Flutter Plugin to use in one of my POC projects. Idea is to create a dropdown field with a search option, something similar to what you can see on Yatra(dot)com.
It will be really helpful if someone can guide me to create a widget by myself to achieve this.
Any guidance is highly appreciated.
Have a look in this site and try out this code
Container(
child: DropdownSearch<String>(
mode: Mode.DIALOG,
showSearchBox: true,
searchBoxDecoration: InputDecoration(
filled: true,
fillColor: Colors.grey,
),
showAsSuffixIcons: true,
showClearButton: false,
dropdownButtonBuilder: (_) => Padding(
padding: const EdgeInsets.all(8.0),
child: const Icon(
Icons.arrow_drop_down,
size: 24,
color: Colors.red,
),
),
showSelectedItem: true,
items: ["bs", "test", "company"],
onChanged: (String newValue) {
setState(() {
// dropDownValue = newValue;
});
},
// selectedItem: dropDownValue,
),
),