Android listview加载不同布局与adapter用法
来源:互联网 发布:软件停止运行怎么回事 编辑:程序博客网 时间:2024/06/07 03:17
Android listview加载不同布局与adapter用法
android开发过程中会经常用到listview,虽然recycleview也出来了,但是还是存在一些bug没有解决,还不是特别的成熟,那我们就来介绍一下listview的使用及其加载不同布局的item的一般写法。
- 首先我们listview需要加载不同的布局,首先我们需要些几个不同的布局(我写不同item的布局喜欢以inflate_功能_type_one来命名,大家可以根据自己的习惯,但是一定要有一个好的编程习惯哦!!!)
布局一:
<?xml version="1.0" encoding="utf-8"?><TextView xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/txt_inflat_type_one" android:background="#44C494" android:layout_width="match_parent" android:layout_height="40dp"></TextView>
布局二:
<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="horizontal" android:background="#ffa07a" android:layout_width="match_parent" android:layout_height="40dp"> <TextView android:id="@+id/txt_inflat_type_two" android:layout_width="200dp" android:layout_height="match_parent" /> <ImageView android:id="@+id/img_inflat_type_two" android:layout_width="match_parent" android:layout_height="match_parent" android:contentDescription="@null" android:background="@mipmap/ic_launcher"/></LinearLayout>
布局三:
<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="horizontal" android:layout_width="match_parent" android:layout_height="40dp"> <TextView android:id="@+id/txt_inflat_type_there_1" android:layout_width="match_parent" android:layout_height="match_parent" /> <TextView android:id="@+id/txt_inflat_type_there_2" android:layout_width="match_parent" android:layout_height="match_parent" /></LinearLayout>
- 接下来就是需要写的是MyAdapter了,我这里是继承BaseAdapter来写的,首先我们需要重写BaseAdapter的四个方法,getCount(listview需要展示的个数,根据数据源而定的,我在这里是写的规固定的)、getItem(获取数据源的单个实体类)、getItemId(获取下角标位置)、getView(UI控件的获取及其数据的挂载)。
这里,我们需要写的是不同布局item显示的样式,我们还需要重写其他两个方法:getItemViewType(获取每一个下角标(position)相对应得item类型),getViewTypeCount(几种布局的显示的总数)。
注意:
//listview显示时的不同布局的item private int TypeOne=0;//注意这个不同布局的类型起始值必须从0开始 private int TypeTwo=1; private int TypeThere=2;
- 因为在实际开发项目中,我们要加载的数据往往是特别大的,这时候我们就要考虑布局的复用,说到复用我们就要来了解一下ListView的原理:ListView中的每一个Item显示都需要Adapter调用一次getView的方法,这个方法会传入一个convertView的参数,返回的View就是这个Item显示的View。如果当Item的数量足够大,再为每一个Item都创建一个View对象,必将占用很多内存,创建View对象(getLayoutInflater().inflate(R.layout.inflate_type_one, parent,false);从xml中生成View,这是属于IO操作)也是耗时操作,所以必将影响性能。Android提供了一个叫做Recycler(反复循环器)的构件,就是当ListView的Item从上方滚出屏幕视角之外,对应Item的View会被缓存到Recycler中,相应的会从下方生成一个Item,而此时调用的getView中的convertView参数就是滚出屏幕的Item的View,所以说如果能重用这个convertView,就会大大改善性能。
getView方法中的操作是这样的:先从xml中创建view对象(inflate操作,我们采用了重用convertView方法优化),然后在这个view去findViewById,找到每一个子View,如:一个TextView等。这里的findViewById操作是一个树查找过程,也是一个耗时的操作,所以这里也需要优化,就是使用viewHolder,把每一个子View都放在Holder中,当第一次创建convertView对象时,把这些子view找出来。然后用convertView的setTag将viewHolder设置到Tag中,以便系统第二次绘制ListView时从Tag中取出。当第二次重用convertView时,只需从convertView中getTag取出来就可以。
我们就需要先写几个不同item需要的viewHolder类:
private class TypeOneViewHolder{ private TextView txt_inflat_type_one; }private class TypeTwoViewHolder{ private TextView txt_inflat_type_two; private ImageView img_inflat_type_two; } private class TypeThereViewHolder{ private TextView txt_inflat_type_there_1; private TextView txt_inflat_type_there_2; }
getView方法:
@Override public View getView(int position, View convertView, ViewGroup parent) { TypeOneViewHolder typeOneViewHolder = null; TypeTwoViewHolder typeTwoViewHolder = null; TypeThereViewHolder typeThereViewHolder = null; int Type=getItemViewType(position); //第一次没有加载convertView if(convertView==null){ if(Type==TypeOne){ convertView=getLayoutInflater().inflate(R.layout.inflate_type_one,parent,false); typeOneViewHolder=new TypeOneViewHolder(); typeOneViewHolder.txt_inflat_type_one= (TextView) convertView.findViewById(R.id.txt_inflat_type_one); convertView.setTag(typeOneViewHolder); }else if(Type==TypeTwo){ convertView=getLayoutInflater().inflate(R.layout.inflate_type_two,parent,false); typeTwoViewHolder=new TypeTwoViewHolder(); typeTwoViewHolder.txt_inflat_type_two= (TextView) convertView.findViewById(R.id.txt_inflat_type_two); typeTwoViewHolder.img_inflat_type_two= (ImageView) convertView.findViewById(R.id.img_inflat_type_two); convertView.setTag(typeTwoViewHolder); }else if(Type==TypeThere){ convertView=getLayoutInflater().inflate(R.layout.inflate_type_there,parent,false); typeThereViewHolder=new TypeThereViewHolder(); typeThereViewHolder.txt_inflat_type_there_1= (TextView) convertView.findViewById(R.id.txt_inflat_type_there_1); typeThereViewHolder.txt_inflat_type_there_2= (TextView) convertView.findViewById(R.id.txt_inflat_type_there_2); convertView.setTag(typeThereViewHolder); } }else { //布局的复用convertView //根据setTag()和getTag()方法来实现布局的复用 if(Type==TypeOne){ typeOneViewHolder= (TypeOneViewHolder) convertView.getTag(); }else if(Type==TypeTwo){ typeTwoViewHolder= (TypeTwoViewHolder) convertView.getTag(); }else if(Type==TypeThere){ typeThereViewHolder= (TypeThereViewHolder) convertView.getTag(); } } //设置数据 if(Type==TypeOne){ typeOneViewHolder.txt_inflat_type_one.setText("第一种布局"+position); }else if(Type==TypeTwo){ typeTwoViewHolder.txt_inflat_type_two.setText("第二种布局"+position); typeTwoViewHolder.img_inflat_type_two.setImageResource(R.mipmap.ic_launcher); }else if(Type==TypeThere){ typeThereViewHolder.txt_inflat_type_there_1.setText("第三种布局"+position+"左"); typeThereViewHolder.txt_inflat_type_there_2.setText("第三种布局"+position+"右"); } return convertView; }
实现效果截图:
最后附整体代码:
package com.example.administrator.baseadapterapplication;import android.content.Context;import android.support.v7.app.AppCompatActivity;import android.os.Bundle;import android.view.View;import android.view.ViewGroup;import android.widget.BaseAdapter;import android.widget.ImageView;import android.widget.ListView;import android.widget.TextView;/** * Android listview加载不同布局与adapter用法 *@author wujun * */public class MainActivity extends AppCompatActivity { private ListView listView; private MyAdapter myAdapter; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); initView(); initData(); } private void initView() { listView= (ListView) findViewById(R.id.listview); } private void initData() { myAdapter=new MyAdapter(MainActivity.this); listView.setAdapter(myAdapter); myAdapter.notifyDataSetChanged(); } //适配器 private class MyAdapter extends BaseAdapter { private Context mcontext; //listview显示时的不同布局的item private int TypeOne=0;//注意这个不同布局的类型起始值必须从0开始 private int TypeTwo=1; private int TypeThere=2; private MyAdapter(Context context){ mcontext=context; } @Override public int getCount() { return 30; } @Override public Object getItem(int position) { return null; } @Override public long getItemId(int position) { return position; } //item的不同布局的判断 @Override public int getItemViewType(int position) {// return super.getItemViewType(position); if(position==1||position==5||position==10||position==15||position==20||position==26){ return TypeOne; }else if(position==2||position==6||position==8||position==13||position==23||position==0){ return TypeTwo; }else { return TypeThere; } } @Override public int getViewTypeCount() {// return super.getViewTypeCount(); return 3; } @Override public View getView(int position, View convertView, ViewGroup parent) { TypeOneViewHolder typeOneViewHolder = null; TypeTwoViewHolder typeTwoViewHolder = null; TypeThereViewHolder typeThereViewHolder = null; int Type=getItemViewType(position); if(convertView==null){ if(Type==TypeOne){ convertView=getLayoutInflater().inflate(R.layout.inflate_type_one,parent,false); typeOneViewHolder=new TypeOneViewHolder(); typeOneViewHolder.txt_inflat_type_one= (TextView) convertView.findViewById(R.id.txt_inflat_type_one); convertView.setTag(typeOneViewHolder); }else if(Type==TypeTwo){ convertView=getLayoutInflater().inflate(R.layout.inflate_type_two,parent,false); typeTwoViewHolder=new TypeTwoViewHolder(); typeTwoViewHolder.txt_inflat_type_two= (TextView) convertView.findViewById(R.id.txt_inflat_type_two); typeTwoViewHolder.img_inflat_type_two= (ImageView) convertView.findViewById(R.id.img_inflat_type_two); convertView.setTag(typeTwoViewHolder); }else if(Type==TypeThere){ convertView=getLayoutInflater().inflate(R.layout.inflate_type_there,parent,false); typeThereViewHolder=new TypeThereViewHolder(); typeThereViewHolder.txt_inflat_type_there_1= (TextView) convertView.findViewById(R.id.txt_inflat_type_there_1); typeThereViewHolder.txt_inflat_type_there_2= (TextView) convertView.findViewById(R.id.txt_inflat_type_there_2); convertView.setTag(typeThereViewHolder); } }else { if(Type==TypeOne){ typeOneViewHolder= (TypeOneViewHolder) convertView.getTag(); }else if(Type==TypeTwo){ typeTwoViewHolder= (TypeTwoViewHolder) convertView.getTag(); }else if(Type==TypeThere){ typeThereViewHolder= (TypeThereViewHolder) convertView.getTag(); } } //设置数据 if(Type==TypeOne){ typeOneViewHolder.txt_inflat_type_one.setText("第一种布局"+position); }else if(Type==TypeTwo){ typeTwoViewHolder.txt_inflat_type_two.setText("第二种布局"+position); typeTwoViewHolder.img_inflat_type_two.setImageResource(R.mipmap.ic_launcher); }else if(Type==TypeThere){ typeThereViewHolder.txt_inflat_type_there_1.setText("第三种布局"+position+"左"); typeThereViewHolder.txt_inflat_type_there_2.setText("第三种布局"+position+"右"); } return convertView; } private class TypeOneViewHolder{ private TextView txt_inflat_type_one; } private class TypeTwoViewHolder{ private TextView txt_inflat_type_two; private ImageView img_inflat_type_two; } private class TypeThereViewHolder{ private TextView txt_inflat_type_there_1; private TextView txt_inflat_type_there_2; } }}
大家有什么android开发问题可以一起交流(QQ:965244491 附微信二维码
2 0
- Android listview加载不同布局与adapter用法
- android ListView加载不同布局
- android ListView加载不同布局
- Android Listview加载不同布局
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- Android listview与adapter用法
- UITableView性能优化 以及动态计算cell高度 新方法
- C语言学习记录(九):迷你shell和迷你ftpd的实现(附源码)
- Android平台访问https 双向认证(上)
- LightOJ 1361 Component Placement 最小割
- Android开发环境搭建的窍门以及难点解决
- Android listview加载不同布局与adapter用法
- 第四章 局域网
- patest L3-007 天梯地图
- 自己网页调用百度地图API
- 程序员接私活经验谈
- Android尺子
- 安卓学习摘要--适配器
- HTML5简介
- 手机开发实战117——蓝牙介绍1