zl程序教程

您现在的位置是:首页 >  工具

当前栏目

Flutter入门:动画相关

2023-09-27 14:25:58 时间
动画

在flutter中 如果想让某个widget执行动画 需要用一个动画类的widget封装一下 比如一个图片


Center(

 child: Image.asset(xxxxxx),

复制代码


想实现透明度动画 使用FadeTransition 如下


Center(

 child: FadeTransition(

 opacity: _speakAnimation,

 child: Image.asset(R.assetsLiveSpeak),

复制代码


关键是opacity 是一个Animation 要想实现一个动画 还需要一个Tween和一个AnimationController。

Tween就是Animation。Tween还需要一个AnimationController 他们的创建及定义如下


class _XXX extends State XXXX with SingleTickerProviderStateMixin{

 AnimationController _speakController;

 Animation _speakAnimation;

 override

 void initState() {

 super.initState();

 _speakController AnimationController(

 vsync: this,

 duration: Duration(seconds: 2),

 _speakAnimation Tween(

 begin: 1.0,

 end: 0.0,

 ).animate(_speakController);

 _speakAnimation.addStatusListener((status) { //监听动画

 if(status AnimationStatus.completed){

 //todo

复制代码


可以看到Tween定义的是动画的起始和结束状态 这里就是透明度的值 。而AnimationController主要是定义时长。

另外Tween可以添加动画监听 addStatusListener 一共有四种状态


enum AnimationStatus {

 /// The animation is stopped at the beginning.

 dismissed,

 /// The animation is running from beginning to end.

 forward,

 /// The animation is running backwards, from end to beginning.

 reverse,

 /// The animation is stopped at the end.

 completed,

复制代码


但是这样还差最后一步 启动动画 因为我们需求是页面一展示即播放 所以在build函数中forward一下即可 当然还可以在其他时机播放 代码如下


class _XXX extends State XXXX with SingleTickerProviderStateMixin{

 AnimationController _speakController;

 Animation _speakAnimation;

 override

 void initState() {

 super.initState();

 _speakController AnimationController(

 vsync: this,

 duration: Duration(seconds: 2),

 _speakAnimation Tween(

 begin: 1.0,

 end: 0.0,

 ).animate(_speakController);

 _speakAnimation.addStatusListener((status) {

 if(status AnimationStatus.completed){

 //todo

 Widget build(BuildContext context) {

 _speakController.forward(); //播放动画

 return Stack(

 children: Widget [

 Center(

 child: FadeTransition(

 opacity: _speakAnimation,

 child: Image.asset(R.assetsLiveSpeak),

复制代码


动画卡顿

从今天的一个需求说起吧 实现一个按钮呼吸效果 很简单 就是使用一个缩放动画即可 如下


class _xxx extends State xxx with SingleTickerProviderStateMixin{

 AnimationController _animationController;

 Animation _animation;

 override

 void initState() {

 super.initState();

 _animationController AnimationController(

 vsync: this,

 duration: Duration(milliseconds: 800),

 _animation Tween(

 begin: 0.8,

 end: 1.0,

 ).animate(_animationController);

 override

 void dispose() {

 _animationController.dispose();

 super.dispose();

 override

 Widget build(BuildContext context) {

 _animationController.repeat(reverse: true);

 return Stack(

 alignment: Alignment.center,

 children: [

 Column(

 children: [

 ScaleTransition(

 scale: _animation,

 child: TextButton(

 onPressed: widget.onOpen,

 child: Container(

 width: 120,

 height: 60,

 padding: EdgeInsets.only(bottom: 8),

 alignment: Alignment.center,

 decoration: BoxDecoration(

 image: DecorationImage(

 image: AssetImage(R.assetsLiveRedPackageBtn)

 child: Text(

 领取 ,

 style: TextStyle(

 fontSize: 22,

 fontWeight: FontWeight.bold,

 color: Color(0xFFB34D35)

复制代码


动画效果是从0.8倍扩大到1.0 然后reverse 一直repeat即可。

但是运行后发现动画出现了异常 动画扩大到1.0后会快速小幅度缩放一次 然后才会还原到0.8 这明显不是我们想要的动画效果 后来我们尝试了其他动画 都有类似的效果。

但是在其他页面上的动画就不会出问题 所以最后排查发现是该页面的定时器影响到了动画。

这个页面里有一个倒计时 通过Timer来更新其中倒计时的文字 而更新使用了setState进行重绘 这样在动画执行到1秒的时候 扩大到1.0又缩回一点的时候 倒计时更新了 由于是setState 所以动画widget也重绘了 这样又变回1.0大小了 然后才缩回0.8


解决方法就是新增一个StatefulWidget类 将Timer和倒计时相关的组件放到这个类中实现 这样倒计时更新只会刷新这一部分 不会刷新动画组件 如下


class TimerText extends StatefulWidget{

 int time;

 TimerText(this.time);

 override

 State StatefulWidget createState() {

 return _TimerText();

class _TimerText extends State TimerText {

 Timer timer;

 override

 void initState() {

 super.initState();

 timer Timer.periodic(Duration(seconds: 1), (timer) {

 setState(() {

 if(widget.time 0){

 timer.cancel();

 else{

 widget.time--;

 override

 void dispose() {

 timer.cancel();

 super.dispose();

 override

 Widget build(BuildContext context) {

 return Text(

 ${widget.time}s ,

 style: TextStyle(

 fontSize: 14,

 color: Color(0xFFF9D873)

}



Flutter小球弹跳动画 Flutter 的动画系统可以帮助开发者实现生动的游戏效果,例如物理效果、平移动画、旋转动画等等。以下是一个使用 Flutter 动画系统实现小球弹跳的示例代码
Flutter常用的几种动画 Flutter 的动画系统可以帮助开发者创建流畅、生动的用户界面。下面是一些关于 Flutter 动画的详细介绍和示例代码。