Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Any tips for reducing lag when running multiple animations at the same time?

Once my app reaches ~4+ animations running concurrently, the animations start to lag a little. Are there any ways I could fix/optimize that? I am using ObjectAnimator and ValueAnimator.

like image 778
Asd Avatar asked Jul 07 '15 01:07

Asd


1 Answers

So, if the views are not having to redraw themselves during the animations, you can enable hardware layers during the duration of the animations. For instance:

final View myView = // your view
Animator animator = ObjectAnimator.ofFloat(myView, View.ALPHA, 0f, 1f);
animator.setDuration(1000);
animator.addAnimatorListener(new Animator.AnimatorListener() {
    @Override
    public void onAnimationStart(Animator animator) {
        myView.setLayerType(View.LAYER_TYPE_HARDWARE, null);
    }

    @Override
    public void onAnimationCancel(Animator animator) {
        myView.setLayerType(View.LAYER_TYPE_NONE, null);
    }

    @Override
    public void onAnimationEnd(Animator animator) {
        // See http://stackoverflow.com/a/19615205/321697
        myView.post(new Runnable() {
            @Override
            public void run() {
                myView.setLayerType(View.LAYER_TYPE_NONE, null);
            }
        }
    }
}
animator.start();

I'd suggest breaking that listener implementation out into a separate class, but the general idea is that you want to put the view into a hardware backed layer as soon as the animation starts (animation properties such as translation, rotation, scale, and alpha are incredibly cheap when backed by a hardware layer) and then clear the layer once the animation is complete.

In the onAnimationEnd callback, you'll notice a link to another answer where there's a bug with 4.0.x if you set the layer type to none in the onAnimationEnd callback. If you're only supporting 4.1 and above, the runnable indirection shouldn't be necessary.

EDIT: If you're animating a color transition, you probably don't want to do the above, as changing the color of the view will require it to be redrawn, causing it to rebuild the hardware layer on each frame.

like image 51
Kevin Coppock Avatar answered Oct 31 '22 01:10

Kevin Coppock