Not able to use items property of BottomNavigationBar in flutter - flutter

I am trying to use BottomNavigationBar in my flutter project and I want to supply items to it. And for that, I have to use items property. But I am not able to find the items property in the BottomNavigationBar. Please see the attached picture.
And here is complete code:
class _MyHomePageState extends State<MyHomePage>
with SingleTickerProviderStateMixin {
#override
Widget build(BuildContext context) {
// This method is rerun every time setState is called, for instance
// as done by the _incrementCounter method above.
// The Flutter framework has been optimized to make rerunning
// build methods fast, so that you can just rebuild anything that
// needs updating rather than having to individually change
// instances of widgets.
return new Scaffold(
appBar: new AppBar(
// Here we take the value from the MyHomePage object that
// was created by the App.build method, and use it to set
// our appbar title.
title: new Text(config.title),
),
bottomNavigationBar: new BottomNavigationBar(
currentIndex: 0,
onTap: (value){
},
),
// a style that looks nicer for build methods.
);
}
}

Are you sure you have the latest version of flutter. As far a i can tell, destination labels were switched to items in a commit in dec 2016:
https://github.com/flutter/flutter/commit/1b9939af9547513061d2e30716f182b490f5362b#diff-f907c739b721784b11a7fec0459d384f

Seems like things have changed as with the newer version of the Dart plugin. I have achieved the same thing via the following code (Note that now we have to use Map with labels property):
import 'package:flutter/material.dart';
void main() {
runApp(new MyApp());
}
class MyApp extends StatelessWidget {
// This widget is the root of your application.
#override
Widget build(BuildContext context) {
return new MaterialApp(
title: 'App Name',
theme: new ThemeData(
primarySwatch: Colors.blue,
),
home: new MyHomePage(title: 'App Name'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
#override
_MyHomePageState createState() => new _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
var bottomBarLabels = [
new DestinationLabel(
icon: new Icon(Icons.live_tv), title: new Text("Live")),
new DestinationLabel(
icon: new Icon(Icons.date_range), title: new Text("Matches")),
];
#override
Widget build(BuildContext context) {
void _handleBottomNavigationBarTap(int newValue) {
switch (newValue) {
case 0:
print("Live Clicked");
// Scaffold.of(context).showSnackBar(new SnackBar(
// content: new Text("Live Clicked"),
// ));
break;
case 1:
print("Matches Clicked");
// Scaffold.of(context).showSnackBar(new SnackBar(
// content: new Text("Matches Clicked"),
// ));
break;
}
}
return new Scaffold(
appBar: new AppBar(
title: new Text(config.title),
),
bottomNavigationBar: new BottomNavigationBar(
labels: bottomBarLabels, onTap: _handleBottomNavigationBarTap),
);
}
}

I was able to use the items with BottomNavigationBar without facing any problems.
import 'package:flutter/material.dart';
void main() {
runApp(new MaterialApp(
home: new MyApp()));
}
class MyApp extends StatefulWidget {
#override
_MyAppState createState() => new _MyAppState();
}
class _MyAppState extends State<MyApp> with SingleTickerProviderStateMixin {
#override
Widget build(BuildContext context) {
return new Scaffold(
appBar: new AppBar(
title: new Text("Bottom Navigation"),
),
bottomNavigationBar: new BottomNavigationBar(
items: [new BottomNavigationBarItem(
icon: new Icon(Icons.account_box), title: new Text("Account")),
new BottomNavigationBarItem(
icon: new Icon(Icons.add), title: new Text("Add")),
new BottomNavigationBarItem(
icon: new Icon(Icons.close), title: new Text("Close")),
],
),
);
}
}

Related

getText() method of FlutterSummerNote returns blank on first button click

I have a project that needs an integration of html editor, and I found interest about FlutterSummerNote package because of its interesting features. However, when I integrate it into my project, I am encountering an error regarding FlutterSummerNote package. When I clicked the Save button for the first time, I am getting blank value, but when I click the second time and so forth I can get the value from _keyEditor.currentState?.getText() method. I am using flutter_summernote: ^1.0.0 version. Below is the sample code. Any help please?
import 'package:flutter/material.dart';
import 'package:flutter_summernote/flutter_summernote.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
// This widget is the root of your application.
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: MyHomePage(title: 'Demo Flutter Summernote'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({required this.title});
final String title;
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
GlobalKey<FlutterSummernoteState> _keyEditor = GlobalKey();
String result = "";
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
elevation: 0,
actions: <Widget>[
IconButton(
icon: Icon(Icons.save),
onPressed: () async {
final value = await _keyEditor.currentState?.getText();
ScaffoldMessenger.of(context).showSnackBar(SnackBar(
duration: Duration(seconds: 5),
content: Text(value ?? "-"),
));
},
)
],
),
backgroundColor: Colors.white,
body: FlutterSummernote(
hint: "Your text here...",
key: _keyEditor,
hasAttachment: true,
customToolbar: """
[
['style', ['bold', 'italic', 'underline', 'clear']],
['font', ['strikethrough', 'superscript', 'subscript']],
['insert', ['link', 'table', 'hr']]
]
""",
),
);
}
I was able to solve this problem by calling the function to get the text twice and consecutively as so:
final value = await _keyEditor.currentState?.getText();
final value = await _keyEditor.currentState?.getText();
ScaffoldMessenger.of(context).showSnackBar(SnackBar(
duration: Duration(seconds: 5),
content: Text(value ?? "-"),
));

Flutter MaterialApp with navigatorKey and key is not restarting

When testing, press the increment button a few times to view if the app restarts.
I was trying to "restart" a toy app in Flutter. I was using the old counter example and after modifying it the behavior is not the expected.
For example, with this code:
import 'package:flutter/material.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatefulWidget {
#override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
final GlobalKey<NavigatorState> _navigatorKey = GlobalKey<NavigatorState>();
UniqueKey _materialKey;
UniqueKey _homeKey;
#override
void initState() {
super.initState();
_awaitAndRun();
}
#override
Widget build(BuildContext context) {
return MaterialApp(
key: _materialKey,
navigatorKey: _navigatorKey,
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
home: MyHomePage(
key: _homeKey,
title: 'Flutter Demo Home Page',
),
);
}
Future<void> _awaitAndRun() async {
print('Starting delay... Please press the button before the time ends.');
await Future<dynamic>.delayed(Duration(seconds: 5));
setState(() {
_materialKey = UniqueKey();
_homeKey = UniqueKey();
});
print('Has been the screen reloaded?');
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
int _counter = 0;
void _incrementCounter() {
setState(() {
_counter++;
});
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(
'You have pushed the button this many times:',
),
Text(
'$_counter',
style: Theme.of(context).textTheme.headline4,
),
],
),
),
floatingActionButton: FloatingActionButton(
onPressed: _incrementCounter,
tooltip: 'Increment',
child: Icon(Icons.add),
),
);
}
}
The awaitAndRun function should restart the App because I am setting the _materialKey and _homeKey as new instances. As part of it, the MyHomePage widget also should be rebuilt (because the key value has changed) but it didn't.
I can understand it's because the _navigatorKey is "saving" the state of the MaterialApp but the MyHomePage should be rebuild because its key has changed!
It's even more strange because if I remove the _materialKey (as shown in the code below), the MyHomePage widget gets rebuilt.
import 'package:flutter/material.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatefulWidget {
#override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
final GlobalKey<NavigatorState> _navigatorKey = GlobalKey<NavigatorState>();
UniqueKey _materialKey;
UniqueKey _homeKey;
#override
void initState() {
super.initState();
_awaitAndRun();
}
#override
Widget build(BuildContext context) {
return MaterialApp(
//key: _materialKey,
navigatorKey: _navigatorKey,
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
home: MyHomePage(
key: _homeKey,
title: 'Flutter Demo Home Page',
),
);
}
Future<void> _awaitAndRun() async {
print('Starting delay... Please press the button before the time ends.');
await Future<dynamic>.delayed(Duration(seconds: 5));
setState(() {
_materialKey = UniqueKey();
_homeKey = UniqueKey();
});
print('Has been the screen reloaded?');
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
int _counter = 0;
void _incrementCounter() {
setState(() {
_counter++;
});
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(
'You have pushed the button this many times:',
),
Text(
'$_counter',
style: Theme.of(context).textTheme.headline4,
),
],
),
),
floatingActionButton: FloatingActionButton(
onPressed: _incrementCounter,
tooltip: 'Increment',
child: Icon(Icons.add),
),
);
}
}
So it doesn't have any sense for me, why does this happen? Why when I set the _materialKey the MyHomePage widget doesn't get rebuilt?
It's pretty normal. Flutter always target safe and clean state and doesn't keep any item usually time. You can use a lot of methods, so I think should provider
You need to game states keep to app state, so I created ToysGame(sample) and added count property, you can use and change this property so unaffected state changes.
Firstly wrap single provider instance to your app page.
home: Provider(
create: (context) => ToysGame(),
child: MyHomePage(
key: _homeKey,
title: 'Flutter Demo Home Page',
),
),
After doesn't keep count on in page state, you should use toys state with provider.
Text(
Provider.of<ToysGame>(context).count.toString(),
style: Theme.of(context).textTheme.headline4,
),
And you want to change value
void _incrementCounter() {
Provider.of<ToysGame>(context, listen: false).count++;
setState(() {});
}
Finally, it's done. I added on my stackhelpover repo with restart app lib name.
(You read provider package and maybe other feature help for you [ change notifier or multi-provider ])
StackHelpOver

