In the previous article we began our look at Adapters by connecting up the List Navigation Spinner in our ActionBar. In this article we’ll look at applying an Adapter to a ListView.
Previously we created a fragment named ListViewFragment which is currently empty, save for inflating a simple layout containing a single ListView. To populate this ListView we use an Adapter. Let’s start by doing something really simple, and very similar to how we connected up our List Navigation Spinner: Use an ArrayAdapter:
public class ListViewFragment extends ListFragment { private static final String[] items = new String[] { "One", "Two", "Three", "Four", "Five" }; @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { return inflater.inflate(R.layout.listview, container, false); } @Override public void onActivityCreated(Bundle savedInstanceState) { super.onActivityCreated(savedInstanceState); ListAdapter adapter = new ArrayAdapter( getActivity(), android.R.layout.simple_list_item_1, items); setListAdapter(adapter); } }
We’ve used a static String array, and a different layout, but essentially this is exactly the same as we did with the Navigation Spinner. This demonstrates how the Adapter is completely decoupled from the control that it is binds to. ArrayAdapter extends BaseAdapter which implements both ListAdapter and SpinnerAdapter interfaces which means that it can be used to populate either of these controls.
This gives us the following:
So what if we want to do something slightly more complex. If we want to use android.R.layout.simple_list_item_2
instead of the previous layout, it includes two TextView objects which we need to bind to. Using the ArrayAdapter as before will not work because we now have to bind two controls, so we’ll use a SimpleAdapter instead:
public class SimpleAdapterFragment extends ListFragment { private static final List
Despite it’s name, SimpleAdapter is actually a little more complex than the very basic ArrayAdapter
implementation that we used before. However, it is actually a pretty simple way of binding multiple controls within each item in our ListView.
It works by storing the data that we want to bind to the control within a List of Maps. Each item in the List represents a single item in the ListView, and the Map contains the values which get assigned to the different controls. The two TextViews in the layout have ids of android.R.id.text1
and android.R.id.text2
and we need to map these values to the controls. This is done using two arrays, keys
contains a list of keys used in the Map, and controlIds
contains a list of control ids. SimpleAdapter will bind the controls to their respective Map values:
controlId[i].setText(map.get(keys[i]));
This gives us the following:
So we’ve seen how we can use ArrayAdapter to perform the simplest of bindings, and then SimpleAdapter to perform something very slightly more complex. Actually we can also use ArrayAdapter to perform this second kind of binding, but there are some optimisations that we need to be aware of before we do so. In the next article we’ll look at this.
The source code for this article is available here.
© 2013 – 2014, Mark Allison. All rights reserved.
Copyright © 2013 Styling Android. All Rights Reserved.
Information about how to reuse or republish this work may be available at http://blog.stylingandroid.com/license-information.