Flutter:如何根据上一页更改页面过渡动画
实现基于侧边栏位置的页面滑动过渡
要实现根据侧边栏导航项上下位置切换对应滑动方向的页面过渡,你可以按照以下步骤修改代码:
1. 定义路由顺序映射
先给每个路由路径分配索引,用来判定页面在侧边栏的上下位置:
final Map<String, int> routeOrder = { '/dash': 0, '/other': 1, '/another': 2, };
2. 自定义页面过渡动画
创建自定义页面构建函数,根据当前页面和目标页面的索引差,返回对应滑动过渡效果的页面:
Page _customTransitionPage(BuildContext context, GoRouterState state, Widget child) { // 获取当前路由与目标路由的索引 final currentIndex = routeOrder[GoRouter.of(context).location] ?? 0; final targetIndex = routeOrder[state.location] ?? 0; // 判断过渡方向:目标索引大于当前 → 向上滑动;反之 → 向下滑动 final isUpward = targetIndex > currentIndex; return CustomTransitionPage( child: child, transitionsBuilder: (context, animation, secondaryAnimation, child) { // 定义滑动动画的偏移参数 const beginUp = Offset(0, 1); const end = Offset(0, 0); final tween = Tween( begin: isUpward ? beginUp : end, end: isUpward ? end : beginUp, ); final offsetAnimation = animation.drive(tween); return SlideTransition( position: offsetAnimation, child: child, ); }, ); }
3. 修改GoRouter配置
将原路由的builder替换为pageBuilder,使用上面定义的自定义过渡函数:
class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp.router( routerConfig: GoRouter( initialLocation: "/dash", routes: [ ShellRoute( builder: (context, state, child) => SideNavBarPage(subPage: child), routes: [ GoRoute( path: '/dash', pageBuilder: (context, state) => _customTransitionPage(context, state, const DashPage()), ), GoRoute( path: '/other', pageBuilder: (context, state) => _customTransitionPage(context, state, const OtherPage()), ), GoRoute( path: '/another', pageBuilder: (context, state) => _customTransitionPage(context, state, const AnotherPage()), ), ], ), ], ), ); } }
4. 保持侧边栏导航逻辑不变
原SideNavBarPage代码无需修改,点击侧边栏项时的context.go会触发路由切换,自动应用对应过渡动画:
class SideNavBarPage extends StatelessWidget { final Widget subPage; const SideNavBarPage({ required this.subPage, super.key, }); @override Widget build(BuildContext context) { return Scaffold( body: Row( children: [ CustomSideNavBar( items: [ CustomSideNavBarItem(onTap: () => context.go("/dash")), CustomSideNavBarItem(onTap: () => context.go("/other")), CustomSideNavBarItem(onTap: () => context.go("/another")), ], ), Expanded(child: subPage), ], ), ); } }
效果说明
- 从
/dash(索引0)切换到/other(索引1)或/another(索引2):页面向上滑动进入 - 从
/another(索引2)切换到/other(索引1)或/dash(索引0):页面向下滑动进入
内容的提问来源于stack exchange,提问作者JakesMD
相关产品推荐
相关产品推荐