Flutter: Persisting Page States

Even after reading this and this, I still can't seem to wrap my head around storing page states in Flutter.
I've built a sample app, which has a main page called MyHomePage and a second page called SecondPage. MyHomePage has a floating action button, which displays SecondPage via Navigator.push(...). The second page contains a text field with an assigned controller. I would like to preserve the text field's text after I close and reopen SecondPage.
I've tried all sorts of combinations with setting buckets, page states and keys (inspired by the links above), but I couldn't make it work.
Also I'd like to store the whole page state automatically - without the need to write/retrieve every single value manually (in case I have a lot of text fields on the page).
Here is my code:
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
PageStorageKey mykey = new PageStorageKey("testkey");
class MyApp extends StatelessWidget {
final PageStorageBucket _bucket = new PageStorageBucket();
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: PageStorage(
bucket: _bucket,
child: MyHomePage(),
)
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key}) : super(key: key);
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("State demo"),
),
body: Center(
child: Column(
children: <Widget>[
],
),
),
floatingActionButton: FloatingActionButton(
onPressed: _openSecondPage,
tooltip: 'Increment',
child: Icon(Icons.add),
),
);
}
_openSecondPage() {
Navigator.push(context, new MaterialPageRoute(builder: (context) => new SecondPage()));
}
}
class SecondPage extends StatefulWidget {
#override
_SecondPageState createState() => _SecondPageState();
}
class _SecondPageState extends State<SecondPage> {
final _aController = TextEditingController();
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Second page"),
),
body: Center(
child: TextField(
controller: _aController,
key: mykey,
autofocus: true,
),
)
);
}
}
EDIT:
Based on Ajay's answer, I was able to greatly simplify the working code. Turns out that in order to persist widget states manually, all you need is an instance of PageStorageBucket in combination with ValueKey instances.
Here are the modifications I did to Ajay's code:
Removed the after_layout plugin (initState method is sufficient).
Removed the global PageStorageKey instance (replaced it with a local ValueKey instance in the page that needs to use it).
Removed global instance of PageStorageBucket and replaced it with a final instance in MyApp, which is passed to the pages that need it via constructor attributes.
Removed PageStorage from the component tree.
Here is the resulting code (simplest working form):
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
final bucket = PageStorageBucket();
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: MyHomePage(bucket: bucket,),
);
}
}
class MyHomePage extends StatefulWidget {
final PageStorageBucket bucket;
const MyHomePage({Key key, this.bucket}) : super(key: key);
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("State demo"),
),
body: Center(
child: Column(
children: <Widget>[],
),
),
floatingActionButton: FloatingActionButton(
onPressed: _openSecondPage,
tooltip: 'Increment',
child: Icon(Icons.add),
),
);
}
_openSecondPage() {
Navigator.push(
context, new MaterialPageRoute(builder: (context) => new SecondPage(bucket: widget.bucket,)));
}
}
class SecondPage extends StatefulWidget {
final PageStorageBucket bucket;
const SecondPage({Key key, this.bucket}) : super(key: key);
#override
_SecondPageState createState() => _SecondPageState();
}
class _SecondPageState extends State<SecondPage> {
static const KEY_A = ValueKey("secondPage.A");
final _aController = TextEditingController();
#override
void initState() {
super.initState();
_aController.addListener(_updateValue);
String value = widget.bucket.readState(context, identifier: KEY_A) ?? "";
_aController.text = value;
}
_updateValue() {
widget.bucket.writeState(context, _aController.text, identifier: KEY_A);
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Second page"),
),
body: Center(
child: TextField(
controller: _aController,
autofocus: true,
),
),
);
}
}
you need to read and write the state as well.
Check out the below code.
Note: I have used after_layout to initialize the text controller.
import 'package:after_layout/after_layout.dart';
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
PageStorageKey mykey = new PageStorageKey("testkey");
final PageStorageBucket _bucket = new PageStorageBucket();
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: PageStorage(
bucket: _bucket,
child: MyHomePage(),
));
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key}) : super(key: key);
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("State demo"),
),
body: Center(
child: Column(
children: <Widget>[],
),
),
floatingActionButton: FloatingActionButton(
onPressed: _openSecondPage,
tooltip: 'Increment',
child: Icon(Icons.add),
),
);
}
_openSecondPage() {
Navigator.push(
context, new MaterialPageRoute(builder: (context) => new SecondPage()));
}
}
class SecondPage extends StatefulWidget {
#override
_SecondPageState createState() => _SecondPageState();
}
class _SecondPageState extends State<SecondPage>
with AfterLayoutMixin<SecondPage> {
final _aController = TextEditingController();
#override
void initState() {
super.initState();
_aController.addListener(_updateValue);
}
#override
void afterFirstLayout(BuildContext context) {
String value =
_bucket.readState(context, identifier: ValueKey(mykey)) ?? "";
print(value);
_aController.text = value;
}
_updateValue() {
_bucket.writeState(context, _aController.text, identifier: ValueKey(mykey));
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Second page"),
),
body: Center(
child: TextField(
controller: _aController,
key: mykey,
autofocus: true,
),
),
);
}
}

