选择项目时,颤振不更新放置在对话框中的 DropdownButton
Posted
技术标签:
【中文标题】选择项目时,颤振不更新放置在对话框中的 DropdownButton【英文标题】:Flutter not updating DropdownButton placed within a dialog when item is selected 【发布时间】:2020-11-10 10:49:57 【问题描述】:我有一个包含 DropdownButton 小部件的 alertDialog。每当我单击下拉菜单中的选项时,我希望它显示所选值。我列出了下面的代码以及 2 个屏幕截图。
我相信这可能是 Flutter 构建小部件的方式的问题,因为当我将 DropdownButton 小部件放在对话框之外时它可以工作,但是将它放在 alertDialog 中会导致它失败。我还注意到,如果我单击 DropdownButton 中的一个选项,然后退出并再次单击对话框,则所选项目会发生变化。但是,我希望更改选定的值,而无需用户点击对话框然后重新进入。
^
上图是用户第一次点击时的对话框。起初,唯一选择的项目是“我无法提供帮助”。每当用户单击 DropdownMenu 小部件并选择不同的选项(例如“其他”)时,此值都应更改。
^
这些是用户可以在下拉菜单中单击的各种选项。当用户点击它时,菜单应相应更新。
代码:
请注意,我已将 _chosenValue 定义为构建函数之外的全局变量。
void _showDecline()
showDialog(
context: context,
builder: (BuildContext context)
return AlertDialog(
title: new Text("Decline Appointment Request"),
content: Container(
height: 100,
width: 200,
child: Column(
children: <Widget>[
new Text("Please select an option for why you declined."),
new DropdownButton<String>(
value: _chosenValue,
underline: Container(),
items: <String>['I\'m not able to help', 'Unclear description', 'Not available at set date and time', 'Other'].map((String value)
return new DropdownMenuItem<String>(
value: value,
child: new Text(value, style: TextStyle(fontWeight: FontWeight.w500),),
);
).toList(),
onChanged: (String value)
setState(()
_chosenValue = value;
);
,
)
],
),
),
actions: <Widget>[
// usually buttons at the bottom of the dialog
new FlatButton(
child: new Text("Close"),
onPressed: () ,
,
),
],
);
,
);
【问题讨论】:
这能回答你的问题吗? How to refresh an AlertDialog in Flutter? 不,我的代码中已经有一个 setState() 操作,并且对话框也放置在一个有状态的小部件中。 所以你试过了,还是不行?使用该链接发布您的最佳尝试,我们会看看有什么问题。 下面的答案都有效。 嗯,大惊喜,他们告诉你的和我 12 小时前的链接告诉你的一样。 【参考方案1】:setState 只会更新当前 StatefulWidget 的 Widget Build 功能。
您应该在 showDialog 中使用 StatefulBuilder。
对于您的情况,只需将 StatefulBuilder 添加为 DropDown 小部件的父级,并在您想要更新 StatefulBuilder 的子级时使用 StateSetter。 它只会更新在 StateFulBuilder 构建器函数下定义的小部件树。
在 DartPad 代码StateFulBuilderDartPad 上查看包括 stateFulBuilder 在内的完整代码。
有关 StatefulBuilder 的更多信息,请访问 StateFulBuilder 文档页面。
【讨论】:
你写自己的答案,而不是投票给副本有什么原因吗? 我没有得到你在评论中提到的那个重复的问题,所以我写下我的答案 我试图解释这些事情,而不是仅仅给出代码......【参考方案2】:import 'dart:convert';
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget
@override
Widget build(BuildContext context)
return MaterialApp(home: HomePage());
class HomePage extends StatefulWidget
@override
_HomePageState createState() => _HomePageState();
class _HomePageState extends State<HomePage>
String _chosenValue;
void _showDecline()
showDialog(
context: context,
builder: (BuildContext context)
return StatefulBuilder(
builder: (BuildContext context, StateSetter setState)
return AlertDialog(
title: new Text("Decline Appointment Request"),
content:
Column(mainAxisSize: MainAxisSize.min, children: <Widget>[
new Text("Please select an option for why you declined."),
SingleChildScrollView(
scrollDirection: Axis.horizontal,
child: new DropdownButton<String>(
hint: Text('Select one option'),
value: _chosenValue,
underline: Container(),
items: <String>[
'I\'m not able to help',
'Unclear description',
'Not available at set date and time',
'Other'
].map((String value)
return new DropdownMenuItem<String>(
value: value,
child: new Text(
value,
style: TextStyle(fontWeight: FontWeight.w500),
),
);
).toList(),
onChanged: (String value)
setState(()
_chosenValue = value;
);
,
)),
]),
actions: <Widget>[
// usually buttons at the bottom of the dialog
new FlatButton(
child: new Text("Close"),
onPressed: ()
Navigator.of(context).pop();
,
),
],
);
,
);
,
);
@override
Widget build(BuildContext context)
return Scaffold(
body: SafeArea(
child: Container(
child: FlatButton(child: Text('Click'), onPressed: _showDecline),
),
),
);
【讨论】:
在我的回答之上,我解决了错误 RIGHT OVERFLOWED BY 68 PIXELS 。 你写自己的答案,而不是投票给副本有什么原因吗?【参考方案3】:看看下面的例子,你必须使用 statefulBuilder 来改变状态。
import 'dart:convert';
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget
@override
Widget build(BuildContext context)
return MaterialApp(home: HomePage());
class HomePage extends StatefulWidget
@override
_HomePageState createState() => _HomePageState();
class _HomePageState extends State<HomePage>
String _chosenValue;
void _showDecline()
showDialog(
context: context,
builder: (BuildContext context)
return StatefulBuilder(
builder: (BuildContext context, StateSetter setState)
return AlertDialog(
title: new Text("Decline Appointment Request"),
content: Container(
height: 100,
width: 200,
child: Column(
children: <Widget>[
new Text("Please select an option for why you declined."),
new DropdownButton<String>(
hint: Text('Select one option'),
value: _chosenValue,
underline: Container(),
items: <String>[
'I\'m not able to help',
'Unclear description',
'Not available at set date and time',
'Other'
].map((String value)
return new DropdownMenuItem<String>(
value: value,
child: new Text(
value,
style: TextStyle(fontWeight: FontWeight.w500),
),
);
).toList(),
onChanged: (String value)
setState(()
_chosenValue = value;
);
,
)
],
),
),
actions: <Widget>[
// usually buttons at the bottom of the dialog
new FlatButton(
child: new Text("Close"),
onPressed: ()
Navigator.of(context).pop();
,
),
],
);
,
);
,
);
@override
Widget build(BuildContext context)
return Scaffold(
body: SafeArea(
child: Container(
child: FlatButton(child: Text('Click'), onPressed: _showDecline),
),
),
);
只要让我知道它是否有效。
【讨论】:
你写自己的答案,而不是投票给副本有什么原因吗?【参考方案4】: onTap: ()
///___________________________________________________________________
// Get.defaultDialog(
// title: " وضعیت دزدگیر",
// middleText: "پیام اعلام وضعیت دزدگیر ارسال گردد؟",
// titleStyle: TextStyle(
// color: mainColor2, fontWeight: FontWeight.bold, fontSize: 16),
// middleTextStyle:
// TextStyle(color: mainColor6.withOpacity(0.9), fontSize: 15),
// );
///----------------------------------------------------------------------
// showDialog(
// context: context,
// builder: (context) => AlertDialog(
// content: Column(
// children: <Widget>[
// TextField(
// decoration: InputDecoration(
// icon: Icon(Icons.account_circle),
// labelText: 'Username',
// ),
// ),
// TextField(
// obscureText: true,
// decoration: InputDecoration(
// icon: Icon(Icons.lock),
// labelText: 'Password',
// ),
// ),
// ],
// ),
// ),
// );
///___________________________________________________________________
List<DropdownMenuItem<String>> listDrop = [];
String selected=null;
void loadData()
listDrop.add(new DropdownMenuItem(
child: new Text("پایدار"),
value:"555",
));
listDrop.add(
new DropdownMenuItem(
child: new Text("لحظه ای"),
value:"444",
),
);
loadData();
Alert(
context: context,
title: "تنظیمات خروجی شماره ۱",
// desc: ".",
// image: Image.asset(
// "assets/settings.png",
// scale: 5,
// ),
content: Directionality(
textDirection: TextDirection.rtl,
child: Center(
child: Column(
children: <Widget>[
SizedBox(height: 20.0),
TextField(
keyboardType: TextInputType.text,
controller: _codeShargController,
decoration: InputDecoration(
labelText: 'نام خروجی',
hintText: '$out1.read('codeShargController')',
),
),
SizedBox(height: 25.0),
Center(
child: DropdownButton(
underline: Container(
height: 1.5,
color: Colors.black26,
),
hint: Text("وضعیت عملکرد"),
items: listDrop,
isExpanded: true,
value: selected,
style: TextStyle(color: Colors.black, fontSize: 16),
onChanged: (newValue)
selected = newValue;
// setState(() );
setState(() selected = newValue; );
,
),
),
SizedBox(height: 25.0),
],
),
),
),
// content: Column(
// children: <Widget>[
//
// SizedBox(height: 10.0),
//
// TextField(
//
// decoration: InputDecoration(
//
// icon: Icon(Icons.account_circle),
// labelText: 'Username',
// ),
// ),
// SizedBox(height: 10.0),
//
// TextField(
// obscureText: true,
// decoration: InputDecoration(
// icon: Icon(Icons.lock),
// labelText: 'Password',
// ),
// ),
// ],
// ),
buttons: [
DialogButton(
onPressed: ()
out1.write(
"codeShargController", _codeShargController.text);
Navigator.pop(context);
,
child: Text(
"ثبت",
style: TextStyle(color: Colors.white, fontSize: 20),
),
)
]).show();
///___________________________________________________________________
【讨论】:
以上是关于选择项目时,颤振不更新放置在对话框中的 DropdownButton的主要内容,如果未能解决你的问题,请参考以下文章