web-dev-qa-db-fra.com

Animation Android l'un après l'autre

J'ai deux TranslateAnimations sur un TextView et je veux qu'ils s'exécutent les uns après les autres. Cependant, en utilisant le code ci-dessous, seul le second est exécuté.

Comment puis-je résoudre ça?

TranslateAnimation animation = new TranslateAnimation(
    Animation.ABSOLUTE, 0.0f, Animation.ABSOLUTE, 0.0f,
    Animation.ABSOLUTE, 0.0f, Animation.ABSOLUTE, -150.0f);
animation.setDuration(200);
wave.startAnimation(animation);

TranslateAnimation animation1 = new TranslateAnimation(
    Animation.ABSOLUTE, 0.0f, Animation.ABSOLUTE, 0.0f,
    Animation.ABSOLUTE, 150.0f, Animation.ABSOLUTE, 0.0f);
animation1.setDuration(200);
wave.startAnimation(animation1);
18
amithgc

EDIT: Andy Boots réponse ci-dessous est la meilleure réponse imo.


Définissez simplement votre première comme ceci et cela démarrera l’autre, une fois l’animation terminée:

animation.setAnimationListener(new AnimationListener() {

        @Override
        public void onAnimationStart(Animation animation) {
            // TODO Auto-generated method stub

        }

        @Override
        public void onAnimationRepeat(Animation animation) {
            // TODO Auto-generated method stub

        }

        @Override
        public void onAnimationEnd(Animation animation) {
            wave.startAnimation(animation1);

        }
    });

edit: la seule raison pour laquelle votre seconde animation est exécutée avec votre code actuel, c'est parce qu'elle annule le jeu de la première animation (les deux sont réellement joués, mais vous ne voyez que la dernière pour commencer). Si vous faites comme je l'ai écrit, ils joueront de manière séquentielle plutôt qu'en parallèle.

32
pgsandstrom

Liez-les ensemble avec Animation Set

AnimationSet as = new AnimationSet(true)
TranslateAnimation animation = new TranslateAnimation(
Animation.ABSOLUTE, 0.0f, Animation.ABSOLUTE, 0.0f,
Animation.ABSOLUTE, 0.0f, Animation.ABSOLUTE, -150.0f);
animation.setDuration(200);
as.addAnimation(animation);

TranslateAnimation animation1 = new TranslateAnimation(
Animation.ABSOLUTE, 0.0f, Animation.ABSOLUTE, 0.0f,
Animation.ABSOLUTE, 150.0f, Animation.ABSOLUTE, 0.0f);
animation1.setDuration(200);
animation1.setStartOffset(200);
as.addAnimation(animation1);

wave.startAnimation(as);
52
andy boot

vous pouvez aussi le faire par XML lui-même en utilisant l'attribut Android:startOffset, et voici un exemple:

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:Android="http://schemas.Android.com/apk/res/Android">
    <scale
        Android:duration="300"
        Android:fromXScale="0%"
        Android:fromYScale="0%"
        Android:pivotX="50%"
        Android:pivotY="50%"
        Android:toXScale="100%"
        Android:toYScale="100%" />
    <alpha
        Android:duration="300"
        Android:fromAlpha="0"
        Android:toAlpha=".5" />
    <alpha
        Android:duration="300"
        Android:fromAlpha=".5"
        Android:startOffset="300"
        Android:toAlpha="1" />

</set>
9
Shqear

Il existe une autre approche pour atteindre cet objectif qui peut être utile lorsque vous devez animer de nombreuses vues les unes après les autres. Vous pouvez utiliser la méthode setStartOffset pour définir un délai avant le début de l'animation. Donc, si vous savez combien de temps il faudra pour que votre première animation se termine, vous pouvez définir cela comme un délai pour votre deuxième animation. Voici un exemple où j'ai animé six ImageButtons et six TextViews dessous les uns après les autres:

public void animateButtons() {
    // An array of buttons
    int[] imageButtonIds = {R.id.searchButton, R.id.favoriteButton, R.id.responseButton, R.id.articleButton, R.id.resumeButton, R.id.subscribeButton};
    // Array of textViews
    int[] textViewIds = {R.id.searchTextView, R.id.favoriteTextView, R.id.responseTextView, R.id.articleTextView, R.id.resumeTextView, R.id.subscribeTextView};

    int i = 1;

    for (int viewId : imageButtonIds) {

        ImageButton imageButton = (ImageButton) findViewById(viewId);
        // Animation from a file fade.xml in folder res/anim
        Animation fadeAnimation = AnimationUtils.loadAnimation(this, R.anim.fade);
        // Delay for each animation is 100 ms bigger than for previous one
        fadeAnimation.setStartOffset(i * 100);
        imageButton.startAnimation(fadeAnimation);

        // The same animation is for textViews
        int textViewId = textViewIds[i-1];
        TextView textView = (TextView) findViewById(textViewId);
        textView.startAnimation(fadeAnimation);

        i ++;
    }
}

Dans mon dossier res/anim, j'ai un fichier, appelé fade.xml avec le contenu suivant:

<?xml version="1.0" encoding="utf-8"?>

<!--  Fade animation with 500 ms duration -->

<alpha xmlns:Android="http://schemas.Android.com/apk/res/Android"
       Android:interpolator="@Android:anim/accelerate_decelerate_interpolator"
       Android:fromAlpha="0.0" Android:toAlpha="1.0"
       Android:duration="500" />
6
wzbozon

Créez un tableau d'animation et utilisez une méthode pour créer AnimationSet.

    Animation[] animations = { 
            getScaleAnimation(0.4f, 1.3f, 2000), 
            getScaleAnimation(1.3f, 1.0f, 500), 
            getScaleAnimation(0.4f, 1.3f, 1000),
            getScaleAnimation(1.3f, 1.0f, 3000), 
            getScaleAnimation(0.4f, 1.3f, 500), 
            getScaleAnimation(1.3f, 1.0f, 1700), 
            getScaleAnimation(0.4f, 1.3f, 2100),
            getScaleAnimation(1.3f, 1.0f, 3400)  
    };
    AnimationSet animationSet = addAnimationAr(animations);
    view.startAnimation(animationSet);

Méthode:

public static AnimationSet addAnimationAr(Animation[] animations) {
    AnimationSet animationSet = new AnimationSet(false);
    long totalAnimationDuration = 0;

    for (int i = 0; i < animations.length; i++) {
        Animation a = animations[i];
        a.setStartOffset(totalAnimationDuration);
        totalAnimationDuration += a.getDuration();
        animationSet.addAnimation(a);
    }

    return animationSet;
}
1
Mete

Si vous utilisez du code, vous pouvez appeler

Animation.setStartOffset() 

pour retarder la deuxième animation.

si vous utilisez xml, vous pouvez utiliser la propriété Android:ordering="sequentially" pour que les deux animations s'exécutent de manière séquentielle.

0
Andy Xiao