AnimationController
class AnimationBaseDemo extends StatefulWidget {
@override
_AnimationBaseDemoState createState() => _AnimationBaseDemoState();
}
class _AnimationBaseDemoState extends State<AnimationBaseDemo> {
double _size = 100;
@override
Widget build(BuildContext context) {
return Center(
child: GestureDetector(
onTap: () {
setState(() {
_size = 200;
});
},child: Container(
height: _size,width: _size,color: Colors.blue,alignment: Alignment.center,child: Text('点我变大',style: TextStyle(color: Colors.white,fontSize: 18),),);
}
}
class _AnimationBaseDemoState extends State<AnimationBaseDemo> with SingleTickerProviderStateMixin{
double _size = 100;
AnimationController _controller;
@override
void initState() {
super.initState();
_controller = AnimationController(vsync: this,duration: Duration(milliseconds: 500));
}
...
}
-
vsync:当创建 AnimationController 时,需要传递一个
vsync
参数,存在vsync
时会防止屏幕外动画消耗不必要的资源,单个 AnimationController 的时候使用 SingleTickerProviderStateMixin,多个 AnimationController 使用 TickerProviderStateMixin。
-
duration:表示动画执行的时间。
class _AnimationBaseDemoState extends State<AnimationBaseDemo> with SingleTickerProviderStateMixin{
double _size = 100;
AnimationController _controller;
@override
void initState() {
super.initState();
_controller = AnimationController(vsync: this,duration: Duration(milliseconds: 500));
}
@override
Widget build(BuildContext context) {
return Center(
child: GestureDetector(
onTap: () {
_controller.forward();
},);
}
@override
void dispose() {
super.dispose();
_controller.dispose();
}
}
_controller = AnimationController(vsync: this,duration: Duration(milliseconds: 500))
..addListener(() {
setState(() {
_size = 100+100*_controller.value;
});
});
_controller = AnimationController(vsync: this,duration: Duration(milliseconds: 500),lowerBound: 100,upperBound: 200)
..addListener(() {
setState(() {
_size = _controller.value;
});
})
_controller = AnimationController(
vsync: this,upperBound: 200)
..addStatusListener((status) {
print('status:$status');
})
-
dismissed:动画停止在开始处。
-
forward:动画正在从开始处运行到结束处(正向运行)。
-
reverse:动画正在从结束处运行到开始处(反向运行)。
-
completed:动画停止在结束处。
-
forward:正向执行动画。
-
reverse:反向执行动画。
-
repeat:反复执行动画。
-
reset:重置动画。
_controller = AnimationController(
vsync: this,upperBound: 200)
..addStatusListener((AnimationStatus status) {
if(status == AnimationStatus.completed){
_controller.reverse();
}else if(status == AnimationStatus.dismissed){
_controller.forward();
}
})
..addListener(() {
setState(() {
_size = _controller.value;
});
});
_controller =
AnimationController(vsync: this,duration: Duration(milliseconds: 500))
..addListener(() {
setState(() {
_color = Color.lerp(_startColor,_endColor,_controller.value);
});
});
class TweenDemo extends StatefulWidget {
@override
_TweenDemoState createState() => _TweenDemoState();
}
class _TweenDemoState extends State<TweenDemo>
with SingleTickerProviderStateMixin {
AnimationController _controller;
Color _startColor = Colors.blue;
Color _endColor = Colors.red;
Color _color = Colors.blue;
@override
void initState() {
super.initState();
_controller =
AnimationController(vsync: this,duration: Duration(milliseconds: 500))
..addListener(() {
setState(() {
_color = Color.lerp(_startColor,_controller.value);
});
});
}
@override
Widget build(BuildContext context) {
return Center(
child: GestureDetector(
onTap: () {
_controller.forward();
},child: Container(
height: 100,width: 100,color: _color,child: Text(
'点我变色',);
}
@override
void dispose() {
super.dispose();
_controller.dispose();
}
}
class _TweenDemoState extends State<TweenDemo>
with SingleTickerProviderStateMixin {
AnimationController _controller;
Animation<Color> _animation;
@override
void initState() {
super.initState();
_controller =
AnimationController(vsync: this,duration: Duration(milliseconds: 500))
..addListener(() {
setState(() {});
});
_animation =
ColorTween(begin: Colors.blue,end: Colors.red).animate(_controller);
}
@override
Widget build(BuildContext context) {
return Center(
child: GestureDetector(
onTap: () {
_controller.forward();
},color: _animation.value,);
}
@override
void dispose() {
super.dispose();
_controller.dispose();
}
}
Curve
class CurveDemo extends StatefulWidget {
@override
_CurveDemoState createState() => _CurveDemoState();
}
class _CurveDemoState extends State<CurveDemo>
with SingleTickerProviderStateMixin {
AnimationController _controller;
Animation _animation;
@override
void initState() {
super.initState();
_controller =
AnimationController(vsync: this,duration: Duration(milliseconds: 1000))
..addListener(() {
setState(() {});
});
_animation = Tween(begin: 100.0,end: 200.0)
.chain(CurveTween(curve: Curves.bounceIn))
.animate(_controller);
}
@override
Widget build(BuildContext context) {
return Center(
child: GestureDetector(
onTap: () {
_controller.forward();
},child: Container(
height: _animation.value,width: _animation.value,child: Text(
'点我变大',);
}
@override
void dispose() {
super.dispose();
_controller.dispose();
}
}
_controller =
AnimationController(vsync: this,duration: Duration(milliseconds: 1000),lowerBound: 100.0,upperBound: 200.0)
..addListener(() {
setState(() {});
});
_animation = CurveTween(curve: Curves.bounceIn).animate(_controller);
_controller =
AnimationController(vsync: this,end: 200.0)
.chain(CurveTween(curve: Curves.bounceIn))
.animate(_controller);
那就自定义一个动画曲线
class _StairsCurve extends Curve {
@override
double transformInternal(double t) {
return t;
}
}
class _StairsCurve extends Curve {
//阶梯的数量
final int num;
double _perStairY;
double _perStairX;
_StairsCurve(this.num) {
_perStairY = 1.0 / (num - 1);
_perStairX = 1.0 / num;
}
@override
double transformInternal(double t) {
return _perStairY * (t / _perStairX).floor();
}
}
_animation = Tween(begin: 100.0,end: 200.0)
.chain(CurveTween(curve: _StairsCurve(5)))
.animate(_controller);
总结
AnimationController _controller;
Animation _animation;
@override
void initState() {
super.initState();
_controller =
AnimationController(vsync: this,duration: Duration(milliseconds: 1000))
..addListener(() {
setState(() {});
});
_animation = Tween(begin: 100.0,end: 200.0)
.animate(_controller);
}
_animation = _controller.drive(Tween(begin: 100.0,end: 200.0));
_animation = Tween(begin: 100.0,end: 200.0)
.chain(CurveTween(curve: Curves.linear))
.animate(_controller);
_animation = _controller
.drive(CurveTween(curve: Curves.linear))
.drive(Tween(begin: 100.0,end: 200.0));
_animation = CurveTween(curve: Curves.linear)
.animate(_controller);
_animation = _controller.drive(CurveTween(curve: Curves.linear));
class MultiControllerDemo extends StatefulWidget {
@override
_MultiControllerDemoState createState() => _MultiControllerDemoState();
}
class _MultiControllerDemoState extends State<MultiControllerDemo>
with TickerProviderStateMixin {
AnimationController _sizeController;
AnimationController _colorController;
Animation<double> _sizeAnimation;
Animation<Color> _colorAnimation;
@override
void initState() {
super.initState();
_sizeController =
AnimationController(vsync: this,duration: Duration(milliseconds: 2000))
..addListener(() {
setState(() {});
});
_sizeAnimation = _sizeController
.drive(CurveTween(curve: Curves.linear))
.drive(Tween(begin: 100.0,end: 200.0));
_colorController =
AnimationController(vsync: this,duration: Duration(milliseconds: 1000))
..addListener(() {
setState(() {});
});
_colorAnimation = _colorController
.drive(CurveTween(curve: Curves.bounceIn))
.drive(ColorTween(begin: Colors.blue,end: Colors.red));
}
@override
Widget build(BuildContext context) {
return Center(
child: GestureDetector(
onTap: () {
_sizeController.forward();
_colorController.forward();
},child: Container(
height: _sizeAnimation.value,width: _sizeAnimation.value,color: _colorAnimation.value,child: Text(
'点我变化',);
}
@override
void dispose() {
super.dispose();
_sizeController.dispose();
_colorController.dispose();
}
}
- AnimationController:动画控制器,控制动画的播放、停止等。继承自Animation< double >,是一个特殊的Animation对象,默认情况下它会线性的生成一个0.0到1.0的值,类型只能是 double 类型,不设置动画曲线的情况下,可以设置输出的最小值和最大值。
- Curve:动画曲线,作用和Android中的Interpolator(差值器)类似,负责控制动画变化的速率,通俗地讲就是使动画的效果能够以匀速、加速、减速、抛物线等各种速率变化。
- Tween:将 AnimationController 生成的 [0,1]值映射成其他属性的值,比如颜色、样式等。
- 创建 AnimationController 。
- 如果需要 Tween 或者 Curve,将 AnimationController 与其关联,Tween 和 Curve 并不是必须的,当然大部分情况都需要。
- 将动画值作用于组件,当没有Tween 和 Curve 时,动画值来源于AnimationController,如果有 Tween 和 Curve,动画值来源于 Tween 或者Curve 的 Animation。