Flutter Drawer Widget - изменить содержимое Scaffold.body
При использовании Flutter Scaffold.Drawer - возможно ли, чтобы ссылки в ящике изменяли содержимое (Scaffold.body) на странице? Аналогично наличию ссылок в навигационном блоке измените фрагмент в Android.
2 ответа
Вы можете просто изменить state
содержания вашего интереса, взаимодействуя с вашим Drawer
такие вещи, как это:
Вот соответствующий код для этого примера:
class TestPage extends StatefulWidget {
@override
_TestPageState createState() => new _TestPageState();
}
class _TestPageState extends State<TestPage> {
String text = "Initial Text";
@override
Widget build(BuildContext context) {
return new Scaffold(
drawer: new Drawer(
child: new ListView(
children: <Widget>[
new Container(child: new DrawerHeader(child: new Container())),
new Container (
child: new Column(
children: <Widget>[
new ListTile(leading: new Icon(Icons.info),
onTap:(){
setState((){
text = "info pressed";
});
}
),
new ListTile(leading: new Icon(Icons.save),
onTap:(){
setState((){
text = "save pressed";
});
}
),
new ListTile(leading: new Icon(Icons.settings),
onTap:(){
setState((){
text = "settings pressed";
});
}
),
]
),
)
],
),
),
appBar: new AppBar(title: new Text("Test Page"),),
body: new Center(child: new Text((text)),
));
}
}
Это очень хорошее решение от Азизы! Спасибо. Оно работает! Я просто хотел бы добавить, что он также может работать для всего тела, заменив его на состояние виджета:
...
class _TestPageState extends State<TestPage> {
String text = "Initial Text";
Widget widgetForBody = SomeWidgetFromClass();
...
...
children: <Widget>[
new Container(child: new DrawerHeader(child: new Container())),
new Container (
child: new Column(
children: <Widget>[
new ListTile(leading: new Icon(Icons.info),
onTap:(){
setState((){
widgetForBody = AnotherWidgetFromClass();
});
}
),
new ListTile(leading: new Icon(Icons.save),
onTap:(){
setState((){
widgetForBody = YetAnotherWidgetFromClass();
});
}
),
...
Вот простой и эффективный способ сделать это с помощью полного примера
class _MyPageState extends State<MyPage> {
Widget bodyWidget;
Widget drawer() {
return
}
Widget bodyFirst() {
return Container(
color: Colors.green, child: Center(child: Text("First Page")));
}
Widget bodySecond() {
return Container(
color: Colors.limeAccent, child: Center(child: Text("Second Page")));
}
Widget bodyThird() {
return Container(
color: Colors.lightBlueAccent,
child: Center(child: Text("Third Page")));
}
@override
void initState() {
super.initState();
bodyWidget = bodyFirst();
}
@override
Widget build(BuildContext context) {
return Scaffold(
drawer: drawer(),
appBar: AppBar(title: Text("My App")),
body: bodyWidget,
);
}
}
Вы можете использовать это для тела лесов:
body: _getDrawerItemWidget(_selectedDrawerIndex));
а затем в основном или государственном классе сделать так:
class HomePageState extends State<HomePage> {
int _selectedDrawerIndex = 0;
_getDrawerItemWidget(int pos) {
switch (pos) {
case 0:
return new MainFragment();
case 1:
return new CardMgmt();
}
}
}
CardMgmt и другие классы в переключателе имеют свой собственный метод сборки, который будет возвращать виджет, и он будет размещен в теле вашего скаффолда. Также они могут быть в том же файле дротика или даже другом файле.
Но у меня есть другая проблема:
Что делать, если вместо элементов ящика у нас есть кнопка в другом классе, например CardMgmt, и мы хотим, чтобы она возвращала виджет и обновляла страницу?