2

Is it possible to create an animation in flutter that doesn't continously change its value, but only with a given time gaps?

I have the following code working right now, but i'm sure there is a better solution out there.

  int aniValue = 0;
  bool lock = false;
  _asyncFunc() async {
    if(lock) return;
    else     lock = true;

    await new Future.delayed(const Duration(milliseconds: 50), () {
      ++aniValue;

      if (aniValue == 41) {
        aniValue = 0;
      }
    });

    lock = false;

    setState(() {});
    _asyncFunc();
  }
3
  • Why do you want to use an animation if you don't want change continuously? Can you please elaborate more on what you actually try to accomplish? Commented Sep 11, 2018 at 17:43
  • I'm working on an application that has an n x m matrix of colored "pixels", and i wan't to refresh all of their colors in every 150ms. Sorry if animations are really out of context, i'm really new in flutter. Commented Sep 11, 2018 at 18:22
  • No, don't worry. Using the animation framework here is the most ideal solution. Commented Sep 11, 2018 at 18:28

1 Answer 1

3

It is possible to define a Curve to animations; to have non-linear progression.

Flutter doesn't provides a "step" curves, but you can make one fairly easily:

class StepCurve extends Curve {
  final int stepCount;

  const StepCurve([this.stepCount = 2]) : assert(stepCount > 1);

  @override
  double transform(double t) {
    final progress = (t * stepCount).truncate();
    return 1 / (stepCount - 1) * progress;
  }
}

You can then freely use it by associating it to a CurveTween:

@override
Widget build(BuildContext context) {
  return AlignTransition(
    alignment: AlignmentGeometryTween(
      begin: Alignment.centerLeft,
      end: Alignment.centerRight,
    )
        .chain(CurveTween(curve: const StepCurve(5)))
        .animate(animationController),
    child: Container(
      color: Colors.red,
      width: 42.0,
      height: 42.0,
    ),
  );
}

enter image description here


Another solution is using TweenSequence.

enter image description here

class TestAnim extends StatefulWidget {
  @override
  _TestAnimState createState() => _TestAnimState();
}

class _TestAnimState extends State<TestAnim>
    with SingleTickerProviderStateMixin {
  AnimationController animationController;

  @override
  void initState() {
    super.initState();
    animationController = AnimationController(
      vsync: this,
      duration: const Duration(seconds: 1),
    )..repeat();
  }

  @override
  Widget build(BuildContext context) {
    final colors = <Color>[
      Colors.red,
      Colors.blue,
      Colors.lime,
      Colors.purple,
    ];

    return DecoratedBoxTransition(
      decoration: TweenSequence(colorsToTween(colors).toList())
          .animate(animationController),
      child: const SizedBox.expand(),
    );
  }
}

Iterable<TweenSequenceItem<Decoration>> colorsToTween(
    List<Color> colors) sync* {
  for (int i = 0; i < colors.length - 1; i++) {
    yield TweenSequenceItem<Decoration>(
      tween: DecorationTween(
        begin: BoxDecoration(color: colors[i]),
        end: BoxDecoration(color: colors[i + 1]),
      ),
      weight: 1.0,
    );
  }
}
Sign up to request clarification or add additional context in comments.

5 Comments

Thanks for your excellent answer, the problem here is that StepCurve has gaps in positons, but i want to have them in time. I mean, the first step would happen after 1s, the second step after another 1s and so on and so forth.
You can convert time to steps. In your example, there are 40 steps for a total duration of 2 seconds.
I noticed Animatables don't have animation value, is there any way to have a counter or current step value here?
I think you want TweenSequence instead
@BenSabo Added an example, go take a look :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.