将新页面转移到焦点的默认颤动动画是将其从底部向上滑动。如何更改此行为并从右侧或左侧滑动新页面?
Navigator.push(
context,
new PageRouteBuilder(
pageBuilder: (BuildContext context, _, __) {
return new SearchView();
}
)
);
用 iOS 过渡替换整个屏幕的模态路线。
页面从右侧滑入,反向退出。当另一页进入覆盖该页面时,该页面也会以视差向左移动。
页面从底部滑入,反向退出,全屏对话框无视差效果。
flutter gallery 示例应用程序中有一个演示:
Navigator.of(context, rootNavigator: true).push(
new CupertinoPageRoute<bool>(
fullscreenDialog: true,
builder: (BuildContext context) => new Tab3Dialog(),
),
);
您可以创建一个带有您想要的动画的函数
Route createRoute(Widget page) {
return PageRouteBuilder(
pageBuilder: (context, animation, secondaryAnimation) => page,
transitionsBuilder: (context, animation, secondaryAnimation, child) {
const begin = Offset(1.0, 0.0);
const end = Offset.zero;
const curve = Curves.ease;
var tween = Tween(begin: begin, end: end).chain(CurveTween(curve: curve));
return SlideTransition(
position: animation.drive(tween),
child: child,
);
},
);
}
每次推送到新屏幕时都会调用它
Navigator.of(context).push(createRoute(SearchView()))
如果你想改变方向,你需要改变
begin
的偏移量
如果你想改变效果你需要改变SlideTransition
import 'package:flutter/material.dart';
void main() {
runApp(
const MaterialApp(
home: Page1(),
),
);
}
class Page1 extends StatelessWidget {
const Page1({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(),
body: Center(
child: ElevatedButton(
onPressed: () {
Navigator.of(context).push(_createRoute());
},
child: const Text('Open Page Two'),
),
),
);
}
}
Route _createRoute() {
return PageRouteBuilder(
pageBuilder: (context, animation, secondaryAnimation) => const Page2(),
transitionsBuilder: (context, animation, secondaryAnimation, child) {
const begin = Offset(1.0, 0.0);
const end = Offset.zero;
const curve = Curves.ease;
var tween = Tween(begin: begin, end: end).chain(CurveTween(curve: curve));
return SlideTransition(
position: animation.drive(tween),
child: child,
);
},
);
}
class Page2 extends StatelessWidget {
const Page2({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(),
body: const Center(
child: Text('Hi, This is Page Two! (slided-In from Right)'),
),
);
}
}
这将创建一个带有过渡的两页路由,请参阅此处了解更多信息
Matteo Antolini 答案的修改版本:
import 'package:flutter/material.dart';
class ScreenNavigator {
final BuildContext cx;
ScreenNavigator({
required this.cx,
});
navigate(Widget page, Tween<Offset> tween) {
Navigator.push(
cx,
PageRouteBuilder(
pageBuilder: (context, animation, secondaryAnimation) {
return page;
},
transitionDuration: Durations.long1,
transitionsBuilder: (context, animation, secondaryAnimation, child) {
// create CurveTween
const Curve curve = Curves.ease;
final CurveTween curveTween = CurveTween(curve: curve);
// chain Tween with CurveTween
final Animatable<Offset> chainedTween = tween.chain(curveTween);
final Animation<Offset> offsetAnimation =
animation.drive(chainedTween);
return SlideTransition(position: offsetAnimation, child: child);
},
),
);
}
}
class NavigatorTweens {
static Tween<Offset> bottomToTop() {
const Offset begin = Offset(0.0, 1.0);
const Offset end = Offset(0.0, 0.0);
return Tween(begin: begin, end: end);
}
static Tween<Offset> topToBottom() {
const Offset begin = Offset(0.0, -1.0);
const Offset end = Offset(0.0, 0.0);
return Tween(begin: begin, end: end);
}
static Tween<Offset> leftToRight() {
const Offset begin = Offset(-1.0, 0.0);
const Offset end = Offset(0.0, 0.0);
return Tween(begin: begin, end: end);
}
static Tween<Offset> rightToLeft() {
const Offset begin = Offset(1.0, 0.0);
const Offset end = Offset(0.0, 0.0);
return Tween(begin: begin, end: end);
}
}
您可以将其复制+粘贴到文件中并在您的应用程序中使用它,例如:
onTap: () {
ScreenNavigator(cx: context)
.navigate(Page(),NavigatorTweens.leftToRight());
},
为了更好地理解页面滑动过渡,阅读官方文档