本文是博主对Adapter(适配器)的一些理解,为了加深对Adapter的理解以及记录自己的阶段学习而写,同时也适合初学者阅读,参考本条博客的逻辑进行学习。
首先有5个代码块,由简单到难,也是按这个顺序来。
(1)XML主代码
(1)只需要一个LIstView来实现,不需要填充内容。因为整个屏幕都是ListView,后面我们再往里面填充即可。
1.<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:orientation="vertical" android:layout_height="match_parent" tools:context=".MainActivity"> <ListView android:layout_width="match_parent" android:layout_height="wrap_content" android:id="@+id/lv_base" /> </LinearLayout>
(2)XML布局代码
(2)这是为了实现每个Item的元素是怎么样来布局的,比如把图片放在哪个位置,文字放在图片左边等等。当然只是布局,并不填充内容进去。
<?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="match_parent"> <ImageView android:id="@+id/imaged" android:layout_width="wrap_content" android:layout_height="match_parent" android:layout_margin="5dp" /> <LinearLayout android:layout_width="wrap_content" android:orientation="vertical" android:layout_height="wrap_content"> <TextView android:id="@+id/tv_title" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textSize="22dp"/> <TextView android:id="@+id/tv_subtitle" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textSize="13dp"/> </LinearLayout> </LinearLayout>
(3)Java内容类代码
(3)然后下面就是Java内容类代码,这是为了填充内容和获取内容的类,不需要继承什么,主要是为了以下Java主函数和Java自定义适配器类中的List容器限制泛型,只能传入内容类对象。
1.package com.example.adapter_test.base_class; public class LayoutData { private int imageViewID; private String textView; private String subtextView; public LayoutData(int imageViewID, String textView, String subtextView) { this.imageViewID = imageViewID; this.textView = textView; this.subtextView = subtextView; } public int getImageViewID() { return imageViewID; } public String getTextView() { return textView; } public String getSubtextView() { return subtextView; } }
(4)Java自定义Adapter代码
(4)然后就是比较难理解的Java自定义Adapter类的编写,话不多说,注释已经很详细了,这个类主要是把数据和ListView连接起来,在主函数中调用此类,最重要的就是getView()方法,灵活度高。
package com.example.adapter_test.base_class; import android.content.Context; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.BaseAdapter; import android.widget.ImageView; import android.widget.TextView; import androidx.annotation.LayoutRes; import com.example.adapter_test.R; import java.util.ArrayList; import java.util.List; public class MyAdapter extends BaseAdapter { //定义数据 private List<LayoutData> data = new ArrayList<LayoutData>(); //定义上下文 private Context context; //定义xml布局文件(也可以直接设置,此处是为了通用度高) private int mResource; //让主函数传参过来(数据,上下文,xml布局文件) public MyAdapter(List<LayoutData> data, Context context, @LayoutRes int resource) { this.data = data; this.context = context; this.mResource = resource; } //下面三个重写函数基本不变 @Override public int getCount() { return data.size(); } @Override public Object getItem(int position) { return data.get(position); } @Override public long getItemId(int position) { return position; } @Override public View getView(int position, View convertView, ViewGroup parent) { //定义一个holder对象 ViewHolder holder; //调用上方的getItem函数,由于向上转换为Object,需要类型转换 //等于data.get(position),这样的话就不用类型转换了 //此处作用是获取对应position的List<Layoutdata> data列表数据的图片和文字 LayoutData dd= (LayoutData) getItem(position); //判断是否已经创建过了,如果没创建过 if(convertView == null) { //创建一个holder对象用来存储findViewByid的控件 holder = new ViewHolder(); //实例化布局 convertView=LayoutInflater.from(context).inflate(mResource, parent, false); //在布局中找控件 holder.img = (ImageView)convertView.findViewById(R.id.imaged); holder.title = (TextView)convertView.findViewById(R.id.tv_title); holder.subtitle = (TextView)convertView.findViewById(R.id.tv_subtitle); //储存对象 convertView.setTag(holder); } //已经创建过了 else { //就不用再找控件了 holder = (ViewHolder)convertView.getTag(); } //以下三句必须放在if语句的外面,否则只会显示一条 //设置图片和文字 holder.img.setImageResource(dd.getImageViewID()); holder.title.setText(dd.getTextView()); holder.subtitle.setText(dd.getSubtextView()); //返回填充完成的Item return convertView; } //储存控件类,布局里有什么控件就定义什么 class ViewHolder{ public ImageView img; public TextView title; public TextView subtitle; } }
(5)Java主代码
(5)最后就是Java主函数,这个比较简单,找一下XML里面的ListView,然后定义一个List data的容器为了存放数据,然后在OnCreate()中填充一下数据,再为ListView设置一个Adapter就可以显示了。
package com.example.adapter_test; import androidx.appcompat.app.AppCompatActivity; import android.os.Bundle; import android.widget.ListView; import com.example.adapter_test.base_class.LayoutData; import com.example.adapter_test.base_class.MyAdapter; import java.util.ArrayList; import java.util.List; public class BaseAdapter extends AppCompatActivity { ListView listView; List<LayoutData> data = new ArrayList<LayoutData>(); @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_base_adapter); listView = findViewById(R.id.lv_base); initdata(); listView.setAdapter(new MyAdapter(data,this,R.layout.simple_adapter_2)); } private void initdata() { LayoutData layoutData1=new LayoutData(R.drawable.local ,"无忌哥","999"); data.add(layoutData1); LayoutData layoutData2=new LayoutData(R.drawable.like ,"wujige","333"); data.add(layoutData2); LayoutData layoutData3=new LayoutData(R.drawable.share ,"oo哥","777"); data.add(layoutData3); } }