http://www.cnblogs.com/wenjiang/p/3196205.html
這次就介紹一下ListView中比較簡單但又非常方便的ArrayAdapter。
ArrayAdapter是BaseAdapter的派生類,在BaseAdapter的基礎上,添加了一項重大的功能:可以直接使用泛型構造。
我們先來看一個簡單的例子:
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ListView listView = (ListView) this.findViewById(R.id.list);
UserAdapter adapter = new UserAdapter(this, R.layout.list_item);
adapter.add(new User(10, "小智", "男"));
adapter.add(new User(10, "小霞", "女"));
listView.setAdapter(adapter);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
class UserAdapter extends ArrayAdapter<User> {
private int mResourceId;
public UserAdapter(Context context, int textViewResourceId) {
super(context, textViewResourceId);
this.mResourceId = textViewResourceId;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
User user = getItem(position);
LayoutInflater inflater = getLayoutInflater();
View view = inflater.inflate(mResourceId, null);
TextView nameText = (TextView) view.findViewById(R.id.name);
TextView ageText = (TextView) view.findViewById(R.id.age);
TextView sexText = (TextView) view.findViewById(R.id.sex);
nameText.setText(user.getName());
ageText.setText(user.getAge());
sexText.setText(user.getSex());
return view;
}
}
class User {
private int mAge;
private String mName;
private String mSex;
public User(int age, String name, String sex) {
this.mAge = age;
this.mName = name;
this.mSex = sex;
}
public String getName() {
return this.mName;
}
public String getAge() {
return this.mAge + "";
}
public String getSex() {
return this.mSex;
}
}
這裏自定義了一個ArrayAdapter,有關於Adapter的使用在之前的SimpleAdapter中已經涉及到了,所以這裏直接就是以自定義的ArrayAdapter作爲例子。
我們這裏需要將學生的信息羅列出來,需要三個TextView:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<TextView
android:id="@+id/name"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/age"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/sex"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>
在自定義ArrayAdapter的時候,最神奇的地方就是我們可以指定ArrayAdapter綁定的數據類型,可以是基本數據類型,也可以是自定義的對象類型,像是這次的User類型。對於自定義的ArrayAdapter的構造方法,存在很多形式,這次是傳進一個View的資源Id,但是我們也可以指定綁定的數據類型。
ArrayAdapter的神奇之處就是我們竟然可以像是操作Array一樣來操作ArrayAdapter!像是例子中的添加操作,而其他的適配器都是需要傳進一個容器的。ArrayAdapter爲什麼可以處理對象類型的數據呢?其實,ArrayAdapter是使用數組中對象的toString()方法來填充指定的TextView,所以我們可以通過重寫對象的toString()方法來自定義ListView的顯示。
@Override
public View getView(int position, View convertView, ViewGroup parent) {
User user = getItem(position);
LayoutInflater inflater = getLayoutInflater();
View view = inflater.inflate(mResourceId, null);
TextView text = (TextView) view.findViewById(R.id.info);
text.setText(user.toString());
return view;
}
class User {
private int mAge;
private String mName;
private String mSex;
public User(int age, String name, String sex) {
this.mAge = age;
this.mName = name;
this.mSex = sex;
}
@Override
public String toString() {
return "姓名:" + mName + " " + "年齡:" + mAge + " " + "性別:" + mSex;
}
}
這樣我們可以只在一行中顯示所有數據。
使用ArrayAdapter最大的疑問就是我們是否需要將一個現成的容器傳入ArrayAdapter中?原本ArrayAdapter本身就用一般容器的基本操作,像是添加新的元素等,但它本身並不能完成當成容器使用,我們更多的時候是要將一個容器中的元素交給ArrayAdapter,由後者決定它的顯示形式。
class UserAdapter extends ArrayAdapter<User> {
private int mResourceId;
public UserAdapter(Context context, int textViewResourceId,
List<User> users) {
super(context, textViewResourceId, users);
this.mResourceId = textViewResourceId;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
User user = getItem(position);
LayoutInflater inflater = getLayoutInflater();
View view = inflater.inflate(mResourceId, null);
TextView text = (TextView) view.findViewById(R.id.info);
text.setText(user.toString());
return view;
}
}
List<User> users = new ArrayList<User>();
users.add(new User(10, "小智", "男"));
users.add(new User(10, "小霞", "女"));
UserAdapter adapter = new UserAdapter(this, R.layout.list_item, users);
listView.setAdapter(adapter);
如果我們將ArrayAdapter綁定的數據類型定義爲Object,我們可以自由的傳入任何類型的容器而不需要任何有關類型轉換的操作!
ArrayAdapter不僅僅是可以顯示TextView,它當讓也像是其他Adapter一樣,可以顯示任何其他非TextView的組件:
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ListView listView = (ListView) this.findViewById(R.id.list);
List<Object> users = new ArrayList<Object>();
users.add(10);
users.add(11);
UserAdapter adapter = new UserAdapter(this, R.layout.list_item,
R.id.info, users);
listView.setAdapter(adapter);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
class UserAdapter extends ArrayAdapter<Object> {
private int mResourceId;
public UserAdapter(Context context, int resourceId,
int textViewResourceId, List<Object> users) {
super(context, resourceId, textViewResourceId, users);
this.mResourceId = resourceId;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
Object user = getItem(position);
LayoutInflater inflater = getLayoutInflater();
View view = inflater.inflate(mResourceId, null);
TextView text = (TextView) view.findViewById(R.id.info);
text.setText(user.toString());
return view;
}
}
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="點擊" />
<TextView
android:id="@+id/info"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>
如果我們的佈局中需要其他組件,必須指定該佈局中用於顯示ArrayAdapter中數據的TextView的Id。
如果只是方便綁定數據的話,其實是沒有必要專門獨立個ArrayAdapter出來,只要覆寫getView()就可以,正如使用容器就是爲了方便大量數據的處理一樣的道理,使用ArrayAdapter也是爲了處理數據較大的情況,像是超過100條或者頻繁動態增刪數據時,就可以使用ArrayAdapter,而且,爲了方便我們刷新UI,ArrayAdapter也提供了setNotifyOnChange()方法,這樣可以降低UI的處理量,使得刷新UI更加快速,主要是通過停止對add,insert,remove和clear的操作來實現這點。