基本使用
-
实现Adapter和ViewHolder
继承RecyclerView.Adapter,设置ViewHolder泛型,ViewHolder一般放在Adapter的内部类
-
编写ViewHolder和Adapter
实现Adapter 和ViewHolder的抽象方法
这里使用ViewBinding,得去build.gradle的android {}标签下开启
viewBinding { enabled = true }
Adapter例子:
class WordAdapter(var dataSet: List<Word>) : RecyclerView.Adapter<WordAdapter.WordViewHolder>() { override fun getItemCount() = dataSet.size override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): WordViewHolder { // 可以根据 viewType 生成不同的Holder,让列表内容多样化 return WordViewHolder.create(parent) } override fun onBindViewHolder(holder: WordViewHolder, position: Int) { val item = dataSet[position] holder.bind(item.word) } class WordViewHolder(private val binding: RecyclerviewItemBinding) : RecyclerView.ViewHolder(binding.root) { fun bind(text: String?) { binding.textView.text = text } companion object { fun create(parent: ViewGroup): WordViewHolder { val binding = RecyclerviewItemBinding.inflate(LayoutInflater.from(parent.context)) return WordViewHolder(binding) } } } }
-
RecyclerView设置Adapter
val wordAdapter = WordAdapter(ArrayList()) val recyclerview = binding.recyclerview recyclerview.adapter = wordAdapter
-
RecyclerView设置布局管理器
recyclerview.layoutManager = LinearLayoutManager(this)
优缺点
优点
有回收和复用,速度快,效率高
缺点
需要额外的空间实现缓存机制,不过问题不大
复用机制
对照着图看代码
流程图
时序图
回收机制
流程图
时序图
布局流程
dispatchLayoutStep1
- Adapter的更新;
- 决定该启动哪种动画;
- 保存当前View的信息(getLeft(), getRight(), getTop(), getBottom()等);
- 如果有必要,先跑一次布局并将信息保存下来。
dispatchLayoutStep2
真正对子View做布局的地方。
- 计算锚点,以锚点开始填充RecyclerView(其实就是执行fill方法)。
- 执行fill方法,判断RecyclerView是否还有空间,如果有,执行layoutChunk方法,直至填充满。
- layoutChunk方法中,寻找到当前要添加的子view,add到RecyclerView中。
- 对子view进行measure和layout。
dispatchLayoutStep3
为动画保存View的相关信息; 触发动画; 相应的清理工作。
其实dispatchLayoutStep3()就是做了一些收尾工作,将一些变量重置,处理下动画。
mState.mLayoutStep
- 初始化为STEP_START
- 执行完dispatchLayoutStep1后,mState.mLayoutStep = State.STEP_LAYOUT;
- 执行完dispatchLayoutStep2后,mState.mLayoutStep = State.STEP_ANIMATIONS;
- 执行完dispatchLayoutStep3后,mState.mLayoutStep = State.STEP_START;