Incorrect sticky header position calculation when changing data
Hi, I'm using StickyHeaderLinearLayoutManager for my EpoxyRecyclerView and in my controller I override the isStickyHeader() function:
override fun isStickyHeader(position: Int): Boolean {
return adapter.getModelAtPosition(position) is MyItemHeader
}I noticed that when switching between 2 data sets (2 different filters on same data) the second sticky header is off by 1 and a normal list item is set as the sticky header. Set 1 has 4 rows and set 2 has 174 rows (including item rows header rows and the first row which is a title row that shows how many items are in the list). Set1: [TitleItem(id: t1, value:2), MyItemHeader(id: h1, value: h1), Item(id: i1, value: val1), Item(id: i3, value: val3)] Set2: [TitleItem(id: t1, value:170), MyItemHeader(id: h1, value: h1), Item(id: i1, value: val1), Item(id: i2, value: val2), Item(id: i3, value: val3), Item(id: i4, value: val4), MyItemHeader(id: h2, value: h2), Item(id: i5, value: val5), ...]
So when switching from Set1 to Set2, id2 is added between id1 and id3, and other rows are added at the end.
When debugging it I see that upon change HeaderPositionsAdapterDataObserver.onItemRangeInserted() is called twice with those parameters:
positionStart: 4, itemCount: 169
positionStart: 3 , itemCount: 1
So after the first call position 6 gets set as a header (headerPositions.add(6)) correctly, but then the second call moves it by one position because that call is interpreted as 1 item is added at position 3.
I think that the problem is that when onItemRangeInserted() is called, the data set in the adapter is already updated with the new data (in AsyncEpoxyDiffer.readOnlyList), as it has 174 items. So on that insert the headers are set with the positions correct for the end of the process (no change on that is needed).
Now the second onItemRangeInserted() call for the insert of item i2 causes a shift in header ids. It assumes that the differ list was changed again, but it wasn't, so no shift of positions should happen
Source: airbnb/epoxy