I am using the RecyclerView
from androidx
(see here).
I am finding that when a row of my RecyclerView
has scrolled off screen, recyclerView.findViewHolderForAdapterPosition()
for the associated position returns null
(as expected).
But what is not expected is that the associated row hasn't yet been recycled. I am checking this by overriding RecyclerView.Adapter.onViewRecycled()
and seeing what is recycled.
So why is a null
ViewHolder
returned for a row that hasn't been recycled?
And a related question is: how do I find those rows that haven't yet been recycled (apart from keeping a list myself using onViewRecycled()
)?
The relevant code I'm using is as follows:
In my Activity
:
// find the row (ViewHolder) for row with specified 'tag'
int position = customAdapter.getPositionForTag(tag);
ViewHolder viewHolder = recyclerView.findViewHolderForAdapterPosition(position);
// viewHolder above is null even if the associated row (with same 'tag') hasn't been recycled yet
In my CustomAdapter
, which extends RecyclerView.Adapter
:
int getPositionForTag(String tag) {
for (int i = 0; i < dataSet.size(); i++) {
if (dataSet.get(i).getTag().equals(tag)) {
return i;
}
}
return -1;
}
@Override
public void onViewRecycled(@NonNull ViewHolder holder) {
// here I monitor which rows are recycled
// I add the 'tag' to the ViewHolder as a convenience, when binding ViewHolder (see below)
Log.d(TAG, "onViewRecycled for tag: " + holder.tag);
}
@Override
public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
// add tag to holder as a convenience...
holder.tag = dataSet.get(position).getTag();
// ... now setup and add views to holder
}