zoukankan      html  css  js  c++  java
  • Android之listview && adapter

      今天我们讲的也是非常重要的一个控件listview—最常用也是最难的

    一个ListView通常有两个职责

    (1)将数据填充到布局。

    (2)处理用户的选择点击等操作。

      第一点很好理解,ListView就是实现这个功能的。第二点也不难做到,在后面的学习中读者会发现,这非常简单。

    一个ListView的创建需要3个元素

    (1)ListView中的每一列的View。

    (2)填入View的数据或者图片等。

    (3)连接数据与ListView的适配器。

    也就是说,要使用ListView,首先要了解什么是适配器。适配器是一个连接数据和AdapterView(ListView就是一个典型的AdapterView,后面还会学习其他的)的桥梁,通过它能有效地实现数据与AdapterView的分离设置,使AdapterView与数据的绑定更加简便,修改更加方便

    Android中提供了很多的Adapter,表4-5列出了常用的几个。

    表4-5 常用适配器

    Adapter

    含义

    ArrayAdapter<T>

    用来绑定一个数组,支持泛型操作

    SimpleAdapter

    用来绑定在xml中定义的控件对应的数据

    SimpleCursorAdapter

    用来绑定游标得到的数据

    BaseAdapter

    通用的基础适配器

     其实适配器还有很多,要注意的是,各种Adapter只不过是转换的方式和能力不一样而已。

     ListView使用SimpleAdapter

    很多时候需要在列表中展示一些除了文字以外的东西,比如图片等。这时候可以使用SimpleAdapter。SimpleAdapter的使用也非常简单,同时它的功能也非常强大。可以通过它自定义ListView中的item的内容,比如图片、多选框等。

    使用simpleAdapter的数据一般都是用HashMap构成的列表,列表的每一节对应ListView的每一行。通过SimpleAdapter的构造函数,将HashMap的每个键的数据映射到布局文件中对应控件上。这个布局文件一般根据自己的需要来自己定义。梳理一下使用SimpleAdapter的步骤。

    (1)根据需要定义ListView每行所实现的布局。

    (2)定义一个HashMap构成的列表,将数据以键值对的方式存放在里面。

    (3)构造SimpleAdapter对象。

    (4)将LsitView绑定到SimpleAdapter上。

    BaseAdapter

      在ListView的使用中,有时候还需要在里面加入按钮等控件,实现单独的操作。也就是说,这个ListView不再只是展示数据,也不仅仅是这一行要来处理用户的操作,而是里面的控件要获得用户的焦点。读者可以试试用SimpleAdapter添加一个按钮到ListView的条目中,会发现可以添加,但是却无法获得焦点,点击操作被ListView的Item所覆盖。这时候最方便的方法就是使用灵活的适配器BaseAdapter了。

       当系统开始绘制ListView的时候,首先调用getCount()方法。得到它的返回值,即ListView的长度。然后系统调用getView()方法,根据这个长度逐一绘制ListView的每一行。也就是说,如果让getCount()返回1,那么只显示一行。而getItem()和getItemId()则在需要处理和取得Adapter中的数据时调用。那么getView如何使用呢?如果有10000行数据,就绘制10000次?这肯定会极大的消耗资源,导致ListView滑动非常的慢,那应该怎么做呢?

    下面就通过微信的例子说明吧!

    下面是布局文件

     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
     8         android:id="@+id/listView1"
     9         android:layout_width="match_parent"
    10         android:layout_height="match_parent" >
    11     </ListView>
    12 
    13 </LinearLayout>
    listview_layout.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="wrap_content"
     5     android:paddingLeft="@dimen/activity_horizontal_margin"
     6     android:paddingRight="@dimen/activity_horizontal_margin"
     7     android:paddingTop="@dimen/activity_horizontal_margin"
     8     android:paddingBottom="@dimen/activity_horizontal_margin"
     9     android:orientation="horizontal" >
    10 
    11     <ImageView
    12         android:id="@+id/face"
    13         android:layout_width="60dp"
    14         android:layout_height="60dp"
    15         android:src="@drawable/houzi" />
    16 
    17 
    18     <LinearLayout
    19         android:layout_weight="1"
    20         android:layout_width="wrap_content"
    21         android:layout_height="wrap_content" 
    22         android:layout_margin="5dp"
    23         android:orientation="vertical" >
    24         
    25         <LinearLayout
    26             android:layout_weight="1"
    27                android:layout_width="match_parent"
    28             android:layout_height="wrap_content" 
    29                android:layout_marginBottom="3dp"
    30             android:orientation="horizontal"  >
    31             
    32                 <TextView
    33                     android:layout_weight="1"
    34                     android:id="@+id/name"
    35                     android:layout_width="wrap_content"
    36                     android:layout_height="wrap_content"
    37                     android:textSize="20sp"
    38                     android:textColor="#7F7F7F"/>
    39                 
    40                  <TextView
    41                     android:id="@+id/date"
    42                     android:layout_width="wrap_content"
    43                     android:layout_height="wrap_content"
    44                     android:textSize="15sp"
    45                     android:textColor="#A9A9A9"/>
    46         </LinearLayout>
    47         <LinearLayout
    48             android:layout_weight="1"
    49                android:layout_width="match_parent"
    50             android:layout_height="wrap_content" 
    51                android:layout_marginBottom="3dp"
    52             android:orientation="horizontal"  >
    53             <TextView
    54                 android:layout_weight="1"
    55                 android:id="@+id/content"
    56                 android:layout_width="wrap_content"
    57                 android:layout_height="wrap_content"
    58                 android:textSize="15sp"
    59                 android:textColor="#A9A9A9"/>
    60             <TextView
    61                 android:id="@+id/noRead"
    62                 android:layout_width="wrap_content"
    63                 android:layout_height="wrap_content"
    64                 android:textSize="15sp"
    65                 android:text=""
    66                 android:textColor="#FF0000"/>
    67         </LinearLayout>
    68     </LinearLayout>
    69 
    70    
    71 
    72 </LinearLayout>
    middle2.xml
     1 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
     2     xmlns:tools="http://schemas.android.com/tools"
     3     android:layout_width="match_parent"
     4     android:layout_height="match_parent"
     5     android:orientation="vertical"
     6     tools:context="com.main.weixin.MainActivity" >
     7 
     8     <!-- 头部 -->
     9     <LinearLayout
    10         android:id="@+id/linearLayout1"
    11         android:layout_width="match_parent"
    12         android:layout_height="wrap_content"
    13       >
    14         
    15         <include layout="@layout/head"/>
    16           
    17     </LinearLayout>
    18 
    19     
    20     <!-- 中间 -->
    21     <LinearLayout
    22         android:layout_weight="1"
    23         android:layout_width="match_parent"
    24         android:layout_height="match_parent">
    25         
    26           <include layout = "@layout/listview_layout"></include>
    27         
    28     </LinearLayout>
    29 
    30     
    31     
    32     <!-- 尾部 -->
    33     <LinearLayout
    34         android:layout_width="match_parent"
    35         android:layout_height="wrap_content"
    36       >
    37         
    38         <include layout="@layout/bottom"/>
    39         
    40     </LinearLayout>
    41 </LinearLayout>
    activity_main.xml

    下面是activity主要文件

     1 package com.weixin.entity;
     2 
     3 public class Messages {
     4 
     5     private String face;
     6     private String name;
     7     private String Date;
     8     private String content;
     9     private Integer noRead;
    10     
    11     public String getFace() {
    12         return face;
    13     }
    14     public void setFace(String face) {
    15         this.face = face;
    16     }
    17     public String getName() {
    18         return name;
    19     }
    20     public void setName(String name) {
    21         this.name = name;
    22     }
    23     public String getDate() {
    24         return Date;
    25     }
    26     public void setDate(String date) {
    27         Date = date;
    28     }
    29     public String getContent() {
    30         return content;
    31     }
    32     public void setContent(String content) {
    33         this.content = content;
    34     }
    35     public Integer getNoRead() {
    36         return noRead;
    37     }
    38     public void setNoRead(Integer noRead) {
    39         this.noRead = noRead;
    40     }
    41     
    42     
    43 
    44 }
    Message
      1 package com.main.weixin;
      2 
      3 import java.util.ArrayList;
      4 import java.util.HashMap;
      5 import java.util.List;
      6 import java.util.Map;
      7 
      8 import com.database.weixin.MyDatabaseOpenHelper;
      9 import com.weixin.entity.Messages;
     10 
     11 import android.app.Activity;
     12 import android.os.Bundle;
     13 import android.util.Log;
     14 import android.view.LayoutInflater;
     15 import android.view.Menu;
     16 import android.view.MenuItem;
     17 import android.view.View;
     18 import android.view.ViewGroup;
     19 import android.view.Window;
     20 import android.widget.AdapterView;
     21 import android.widget.AdapterView.OnItemClickListener;
     22 import android.widget.BaseAdapter;
     23 import android.widget.ListView;
     24 import android.widget.SimpleAdapter;
     25 import android.widget.TextView;
     26 
     27 
     28 public class MainActivity extends Activity {
     29     
     30     private SimpleAdapter sa;
     31     private BaseAdapter ba;
     32     private ListView lv;
     33     private List<Messages> listMessage = new ArrayList<Messages>();
     34     private List<Map<String,Object>> listMessage2 = new ArrayList<Map<String,Object>>();
     35 
     36     @Override
     37     protected void onCreate(Bundle savedInstanceState) {
     38         super.onCreate(savedInstanceState);
     39         requestWindowFeature(Window.FEATURE_NO_TITLE);
     40         setContentView(R.layout.activity_main);
     41         
     42         
     43       //模拟读取数据库或者互联网
     44         for(int i=0 ; i<100 ; i++){
     45             Messages message = new Messages();
     46             message.setFace("houzi");
     47             message.setName("孙行者"+i);
     48             message.setDate("昨天");
     49             message.setContent("有空吗?今晚一起吃饭");
     50             message.setNoRead(i);
     51             listMessage.add(message);//方法一
     52             
     53             
     54        /*     //定义一个界面与数据混合体,一个Item代表一行记录
     55             Map<String,Object> item = new HashMap<String,Object>();
     56             //一行多个空件
     57             item.put("face", R.drawable.houzi);
     58             item.put("name", "孙行者"+i);
     59             item.put("date", "昨天");
     60             item.put("content", "有空吗?今晚一起吃饭");
     61             listMessage2.add(item);*/
     62             
     63         }
     64         
     65         lv = (ListView) findViewById(R.id.listView1);
     66         
     67         /*   sa = new SimpleAdapter(this,
     68                 listMessage2, //data 不仅是数据,而是数据与界面高耦合的混合体
     69                 R.layout.middle1,
     70                 new String[]{"face","name","date","content"}, 
     71                 new int[]{R.id.face,R.id.name,R.id.date,R.id.content});
     72         
     73         lv.setAdapter(sa);
     74         
     75         //添加事件
     76         lv.setOnItemClickListener(new OnItemClickListener(){
     77 
     78             @Override
     79             public void onItemClick(AdapterView<?> parent, View view,
     80                     int position, long id) {
     81                 
     82                 Map<String,Object> item =listMessage2.get(position);
     83                 item.put("name", "行者孙"+position);
     84                 sa.notifyDataSetChanged();
     85             }
     86             
     87         }); */
     88         
     89         
     90     //简单理解为VC绑在一起
     91         ba = new BaseAdapter(){
     92 
     93             //返回记录数目
     94             @Override
     95             public int getCount() {
     96                 
     97                 return listMessage.size();
     98                 
     99             }
    100             
    101             //每一个item项,返回一次界面
    102             @Override
    103             public View getView(int position, View convertView, ViewGroup parent) {
    104                 View view ;
    105                 
    106                 //布局不变,数据变
    107                 
    108                 
    109                 //如果缓存为空,我们生成新的布局作为1个item
    110                 if(convertView == null){
    111                     Log.i("info:", "没有缓存,重新生成"+position);
    112                     LayoutInflater inflater = MainActivity.this.getLayoutInflater();
    113                     
    114 
    115                         //因为getView()返回的对象,adapter会自动赋给ListView
    116                         view = inflater.inflate(R.layout.middle2, null);
    117                         
    118                 }else{
    119                     Log.i("info:", "有缓存,不需要重新生成"+position);
    120                     view = convertView;
    121                     
    122                 }
    123                 
    124                 Messages m = listMessage.get(position);
    125                 Integer noRead = m.getNoRead();
    126                 
    127                 TextView tv_name = (TextView) view.findViewById(R.id.name);
    128                 tv_name.setText(m.getName());
    129                 
    130                 TextView tv_date = (TextView) view.findViewById(R.id.date);
    131                 tv_date.setText(m.getDate());
    132                 
    133                 TextView tv_content = (TextView) view.findViewById(R.id.content);
    134                 tv_content.setText(m.getContent());
    135                 
    136                 System.out.println(noRead);
    137                 
    138                 if( noRead !=0){
    139                     TextView tv_noRead = (TextView) view.findViewById(R.id.noRead);
    140                     //这里的setText()方法接收的是一个字符串类型,而你给了一个Integer类型给它,所以报错了,这里需要把Integer类型转为String类型即可
    141                     tv_noRead.setText(noRead.toString());
    142                 
    143                 }
    144                 
    145                 return view ;
    146                 
    147             }
    148    
    149             @Override
    150             public Object getItem(int position) {
    151                 return null;
    152             }
    153 
    154             @Override
    155             public long getItemId(int position) {
    156                 return 0;
    157             }
    158 
    159             
    160         };
    161         lv.setAdapter(ba);
    162         
    163        //添加事件
    164         lv.setOnItemClickListener(new OnItemClickListener(){
    165 
    166             @Override
    167             public void onItemClick(AdapterView<?> parent, View view,
    168                     int position, long id) {
    169                 Messages message = listMessage.get(position);
    170                 if(message.getNoRead()!=0){
    171                     
    172                     message.setName("行者孙"+position);
    173                     message.setNoRead(0);
    174                     
    175                     view.findViewById(R.id.noRead).setVisibility(View.INVISIBLE);
    176                     
    177                 }else{
    178                     message.setName("孙行者"+position);
    179                 }
    180                 
    181                 ba.notifyDataSetChanged();//
    182             }
    183             
    184         });
    185     }
    186 
    187 
    188     @Override
    189     public boolean onCreateOptionsMenu(Menu menu) {
    190         getMenuInflater().inflate(R.menu.main, menu);
    191         return true;
    192     }
    193 
    194     @Override
    195     public boolean onOptionsItemSelected(MenuItem item) {
    196         int id = item.getItemId();
    197         if (id == R.id.action_settings) {
    198             return true;
    199         }
    200         return super.onOptionsItemSelected(item);
    201     }
    202 }

    效果如下:

    convertView相当于一个缓存,开始为0,当有条目变为不可见,它缓存了它的数据,后面再出来的条目只需要更新数据就可以了,这样大大节省了系统资料的开销。

  • 相关阅读:
    MAC下cocos2dx环境搭建
    eclipse混淆打包出错
    eclipseme升级
    MyEclipse 10 中增加插件
    j2me图片处理大全
    关于svn使用
    NFS相关
    BMP文件格式图解
    UDA1341TS
    OpenOCD初始化脚本(uboot)
  • 原文地址:https://www.cnblogs.com/lgk1002/p/6111161.html
Copyright © 2011-2022 走看看