#仅个人学习记录,如有疏漏,请多见谅
使用RecyclerView效果:(效果演示,本文不用该例子)

实现分析:
观察列表,这是一个支持滑动的竖直(也可以是网格)形状的列表,每个列表项的数值会根据位置而不同。并且每个列表项都有一个布局(这里相同,且只有一个标签。复杂点程序可以每个列表项布局不同)。那为什么叫RecyclerView呢?Recycler是回收复用的意思,也就是说RecyclerView实现了某些部件的复用,这就提升了流畅度。既然是回收,那么滑动显示出来的列表项应该是实时生成的,而不是把全部数据一次全部加载成一个列表。同时实时生成的列表项都摆放在正确的位置。
那么要实现这些机制需要什么呢?
①最基本的,一个RecyclerView组件,在需要的位置占一个坑来放置你的列表。
②列表的形状可以有多样,比如竖直型或者网格型。列表滑动操作,新列表项正确摆放,这些都需要一个有着管理器身份的东西,这就是LayoutManager。
③显然需要给列表项设计布局文件,即列表项视图XML。
④既然有列表项视图,并且每个列表项是实时生成的,因此生成的一个列表项应该有实时生成的一个view子对象相对应。同时为了实现回收,实际上安卓是生成ViewHolder,即视图容器,它装载着View子对象。
⑤ViewHolder只是个容器,它需要有人去生成,控制它。并且每个列表项的数据因位置而不同,根据MVC模式,需要一个处于控制层的东西,作为连通数据与视图的媒介,这就是控制器对象Adapter。
代码实现:
①在布局文件添加一个RecyclerView组件
<androidx.recyclerview.widget.RecyclerView
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/recycle_view"
android:layout_width="match_parent"
android:layout_height="match_parent">
</androidx.recyclerview.widget.RecyclerView>②设置LayoutManager管理器
private RecyclerView mRecyclerView;
mRecyclerView=View.findViewById(R.id.recycle_view)
mRecyclerView.setLayoutManager(new LinearLayoutManager(getActivity()));
在布局文件对应的Java类文件中,实例化RecyclerView组件后,调用setLayoutManager方法设置一个管理器,参数决定列表形状,这里是new LinearLayoutManager(getActivity())代表竖直型列表。还可以是GridLayoutManager类,代表网格形式。
③新建一个列表项视图xml
目录layout右键->new resource file,创建,比较简单。这里简单实例一个。
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:padding="8dp">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/crime_title"
android:text="@string/crime_title_label"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/crime_date"
android:text="@string/crime_date_label"/>
</LinearLayout>④创建Adapter类实现ViewHolder控制
Adapter负责:
1.创建必要的ViewHolder
2.绑定ViewHolder至模型层数据
RecycleView需要显示视图对象时,就会去找它的Adapter。
程序运行,RecycleView首次会调用Adapter的getItemCount方法,获取数据项的数量。因此Adapter类的getItemCount方法必须覆盖,返回值不能是0,否则列表为空。(RecycleView,Adapter,ViewHolder,LayoutManager各司其职)。
获取数据项的数量后,RecycleView会调用Adapter的onCreateViewHolder方法,创建一个ViewHolder实例。紧接着会马上调用Adapter的onBindViewHolder方法,这个方法的一个参数是刚获取的ViewHolder实例,另一个是ViewHolder在列表的位置position(程序会自动确定)。该方法实现将目标位置的数据绑定到ViewHolder视图上。在未获取够用的ViewHolder,这两个函数循环调用。
由于回收机制的存在,在获取了够用的ViewHolder后,RecycleView就会停止调用onCreateViewHolder方法。它会将旧的(屏幕外)的ViewHolder回收利用,节约时间和内存。
创建一个Adapter类,继承自RecycleView.Adapter<创建的ViewHolder类>
假设我已经创建了一个ViewHolder类叫CrimeHolder类。
private class CrimeAdapter extends RecyclerView.Adapter<CrimeHolder>{
private List<Crime> mCrimes;
public CrimeAdapter(List<Crime> crimes) {
mCrimes = crimes;
}
@NonNull
@Override
public CrimeHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_item_crime,parent,false);
CrimeHolder crimeHolder =new CrimeHolder(view);
return crimeHolder;
}
@Override
public void onBindViewHolder(@NonNull CrimeHolder holder, int position) {
Crime crime = mCrimes.get(position);
holder.bind(crime);
}
@Override
public int getItemCount() {
return mCrimes.size();
}
}onCreateViewHolder方法自动识别为CrimeHolder类型。在其中根据布局文件,生成View子对象,装载到一个CrimeHolder实例中,然后返回该CrimeHolder实例。
onBindViewHolder方法中实现数据绑定,这里有一点需要注意的是,因为回收机制的存在,onCreateViewHolder调用不频繁,因此业务逻辑不要写在onCreateViewHolder中,并且onBindViewHolder方法应该轻巧高效,保证流畅性。
getItemCount方法返回数据项的数量。因此Adapter实例在创建使用的时候应该要传入你的列表数据,这里通过构造方法传入一个Crime类的数组作示例。
⑤创建ViewHolder类来装载View子对象
在Adapter类的实现中,我们用的CrimeHolder类,因此我们创建CrimeHolder类继承自RecycleView.ViewHolder
private class CrimeHolder extends RecyclerView.ViewHolder{
private TextView mTitleTextView;
private TextView mDateTextView;
public CrimeHolder(@NonNull View itemView) {
super(itemView);
mTitleTextView = (TextView) itemView.findViewById(R.id.crime_title);
mDateTextView = (TextView) itemView.findViewById(R.id.crime_date);
}
public void bind(Crime crime){
mTitleTextView.setText(crime.getTitle());
mDateTextView.setText(crime.getDate().toString());
}
}在CrimeHolder类的构造方法中,super(itemView),实际上是把view视图给基类引用。这个view视图在onCreateViewHolder方法中作为构造方法的参数传递过来的,当然也可以自己实现在构造方法中创建view视图。
同时还在CrimeHolder类中创建了一个bind方法,实现数据的绑定。这样每生成一个CrimeHolder时,直接在onCreateViewHolder中调用该实例的bind方法就可以方便的实现数据绑定。
⑥绑定RecycleView组件与Adapter控制器
mAdapter = new CrimeAdapter(crimes);
mCrimeRecyclerView.setAdapter(mAdapter);实例化一个Adapter对象,调用RecycleView的setAdapter方法。
补充内容:(学习过程中记录)
Adapter的notifyDataSetChanged方法:刷新显示列表项(个人猜测是不断调用onBindViewHolder方法)