Flutter_学习记录_动画的简单了解

AnimationController简单实现如下的效果图:

1. 只用AnimationController实现简单动画

1.1 完整代码案例

dart 复制代码
import 'package:flutter/material.dart';

class AnimationDemo extends StatefulWidget {
  const AnimationDemo({super.key});

  @override
  State<AnimationDemo> createState() => _AnimationDemoState();
}

class _AnimationDemoState extends State<AnimationDemo> with TickerProviderStateMixin {

  late AnimationController animationDemoController;
  @override
  void initState() {
    super.initState();

    animationDemoController = AnimationController(
      vsync: this,
      // 初始值,要在 lowerBound 和 upperBound 之间
      value: 32.0,
      // 最小值
      lowerBound: 32.0,
      // 最大值
      upperBound: 100.0,
      // 设置动画的时间
      duration: Duration(milliseconds: 3000)
    );

    animationDemoController.addListener((){
      // 更新页面
      setState(() {
        
      });
    });

    // 添加status的监听
    animationDemoController.addStatusListener((AnimationStatus status){
      print(status);
    });
  }

  @override
  void dispose() {
    super.dispose();
    // 销毁 animationDemoController
    animationDemoController.dispose();
  }


  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text("AnimationDemo"),
      ),
      body: Center(
        child: IconButton(
          icon: Icon(Icons.favorite),
          iconSize: animationDemoController.value,
          onPressed: (){
            switch (animationDemoController.status) {
              case AnimationStatus.completed:
                // 反转动画
                animationDemoController.reverse();
                break;
              default:
                // 开始动画
                animationDemoController.forward();
            }
          },
        ),
      ),
    );
  }
}

1.2 代码说明

(1) AnimationController

  • animationDemoController 是动画的核心控制器。
  • duration 定义了动画的持续时间(例如 2 秒)。
  • vsync 参数确保动画与屏幕刷新同步,避免资源浪费。
  • value 设置初始值。
  • lowerBound 设置最小值。
  • upperBound 设置 最大值。

(2) addListener 添加监听,可以监听到 animationDemoController.value的值的变化。

  • 如果需要需要用到 animationDemoController.value的值更新UI,则需要调用 setState的方法。
dart 复制代码
animationDemoController.addListener((){
      // 更新页面
      setState(() {
        
      });
    });

(3)addStatusListener 添加动画状态的监听,只有添加了这个监听,才能在后面获取到动画状态的变化。

dart 复制代码
            switch (animationDemoController.status) {
              case AnimationStatus.completed:
                // 反转动画
                animationDemoController.reverse();
                break;
              default:
                // 开始动画
                animationDemoController.forward();
            }

(4) 开始动画

dart 复制代码
animationDemoController.forward()

(5)反转动画

dart 复制代码
animationDemoController.reverse();

2. 用AnimationControllerAnimation实现简单动画

2.1 完整代码示例

dart 复制代码
import 'package:flutter/material.dart';

class AnimationDemo extends StatefulWidget {
  const AnimationDemo({super.key});

  @override
  State<AnimationDemo> createState() => _AnimationDemoState();
}

class _AnimationDemoState extends State<AnimationDemo> with TickerProviderStateMixin {

  late AnimationController animationDemoController;
  late Animation animation;
  late Animation animationColor;
  // 设置动画取消
  late CurvedAnimation curve;

  @override
  void initState() {
    super.initState();

    animationDemoController = AnimationController(
      vsync: this,
      // 设置动画的时间
      duration: Duration(milliseconds: 3000)
    );

    animation = Tween(begin: 32.0, end: 100.0).animate(animationDemoController);
    animationColor = ColorTween(begin: Colors.red, end: Colors.green).animate(animationDemoController);

    animationDemoController.addListener((){
      // 更新页面
      setState(() {
        
      });
    });

    // 添加status的监听
    animationDemoController.addStatusListener((AnimationStatus status){
      print(status);
    });
  }

  @override
  void dispose() {
    super.dispose();
    // 销毁 animationDemoController
    animationDemoController.dispose();
  }


  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text("AnimationDemo"),
      ),
      body: Center(
        child: IconButton(
          icon: Icon(Icons.favorite),
          iconSize: animation.value,
          color: animationColor.value,
          onPressed: (){
            switch (animationDemoController.status) {
              case AnimationStatus.completed:
                // 反转动画
                animationDemoController.reverse();
                break;
              default:
                // 开始动画
                animationDemoController.forward();
            }
          },
        ),
      ),
    );
  }
}

2.2 代码说明

(1) Tween

  • Tween(begin: xx, end:xx) 定义了动画的范围:
  • begin 是起始值。
  • end 是结束值。

(2) animationDemoController.value animation.value 来替代

3. 用AnimationControllerAnimationCurvedAnimation实现简单动画

CurvedAnimation 可以添加缓动效果(如 Curves.easeInOut),完整代码示例:

dart 复制代码
import 'package:flutter/material.dart';

class AnimationDemo extends StatefulWidget {
  const AnimationDemo({super.key});