How To Fix Bottom navigation in flutter?

How to fix Bottom Navigation in Flutter?
MediaQuery.Of() called with context That does not contain a
MediaQuery.Bottom Navigation Not working.
This code Showing Error What is MediaQuery.Of() called with context That does not contain a MediaQuery?
import 'package:flutter/material.dart';
void main(){
runApp(Home());
}
class Home extends StatefulWidget{
#override
State<StatefulWidget> createState() => _HomeState();
}
class _HomeState extends State<Home>{
int currindex=0;
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Bottom Nav "),
),
body: Container(),
bottomNavigationBar: BottomNavigationBar(
currentIndex: currindex,
items:[BottomNavigationBarItem(
icon: Icon(Icons.home),
title: Text("Home"),
backgroundColor: Colors.blue
),
BottomNavigationBarItem(
icon: Icon(Icons.search),
title: Text("Search"),
backgroundColor: Colors.blue
),
BottomNavigationBarItem(
icon: Icon(Icons.person),
title: Text("Profile"),
backgroundColor: Colors.blue
),],
onTap: (index){
setState(() {
currindex=index;
});
},
));
}
}
it is because you are not using MaterialApp(), you need to use MaterialApp() in your widget tree
look at this demo....
void main() => runApp(Home());
class Home extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
title: //your Title,
theme: //your theme,
home: HomePage(),
);
}
}
class HomePage extends StatefulWidget{
#override
State<StatefulWidget> createState() => _HomePageState();
}
//and your _HomePageState widget goes here

