Adapter也就是适配器,那什么是适配器呢?其实适配器你可以理解为一个连接前台界面和后台数据的接口。
在ListView,GridView时经常和Adapter一起使用。可能最早接触ListView的时候我们就是知道ListView通过setAdapter()函数来列出一个字符串数组。那么像QQ列表一样的ListView是怎样做的呢?
好,下来教大家做。
那么我就以一个实际的Dome来告诉大家如何去做一个QQ列表一样的ListView。先来看一下目标
那么好我们一起来做。
第一步:创建一个Item类
这个类所包含的就是将我们在一个ListView中的一栏所展示的内容,比如字符串呀,图片资源呀等等,我们可以在上面看出我们的Item中是要有三个内容的,名字,图片资源和手机号。这个类很简单不过多介绍了。
public class AdapterItem { private String name; private int imageResourceId; private String phoneNumber; public AdapterItem() { } public AdapterItem(String name, int imageResourceId, String phoneNumber) { this.name = name; this.imageResourceId = imageResourceId; this.phoneNumber = phoneNumber; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getImageResourceId() { return imageResourceId; } public void setImageResourceId(int imageResourceId) { this.imageResourceId = imageResourceId; } public String getPhoneNumber() { return phoneNumber; } public void setPhoneNumber(String phoneNumber) { this.phoneNumber = phoneNumber; } @Override public String toString() { return "AdapterItem{" + "name='" + name + '\'' + ", imageResourceId=" + imageResourceId + ", phoneNumber='" + phoneNumber + '\'' + '}'; } }
第二步:创建一个用来控制ListView中一项的XML布局文件
以上面的结果可以看出,左边是一个图片,右边是一个两个显示字符串的TextView,为了更接近QQ效果我对显示图片的View做了处理,就是把图片显示成圆形,这个处理不做介绍,大家可以换成ImageView用方形图片可以达到同样学习效果。
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" android:paddingLeft="16dp" android:paddingRight="16dp" android:paddingTop="4dp" android:paddingBottom="4dp"> <com.jack.csdn.csdn_dome.ui.adapter.CircularImage android:id="@+id/adapter_item_circularImage" android:layout_width="40dp" android:layout_height="40dp" /> <TextView android:id="@+id/adapter_item_textView1" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignTop="@+id/adapter_item_circularImage" android:layout_toRightOf="@+id/adapter_item_circularImage" android:textSize="@dimen/abc_text_size_body_1_material" android:text="Simple Text" android:textColor="#FF000000" android:layout_marginLeft="16dp" /> <TextView android:id="@+id/adapter_item_textView2" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignLeft="@+id/adapter_item_textView1" android:layout_alignBottom="@+id/adapter_item_circularImage" android:textSize="@dimen/abc_text_size_caption_material" android:text="Simple Text Caption" /> </RelativeLayout>
CircularImage类的源码(这个和我这一节的内容无关,也可以换成ImageView,对这个类不做介绍):
public class CircularImage extends MaskedImage { public CircularImage(Context paramContext) { super(paramContext); } public CircularImage(Context paramContext, AttributeSet paramAttributeSet) { super(paramContext, paramAttributeSet); } public CircularImage(Context paramContext, AttributeSet paramAttributeSet, int paramInt) { super(paramContext, paramAttributeSet, paramInt); } public Bitmap createMask() { int i = getWidth(); int j = getHeight(); Bitmap.Config localConfig = Bitmap.Config.ARGB_8888; Bitmap localBitmap = Bitmap.createBitmap(i, j, localConfig); Canvas localCanvas = new Canvas(localBitmap); Paint localPaint = new Paint(1); localPaint.setColor(-16777216); float f1 = getWidth(); float f2 = getHeight(); RectF localRectF = new RectF(0.0F, 0.0F, f1, f2); localCanvas.drawOval(localRectF, localPaint); return localBitmap; } }
MaskedImage类的源码:
public abstract class MaskedImage extends ImageView { private static final String TAG = MaskedImage.class.getSimpleName(); private static final Xfermode MASK_XFERMODE; private Bitmap mask; private Paint paint; static { PorterDuff.Mode localMode = PorterDuff.Mode.DST_IN; MASK_XFERMODE = new PorterDuffXfermode(localMode); } public MaskedImage(Context paramContext) { super(paramContext); } public MaskedImage(Context paramContext, AttributeSet paramAttributeSet) { super(paramContext, paramAttributeSet); } public MaskedImage(Context paramContext, AttributeSet paramAttributeSet, int paramInt) { super(paramContext, paramAttributeSet, paramInt); } public abstract Bitmap createMask(); protected void onDraw(Canvas paramCanvas) { Drawable localDrawable = getDrawable(); if (localDrawable == null) return; try { if (this.paint == null) { Paint localPaint1 = new Paint(); this.paint = localPaint1; this.paint.setFilterBitmap(false); Paint localPaint2 = this.paint; Xfermode localXfermode1 = MASK_XFERMODE; @SuppressWarnings("unused") Xfermode localXfermode2 = localPaint2.setXfermode(localXfermode1); } float f1 = getWidth(); float f2 = getHeight(); int i = paramCanvas.saveLayer(0.0F, 0.0F, f1, f2, null, 31); int j = getWidth(); int k = getHeight(); localDrawable.setBounds(0, 0, j, k); localDrawable.draw(paramCanvas); if ((this.mask == null) || (this.mask.isRecycled())) { Bitmap localBitmap1 = createMask(); this.mask = localBitmap1; } Bitmap localBitmap2 = this.mask; Paint localPaint3 = this.paint; paramCanvas.drawBitmap(localBitmap2, 0.0F, 0.0F, localPaint3); paramCanvas.restoreToCount(i); return; } catch (Exception localException) { StringBuilder localStringBuilder = new StringBuilder() .append("Attempting to draw with recycled bitmap. View ID = "); Log.i(TAG,"localStringBuilder==" + localStringBuilder); } } }
第三步:创建一个继承自BaseAdapter的类。
先上源码:
public class MyAdapter extends BaseAdapter { private List<AdapterItem> mAdapterItemList = new ArrayList<>(); private Context mContext; public MyAdapter(Context context ,List<AdapterItem> adapterItemList) { this.mAdapterItemList = adapterItemList; this.mContext = context; } @Override public int getCount() { return mAdapterItemList.size(); } @Override public long getItemId(int position) { return 0; } @Override public Object getItem(int position) { if(position<0||position>=mAdapterItemList.size()){ return null; } return mAdapterItemList.get(position); } @Override public View getView(int position, View mView, ViewGroup parent) { //1.获取布局文件 mView= LayoutInflater.from(mContext).inflate(R.layout.adapter_item_layout, null); //2.获取布局文件中的组件 //3.为各个组件设置相应的属性(文字,图片。。。) ((TextView)mView.findViewById(R.id.adapter_item_textView1)).setText(mAdapterItemList.get(position).getName()); ((TextView)mView.findViewById(R.id.adapter_item_textView2)).setText(mAdapterItemList.get(position).getPhoneNumber()); ((CircularImage)mView.findViewById(R.id.adapter_item_circularImage)).setImageResource(mAdapterItemList.get(position).getImageResourceId()); return mView; } }看到getView()了吧,我们就是要在这个上面去做我们对一个Item设置不同的内容的地方。
这个类中新增两个成员变量,Context和一个List<AdapterItem>的对象。我们要获取资源文件,就要用到上下文(就是Context),而List就是我们的数据了,不是说了Adapter不是视图和数据之间的接口嘛,所以就要有这两个喽(可以先简单这样理解)。
然后通过LayoutInflater的静态函数得到一个LayoutInflater的对象,然后通过inflate的方法就可以载入一个布局文件,然后就可以通过findViewByIdde的方法来获得其中的组件。
为组件设置文字图片的额操作不做解释了。
第四步:使用我们自己的Adapter
这里先上源码:
public class AdapterActivity extends ActionBarActivity { private ListView mListView ; private MyAdapter mMyAdapter ; private List<AdapterItem> mAdapterItemList = new ArrayList<>(); @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_adapter); //1.获取ListView组件 mListView = (ListView)findViewById(R.id.adapter_listView); //2.初始化数据 int[] imageResourceIds = new int[]{R.drawable.img_1,R.drawable.img_2,R.drawable.img_3,R.drawable.img_4,R.drawable.img_5,R.drawable.img_6}; String[] phoneNumbers = getResources().getStringArray(R.array.adapter_number_resources); String[] names = getResources().getStringArray(R.array.adapter_name_resources); for(int i =0;i<names.length;i++){ mAdapterItemList.add(new AdapterItem(names[i],imageResourceIds[i],phoneNumbers[i])); } //3.初始化Adapter mMyAdapter = new MyAdapter(this,mAdapterItemList); //4.使用ListView的setAdapter()函数关联视图和数据 mListView.setAdapter(mMyAdapter); } }Activity布局文件:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context="com.jack.csdn.csdn_dome.ui.adapter.AdapterActivity"> <ListView android:id="@+id/adapter_listView" android:layout_width="match_parent" android:layout_height="wrap_content" android:paddingTop="4dp" android:paddingBottom="4dp"> </ListView> </RelativeLayout>
arrays资源文件中两条数组资源:
<string-array name="adapter_number_resources"> <item>15674838520</item> <item>15474858521</item> <item>15774878522</item> <item>13874798523</item> <item>13974938524</item> <item>15274038525</item> </string-array> <string-array name="adapter_name_resources"> <item>张三</item> <item>王灿</item> <item>花花</item> <item>李斌</item> <item>蔡青</item> <item>涛哥</item> </string-array>drawable文件夹下的图片资源:
快去动手试试吧。有问题联系我。