【问题标题】:Flutter animation how to fade in/out gradually颤动动画如何逐渐淡入/淡出
【发布时间】:2018-03-10 14:05:07
【问题描述】:

我开始使用 Flutter 并尝试制作一个在不断淡入淡出的同时旋转的动画。到目前为止,旋转有效,但我在褪色效果方面遇到了困难。小部件将逐渐变得透明,但在旋转一圈后,它会跳回不透明状态,然后再次变为透明。我正在尝试解决这个问题,但我似乎不知道如何解决。使用.forward().reverse() 不起作用,但我可能错误地实现了不透明动画。

class AnimatedLoader extends AnimatedWidget {
  static final _opacityTween = new Tween<double>(begin: 1.0, end: 0.3);

  AnimatedLoader({
    Key key,
    this.alignment: FractionalOffset.center,
    Animation<double> turns,
    Animation<double> animation,
    this.child,
  }) : super(key: key, listenable: turns);

  Animation<double> get turns => listenable;

  final FractionalOffset alignment;
  final Widget child;

  @override
  Widget build(BuildContext context) {
    final Animation<double> animation = listenable;
    final double turnsValue = turns.value;
    final Matrix4 transform = new Matrix4.rotationZ(turnsValue * math.PI * 2.0);
    return new Transform(
      alignment: alignment,
      transform: transform,
      child: new Opacity(
        opacity: _opacityTween.evaluate(animation),
        child: child,
      )
    );
  }
}

class AppLoader extends StatefulWidget {
  AppLoaderState createState() => new AppLoaderState();
}

class AppLoaderState extends State<AppLoader> with TickerProviderStateMixin {
  AnimationController _controller;
  AnimationController _controllerOp;
  Animation<double> animation;

  @override initState(){
    super.initState();
    _controller = new AnimationController(
      duration: const Duration(milliseconds: 1500),
      vsync: this,
    )..repeat();

    _controllerOp = new AnimationController(
      duration: const Duration(milliseconds: 800),
      vsync: this,
    );
    animation = new Tween(begin: 0.0, end: 300.0).animate(_controllerOp);

    animation.addStatusListener((status) {
      if (status == AnimationStatus.completed) {
        _controllerOp.reverse();
      } else if (status == AnimationStatus.dismissed) {
        _controllerOp.forward();
      }
    });
    _controllerOp.forward();
  }

  @override
  Widget build(BuildContext context) {
    return new Center (
      child: new AnimatedLoader(
        turns: _controller,
        alignment: FractionalOffset.center,
        animation: _controllerOp,
        child: new Container(
          margin: new EdgeInsets.symmetric(vertical: 10.0),
          height: 150.0,
          width: 150.0,
          child: new FlutterLogo(),
        )
      ),
    );
  }

抱歉,我的代码太长了,我不确定我可能在哪个部分犯了错误。

【问题讨论】:

  • 您可以尝试使用 AnimatedOpacity 代替 Opacity 吗?只是一个想法:)

标签: dart flutter


【解决方案1】:

我认为你在正确的轨道上,但你应该只使用一个 AnimationController 每个 AnimatedWidget。我修复了您代码中的一些错误。

import 'package:flutter/material.dart';
import 'dart:math' as math;

void main() {
  runApp(new MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return new MaterialApp(
      home: new MyHomePage(),
    );
  }
}

class MyHomePage extends StatelessWidget {
  Widget build(BuildContext context) {
    return new Scaffold(
      body: new AppLoader(),
    );
  }
}

class PulsateCurve extends Curve {
  @override
  double transform(double t) {
    if (t == 0 || t == 1)
      return 0.3;
    return math.sin(t * math.PI) * 0.35 + 0.65;
  }
}

class AnimatedLoader extends AnimatedWidget {
  static final _opacityTween = new CurveTween(curve: new PulsateCurve());

  AnimatedLoader({
    Key key,
    this.alignment: FractionalOffset.center,
    Animation<double> animation,
    this.child,
  }) : super(key: key, listenable: animation);

  final FractionalOffset alignment;
  final Widget child;

  @override
  Widget build(BuildContext context) {
    final Animation<double> animation = listenable;
    final Matrix4 transform = new Matrix4.rotationZ(animation.value * math.PI * 2.0);
    return new Transform(
        alignment: alignment,
        transform: transform,
        child: new Opacity(
          opacity: _opacityTween.evaluate(animation),
          child: child,
        )
    );
  }
}

class AppLoader extends StatefulWidget {
  AppLoaderState createState() => new AppLoaderState();
}

class AppLoaderState extends State<AppLoader> with TickerProviderStateMixin {
  AnimationController _controller;

  @override initState() {
    super.initState();
    _controller = new AnimationController(
      duration: const Duration(milliseconds: 1500),
      vsync: this,
    )..repeat();
  }

  @override
  Widget build(BuildContext context) {
    return new Center (
      child: new AnimatedLoader(
          animation: _controller,
          alignment: FractionalOffset.center,
          child: new Container(
            margin: new EdgeInsets.symmetric(vertical: 10.0),
            height: 150.0,
            width: 150.0,
            child: new FlutterLogo(),
          )
      ),
    );
  }
}

【讨论】:

    猜你喜欢
    • 2014-01-20
    • 2012-12-18
    • 2019-02-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-11-14
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多