Navigating to another page from drawer menu and setting title to app bar

i am new to flutter and would like someone to help me with code i found in github that i would like to use. take a look at the link below
https://github.com/JohannesMilke/drawer_example
this is an example of a navigational drawer. i like the way the developer coded it and would like to use this example. the problem is that the developer didnt implement navigating to another page. when you click on item in the drawer, it just print a message in the console.
i want to take this a step further. i want to modified the code so that when you click on a item it will navigate to another page and the drawer will b closed. the drawer icon should remain on the toolbar on the new page displayed. also, when you navigate to another page the title of that page should be set in the toolbar.
when i looked at the code , i have an idea where to change but i am not successful. i think i need to change the body tag at the bottom of the code. the problem is that i dont know how to call the DrawerWidgetState class in drawer_widget.dart file.
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
final String appTitle = 'Ttitle';
#override
Widget build(BuildContext context) => MaterialApp(
title: appTitle,
theme: ThemeData(
primaryColor: Colors.red,
textTheme: TextTheme(
subhead: TextStyle(
color: Colors.black.withOpacity(0.4),
),
),
dividerColor: Colors.black.withOpacity(0.4),
),
home: MainPage(appTitle: appTitle),
);
}
class MainPage extends StatefulWidget {
final String appTitle;
const MainPage({this.appTitle});
#override
MainPageState createState() => MainPageState();
}
class MainPageState extends State<MainPage> {
#override
Widget build(BuildContext context) => Scaffold(
appBar: AppBar(
title: Text(widget.appTitle),
),
drawer: DrawerWidget(),
body: container()
);
}
i define the following function in drawer_widget.dart file
getDrawerItemWidget(int pos) {
print('testing');
switch (pos) {
case 0:
return new FirstFragment();
case 1:
return new SecondFragment();
case 2:
return new ThirdFragment();
default:
return new Text("Error");
}
}
but i dont know how to call it from Mainpage Body tag and set title accordingly. can someone help modify the code so that i can nagivate to another page and set title? full code is in
https://github.com/JohannesMilke/drawer_example
thanks in advance
Using the drawer_example library you need to make some small changes in order to make it work.
Over your drawer_widget.dart add this add the beginning:
typedef TitleCallback = void Function(String, int);
Once you do that, your Drawer StatefulWidget should looks this way:
class DrawerWidget extends StatefulWidget {
final TitleCallback callback;
final int tabIndex;
#override
DrawerWidgetState createState() => DrawerWidgetState();
DrawerWidget(this.callback, this.tabIndex);
}
and your initState:
#override
void initState() {
selectedDrawerIndex = widget.tabIndex;
selectedProfileIndex = 0;
super.initState();
}
This will be the constructor to pass the new value back to your main.dart file.
Inside the ListTile, you can add the following logic:
ListTile(
leading: Icon(item.icon),
title: Text(item.name),
selected: selectedDrawerIndex == currentIndex,
onTap: () {
final item = getOffsetIndex(drawerGroups, currentIndex);
print('Selected index $selectedDrawerIndex with name ${item.name}');
setState(() {
selectedDrawerIndex = currentIndex;
widget.callback(item.name, selectedDrawerIndex);
});
Navigator.pop(context); // to close the Drawer
},
)
If you can check, the line: widget.callback(item.name); sends the tab name over the callback and that logic can be applied any where you want to change your title. It can even be a hard coded title like:
widget.callback("Second Tab");
Now, going back to your main.dart file:
class MyApp extends StatefulWidget {
final String title;
ListExample(this.title);
#override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
List<Widget> _fragments = <Widget> [
Container(
child: Text("Fragment One"),
),
Container(
child: Text("Fragment Two"),
),
Container(
child: Text("Fragment Three"),
),
];
String titleAppBar = "Testing";
int tabIndex = 0;
#override
void initState() {
setState(() {
titleAppBar = widget.title;
});
super.initState();
}
#override
Widget build(BuildContext context) {
return MaterialApp(
title: widget.title,
home: Scaffold(
appBar: AppBar(
title: Text(titleAppBar),
),
drawer: DrawerWidget((title, index) {
setState(() {
titleAppBar = title;
tabIndex = index;
});
}, tabIndex),
body: _fragments[tabIndex],
),
);
}
}
Final Result:
Looking at the example on GitHub, it's overcomplicating something that's too easy with Flutter.
Here's a simple example on how to use a Drawer on Flutter:
main.dart
import 'package:flutter/material.dart';
import 'another_page.dart';
import 'home_page.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
// declaring your routes will allow you to push and remove everything from the stack (including the drawer) with pushNamedAndRemoveUntil()
routes: {
'home': (context) => HomePage(),
'anotherPage': (context) => AnotherPage(),
},
initialRoute: 'home',
);
}
}
home_page.dart (another_page.dart is exactly the same for illustration purpose)
import 'package:flutter/material.dart';
import 'menu_drawer.dart';
class HomePage extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Scaffold(
drawer: MenuDrawer(),
appBar: AppBar(
title: Text('Home'),
),
body: Center(
child: Text('Home'),
),
);
}
}
menu_drawer.dart
import 'package:flutter/material.dart';
class MenuDrawer extends StatelessWidget {
// Push the page and remove everything else
navigateToPage(BuildContext context, String page) {
Navigator.of(context).pushNamedAndRemoveUntil(page, (Route<dynamic> route) => false);
}
#override
Widget build(BuildContext context) {
return Drawer(
child: ListView(
// This could be mapped from a List of items
children: <Widget>[
ListTile(
leading: Icon(Icons.home),
title: Text('Home'),
onTap: () => navigateToPage(context, 'home'),
),
ListTile(
leading: Icon(Icons.panorama),
title: Text('Another page'),
onTap: () => navigateToPage(context, 'anotherPage'),
),
],
),
);
}
}
Final result: