我想确定RecyclerView中最可见的项目,因此我使用以下方法:
public int getMostVisibleIndex() {
// try to figure which child is the most visible on screen
LinearLayoutManager layoutManager = ((LinearLayoutManager) getLayoutManager());
mFirstVisibleIndex = layoutManager.findFirstVisibleItemPosition();
mLastVisibleIndex = layoutManager.findLastVisibleItemPosition();
// How do I use convertPreLayoutPositionToPostLayout() ?
VisibleIndex mostVisible = null;
if (mFirstVisibleIndex != -1|| mLastVisibleIndex != -1) {
// if it's not the same
if (mFirstVisibleIndex != mLastVisibleIndex) {
LinearLayoutManager linearLayoutManager = (LinearLayoutManager) this.getLayoutManager();
// get the visible rect of the first item
Rect firstPercentageRect = new Rect();
linearLayoutManager.findViewByPosition(mFirstVisibleIndex).getGlobalVisibleRect(firstPercentageRect);
// get the visible rect of the last item
Rect lastPercentageRect = new Rect();
linearLayoutManager.findViewByPosition(mLastVisibleIndex).getGlobalVisibleRect(lastPercentageRect);
// since we're on a horizontal list
if (firstPercentageRect.width() > lastPercentageRect.width()) {
return mFirstVisibleIndex;
} else {
return mLastVisibleIndex;
}
} else {
return mFirstVisibleIndex;
}
}
return -1;
}
它很好用,但是当我更改数据集并在适配器中调用任何
notify*Changed
方法后,如果尝试使用上述功能,则findFirstVisibleItemPosition
和findLastVisibleItemPosition
返回的项目位置是错误的。我注意到他们俩都在后台使用getlayoutposition,而且我还注意到文档中的内容:
如果LayoutManager需要调用需要该项目的适配器位置的外部方法,则可以使用getAdapterPosition()或convertPreLayoutPositionToPostLayout(int)。
听起来
convertPreLayoutPositionToPostLayout
正是我想要的东西,但我不知道如何从RecyclerView
中访问它。有任何想法吗?
谢谢。
最佳答案
就我而言,一次在recyclerview中我最多只能有2个可见视图,并且
我在onScrolled
中始终使用mostVisibleItemPosition
当用户滚动时播放视频内容。
因此getTop()
返回此视图相对于其父视图的顶部位置,并且当用户开始滚动firstView
离开屏幕时,firstView.getTop()
将返回负值,而secondView.getTop()
为正值且secondView
到达顶部接近屏幕中心获取firstView.getTop()
的绝对值,我们将确定父视图顶部上方firstView
顶部有多少像素,获得secondView.getTop()
我们将确定父底部上方secondView
顶部有多少像素,是mostVisibleItemPosition
将更改的位置。
private void detectMostVisibleItem() {
int firstItemPosition = layoutManager.findFirstVisibleItemPosition();
int secondItemPosition = layoutManager.findLastVisibleItemPosition();
if (firstItemPosition == secondItemPosition) {
mostVisibleItemPosition = firstItemPosition;
} else {
View firstView = layoutManager.findViewByPosition(firstItemPosition);
View secondView = layoutManager.findViewByPosition(secondItemPosition);
if (Math.abs(firstView.getTop()) <= Math.abs(secondView.getTop())) {
if (mostVisibleItemPosition != firstItemPosition) {
mostVisibleItemPosition = firstItemPosition;
...
}
} else {
if (mostVisibleItemPosition != secondItemPosition) {
mostVisibleItemPosition = secondItemPosition;
...
}
}
}
}