179 votes

NavigationView get/find header layout

Dans ma NavigationView, j'ai une mise en page d'en-tête avec l'id "viewId" et des boutons actifs. Pour configurer ces boutons, je procède comme suit dans l'activité onPostCreate :

final View panel = findViewById(R.id.viewId);
panel.setOnClickListener(new View.OnClickListener() {
... setup goes here ...
});

Avec la nouvelle version de la bibliothèque de support Android, ( 23.1.0 ), la vue ne peut pas être trouvée, il retourne null. Avec les versions précédentes, cela fonctionnait bien. S'agit-il d'un bogue ou est-ce que j'utilise mal cette fonctionnalité ? Si oui, comment accéder à la mise en page de l'en-tête et y ajouter un comportement ?

451voto

ianhanniballake Points 18370

Commutateurs de la version 23.1.0 NavigationView à l'utilisation d'un RecyclerView (plutôt que l'ancien ListView ) et l'en-tête est ajouté comme l'un de ces éléments. Cela signifie qu'il n'est pas immédiatement disponible pour appeler findViewById() - une passe de mise en page est nécessaire avant qu'elle ne soit attachée à la NavigationView .

Pour version 23.1.1 de la bibliothèque de support, vous pouvez maintenant obtenir une référence à la vue d'en-tête en utilisant getHeaderView() :

View headerLayout = navigationView.getHeaderView(0); // 0-index header

Cela a l'avantage de fonctionner sur les en-têtes ajoutés via XML et via le code.

Si vous utilisez toujours la version 23.1.0, selon le bogue connexe vous pouvez gonfler l'en-tête dans le code et utiliser findViewById() sur ce point :

View headerLayout = 
    navigationView.inflateHeaderView(R.layout.navigation_header);
panel = headerLayout.findViewById(R.id.viewId);
// panel won't be null

Jusqu'à ce que vous passiez au 23.1.1.

1 votes

Merci pour votre aide rapide, je vais utiliser la solution de contournement. La méthode dédiée semble être la meilleure solution, j'espère qu'elle sera disponible dans les prochaines versions.

0 votes

OnLayoutChangeListener nécessite un sdk de niveau 11, mais j'en ai 9 dans mon application. Une idée, s'il vous plaît, pour contourner ce problème findViewById en retournant sur null para NavigationView en-tête ?

3 votes

@AlexanderFarber - le code que j'ai posté fonctionne jusqu'à l'API 7.

149voto

Francois Dermu Points 41

Désormais, avec la version 23.1.1 de la bibliothèque de support de conception, vous pouvez utiliser les éléments suivants

NavigationView navigationView = (NavigationView) findViewById(R.id.your_nav_view_id);
View header = navigationView.getHeaderView(0)
TextView text = (TextView) header.findViewById(R.id.textView);

0 votes

Vous pouvez également utiliser navigationView.getHeaderCount() au cas où vous auriez plus d'un en-tête pour une raison quelconque.

13voto

Wahib Haq Points 390

Voici comment je l'ai fait en utilisant ButterKnife et ça marche pour moi.

protected static class HeaderViewHolder {

    @BindView(R.id.button)
    Button button;

    HeaderViewHolder(View view) {
        ButterKnife.bind(this, view);
    }
}

et ensuite utiliser ce support de vue comme ceci :

View header = navigationView.getHeaderView(0);
headerViewHolder = new HeaderViewHolder(header);

2 votes

C'est parfait lorsque vous voulez supprimer la logique liée à la vue de votre activité. Une idée géniale !

2 votes

Cela fonctionne parfaitement avec ButterKnife, merci mon frère.

8voto

Campino Points 26

Pour moi c'était la même situation avec 23.1.0, après la mise à jour l'exception du pointeur nul est devenue. Dans ce cas, le NavigatorView ressemble :

<android.support.design.widget.NavigationView
  android:id="@+id/navigation_view"
  android:layout_height="match_parent"
  android:layout_width="wrap_content"
  android:layout_gravity="start"
  android:fitsSystemWindows="true"
  app:headerLayout="@layout/nav_header"
  app:menu="@menu/menu_nav"/>

J'ai essayé la solution proposée par ianhanniballake mais cela ne fonctionne pas. Alors j'ai gonflé avec la phrase :

LayoutInflater.from(getContext()).inflate(R.layout.nav_header, mNavigationView);

Après cela, je peux trouver par id toutes les vues définies dans nav_heard disposition .

3voto

indrit saveta Points 43
NavigationView navigationView = findViewById(R.id.your_nav_view);
View header = navigationView.getHeaderView(0);
TextView textUsername = header.findViewById(R.id.textView);
textUsername.setText("you text here ")

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X