Flutter 不显示下拉选择
Posted
技术标签:
【中文标题】Flutter 不显示下拉选择【英文标题】:Dropdown selection not displaying with Flutter 【发布时间】:2019-02-08 14:27:18 【问题描述】:我从 JSON 中获取项目并在下拉列表中显示它们。当该人从下拉列表中选择一个项目时,我得到了选择,但所选项目没有改变。
例如,我们在列表中有 (tokyo, paris, new york)。默认选择是东京。当该人选择巴黎时,我明白了,但下拉列表中的选择没有改变。
这是我的代码:
new DropdownButton(
value: cities.elementAt(0),
hint: new Text("Ville"),
items: cities.map((String value)
return new DropdownMenuItem(
value: value,
child: new Row(
children: <Widget>[
new Icon(
Icons.location_city,
color: Colors.deepOrange,
),
new Text(value)
],
),
);
).toList(),
onChanged: (String value)
getTravelCity(value);
,
),
当人选择一个项目时,它仍然显示默认值。
【问题讨论】:
***.com/questions/51735906/… 我试过了,但还是有同样的问题 【参考方案1】:确保您没有在 Widget 中声明 selectedValue,下面的示例非常适合我。
这是dartpad 上的工作代码,用于测试它
var currentSelectedValue;
const deviceTypes = ["Mac", "Windows", "Mobile"];
Widget typeFieldWidget()
return Container(
padding: EdgeInsets.symmetric(horizontal: 20),
child: FormField<String>(
builder: (FormFieldState<String> state)
return InputDecorator(
decoration: InputDecoration(
border: OutlineInputBorder(
borderRadius: BorderRadius.circular(5.0))),
child: DropdownButtonHideUnderline(
child: DropdownButton<String>(
hint: Text("Select Device"),
value: currentSelectedValue,
isDense: true,
onChanged: (newValue)
setState(()
currentSelectedValue = newValue;
);
print(currentSelectedValue);
,
items: deviceTypes.map((String value)
return DropdownMenuItem<String>(
value: value,
child: Text(value),
);
).toList(),
),
),
);
,
),
);
【讨论】:
如果您使用SetState
就可以了,我需要StatelessWidget
如果不执行 setState 就无法在屏幕上呈现新内容,这就是 Flutter 的工作原理,它需要通过执行 setState 来重绘小部件,您可以更改内存中的变量值但呈现更新的值在屏幕上,您需要通过调用 setState 来重绘 ui;
如果您尝试了上面的代码,它将起作用,如果您想添加新元素,只需将该元素添加到您的列表中,例如上面代码中的deviceTypes
,这样新元素就会反映在下拉列表中向下,只要下拉列表在屏幕上呈现,它就会获取新列表。
我已经用工作代码的 dartpad 链接更新了答案,请检查一下
最重要的问题:“确保你没有在 Widget 中声明 selectedValue”!【参考方案2】:
This is the solution: "StatefulBuilder()"
Future<void> AgregarContacto() async
String dropdownValue = 'Exento';
return showDialog<void>(
context: context,
barrierDismissible: true, // user must tap button!
builder: (BuildContext context)
return StatefulBuilder(
builder: (BuildContext context, StateSetter setState)
return AlertDialog(
title: Text('Agregar cliente', textAlign: TextAlign.center,),
content:
SingleChildScrollView(
child: ListBody(
children: <Widget>[
Center(
child: Material(
type: MaterialType.transparency,
child: DropdownButton<String>(
items: <String>[
'Responsable inscripto',
'Monotributista',
'Exento',
'Consumidor final',
'No responsable'
]
.map<DropdownMenuItem<String>>((
String value)
return DropdownMenuItem<String>(
value: value,
child: Text(value),
); //DropMenuItem
).toList(),
value: dropdownValue,
onChanged: (String newValue)
setState(()
dropdownValue = newValue;
print("new$newValue");
); //setState
,
//OnChange
isExpanded: false,
hint: Text('Responsable inscripto',
style: TextStyle(color: Colors.black),),
),
), //Material
), //Center
],
),
),
actions: <Widget>[
FlatButton(
child: Text('Regret'),
onPressed: ()
Navigator.of(context).pop();
,
),
],
);
);
,
);
【讨论】:
这正是我想要的。我有一个很长的无状态屏幕,并且希望在该状态下只有一个下拉菜单。这篇文章只是给了我这个。干杯。我测试了它,它就像魅力一样。【参考方案3】:这是 Flutter 的 Github 中报告的错误。
正确的实现方式是:
class _DropdownButtonBugState extends State<DropdownButtonBug>
final List<String> _items = ['One', 'Two', 'Three', 'Four'].toList();
String _selection;
@override
void initState()
_selection = _items.first;
super.initState();
@override
Widget build(BuildContext context)
final dropdownMenuOptions = _items
.map((String item) =>
new DropdownMenuItem<String>(value: item, child: new Text(item))
)
.toList();
return new Scaffold(
body: new DropdownButton<String>(
value: _selection,
items: dropdownMenuOptions,
onChanged: (s)
setState(()
_selection = s;
);
)
);
【讨论】:
【参考方案4】:如果在选择后未更新所选值,则可以将下拉按钮包装在 StatefulBuilder() 小部件中。
【讨论】:
【参考方案5】:对于那些将来面临这个问题的人。使用变量将值设置为 DropdownButton 并在调用 onChanged 时使用 setState 更新变量
Expanded(child: DropdownButton<String>(
items: cities.map((String value)
return DropdownMenuItem<String>(
value: value,
child: Text(value),
);
).toList(),
value: city,
onChanged: (String val)
_onDropDownChanged(val);
,
),)
使用状态更新城市变量
void _onDropDownChanged(String val)
setState(()
this.city = val;
);
欲了解更多信息,请查看下面的链接
https://github.com/FazalHussain/Flutter-Demo/blob/trip_cost_app/lib/main.dart
【讨论】:
这让我惊醒了。直到我用了这个【参考方案6】:因为你需要用“setState(() );”更新“value:”参数方法和新值必须与传递给“onChanged:”的类型相同。我建议这样做,因为您可以动态更改您的图标。
1) 在文件顶部声明一个新类;
class city
final String name;
final IconData icon;
const city(
this.name,
this.icon,
);
2) 在你的小部件状态中添加这个:
class yourState extend<myWidget>
List<city> cities = [
new city(name: "tokio", icon: Icons.location_city),
new city(name: "paris", icon: Icons.location_city),
new city(name: "new york", icon: Icons.location_city),
];
int index = 0;
Widget drop()
return DropdownButton(
value: cities[index],
hint: new Text("Ville"),
items: cities.map((city value)
return new DropdownMenuItem(
value: value,
child: new Row(
children: <Widget>[
new Icon(
value.icon,
color: Colors.deepOrange,
),
new Text(value.name)
],
),
);
).toList(),
onChanged: (city value)
setState(()
index = cities.indexOf(value);
print(index);
);
//getTravelCity(value.name);
);
现在在您想要 DropDown 的地方调用“drop()”。再见!!
【讨论】:
我认为DropdownButton
的value
属性已更新。现在不用分配实际的String Value
,您可以只使用索引来代替【参考方案7】:
在我最近的应用程序中使用了此代码并且它有效。也许您可以将其与您的代码进行比较。
return DropdownButton<String>(
style: Theme.of(context).textTheme.title,
items: _persons.map((String val)
return new DropdownMenuItem<String>(
value: val,
child: new Container(
child: new Card(
child: new Row(children: <Widget>[
new Icon(Icons.person),
new Text(val),
]),
),
),
);
).toList(),
hint: new Card(
child: new Row(children: <Widget>[
new Icon(Icons.person),
new Text("check"),
])),
value: _selectedPerson,
onChanged: (newVal)
_selectedPerson = newVal;
setState(() );
);
【讨论】:
【参考方案8】:您将第一个城市硬编码为下拉列表的值。
new DropdownButton(
value: cities.elementAt(0), //this one
...
您需要有一些state
变量来保存所选城市。
class YourStatefulWidgetState extends State<YourStatefulWidget>
@override
initState()
super.initState();
selectedCity = cities.elementAt(0)
@override
Widget build(BuildContext context)
...
new DropdownButton(
value: selectedCity,
hint: new Text("Ville"),
items: cities.map((String value)
return new DropdownMenuItem(value: value,
child: new Row(
children: <Widget>[
new Icon(
Icons.location_city, color: Colors.deepOrange,),
new Text(value)
],
),);
).toList(),
onChanged: (String value)
setState(()
selectedCity = getTravelCity(value);
);
,),
...
【讨论】:
我忘了告诉你下拉菜单在 AlertDialog 中 @PondikpaTchabao 你有自己的对话框小部件吗?我认为此代码不适用于您的情况,因为setState
调用正在更新构建对话框的小部件,而不是对话框。您应该创建自己的“DropdownAlertDialog”Stateful
小部件【参考方案9】:
我厌倦了所有选项,包括所有颤振问题。 但是经过2个小时的搜索。我找到了我的 Bloc 实现小部件的解决方案。
onChanged: (Object value)
selectedCity = getTravelCity(value);
setState((); );
);
您可以在这里感受到不同。由于我在 BlocBuilder 下填充了某种状态的列表,因此它不允许您重建下拉菜单。因此,在设置 dropdownValue 之后,调用 setState 方法。它会让你体现价值。
谢谢!
【讨论】:
以上是关于Flutter 不显示下拉选择的主要内容,如果未能解决你的问题,请参考以下文章
DataGridViewComboBox 下拉列表不显示任何可供选择的项目,下拉不起作用
如何使已选择的选项不显示在另一个选择选项下拉 JAVASCRIPT/ANGULARJs