Autore Topic: CheckBox in una ListView con custom layout  (Letto 4435 volte)

Offline niko_2307

  • Nuovo arrivato
  • *
  • Post: 27
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    HTC Hero
CheckBox in una ListView con custom layout
« il: 13 Settembre 2010, 17:46:16 CEST »
0
Salve a tutti,
come da titolo sto cercando di implementare una listView che abbia al suo interno delle checkbox.
alla pressione di un button vorrei prelevare i dati di quelle view che sono state selezionate, ma il mio problema è che non riesco a verificare se una checkbox in una determinata row è selezionata.

allego un'immagine per chiarire l'idea

Codice (XML): [Seleziona]
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
       xmlns:android="http://schemas.android.com/apk/res/android"
       android:layout_width="fill_parent"
       android:layout_height="60dip"
       android:padding="5dip">


        <CheckBox
               android:id="@+id/checkedFriend"
               android:layout_width="50dip"
               android:layout_height="50dip"
       >
        </CheckBox>


        <TextView
               android:text="Nome"
               android:layout_marginLeft="5dip"
               android:textAppearance="?android:attr/textAppearanceLarge"
               android:id="@+id/nameFriend"
               android:layout_toRightOf="@id/checkedFriend"
               android:layout_width="wrap_content"
               android:layout_height="wrap_content"></TextView>
        <TextView
               android:text="Distanza"
               android:textAppearance="?android:attr/textAppearanceMedium"
               android:textColor="#6b71f1"
               android:id="@+id/distFriend"
               android:layout_width="wrap_content"
               android:layout_height="wrap_content" android:layout_alignLeft="@+id/nameFriend" android:layout_below="@+id/nameFriend">
        </TextView>
</RelativeLayout>


