前言
ListView 是Android的重要控件之一,可以提供多行數據的瀏覽;ListView可以實現複雜的佈局;這邊先從ListView簡單的使用入手;
添加ListView控件
- 在activity_main.xml中添加控件ListView;
<ListView
android:id="@+id/lv_data_shower"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_below="@id/rl_title"
android:layout_marginTop="@dimen/space_10"
/>
- 在MainActivity.java中獲取ListView的實例;
mLVDataShower = (ListView)findViewById(R.id.lv_data_shower);
- 爲ListView添加Adapter;
mAdapter = new DataShowerAdapter(getApplicationContext());
mLVDataShower.setAdapter(mAdapter);
- 爲ListView設置點擊事件監聽;
getItem
可以從Adapter中獲取一條裏綁定的數據對象,前提是Adapter中覆寫了getItem
並返回對象;
mLVDataShower.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
ItemBean itemBean = (ItemBean) mAdapter.getItem(position);
itemAlert(itemBean);
}
});
Adapter的實現
Adapter可以用來給ListView提供數據和佈局;
- 在res->layout 中創建 data_shower_item.xml文件,用來爲ListView每個item提供佈局;這裏只提供兩個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">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="@dimen/list_item_height">
<TextView
android:id="@+id/tv_sms"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textColor="@color/colorPrimaryDark"
android:layout_alignParentRight="true"
android:layout_centerVertical="true"
android:textSize="@dimen/text_size_15"
/>
<TextView
android:id="@+id/tv_number"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textColor="@color/colorPrimaryDark"
android:layout_alignParentLeft="true"
android:layout_centerVertical="true"
android:textSize="@dimen/text_size_15"
/>
</RelativeLayout>
</LinearLayout>
- 繼承
BaseAdapter
,覆寫必須要實現的抽象方法;
public class DataShowerAdapter extends BaseAdapter {
@Override
public int getCount() {
return 0;
}
@Override
public Object getItem(int position) {
return null;
}
@Override
public long getItemId(int position) {
return 0;
}
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
return null;
}
}
- 創建構造方法;將上下文傳入;新建數據庫helper對象,從數據庫中獲取要顯示的數據;獲取LayoutInflater對象,以便稍後獲取佈局對象;
public DataShowerAdapter(Context context) {
this.mContext = context;
this.mItemsDBHelper = new ItemsDBHelper(this.mContext);
this.mItems = mItemsDBHelper.loadItems();
this.mInflater = LayoutInflater.from(context);
}
- 設置ListVeiw要顯示的條數;
@Override
public int getCount() {
return this.mItems.size();
}
- 設置每一條在ListView中的位置;
@Override
public long getItemId(int position) {
return position;
}
- 設置每一條返回的數據對象;
@Override
public Object getItem(int position) {
return this.mItems.get(position);
}
- 設置每一條的佈局;
DataShowerHolder
用來緩存每一條中控件,防止不斷的new造成的卡頓或OOM;
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
DataShowerHolder holder;
if(convertView == null){
convertView = mInflater.inflate(R.layout.data_shower_item, null);
holder = new DataShowerHolder();
holder.tvSms = (TextView)convertView.findViewById(R.id.tv_sms);
holder.tvNumber = (TextView)convertView.findViewById(R.id.tv_number);
convertView.setTag(holder);//綁定ViewHolder對象
} else {
holder = (DataShowerHolder)convertView.getTag();//取出ViewHolder對象
}
holder.tvSms.setText(mItems.get(position).getSms());
holder.tvNumber.setText(mItems.get(position).getNumber());
return convertView;
}
- 創建內部類
DataShowerHolder
,用來做ListView 的控件緩存;
private class DataShowerHolder {
public TextView tvSms;
public TextView tvNumber;
}
- 現在Adapter看起來是這樣子的;
package com.youli.feiyu.fynotification.adapter;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.TextView;
import com.youli.feiyu.fynotification.R;
import com.youli.feiyu.fynotification.bean.ItemBean;
import com.youli.feiyu.fynotification.utility.ItemsDBHelper;
import java.util.ArrayList;
/**
* Created by Sean on 16/2/23.
*/
public class DataShowerAdapter extends BaseAdapter {
private Context mContext;
private LayoutInflater mInflater;
private ArrayList<ItemBean> mItems;
private ItemsDBHelper mItemsDBHelper;
public DataShowerAdapter(Context context) {
this.mContext = context;
this.mItemsDBHelper = new ItemsDBHelper(this.mContext);
this.mItems = mItemsDBHelper.loadItems();
this.mInflater = LayoutInflater.from(context);
}
@Override
public int getCount() {
return this.mItems.size();
}
@Override
public Object getItem(int position) {
return this.mItems.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(final int position, View convertView, ViewGroup parent) {
DataShowerHolder holder;
if(convertView == null){
convertView = mInflater.inflate(R.layout.data_shower_item, null);
holder = new DataShowerHolder();
holder.tvSms = (TextView)convertView.findViewById(R.id.tv_sms);
holder.tvNumber = (TextView)convertView.findViewById(R.id.tv_number);
convertView.setTag(holder);//綁定ViewHolder對象
} else {
holder = (DataShowerHolder)convertView.getTag();//取出ViewHolder對象
}
holder.tvSms.setText(mItems.get(position).getSms());
holder.tvNumber.setText(mItems.get(position).getNumber());
return convertView;
}
private class DataShowerHolder {
public TextView tvSms;
public TextView tvNumber;
}
}
ListView刷新數據
如果後來添加/刪除/修改了一條數據ListView該如何刷新?
- 添加/刪除/修改數據源,然後調用下
notifyDataSetChanged
;
public void deleteItem(ItemBean itemBean) {
mItems.remove(itemBean);
mItemsDBHelper.deleteItem(itemBean);
notifyDataSetChanged();
}
總結
- ListView的顯示 ,需要設置好Adapter;
- Adapter是ListView的數據和佈局來源;
- 在Adapter中要做好控件的緩存,避免卡頓和OOM;
- 調用Adapter的
notifyDataSetChanged
可以刷新ListView;