web-dev-qa-db-fra.com

Puis-je ouvrir la disposition des tiroirs avec animation par programmation?

J'ai créé le tiroir d'applications en utilisant la bibliothèque suivante: http://developer.Android.com/training/implementing-navigation/nav-drawer.html

Je souhaite afficher le tiroir de navigation avec animation lors de l'ouverture de l'application. Comment puis je faire ça?

21
benleung

Écouteur Predraw, alias le safeway

Voici l'exemple d'écouteur de prédraw. Il démarrera littéralement l'animation dès que possible, ce qui est peut-être un peu trop rapide. Vous voudrez peut-être faire une combinaison de cela avec un exécutable affiché en second. Je ne montrerai pas les deux combinés, seulement séparés.

@Override
protected void onCreate(Bundle savedInstanceState) {
    ...
    // Building NavDrawer logic here. Just a method call would be best.
    ...

    ViewTreeObserver vto = drawer.getViewTreeObserver();
    if (vto != null) vto.addOnPreDrawListener(new ShouldShowListener(drawer));
}

private static class ShouldShowListener implements OnPreDrawListener {

    private final DrawerLayout drawerLayout;

    private ShouldShowListener(DrawerLayout drawerLayout) {
        this.drawerLayout= drawerLayout;
    }

    @Override
    public boolean onPreDraw() {
        if (view != null) {
            ViewTreeObserver vto = view.getViewTreeObserver();
            if (vto != null) {
                vto.removeOnPreDrawListener(this);
            }
        }

        drawerLayout.openDrawer(Gravity.LEFT);
        return true;
    }
}

PostDelay Runnable, alias vivre dangereux

// Delay is in milliseconds
static final int DRAWER_DELAY = 200;

@Override
protected void onCreate(Bundle savedInstanceState) {
    ...
    // Building NavDrawer logic here. Just a method call would be best.
    ...
    new Handler().postDelayed(openDrawerRunnable(), DRAWER_DELAY);
}

private Runnable openDrawerRunnable() {
    return new Runnable() {

        @Override
        public void run() {
            drawerLayout.openDrawer(Gravity.LEFT);
        }
    }
}

[~ # ~] avertissement [~ # ~]

S'ils tournent au démarrage de l'application pour la première fois BOOM! Lisez cet article de blog pour plus d'informations http: // corner. squareup.com/2013/12/Android-main-thread-2.html . La meilleure chose à faire serait d'utiliser l'écouteur de prédraw ou de supprimer votre exécutable dans onPause.

53
MinceMan

Vous pouvez appeler openDrawer(int gravity) sur le DrawerLayout pour lui ouvrir le tiroir avec une animation.

7
Brayden

Vous devez appeler drawerLayout.openDrawer(Gravity.LEFT) pour animer l'ouverture du tiroir. Le tiroir ne s'animera pas si vous passez l'appel trop tôt dans le cycle de vie de l'activité.

La solution la plus simple consiste à simplement définir un indicateur dans onCreate () et à agir dessus dans onResume ().

Vous voulez vous assurer que vous définissez uniquement l'indicateur lorsque savedInstanceState est null indiquant que l'activité n'est pas reprise à partir de l'arrière-plan. Vous ne voulez pas que le tiroir glisse à chaque fois que vous changez d'orientation ou changez d'application.

public class MainActivity extends ActionBarActivity {
    private DrawerLayout drawerLayout;
    private boolean firstResume = false;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        drawerLayout = (DrawerLayout)findViewById(R.id.drawer);

        if(savedInstanceState == null){
            firstResume = true;
        }
    }

    @Override
    protected void onResume() {
        super.onResume();

        if(firstResume) {
            drawerLayout.openDrawer(Gravity.LEFT);
        }

        firstResume = false;
    }
}

Vous pouvez également utiliser un OnPreDrawListener mais je pense que c'est un peu inutilement compliqué car onPreDraw est appelé plusieurs fois, vous devez donc supprimer l'écouteur après avoir ouvert le tiroir. Vous supposez également que preDraw est un moment approprié pour activer le tiroir, qui est une implémentation interne de la disposition du tiroir. Une future implémentation pourrait ne pas s'animer correctement avant après onDraw par exemple.

Retarder l'ouverture du tiroir d'un nombre arbitraire de millisecondes est un moyen dangereux de résoudre ce problème. Dans le pire des cas, l'appel pour ouvrir le tiroir pourrait se produire après onDestroy si l'utilisateur s'éloigne rapidement.

1
Jared Kells