Flutter: Routing using GoRouter
06-Mar-2023 - Sophoun
Hi reader, today I want to show you how I work with GoRouter. GoRouter is a Flutter library that currently maintains by the Flutter team. With GoRouter it can simplify our navigator.
Imagine you have an application that requires the user to activate an account before using it. And after the user is activated, user goes to the detail screen and does not touch their screen for about 30 seconds, you need to show the PIN screen up to protect the user's information. After the user input PIN back, you show the screen that the user just leave previously. But if the user ignores the PIN and presses back, you need to navigate back to the home screen and clear all the route history, Poof. A lot, right? Ok now let's see how we solve this in our project.
To use GoRouter you need to add the go_router
package into your pubspec.yaml
like below
dependencies: go_router: ^6.2.0 # or latest version
After that, you must run the pub get command to pull down the dependency
flutter pub get
Now it's time to start using GoRouter in our project.
Firstly, you need to declare a GoRouter object to where your project can route to.
final router = GoRouter( routes: [ GoRoute( path: "/", builder: (context, state) => const HomePage(), ), GoRoute( path: "/details", builder: (context, state) => const DetailPage(), ), ], );
Now you have 2 routes so, you can navigate between using the 2. Then add that route to the MaterialApp.route
in the main.dart
file.
class MyApp extends StatelessWidget { const MyApp({super.key}); Widget build(BuildContext context) { return MaterialApp.router( title: 'App', // Add router here routerConfig: router, ); } }
To navigate the screen, just call an extension function provided by the GoRouter. Below is how to push the screen.
context.push("details");
Or pop the screen using
context.pop();
It's simple, right? Now let's dig in.
Now we want to show a dialog to the project detail screen with a password while the user not touches the screen for some time.
Just like a normal dialog, we just show it like below when the time arrives.
final controller = TextEditingController(); showDialog( context: context, // to prevent dismiss while touching outside dialog barrierDismissible: false, builder: (context) => Material( color: Colors.white, child: WillPopScope( // to prevent diadialog dismiss form system back button onWillPop: () async => false, child: Column( mainAxisAlignment: MainAxisAlignment.center, crossAxisAlignment: CrossAxisAlignment.center, mainAxisSize: MainAxisSize.min, children: [ const Text("Input pin here"), TextFormField( controller: controller, ), Row( mainAxisAlignment: MainAxisAlignment.center, children: [ ElevatedButton( onPressed: () { // TODO() }, child: const Text("Cancel"), ), ElevatedButton( onPressed: () { // TODO() }, child: const Text("Ok"), ), ], ), ], ), ), ), );
This way, this dialog will stand still and have no way to exit.
So now we start to implement the logic to dismiss our dialog and move the user to the previous screen and if you click on cancel just move the user back to the home screen instead.
The GoRouter is useful when you're in the same context or widget tree, but this is a dialog, so you can't access the GoRouter anymore.
The solution is very simple, you just manipulate the dialog as you do with a normal Navigator object can do and call the go router to route the screen behind.
Here is a sample of the Cancel button
ElevatedButton( onPressed: () { // Close dialog Navigator.of(context).pop(); // Use GoRouter to navigate to home page context.go("/"); }, child: const Text("Cancel"), ),
And also here is a sample code of the OK button
ElevatedButton( onPressed: () { // Check what ever logic if (controller.text == "123") { // Call pop the dialog. // This way you still stay at // where you leave previously Navigator.of(context).pop(); } }, child: const Text("Ok"), ),
Working with GoRouter, helps me to simplify the navigation of each page. Without GoRouter you will be having a hard time keeping references of the navigator key and the BuildContext.
It's the very first article in my life so, so I don't expect to be good but, If you find something helpful with this article, I'm proud of myself that can help everyone. Goodbye at this time, see you in the next article that would be talked about GoRouter with ShellRoute
.