flutter 路由
本文最后更新于:2022年4月22日 上午
flutter 路由
flutter
中的路由和 vue
中的路由有些类似,也是通过路由配置表的方式来进行设置
在 flutter
中,路由的转场动画默认为ios
端路由跳转是从右向左进入页面,android
端是从底部滑到顶部的方式进入页面
配置项目路由
routes
路由配置表onGenerateRoute
类似于vue
中的全局导航守卫,路由跳转时的钩子onUnknownRoute
找不到路由时的钩子,一般跳转到404
页面
main() => runApp(MyApp());
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
debugShowCheckedModeBanner: false,
initialRoute: AppRouterName.INIT_PAGE,
routes: appRouter,
home: HomePage(),
// 自定义返回,类似于导航守卫
onGenerateRoute: (settings) {
print('settings: $settings');
switch (settings.name) {
case '/goodsDetail':
return MaterialPageRoute(
builder: (ctx) => DetailPage(),
);
}
},
// 404 路由
onUnknownRoute: (setting) => MaterialPageRoute(builder: (ctx) => UnknownPage()),
);
}
}
路由配置文件
import 'package:flutter/material.dart';
import '../pages/home.dart';
import '../pages/about.dart';
import '../pages/detail.dart';
class AppRouterName {
static const INIT_PAGE = '/home';
static const home = '/home';
static const detail = '/home/detail';
static const about = '/about';
}
final Map<String, WidgetBuilder> appRouter = {
AppRouterName.home: (ctx) => HomePage(),
AppRouterName.detail: (ctx) => DetailPage(),
AppRouterName.about: (ctx) => AboutPage(),
};
路由跳转
跳转的方式最主要有两种,一种是命名路由(vue
和react
的编程跳转都是这种),一种是匿名路由
命名路由方式跳转
通过 Navigator.of(context).pushNamed('/goodsDetail');
进行跳转
ElevatedButton(
onPressed: () {
Navigator.of(context).pushNamed('/home/detail');
},
child: Text('跳转到详情页'),
)
匿名路由方式跳转
Navigator.of(context).push()
进行跳转
onPressed: () {
Navigator.of(context).push(MaterialPageRoute(builder: (context) {
return DetailPage();
}));
},
child: Text('进入详情'),
),
返回页面
返回前一页的方式很简单
Navigator.of(context).pop();
跳转时传入参数
匿名路由传参
ElevatedButton(
onPressed: () {
Navigator.of(context).pushNamed('/home/detail', arguments: {"id": '3306'});
},
child: Text('跳转到详情页'),
)
匿名路由传参
Navigator.of(context).push(MaterialPageRoute(
builder: (context) => DetailPage(),
settings: RouteSettings(arguments: {'id': '8000'}),
));
接收
通过 ModalRoute.of(context)!.settings.argements
进行接收
@override
Widget build(BuildContext context) {
final params = ModalRoute.of(context)!.settings.arguments as Map<String, String>;
return Text('详情页 商品id:${params['id']}');
}
跳转时接收返回的参数
flutter
在跳转到某个页面后,可以接收这个页面携带回来的一些参数,使用方式也很简单
接收返回的参数
ElevatedButton(
onPressed: () async {
// 命名路由跳转传参,可以等待返回的结果
final res = await Navigator.of(context).pushNamed(AppRouterName.detail);
print('接收到的结果 $res'); // 用户已操作完毕
},
child: Text('进入详情'),
),
返回时传入参数
Navigator.of(context).pop('用户已操作完毕');
监听页面返回
使用 Scaffold
创建的页面左上角默认有一个返回按钮,点击就可以返回,如果需要监听这个返回有以下两种方式
方式一、WillPopScope
- 将其包裹在
Scaffold
外层 onWillPop
方法返回一个通过Futrue
包装的flase
- 在
onWillPop
手动执行Navigator.of(context).pop()
import 'package:flutter/material.dart';
class DetailPage extends StatelessWidget {
const DetailPage({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
final params = ModalRoute.of(context)!.settings.arguments as Map<String, String>;
// 捕捉返回事件
return WillPopScope(
onWillPop: () async {
Navigator.of(context).pop('用户已操作完毕');
return false;
},
child: Scaffold(
appBar: AppBar(title: Text('详情页')),
body: Container(
child: Text('详情页 商品id:${params['id']}'),
),
),
);
}
}
方式二、leading
覆盖 AppBar
中的默认 leading
属性,传入一个空的 Container
Navigator 2.0
还新增了一些新的 api
,但以上这些基本就够项目使用了
本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议,转载请注明出处。