ListView是手机系统中使用非常广泛的一种组件,它以垂直列表的形式显示所有列表项。
创建ListView有两种方式:
- 直接使用ListView创建。
- 让Activity继承ListActivity。
一旦在程序中获得ListView之后,接下来需要为ListView设置它要显示的列表项了。在这一点上,ListView与前面介绍的AutoComplete、Spinner类似,他们都需要一个供显示的列表项,这就需要借助于内容Adapter了,内容Adapter负责提供需要显示的列表项。
ListView的常用XML属性
XML属性 | 说明 |
android:choiceMode | 设置ListView的选择行为 |
android:divider | 设置list列表项的分隔条(既可用颜色分隔,也可用用Drawable分隔) |
android:dividerHeight | 设置分隔条的高度 |
android:entries | 指定一个数组资源,android将根据该数组资源来生成ListView |
android:footerDividersEnabled | 如果设置为false,则不在footer view之前绘制隔条 |
android:headerDividersEnabled | 如果设置为false,则不在header view之后绘制隔条 |
页面布局代码:layout/main.xml
1 <?xml version="1.0" encoding="utf-8"?>
2 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
3 android:layout_width="match_parent"
4 android:layout_height="match_parent"
5 android:orientation="vertical" >
6
7 <!-- 直接使用数组资源给出列表项 -->
8 <ListView
9 android:layout_width="fill_parent"
10 android:layout_height="wrap_content"
11 android:entries="@array/books"
12 android:divider="@drawable/red"
13 android:headerDividersEnabled="false"
14 />
15 <!-- 使用ArrayAdapter提供列表项的ListView -->
16 <ListView
17 android:id="@+id/list2"
18 android:layout_width="fill_parent"
19 android:layout_height="wrap_content"
20 android:divider="@drawable/green"
21 />
22 </LinearLayout>
页面布局代码里面写了两个ListView,第一个通过android:entries指定了列表数组,第二个通过ArrayAdapter使用数组提供列表项。
1 package com.yangjing.arrayadapterlist;
2
3 import android.app.Activity;
4 import android.os.Bundle;
5 import android.widget.ArrayAdapter;
6 import android.widget.ListView;
7
8 public class Arrayadapterlist extends Activity{
9
10 @Override
11 protected void onCreate(Bundle savedInstanceState) {
12 // TODO Auto-generated method stub
13 super.onCreate(savedInstanceState);
14 setContentView(R.layout.main);
15 ListView list2 = (ListView)findViewById(R.id.list2);
16 //定义一个数组
17 String[] arr ={"小智", "小刚" , "大木博士"};
18 //将数组包装ArrayAdapter
19 ArrayAdapter<String> arrayAdapter = new ArrayAdapter<String>(
20 this , android.R.layout.simple_list_item_1 , arr);
21 //为ListView设置Adapter
22 list2.setAdapter(arrayAdapter);
23 }
24 }
ArrayAdapter<String> arrayAdapter = new ArrayAdapter<String>(this , android.R.layout.simple_list_item_1 , arr);
创建ArrayAdapter时必须指定一textViewResourceId,该参数决定每个列表项的外观形式。Android为该属性提供了如下属性值:
- simple_list_item_1:每一个列表项都是普通的textView
- simple_list_item_2:每一个列表项都是普通的textView(字体略大)
- simple_list_item_checked:每一个列表项都是一个已勾选的列表项
- simple_list_item_multiple_choice:每个列表项都是带多选框的文本
- simple_list_item_single_choice:每个列表项都是带多单选按钮的文本
最初运行的效果:
将上面创建的arrayadapter改为:ArrayAdapter<String> arrayAdapter = new ArrayAdapter<String>(
this , android.R.layout.simple_list_item_single_choice , arr);
效果如下:
实例:基于ListActivity实现列表
如果程序的窗口仅仅需要显示一个列表,则可以直接让Activity继承ListActivity来实现,ListActivity的子类无需调用setContentView()方法来显示某个界面,而是直接传入一个Adapter,ListActivity的类就呈现出一个列表。
比如下面的程序:
界面程序:main.xml
1 <?xml version="1.0" encoding="utf-8"?>
2 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
3 android:layout_width="match_parent"
4 android:layout_height="match_parent"
5 android:orientation="vertical" >
6
7 <ListView android:id="@+id/android:list"
8 android:layout_width="match_parent"
9 android:layout_height="match_parent"
10 android:background="#0000ff"
11 android:layout_weight="1"
12 android:drawSelectorOnTop="false"></ListView>
13
14 <!-- ① android:drawSelectorOnTop="true" 点击某一条记录,颜色会显示在最上面,记录上的文字被遮住,所以点击文字不放,文字就看不到
15
16 ② android:drawSelectorOnTop="false" 点击某条记录不放,颜色会在记录的后面,成为背景色,但是记录内容的文字是可见的 -->
17 </LinearLayout>
主java程序:ListActivityTest.java
1 package com.yangjing.listactivitytest;
2
3 import android.app.ListActivity;
4 import android.os.Bundle;
5 import android.widget.ArrayAdapter;
6
7 public class ListActivityTest extends ListActivity{
8
9 @Override
10 protected void onCreate(Bundle savedInstanceState) {
11 super.onCreate(savedInstanceState);
12 //设置使用自己的界面
13 //setContentView(R.layout.main);
14 String[] arr = {"小狮","灵感","离","小黑","放生","灵"};
15 ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,android.R.layout.simple_list_item_multiple_choice,arr);
16 //设置窗口显示列表
17 setListAdapter(adapter);
18 }
19
20 }
效果如下:
使用SimpleAdapter创建ListView
关于SimpleAdapter的一些解释以及他的构成:
这是一个简单的适配器,可以将静态数据映射到XML文件中定义好的视图。你可以指定由Map组成的List(比如ArrayList)类型的数据。在ArrayList中的每个条目对应List中的一行。
Maps包含每一行的数据。你可以指定一个XML布局以指定每一行的视图,根据Map中的数据映射关键字到指定的视图。绑定数据到视图分两个阶段,首先,如果设置了SimpleAdapter.ViewBinder,
那么这个设置的ViewBinder的setViewValue(android.view.View, Object, String)将被调用。如果setViewValue的返回值是true,则表示绑定已经完成,将不再调用系统默认的绑定实现。
如果返回值为false,视图将按以下顺序绑定数据:
如果View实现了Checkable(例如CheckBox),期望绑定值是一个布尔类型。
TextView.期望绑定值是一个字符串类型,通过调用setViewText(TextView, String)绑定。
ImageView,期望绑定值是一个资源id或者一个字符串,通过调用setViewImage(ImageView, int) 或 setViewImage(ImageView, String)绑定数据。
如果没有一个合适的绑定发生将会抛出IllegalStateException。
public SimpleAdapter (Context context, List<? extends Map<String, ?>> data, int resource, String[] from, int[] to)
参数:
- context:上下文,比如this。关联SimpleAdapter运行的视图上下文
- data:Map列表,列表要显示的数据,这部分需要自己实现,类型要与上面的一致,每条项目要与from中指定条目一致
- resource:ListView单项布局文件的Id,这个布局就是你自定义的布局了,你想显示什么样子的布局都在这个布局中。这个布局中必须包括了to中定义的控件id
- from:一个被添加到Map上关联每一个项目列名称的列表,数组里面是列名称
- to:是一个int数组,数组里面的id是自定义布局中各个控件的id,需要与上面的from对应
下面用个实例解释下SimpleAdapter的用法:
界面程序:main.xml
1 <?xml version="1.0" encoding="utf-8"?>
2 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
3 android:layout_width="match_parent"
4 android:layout_height="match_parent"
5 android:orientation="vertical" >
6 <!-- 定义一个ListView -->
7 <ListView android:id="@+id/mylist"
8 android:layout_width="fill_parent"
9 android:layout_height="wrap_content"></ListView>
10
11 <!-- 定义一个ImageView,作为列表项的一部分 -->
12 <ImageView android:id="@+id/header"
13 android:layout_width="wrap_content"
14 android:layout_height="wrap_content"
15 android:paddingLeft="10dp"/>
16
17 <!-- 定义一个TextView,用于作为列表项的一部分 -->
18 <TextView android:id="@+id/name"
19 android:layout_width="wrap_content"
20 android:layout_height="wrap_content"
21 android:textSize="16dp"
22 android:gravity="center_vertical"
23 android:paddingLeft="10dp"/>
24 </LinearLayout>
主程序:SimpleAdapterTest.java
1 package com.yangjing.simpleadaptertest;
2
3 import java.util.ArrayList;
4 import java.util.HashMap;
5 import java.util.List;
6 import java.util.Map;
7
8 import android.app.Activity;
9 import android.os.Bundle;
10 import android.widget.ListView;
11 import android.widget.SimpleAdapter;
12
13 public class SimpleAdapterTest extends Activity{
14
15 //首先定义好name和头像
16 private String[] names = new String[]{"小狮","灵感","离","小黑"};
17
18 private int[] imageIds = new int[]{R.drawable.tiger,R.drawable.nongyu,R.drawable.libai,R.drawable.qingzhao};
19
20 @Override
21 protected void onCreate(Bundle savedInstanceState) {
22 super.onCreate(savedInstanceState);
23 setContentView(R.layout.main);
24
25 //创建一个list集合,list集合元素是Map
26 List<Map<String, Object>> listItems = new ArrayList<Map<String,Object>>();
27
28 for (int i = 0; i < names.length; i++) {
29 Map<String, Object> listItem = new HashMap<String, Object>();
30 listItem.put("header", imageIds[i]);
31 listItem.put("personName", names[i]);
32 listItems.add(listItem);
33 }
34
35 SimpleAdapter simpleAdapter = new SimpleAdapter(
36 this,
37 listItems,
38 R.layout.main,
39 new String[]{"header","personName"},
40 new int[]{R.id.header,R.id.name});
41 ListView list = (ListView) findViewById(R.id.mylist);
42 //为ListView设置Adapter
43 list.setAdapter(simpleAdapter);
44 }
45 }
效果如下: