Итак, у меня есть виджет панели приложений, который отлично работает:
typedef void BoolCallback(bool val);
class MyAppBar extends PreferredSize {
final int opacity;
final String title;
MyAppBar(this.opacity, [this.title]);
@override
Size get preferredSize => Size.fromHeight(kToolbarHeight);
@override
Widget build(BuildContext context) {
return AppBar(
title: Text(title != null ? title : ''),
backgroundColor: Colors.white,
centerTitle: true,
leading: Container(
color: Color(0x00ffffff), child: IconButton(
icon: Icon(Icons.lightbulb_outline),
iconSize: 120,
onPressed: () {},
)),
actions: [
Switch(value: true, onChanged: (val){
callback(val);}),
],
flexibleSpace: Container(
decoration: myBoxDecoration(opacity)
),
);
}
}
Который вызывается из:
bool _isOn = true;
(...)
Scaffold(
appBar: MyAppBar((val) => _isOn = val, 0xff, 'dummy title'),
body: _isOn ? Widget1 : Widget2
(...)
Однако из-за недавних разработок я хотел бы включить кнопку переключения в крайнем правом углу панели приложений с функцией обратного вызова, чтобы тело изменялось в зависимости от значения switch. Как я могу просто это сделать? Мне нужно избавиться от панели приложений и перейти к настраиваемому контейнеру? Любая помощь очень ценится!
Изменить: после некоторой помощи в разделе комментариев (исчезли?) Я использовал действие, чтобы добавить кнопку и использовать обратный вызов. Однако основная проблема заключается в том, что кнопка переключения имеет состояние, и я не знаю, как объединить виджет с отслеживанием состояния и PreferredSize ...
1 ответ
Что вы можете сделать, так это использовать обратный вызов, который размещается над «Scaffold». Здесь будет изменено состояние bool.
bool _isOn = true;
void toggle() {
setState(() => _isOn = !_isOn);
}
Scaffold(
appBar: MyAppBar(toggle: toggle, isOn: _isOn),
body: _isOn ? Widget1() : Widget2()
);
Тогда где на самом деле находится appBar:
class MyAppBar extends PreferredSize {
final Function toggle;
final bool isOn;
MyAppBar({this.toggle, this.isOn});
@override
Size get preferredSize => Size.fromHeight(kToolbarHeight);
@override
Widget build(BuildContext context) {
return AppBar(centerTitle: true, title: Text("TITLE"), actions: [
Switch(
value: isOn,
onChanged: (val) {
toggle();
}),
]);
}
}
Вариант 2
Это почти то же самое, я просто хочу, чтобы вы знали, что вы можете расширить его до StatefulWidget , если хотите. В этом примере я не передаю логическое в качестве аргумента.
bool _isOn = true;
void toggle() {
setState(() => _isOn = !_isOn);
}
Scaffold(
appBar: MyAppBar(toggle: toggle),
body: _isOn ? Widget1() : Widget2()
);
Тогда где на самом деле находится appBar:
class MyAppBar extends StatefulWidget implements PreferredSizeWidget {
final Function toggle;
MyAppBar({this.toggle});
@override
Size get preferredSize => Size.fromHeight(kToolbarHeight);
@override
_MyAppBar createState() => _MyAppBar();
}
class _MyAppBar extends State<MyAppBar> {
bool isOn = true;
@override
Widget build(BuildContext context) {
return AppBar(centerTitle: true, title: Text("TITLE"), actions: [
Switch(
value: isOn,
onChanged: (val) {
widget.toggle();
setState(() {
isOn = val;
});
}),
]);
}
}
Похожие вопросы
Новые вопросы
flutter
Используйте этот тег для вопросов о наборе инструментов кроссплатформенного пользовательского интерфейса Flutter. Если ваш вопрос касается конкретной платформы, отметьте ее также (например, [android], [ios] и т. д.). Вы также можете включить тег [dart] для вопросов по кодированию.