Edit: Okay, I found a solution. Don't know that it's the proper solution, but it does work correctly. Added to the code below.
I'm trying to allow a user to select a number of directories from a checklist, and return them upon clicking a "Submit" button. Here's a snippet of my code. It populates the ListView with all the directories on /sdcard/, and for the initial selection (of however many I pick) when I submit, the log shows the correct choices returned. However, if I uncheck an item, and click "Submit" again, it still shows as if all are selected. Do I need to write a handler to uncheck an item? I thought that was taken care of by the choiceMode selection? Thanks!
private SparseBooleanArray a;
directoryList.setAdapter(new ArrayAdapter<String>(this, android.R.layout.simple_list_item_multiple_choice, directoryArray));
submitButton = (Button)findViewById(R.id.submit_button);
submitButton.setOnClickListener(new OnClickListener()
{
@Override
public void onClick(View v)
{
a = new SparseBooleanArray();
a.clear();
a = directoryList.getCheckedItemPositions();
for (int i = 0; i < a.size(); i++)
{
//added if statement to check for true. The SparseBooleanArray
//seems to maintain the keys for the checked items, but it sets
//the value to false. Adding a boolean check returns the correct result.
if(a.valueAt(i) == true)
Log.v("Returned ", directoryArray[a.keyAt(i)]);
}
}
});
Did some more debugging and found a solution that worked for me. Edited into code above. For some reason, the SparseBooleanArray doesn't empty itself; it maintains the keys of the boxes that have been checked. When getCheckedItemPositions() is called, however, it sets the VALUE to false. So the key is still in the returned array, but it has a value of false. Only the checked boxes will be marked with a value of true.
I know you found a solution that works for you, but the cleaner and simpler solution that will probably work most of the time is this (I want to persist all the ids of the elements selected):
(in my ListActivity):
SparseBooleanArray selectedPos = getListView()
.getCheckedItemPositions();
ListAdapter lAdapter = getListAdapter();
List<Long> ids = new ArrayList<Long>();
for (int i = 0; i < lAdapter.getCount(); i++) {
if (selectedPos.get(i)) {
ids.add(lAdapter.getItemId(i));
}
}
didn't mean to do this as an answer but i had to expand on what you did to do multi select. Why did you do a field variable for your selections? i just did local SparseBooleanArray...
public class NaughtyAndNice extends ListActivity {
TextView selection;
String[] items={"lorem","ipsum", "dolor", "sit", "amet",
"consectetuer", "adipisc", "jklfe", "morbi", "vel",
"ligula", "vitae", "carcu", "aliequet"};
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
setListAdapter(new ArrayAdapter<String>(this,android.R.layout.simple_list_item_multiple_choice,items));
selection = (TextView)findViewById(R.id.selection);
this.getListView().setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
}
public void onListItemClick(ListView parent, View view, int position, long id){
SparseBooleanArray choices = parent.getCheckedItemPositions();
StringBuilder choicesString = new StringBuilder();
for (int i = 0; i < choices.size(); i++)
{
//added if statement to check for true. The SparseBooleanArray
//seems to maintain the keys for the checked items, but it sets
//the value to false. Adding a boolean check returns the correct result.
if(choices.valueAt(i) == true)
choicesString.append(items[choices.keyAt(i)]).append(" ");
}
selection.setText(choicesString);
}
}
No need to use SparseBooleanArray choices = parent.getCheckedItemPositions();
StringBuilder
is enough for this.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With