on
Navigation
Now that I have the first screen of the app it’s time to add the second screen and find out how Flutter navigation works. The new screen will show a list of quizes (or sets of questions). Tapping on a quiz will take a user to the list of questions (the screen I already have).
Flutter offers several ways to navigate.
Routes
In terms of Flutter, routes are screens and pages. Navigating to another route (showing another screen) is quite simple:
// in QuizListWidget
onPressed: () {
Navigator.push(
context,
MaterialPageRoute(builder: (context) => QuestionListWidget()),
);
}
Getting back is also not that hard:
// in QuestionListWidget
onPressed: () {
Navigator.pop(context);
}
While this approach is very easy to implement it does couple screens. And that is something I would like to avoid.
This can be achieved by navigating using named routes.
Named routes
The concept is simple: you register a name for route and when navigating you specify the name of the route instead of the screen class.
onPressed: () {
Navigator.pushNamed(context, '/quiz');
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
initialRoute: '/',
routes: {
'/': (context) => MyHomePage(title: "Quizes"),
'/quiz': (context) {
return BlocProvider(
bloc: QuestionListBloc(), child: QuestionListWidget());
}
},
);
}
}
Now instead of home widget I have to specify the initial route to be opened.
Passing the arguments
There is one thing missing: I need to pass some arguments to the screen of questions. Even with named routes it is easy:
class QuestionListScreenArguments {
final String quizId;
final String quizName;
QuestionListScreenArguments(this.quizId, this.quizName);
}
class QuestionListWidget extends StatelessWidget {
static const route = '/quiz';
@override
Widget build(BuildContext context) {
final args = ModalRoute.of(context).settings.arguments
as QuestionListScreenArguments;
// ...
}
onPressed: () {
Navigator.pushNamed(context, '/quiz',
arguments: QuestionListScreenArguments(_quiz.id, _quiz.name));
}
Useful links: