Android之自定义Adapter的ListView

来源:互联网 发布:c语言最新函数库 编辑:程序博客网 时间:2024/05/17 04:53
在开发中,我们经常使用到ListView这个控件。Android的API也提供了许多创建ListView适配器的快捷方式。例如ArrayAdapter、SimpleAdapter和SimpleCursorAdapter等。但你是否发现,如果采用这些系统自带的适配器,对于事件的响应只能局限在一个行单位。假设一行里面有一个按钮和一个图片控件,它们之间的响应操作是不一样的。若采用系统自带的适配器,就不能精确到每个控件的响应事件。这时,我们一般采取自定义适配器来实现这个比较精确地请求。

       ListView的创建,一般要具备两大元素:

       1)数据集,即要映射的字符串、图片信息之类。

       2)适配器,实现把要映射的字符串、图片信息映射成视图(如Textview、Image等组件),再添加到ListView中。

       下面是一个实操例子:

      实现细节:

       1、创建数据集,一般定义如下

        private List<Map<String, Object>> listItems;

        元素添加方式:

       Map<String, Object> map = new HashMap<String, Object>();
        map.put("image", imgeIDs[i]);          //图片资源
        map.put("title", "物品名称:");           //物品标题
        map.put("info", goodsNames[i]);      //物品名称
        map.put("detail", goodsDetails[i]);   //物品详情
        listItems.add(map);                         //添加一项

       2、创建适配器

       public class ListViewAdapter extends BaseAdapter{........}  //自定义的适配器一般继承BaseAdapter类

        listViewAdapter = new ListViewAdapter(this, listItems);

        3、给ListView设置适配器

       listView.setAdapter(listViewAdapter);

       4、这里还有个关键点,如何把list_item.xml布局作为一个视图,添加到listView中:

        LayoutInflater listContainer;   //视图容器工厂

        listContainer = LayoutInflater.from(context); //创建视图容器工厂并设置上下文

        convertView = listContainer.inflate(R.layout.list_item, null);   //创建list_item.xml布局文件的视图

      

        实例视图如下:

1)布局文件main.xml      
  1. <?xmlversion="1.0"encoding="utf-8"?> 
  2. <LinearLayoutxmlns:Android="http://schemas.android.com/apk/res/android" 
  3.     Android:orientation="vertical" 
  4.     Android:layout_width="fill_parent" 
  5.     Android:layout_height="fill_parent"> 
  6.       
  7.     <!-- 结算 --> 
  8.     <LinearLayoutAndroid:gravity="center_horizontal" 
  9.     Android:orientation="horizontal"android:layout_width="fill_parent" 
  10.     Android:layout_height="wrap_content"> 
  11.     <TextViewAndroid:text="结算: " 
  12.         Android:layout_width="wrap_content" 
  13.         Android:layout_height="wrap_content"   
  14.         Android:textColor="#FFFFFFFF"   
  15.         Android:textSize="20px"/> 
  16.     <ImageButtonAndroid:id="@+id/imgbt_sum"   
  17.         Android:layout_width="40px" 
  18.         Android:layout_height="40px" 
  19.         Android:background ="@drawable/shopping"/> 
  20.     </LinearLayout> 
  21.       
  22.     <TextViewAndroid:text="商品列表: " 
  23.         Android:layout_width="wrap_content" 
  24.         Android:layout_height="wrap_content"   
  25.         Android:textColor="#FFFFFFFF"/> 
  26.           
  27.     <!-- 商品列表 -->   
  28.     <ListViewAndroid:id="@+id/list_goods"   
  29.         Android:layout_width="fill_parent" 
  30.         Android:layout_height="wrap_content"/> 
  31.           
  32. </LinearLayout> 

       列表项布局文件list_item.xml     

  1. <?xmlversion="1.0"encoding="utf-8"?> 
  2. <LinearLayoutxmlns:Android="http://schemas.android.com/apk/res/android" 
  3.     Android:orientation="horizontal"android:layout_width="fill_parent" 
  4.     Android:layout_height="fill_parent"> 
  5.  
  6.     <!-- 商品图片 --> 
  7.     <ImageViewAndroid:id="@+id/imageItem"   
  8.         Android:layout_width="wrap_content" 
  9.         Android:layout_height="wrap_content"   
  10.         Android:layout_margin="5px"/> 
  11.       
  12.     <!-- 商品信息 --> 
  13.     <LinearLayoutAndroid:orientation="vertical" 
  14.         Android:layout_width="wrap_content"   
  15.         Android:layout_height="wrap_content"> 
  16.  
  17.         <TextViewAndroid:id="@+id/titleItem"   
  18.             Android:layout_width="wrap_content" 
  19.             Android:layout_height="wrap_content"   
  20.             Android:textColor="#FFFFFFFF" 
  21.             Android:textSize="13px"/> 
  22.         <TextViewAndroid:id="@+id/infoItem"   
  23.             Android:layout_width="wrap_content" 
  24.             Android:layout_height="wrap_content"   
  25.             Android:textColor="#FFFFFFFF" 
  26.             Android:textSize="22px"/> 
  27.     </LinearLayout> 
  28.       
  29.     <!-- 购买和商品详情 --> 
  30.     <LinearLayoutAndroid:gravity="right" 
  31.     Android:orientation="horizontal"android:layout_width="fill_parent" 
  32.     Android:layout_height="wrap_content"> 
  33.     <CheckBoxAndroid:id="@+id/checkItem"   
  34.         Android:layout_width="wrap_content" 
  35.         Android:layout_height="wrap_content"   
  36.         Android:layout_margin="5px"/> 
  37.     <Button Android:id="@+id/detailItem"   
  38.         Android:layout_width="wrap_content" 
  39.         Android:layout_height="wrap_content"   
  40.         Android:layout_margin="5px"/> 
  41.     </LinearLayout> 
  42. </LinearLayout> 

       2)代码,主代码:       

  1. package com.myAndroid.test;  
  2.  
  3. import java.util.ArrayList;  
  4. import java.util.HashMap;  
  5. import java.util.List;  
  6. import java.util.Map;  
  7.  
  8. importAndroid.app.Activity;  
  9. importAndroid.app.AlertDialog;  
  10. importAndroid.content.DialogInterface;  
  11. importAndroid.os.Bundle;  
  12. importAndroid.view.View;  
  13. importAndroid.view.View.OnClickListener;  
  14. importAndroid.widget.ArrayAdapter;  
  15. importAndroid.widget.ImageButton;  
  16. importAndroid.widget.ListView;  
  17.  
  18. publicclass MyListViewextends Activity {  
  19.       
  20.     private ListView listView;  
  21.     private ImageButton imgbt_sum;  
  22.     private ListViewAdapter listViewAdapter;  
  23.     private List<Map<String, Object>> listItems;  
  24.     private Integer[] imgeIDs = {R.drawable.cake,   
  25.             R.drawable.gift, R.drawable.letter,  
  26.             R.drawable.love, R.drawable.mouse,  
  27.             R.drawable.music};  
  28.     private String[] goodsNames = {"蛋糕","礼物",   
  29.             "邮票","爱心", "鼠标", "音乐CD"};  
  30.     private String[] goodsDetails = {  
  31.             "蛋糕:好好吃。",   
  32.             "礼物:礼轻情重。",   
  33.             "邮票:环游世界。",   
  34.             "爱心:世界都有爱。",  
  35.             "鼠标:反应敏捷。",  
  36.             "音乐CD:酷我音乐。"};  
  37.       
  38.     /** Called when the activity is first created. */ 
  39.     @Override 
  40.     publicvoid onCreate(Bundle savedInstanceState) {  
  41.         super.onCreate(savedInstanceState);  
  42.         setContentView(R.layout.main);  
  43.           
  44.         listView = (ListView)findViewById(R.id.list_goods);   
  45.         imgbt_sum = (ImageButton) findViewById(R.id.imgbt_sum);  
  46.         imgbt_sum.setOnClickListener(new ClickEvent());  
  47.         listItems = getListItems();  
  48.         listViewAdapter = new ListViewAdapter(this, listItems);//创建适配器  
  49.         listView.setAdapter(listViewAdapter);  
  50.     }  
  51.       
  52.     /**
  53.      * 初始化商品信息
  54.      */ 
  55.     private List<Map<String, Object>> getListItems() {  
  56.         List<Map<String, Object>> listItems = new ArrayList<Map<String, Object>>();  
  57.         for(int i =0; i < goodsNames.length; i++) {  
  58.             Map<String, Object> map = new HashMap<String, Object>();   
  59.             map.put("image", imgeIDs[i]);              //图片资源  
  60.             map.put("title","物品名称:");             //物品标题  
  61.             map.put("info", goodsNames[i]);    //物品名称  
  62.             map.put("detail", goodsDetails[i]);//物品详情  
  63.             listItems.add(map);  
  64.         }     
  65.         return listItems;  
  66.     }  
  67.       
  68.     class ClickEventimplements OnClickListener{  
  69.  
  70.         @Override 
  71.         publicvoid onClick(View v) {  
  72.             // TODO Auto-generated method stub 
  73.             String goodsList = "";  
  74.             for(int i =0; i < listItems.size(); i++) {  
  75.                 goodsList += listViewAdapter.hasChecked(i)? goodsNames[i] +"  ": "";  
  76.             }  
  77.             new AlertDialog.Builder(MyListView.this)  
  78.             .setTitle("购物清单:")  
  79.             .setMessage("你好,你选择了如下商品:\n" + goodsList)  
  80.             .setPositiveButton("确定",null)  
  81.             .show();  
  82.         }  
  83.           
  84.     }  
  85. }  

