The current code tests bottom against ScrollPosition + Height with bottom starting from 0:
It seems that the test, if i starts at FirstVisibleIndex, should be against the height of the visible items, as follows:
B4X:
'Gets the index of the last visible item.
Public Sub getLastVisibleIndex As Int
Dim first As Int = getFirstVisibleIndex
Dim bottom As Int
For i = first To items.Size - 1
bottom = bottom + heights.Get(i) + dividerHeight
If bottom >= sv.ScrollPosition + sv.Height Then Return Max(i - 1, first)
Next
Return items.Size - 1
End Sub
It seems that the test, if i starts at FirstVisibleIndex, should be against the height of the visible items, as follows:
B4X:
'Gets the index of the last visible item.
Public Sub getLastVisibleIndex As Int
Dim first As Int = getFirstVisibleIndex
Dim bottom As Int
For i = first To items.Size - 1
bottom = bottom + heights.Get(i) + dividerHeight
If bottom >= sv.Height Then Return Max(i - 1, first)
Next
Return items.Size - 1
End Sub