Codice (Java): [Seleziona]
Button invita = (Button)findViewById(R.id.send);
invita.setOnClickListener(new OnClickListener() {
                       
                        @Override
                        public void onClick(View v) {
                               
                               
                                Friend f;
                                for (int i = 0; i < friendList.size(); i++) {
                                        CheckBox chk = (CheckBox)findViewById(i);
                                       
                                       
                                        if (chk.isChecked()) {
                                                f =  friendList.get(i);
                                                Toast.makeText( getApplicationContext(), "Nome: " + f.nome, Toast.LENGTH_SHORT ).show();
                                        }
                                       
                                }

Offline JD

  • Amministratore
  • Utente storico
  • *****
  • Post: 1600
  • Respect: +232
    • leinardi
    • Mostra profilo
  • Dispositivo Android:
    LG Nexus 5
  • Sistema operativo:
    L'ultima Ubuntu
Re:CheckBox in una ListView con custom layout
« Risposta #1 il: 13 Settembre 2010, 18:03:19 CEST »
0
Io ti consiglio di utilizzare ListView.CHOICE_MODE_MULTIPLE:



Prova a dare uno sguardo all'esempio presente nelle APIDemo: List11.java | Android Developers

Potresti poi gestire gli item selezionati in 2 modi:
  • Utilizzare setOnItemClickListener(listener) e verificare, al click di ogni elemento, se la box è spuntata o meno
  • Ottenere una lista degli item spuntati tramite getCheckedItemPositions(): ListView | Android Developers
« Ultima modifica: 13 Settembre 2010, 21:22:16 CEST da JD »
È stata trovata una soluzione al tuo problema?
Evidenzia il post più utile premendo . È un ottimo modo per ringraziare chi ti ha aiutato ;).
E se hai aperto tu il thread marcalo come risolto cliccando !

Offline niko_2307

  • Nuovo arrivato
  • *
  • Post: 27
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    HTC Hero
Re:CheckBox in una ListView con custom layout
« Risposta #2 il: 13 Settembre 2010, 18:12:46 CEST »
0
ti ringrazio per il consiglio, però  ho la necessità di utilizzare un custom adapter

Offline JD

  • Amministratore
  • Utente storico
  • *****
  • Post: 1600
  • Respect: +232
    • leinardi
    • Mostra profilo
  • Dispositivo Android:
    LG Nexus 5
  • Sistema operativo:
    L'ultima Ubuntu
Re:CheckBox in una ListView con custom layout
« Risposta #3 il: 13 Settembre 2010, 18:33:30 CEST »
0
Non dovrebbe essere un problema, non ho provato ma su StackOverflow dicono che si può benissimo fare:
Citazione
You can still use this technique with your own layout, so long as you include a CheckedTextView with android:id="@android:id/text1" as shown in the android.R.layout.simple_list_item_multiple_choice resource, a copy of which ships with your SDK.

CheckedTextView set to checked oncreate in listview? - Stack Overflow
  multiple    item   in ListView - Stack Overflow
Android save Checkbox State in ListView with Cursor Adapter - Stack Overflow

android.R.layout.simple_list_item_multiple_choice resource:
Codice (XML): [Seleziona]
<CheckedTextView xmlns:android="http://schemas.android.com/apk/res/android"
   android:id="@android:id/text1"
   android:layout_width="match_parent"
   android:layout_height="?android:attr/listPreferredItemHeight"
   android:textAppearance="?android:attr/textAppearanceLarge"
   android:gravity="center_vertical"
   android:checkMark="?android:attr/listChoiceIndicatorMultiple"
   android:paddingLeft="6dip"
   android:paddingRight="6dip"
/>
È stata trovata una soluzione al tuo problema?
Evidenzia il post più utile premendo . È un ottimo modo per ringraziare chi ti ha aiutato ;).
E se hai aperto tu il thread marcalo come risolto cliccando !

Offline Ricky`

  • Amministratore
  • Utente storico
  • *****
  • Post: 3489
  • Respect: +506
    • Github
    • Google+
    • rciovati
    • Mostra profilo
Re:CheckBox in una ListView con custom layout
« Risposta #4 il: 13 Settembre 2010, 20:11:11 CEST »
0
Io non sono mai riuscito ad usare la soluzione che hai postato tu. Avevo anche aperto una discussione a riguardo.
Ho dovuto gestire tutto "a mano". Quando la riga viene cliccata salvo in un apposita variabile di tipo SparseBooleanArray la sua posizione o viceversa se è già stata selezionata la rimuovo.

Offline niko_2307

  • Nuovo arrivato
  • *
  • Post: 27
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    HTC Hero
Re:CheckBox in una ListView con custom layout
« Risposta #5 il: 14 Settembre 2010, 12:32:49 CEST »
0
Io non sono mai riuscito ad usare la soluzione che hai postato tu. Avevo anche aperto una discussione a riguardo.
Ho dovuto gestire tutto "a mano". Quando la riga viene cliccata salvo in un apposita variabile di tipo SparseBooleanArray la sua posizione o viceversa se è già stata selezionata la rimuovo.

ho fatto anch'io così, solo che, se la lista è grande, quando la scorro la view viene reinizializzata e i risultati vengono resettati.
qualche suggerimento per evitare che ciò accada?

questo è il codice dell'adapter
Codice (Java): [Seleziona]
 private class FriendAdapter extends ArrayAdapter<Friend> implements OnCheckedChangeListener {
                 private DecimalFormat df;
                 private List<Friend> friends;
                 private SparseBooleanArray mCheckStates;
                 
                 public FriendAdapter ( Context context, int resourceId, List<Friend> friends) {
                             super( context, resourceId, friends );
                             this.friends = friends;
                            df = new DecimalFormat("#,###");
                            mCheckStates = new SparseBooleanArray(friends.size());
                 }
                 
                 public View getView(int position, View convertView, ViewGroup parent) {
                        if (convertView == null) {
                                LayoutInflater inflater = (LayoutInflater) getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
                                convertView = inflater.inflate(R.layout.row_layout_friend, null);
                        }
                       
                        Friend f = friends.get(position);
                       
                        if (f != null) {
                                TextView nome = (TextView) convertView.findViewById(R.id.nameFriend);
                                TextView distanza = (TextView) convertView.findViewById(R.id.distFriend);
                               
                                if (nome != null) {
                                        nome.setText(f.nome);
                                }
                               
                                if(distanza != null){
                                       
                                        Location friendLocation = new Location("gps");
                                        friendLocation.setLatitude(f.latitudine);
                                        friendLocation.setLongitude(f.longitudine);
                                        double dist = e.distanceFrom(friendLocation);
                                        if (dist >= 1 ) {
                                                distanza.setText(df.format(dist) + " km");
                                        } else {
                                                distanza.setText(df.format(dist*1000) + " metri");
                                        }      
                                }                              
                                                               
                        }
                               
                        CheckBox chk = (CheckBox) convertView.findViewById(R.id.checkedFriend);
                        chk.setTag(position);
                        chk.setChecked(mCheckStates.get(position, true));
                        setChecked(position, true);
                        chk.setOnCheckedChangeListener(this);
 
                        return convertView;
                         
                 }
                 
                 public boolean isChecked(int position) {
                         return mCheckStates.get(position, false);
                }

                 public void setChecked(int position, boolean isChecked) {
                         mCheckStates.put(position, isChecked);
                         notifyDataSetChanged();
                }

                public void toggle(int position) {
                        setChecked(position, !isChecked(position));
                }

               public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                       mCheckStates.put((Integer) buttonView.getTag(), isChecked);
               }
   
   
    }  

Offline Ricky`

  • Amministratore
  • Utente storico
  • *****
  • Post: 3489
  • Respect: +506
    • Github
    • Google+
    • rciovati
    • Mostra profilo
Re:CheckBox in una ListView con custom layout
« Risposta #6 il: 14 Settembre 2010, 12:38:59 CEST »
0
Metti un campo nella  classe Friend che ti tiene in memoria se è stato selezionato o meno. E' una porcheria, lo so.

Offline niko_2307

  • Nuovo arrivato
  • *
  • Post: 27
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    HTC Hero
Re:CheckBox in una ListView con custom layout
« Risposta #7 il: 14 Settembre 2010, 19:19:36 CEST »
0
Metti un campo nella  classe Friend che ti tiene in memoria se è stato selezionato o meno. E' una porcheria, lo so.
ho provato ma ancora non riesco
Codice (Java): [Seleziona]
private class FriendAdapter extends ArrayAdapter<Friend> implements OnCheckedChangeListener {
                 private DecimalFormat df;
                 private List<Friend> friends;
                 private SparseBooleanArray mCheckStates;
                 
                 public FriendAdapter ( Context context, int resourceId, List<Friend> friends) {
                            super( context, resourceId, friends );
                            this.friends = friends;
                            df = new DecimalFormat("#,###");
                            mCheckStates = new SparseBooleanArray(friends.size());
                 }
                 
                 public View getView(int position, View convertView, ViewGroup parent) {
                        if (convertView == null) {
                                LayoutInflater inflater = (LayoutInflater) getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
                                convertView = inflater.inflate(R.layout.row_layout_friend, null);
                        }
                       
                        Friend f = friends.get(position);
                       
                        if (f != null) {
                                TextView nome = (TextView) convertView.findViewById(R.id.nameFriend);
                                TextView distanza = (TextView) convertView.findViewById(R.id.distFriend);
                               
                                if (nome != null) {
                                        nome.setText(f.nome + " #" + f.selezionato);
                                }
                               
                                if(distanza != null){
                                       
                                        Location friendLocation = new Location("gps");
                                        friendLocation.setLatitude(f.latitudine);
                                        friendLocation.setLongitude(f.longitudine);
                                        double dist = e.distanceFrom(friendLocation);
                                        if (dist >= 1 ) {
                                                distanza.setText(df.format(dist) + " km");
                                        } else {
                                                distanza.setText(df.format(dist*1000) + " metri");
                                        }      
                                }
                               
                               
                                CheckBox chk = (CheckBox) convertView.findViewById(R.id.checkedFriend);
                                chk.setTag(position);
                               
                                if (f.selezionato == 1) {
                                        chk.setChecked(true);
                                        setChecked(position, true);
                                }
                                if (f.selezionato == 0) {
                                        chk.setChecked(false);
                                        setChecked(position, false);
                                }
                               

                                chk.setOnCheckedChangeListener(this);
                               
                        }
                               
           
 
                        return convertView;
                         
                 }
                 
                 public boolean isChecked(int position) {
                         return mCheckStates.get(position, false);
                }

                 public void setChecked(int position, boolean isChecked) {
                         mCheckStates.put(position, isChecked);
                          notifyDataSetChanged();
                }

        public void toggle(int position) {    
                if (friends.get(position).selezionato == 0) {
                        friends.get(position).selezionato = 1;
                        } else {
                                friends.get(position).selezionato = 0;
                        }
                setChecked(position, !isChecked(position));
        }

        public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
            mCheckStates.put((Integer) buttonView.getTag(), isChecked);
        }

Offline niko_2307

  • Nuovo arrivato
  • *
  • Post: 27
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    HTC Hero
Re:CheckBox in una ListView con custom layout
« Risposta #8 il: 15 Settembre 2010, 18:19:07 CEST »
0
qualche altro suggerimento?