2010-09-13 10 views
1

Je construis une liste et la liste contient pour chaque contact une case à cocher pour choisir celui à modifier par exemple, le problème est que lorsque la liste est devenue plus longue que l'écran du téléphone et le défilement est actif; Lorsque je sélectionne une case à cocher, une seconde est automatiquement sélectionnée en bas de la liste. Le problème est la sélection automatique de la deuxième case à cocher; s'il vous plaît laissez-moi savoir comment puis-je le réparer ??Sélection automatique des cases à cocher dans listview - android

ci-dessous est le code que je utilise pour la méthode getView

public View getView(int position, View converView, ViewGroup parent){ 


    View row = converView; 
    if(row == null){ 
    LayoutInflater inflater = getLayoutInflater(); 
    row = inflater.inflate(R.layout.edit, parent, false); 
    } 

    TextView label = (TextView)row.findViewById(R.id.label); 
    label.setText(items[position]); 

    CheckBox cb = (CheckBox)row.findViewById(R.id.del); 

    ImageView icon = (ImageView)row.findViewById(R.id.icon); 
    icon.setImageResource(images.get(position)); 

    Log.i("Pos", ""+position); 


    return row; 
    } 
} 

Répondre

5

Le problème est que la liste réutilise votre point de vue (d'où l'argument convertView dans getView). Dans votre code, si vous obtenez un converti qui n'est pas nul, vous devez changer son état de case à cocher en fonction de ce qui est pertinent pour le nouveau contenu.

Supposons que view1 soit d'abord associé à l'ID 1 et que vous le vérifiiez. Ensuite, vous faites défiler et view1 est converti pour afficher l'ID 10. Mais puisque la vue n'est pas recréée, il aura toujours l'état de case à cocher de l'élément avec l'ID 1.

Donc, fondamentalement, la solution est de stocker quelque part les éléments sont sélectionnés et dans notre méthode getView, vous feriez

cb.setChecked(isItemChecked(position)); 

et vous devez mettre en œuvre isItemChecked (int position);

Un inefficace, mais la mise en œuvre de travail serait d'utiliser un tableau de booléens dans votre activité, disons que

boolean[] itemChecked; 

Et puis dans getView, vous définissez un écouteur sur la case cochée (devoir faire dernière position pour ce travailler). Vous définissez également l'état vérifié en utilisant le tableau.

cb.setOnCheckedChangeListener (new OnCheckedChangeListener() { 
    public void onCheckedChanged (CompoundButton btn, boolean isChecked) { 
    itemChecked[position] = isChecked; 
    } 
}); 

cb.setChecked(itemChecked[position]); 

Mais encore une fois, en utilisant un tableau pour ce qui est peut-être pas la mise en œuvre la plus efficace, surtout si vous avez un grand nombre d'éléments dans votre liste.

+0

Merci beaucoup Julien, ça a marché, j'ai juste changé une chose, j'ai changé boolean [] itemChecked; à boolean itemChecked [] = new boolean [100]; parce que ça me donnait l'Exception Null Pointer ... – Waqar

0

yyou peut également utiliser un SparseBooleanArray qui vous permet d'utiliser la position de la liste comme la clé

0

fonctionne bien pour moi

public View getGroupView(int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) { 

     final ViewHolder holder; 
     final Season season = (Season) getGroup(groupPosition); 
     if (convertView == null) { 
      LayoutInflater vi = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
      convertView = vi.inflate(R.layout.season, parent, false); 
      holder = new ViewHolder(); 
      holder.title = (TextView) convertView.findViewById(R.id.season_title); 
      holder.checkBox = (CheckBox) convertView.findViewById(R.id.season_check_box); 
      convertView.setTag(holder); 
     } else { 
      holder = (ViewHolder) convertView.getTag(); 
     } 

     holder.title.setText(season.getTitle()); 
     holder.checkBox.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() { 
      @Override 
      public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) { 
       season.setChecked(isChecked); 
       adapter.notifyDataSetChanged(); 
      } 
     }); 

     holder.checkBox.setChecked(season.isChecked()); // position is important! Must be before return statement! 
     return convertView; 
    } 

    protected class ViewHolder { 
     protected TextView title; 
     protected CheckBox checkBox; 
    }