适配器代码:     
  1. package com.myAndroid.test;  
  2.  
  3. import java.util.List;  
  4. import java.util.Map;  
  5.  
  6. importAndroid.app.AlertDialog;  
  7. importAndroid.content.Context;  
  8. importAndroid.util.Log;  
  9. importAndroid.view.LayoutInflater;  
  10. importAndroid.view.View;  
  11. importAndroid.view.ViewGroup;  
  12. importAndroid.widget.BaseAdapter;  
  13. importAndroid.widget.Button;  
  14. importAndroid.widget.CheckBox;  
  15. importAndroid.widget.CompoundButton;  
  16. importAndroid.widget.ImageView;  
  17. importAndroid.widget.ListView;  
  18. importAndroid.widget.TextView;  
  19.  
  20. publicclass ListViewAdapterextends BaseAdapter {  
  21.     private Context context;                       //运行上下文  
  22.     private List<Map<String, Object>> listItems;   //商品信息集合  
  23.     private LayoutInflater listContainer;          //视图容器  
  24.     privateboolean[] hasChecked;                  //记录商品选中状态  
  25.     publicfinalclass ListItemView{               //自定义控件集合    
  26.             public ImageView image;    
  27.             public TextView title;    
  28.             public TextView info;  
  29.             public CheckBox check;  
  30.             public Button detail;         
  31.      }    
  32.       
  33.       
  34.     public ListViewAdapter(Context context, List<Map<String, Object>> listItems) {  
  35.         this.context = context;           
  36.         listContainer = LayoutInflater.from(context);   //创建视图容器并设置上下文 
  37.         this.listItems = listItems;  
  38.         hasChecked = newboolean[getCount()];  
  39.     }  
  40.  
  41.     publicint getCount() {  
  42.         // TODO Auto-generated method stub 
  43.         return listItems.size();  
  44.     }  
  45.  
  46.     public Object getItem(int arg0) {  
  47.         // TODO Auto-generated method stub 
  48.         returnnull;  
  49.     }  
  50.  
  51.     publiclong getItemId(int arg0) {  
  52.         // TODO Auto-generated method stub 
  53.         return0;  
  54.     }  
  55.       
  56.     /**
  57.      * 记录勾选了哪个物品
  58.      * @param checkedID 选中的物品序号
  59.      */ 
  60.     privatevoid checkedChange(int checkedID) {  
  61.         hasChecked[checkedID] = !hasChecked[checkedID];  
  62.     }  
  63.       
  64.     /**
  65.      * 判断物品是否选择
  66.      * @param checkedID 物品序号
  67.      * @return 返回是否选中状态
  68.      */ 
  69.     publicboolean hasChecked(int checkedID) {  
  70.         return hasChecked[checkedID];  
  71.     }  
  72.       
  73.     /**
  74.      * 显示物品详情
  75.      * @param clickID
  76.      */ 
  77.     privatevoid showDetailInfo(int clickID) {  
  78.         new AlertDialog.Builder(context)  
  79.         .setTitle("物品详情:" + listItems.get(clickID).get("info"))  
  80.         .setMessage(listItems.get(clickID).get("detail").toString())                
  81.         .setPositiveButton("确定",null)  
  82.         .show();  
  83.     }  
  84.       
  85.          
  86.     /**
  87.      * ListView Item设置
  88.      */ 
  89.     public View getView(int position, View convertView, ViewGroup parent) {  
  90.         // TODO Auto-generated method stub 
  91.         Log.e("method","getView");  
  92.         finalint selectID = position;  
  93.         //自定义视图 
  94.         ListItemView  listItemView = null;  
  95.         if (convertView ==null) {  
  96.             listItemView = new ListItemView();   
  97.             //获取list_item布局文件的视图 
  98.             convertView = listContainer.inflate(R.layout.list_item, null);  
  99.             //获取控件对象 
  100.             listItemView.image = (ImageView)convertView.findViewById(R.id.imageItem);  
  101.             listItemView.title = (TextView)convertView.findViewById(R.id.titleItem);  
  102.             listItemView.info = (TextView)convertView.findViewById(R.id.infoItem);  
  103.             listItemView.detail= (Button)convertView.findViewById(R.id.detailItem);  
  104.             listItemView.check = (CheckBox)convertView.findViewById(R.id.checkItem);  
  105.             //设置控件集到convertView 
  106.             convertView.setTag(listItemView);  
  107.         }else {  
  108.             listItemView = (ListItemView)convertView.getTag();  
  109.         }  
  110. //      Log.e("image", (String) listItems.get(position).get("title"));  //测试 
  111. //      Log.e("image", (String) listItems.get(position).get("info")); 
  112.           
  113.         //设置文字和图片 
  114.         listItemView.image.setBackgroundResource((Integer) listItems.get(  
  115.                 position).get("image"));  
  116.         listItemView.title.setText((String) listItems.get(position)  
  117.                 .get("title"));  
  118.         listItemView.info.setText((String) listItems.get(position).get("info"));  
  119.         listItemView.detail.setText("商品详情");  
  120.         //注册按钮点击时间爱你 
  121.         listItemView.detail.setOnClickListener(new View.OnClickListener() {  
  122.             @Override 
  123.             publicvoid onClick(View v) {  
  124.                 //显示物品详情 
  125.                 showDetailInfo(selectID);  
  126.             }  
  127.         });  
  128.         // 注册多选框状态事件处理 
  129.         listItemView.check  
  130.                 .setOnCheckedChangeListener(new CheckBox.OnCheckedChangeListener() {  
  131.                     @Override 
  132.                     publicvoid onCheckedChanged(CompoundButton buttonView,  
  133.                             boolean isChecked) {  
  134.                         //记录物品选中状态 
  135.                         checkedChange(selectID);  
  136.                     }  
  137.         });  
  138.           
  139.         return convertView;  
  140.     }  

        至于,如何实现系统自带的适配器,如ArrayAdapter、SimpleAdapter和SimpleCursorAdapter等,有机会再补充。

原文链接:http://www.linuxidc.com/Linux/2011-05/35394.htm

0 0