iT邦幫忙

2021 iThome 鐵人賽

DAY 25
0
Modern Web

Flutter web 的奇妙冒險系列 第 25

Day 25 | Flutter 路由管理套件 - auto_route

Navigator 1.0

Flutter 有內建一個路由管理 API Navigator ,而Flutter也在今年發表了 Navigator 2.0 但因為工作上是使用 fluro 這個路由管理套件,所以就沒特別研究了 Navigator 2.0,只能大概說明一下 Navigator 1.0

用起來算是很簡單,我們可以直接用 Navigator.push 裡面會就放我們要打開的新頁面。

Navigator.push( 
      context,
      MaterialPageRoute(builder: (context) {
        return NewRoute();
      }),
    );

但為了方便管理通常都會使用命名路由的方式,然後將原本的 home: 換成 '/': (context) => const MyHomePage()

 MaterialApp(
      routes: {
        '/': (context) => const MyHomePage(),
        'users_list': (context) => const UsersListPage(),
      },
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
    );

如果要到另外一個頁面就是使用 Navigator.pushNamed

Navigator.pushNamed(context, 'users_list');

但對於一些動態路由或者需要傳參數的頁面就會有點麻煩,所以大部分都會使用路由管理套件,雖然工作上是使用 fluro但架設起來也是有點龐大,所以就決定試玩一下另外一個套件 auto_route

auto_route

dependencies:
	auto_route: ^2.4.2
dev_dependencies:
	auto_route_generator: ^2.4.1

先建立另外一個檔案 router.dart

import 'package:auto_route/auto_route.dart';
import 'package:flutter_rest_api_playground/view/users/users_detail_page.dart';
import 'package:flutter_rest_api_playground/view/users/users_list_page.dart';

import '../main.dart';

@MaterialAutoRouter(
  replaceInRouteName: 'Page,Route',
  routes: <AutoRoute>[
    AutoRoute(page: MyHomePage, path: '/', initial: true),
    AutoRoute(page: UsersListPage, path: '/users'),
    AutoRoute(page: UserDetailPage, path: '/user/:id'),
  ],
)
class $AppRouter {}

註冊路由就是會用 AutoRoute 裡面頁面以及路由,首頁的話就加上 initial: true ,而如果需要動態路由就可以 : 來標示,整體看起來跟網頁很像。

replaceInRouteName 則是將我們的所註冊的頁面輸出成另外一個名字避免混淆,這樣讓我們 push 時就會是使用 UsersListRoute 而不是 UsersListPage

因為auto_run會需要使用 codegen 所以一樣要跑 build_runner。

使用時就將 MaterialApp 改為 MaterialApp.router ,然後實例化 AppRouter

class MyApp extends StatelessWidget {
  MyApp({Key? key}) : super(key: key);
  final _appRouter = AppRouter();

  @override
  Widget build(BuildContext context) {
    return MaterialApp.router(
      routerDelegate: AutoRouterDelegate(_appRouter),
      routeInformationParser: _appRouter.defaultRouteParser(),
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
    );
	}
}

要導轉頁面時也算蠻簡單的:

AutoRouter.of(context).pushNamed('/users');

AutoRouter.of(context).push(UsersListRoute());

可以選擇要直接使用註冊的 path 或者是 codegen出來的 xxxxxRoute

而需要接收參數的頁面的宣告也很直觀

class UserDetailPage extends StatefulWidget {
  const UserDetailPage({Key? key, @PathParam('id') required this.userId})
      : super(key: key);
  final String userId;
  @override
  State<UserDetailPage> createState() => _UserDetailPageState();
}

加上 @PathParam 即可, () 放我們在註冊時的 : 的命名,所以以這個例子來說就是使用

@PathParam('id') 並把傳給 userId

使用上就直接在字串中加入我們的變數或者使用 UserDetailRoute 裡面傳參數

AutoRouter.of(context).pushNamed('/user/${userInfo.id}');
AutoRouter.of(context).push(UserDetailRoute(userId: userInfo.id.toString()));

寫到今天突然發現好像快沒有東西可以寫了, 明天可能會試著玩玩其他狀態管理框架。


今天的程式碼:
https://github.com/zxc469469/flutter_rest_api_playground/tree/Day25

參考資料:

  1. https://book.flutterchina.club/chapter2/flutter_router.html#_2-4-1-一个简单示例

上一篇
Day 24 | 在flutter 中串接 restful api - MobX的非同步操作
下一篇
Day 26 | 共享 MobX store with get_it
系列文
Flutter web 的奇妙冒險30

尚未有邦友留言

立即登入留言