  @override
  State<AnimationDemo> createState() => _AnimationDemoState();
}

class _AnimationDemoState extends State<AnimationDemo> with TickerProviderStateMixin {

  late AnimationController animationDemoController;
  late Animation animation;
  late Animation animationColor;
  // 设置动画曲线
  late CurvedAnimation curve;

  @override
  void initState() {
    super.initState();

    animationDemoController = AnimationController(
      vsync: this,
      // 设置动画的时间
      duration: Duration(milliseconds: 3000)
    );

    curve = CurvedAnimation(parent: animationDemoController, curve: Curves.bounceOut);
    animation = Tween(begin: 32.0, end: 100.0).animate(curve);
    animationColor = ColorTween(begin: Colors.green, end: Colors.red).animate(curve);

    animationDemoController.addListener((){
      // 更新页面
      setState(() {
        
      });
    });

    // 添加status的监听
    animationDemoController.addStatusListener((AnimationStatus status){
      print(status);
    });
  }

  @override
  void dispose() {
    super.dispose();
    // 销毁 animationDemoController
    animationDemoController.dispose();
  }


  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text("AnimationDemo"),
      ),
      body: Center(
        child: IconButton(
          icon: Icon(Icons.favorite),
          iconSize: animation.value,
          color: animationColor.value,
          onPressed: (){
            switch (animationDemoController.status) {
              case AnimationStatus.completed:
                // 反转动画
                animationDemoController.reverse();
                break;
              default:
                // 开始动画
                animationDemoController.forward();
            }
          },
        ),
      ),
    );
  }
}

4 用AnimationControllerAnimatedWidget实现简单动画

完整代码实例:

dart 复制代码
import 'package:flutter/material.dart';

class AnimationDemo extends StatefulWidget {
  const AnimationDemo({super.key});

  @override
  State<AnimationDemo> createState() => _AnimationDemoState();
}

class _AnimationDemoState extends State<AnimationDemo> with TickerProviderStateMixin {

  late AnimationController animationDemoController;
  late Animation animation;
  late Animation animationColor;
  // 设置动画曲线
  late CurvedAnimation curve;

  @override
  void initState() {
    super.initState();

    animationDemoController = AnimationController(
      vsync: this,
      // 设置动画的时间
      duration: Duration(milliseconds: 3000)
    );

    curve = CurvedAnimation(parent: animationDemoController, curve: Curves.bounceOut);
    animation = Tween(begin: 32.0, end: 100.0).animate(curve);
    animationColor = ColorTween(begin: Colors.green, end: Colors.red).animate(curve);

    // 添加status的监听
    animationDemoController.addStatusListener((AnimationStatus status){
      print(status);
    });
  }

  @override
  void dispose() {
    super.dispose();
    // 销毁 animationDemoController
    animationDemoController.dispose();
  }


  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text("AnimationDemo"),
      ),
      body: Center(
      	//  AnimationHeart 是基于 AnimatedWidget 创建的
        child: AnimationHeart(
          animations: [animation, animationColor], 
          controller: animationDemoController
        ),
      ),
    );
  }
}

// 基于 AnimatedWidget 创建 AnimationHeart的控件
class AnimationHeart extends AnimatedWidget {

  final List animations;
  final AnimationController controller;

  const AnimationHeart({
    super.key, 
    required this.animations, 
    required this.controller
  }) : super(listenable: controller);

  @override
  Widget build(BuildContext context) {
    return IconButton(
      icon: Icon(Icons.favorite),
      iconSize: animations[0].value,
      color: animations[1].value,
      onPressed: (){
        switch (controller.status) {
          case AnimationStatus.completed:
            // 反转动画
            controller.reverse();
            break;
          default:
            // 开始动画
            controller.forward();
        }
      },
    );
  }
}
相关推荐
qziovv12 小时前
前端转flutter——项目架构、初始化
前端·flutter
恋猫de小郭15 小时前
Flutter 3.47 首坑,analysis_options 问题连环回归
android·前端·flutter
xiangxiongfly91516 小时前
Flutter flutter_gen_runner总结
flutter·flutter_gen
GitLqr1 天前
Flutter 3.47 与 Dart 3.13:你必须了解的迁移指南
flutter·ios·dart
程序员老刘1 天前
跨平台开发地图 | 2026年8月
flutter·ai编程·客户端
杉氧2 天前
Flutter 跨平台多端适配与 Android/iOS 一键自动化打包发布
android·前端·flutter
恋猫de小郭2 天前
Dart 3.13 大更新,感觉比 Flutter 更带劲
android·前端·flutter
静水流深zz3 天前
Flutter AI Harness 如何让 Agent 参与软件开发全流程
android·前端·人工智能·flutter·大前端
SoaringHeart3 天前
Flutter最佳实践:Web项目中文字体首次加载乱码问题解决
前端·flutter
程序员老刘3 天前
Flutter 3.47 更新要点:Material 正式分家,老项目先别急着更新
flutter·ai编程·客户端