如何获取 RecyclerView 的滑动距离

 我来答
磕悄柯B0
2016-06-29 · TA获得超过330个赞
知道小有建树答主
回答量:152
采纳率:64%
帮助的人:28.3万
展开全部
RecyclerView 虽然有getScrollX() 和 getScrollY(), 但是测试发现这两个函数总是返回0,太无语了。因此想到了下面几种方法来实现获取滑动距离:
1. 利用OnScrollListener
[java]
view plain copy

mRecyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
private int totalDy = 0;
@Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
totalDy -= dy;
}
});
如代码所述,totalDy的确保存了 RecyclerView 的滑动距离,但是当我向下滑动 RecyclerView ,之后插入/删除/移动 Item 的时候,totalDy 就变得不精确了;比如删除或者插入新的Item,那么totalDy就不能再回归到 0了。

解决办法:监听RecyclerView的addOnScrollListener后自己记录onScrolled的dy,同时给adapter加个registerAdapterDataObserver,监听插入/删除/移动,自己加减前面记录的dy滚动值。自己没有试过,不知道是否可行!

2. 有人说可以尝试computeVerticalScrollOffset()-----不行

[java]
view plain copy
totalDy = recyclerView.computeVerticalScrollOffset();
然而compute方法计算出的并不是滑动的精确距离,stackOverflow上有答案解释其为 item 的平均高度 * 可见 item 数目,不是我们需要的精确距离。

3. 还有人说可以尝试getChildAt(0) -----不行

[java] view plain copy
totalDy = recyclerView.getChildAt(0).getTop();
依靠第一个item的滑动距离来进行动画的设置,但是根据该方法得出的 totalDy 在滑动到一定程度后清零。

这是因为recyclerViewl.getChildAt(0) 返回的永远是第一个可见的child,不是所有view list 的第一个child,因此这种用法是得不到滑动距离的。
另外下面这三种用法都是等价的,都是获取第一个可见的child:

[java]
view plain copy
LinearLayoutManager layoutManager = (LinearLayoutManager) this.getLayoutManager();
View firstVisiableChildView = this.getChildAt(0);
View firstVisiableChildView = layoutManager.getChildAt(0)
int position = layoutManager.findFirstVisibleItemPosition();
View firstVisiableChildView = layoutManager.getChildAt(position)
但是下面这种就不是获取第一个可见的child,而是获得所有view list 的第一个child。但是滑动一段距离后它总是返回null,即第一个child被recycle后,总是返回null。

[java]
view plain copy
//Don't use this function to get the first item, it will return null when the first item is recycled.
LinearLayoutManager layoutManager = (LinearLayoutManager) this.getLayoutManager();
View child2 = layoutManager.findViewByPosition(0);
4.如果LayoutManager用的是LinearLayoutManager,强烈推荐下面的方法获取滑动距离:

[java]
view plain copy
public int getScollYDistance() {
LinearLayoutManager layoutManager = (LinearLayoutManager) this.getLayoutManager();
int position = layoutManager.findFirstVisibleItemPosition();
View firstVisiableChildView = layoutManager.findViewByPosition(position);
int itemHeight = firstVisiableChildView.getHeight();
return (position) * itemHeight - firstVisiableChildView.getTop();
}
就烦条0o
2018-08-03 · 知道合伙人软件行家
就烦条0o
知道合伙人软件行家
采纳数:33315 获赞数:46488
从事多年系统运维,喜欢编写各种小程序和脚本。

向TA提问 私信TA
展开全部
建议监听RecyclerView的addOnScrollListener后自己记录onScrolled的dy,同时给adapter加个registerAdapterDataObserver,监听插入/删除/移动,自己加减前面记录的dy滚动值。
本回答被网友采纳
已赞过 已踩过<
你对这个回答的评价是?
评论 收起
推荐律师服务: 若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询

为你推荐:

下载百度知道APP,抢鲜体验
使用百度知道APP,立即抢鲜体验。你的手机镜头里或许有别人想知道的答案。
扫描二维码下载
×

类别

我们会通过消息、邮箱等方式尽快将举报结果通知您。

说明

0/200

提交
取消

辅 助

模 式