RecyclerView.ViewHolder-getLayoutPosition与getAdapterPosition [英] RecyclerView.ViewHolder - getLayoutPosition vs getAdapterPosition

查看:579
本文介绍了RecyclerView.ViewHolder-getLayoutPosition与getAdapterPosition的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

自新的支持库版本(22.x)起,不推荐使用RecyclerView.ViewHolder类的getPosition()方法代替本主题中提到的方法.我阅读文档并没有真正的区别. 有人可以解释外行用语的区别吗?

Since the new support library version (22.x) the getPosition() method of the RecyclerView.ViewHolder class has been deprecated in lieu of the methods mentioned in the topic. I don't really get the difference from reading the docs. Could somebody explain the difference in layman's terms?

我有以下用例-我给我的适配器一个List,并且还希望能够为每个列表项关联额外的信息.我有一个位置到外部的映射,该映射可供持有人使用,以便他们可以获取自己的额外职位并对其进行处理.在持有人中,我应该使用哪种方法?

I have the following use case - I give my adapter a List, and also want to be able to associate extra info for each list item. I have a position-to-extra mapping, and the mapping is available for the holders so that they can fetch the extra for their position and do stuff with it. In the holder, which method should I use?

将索引0和1的列表项转换为位置时,持有者的位置会怎样?这些方法返回什么?

What happens with the holder positions when list items at indices 0 and 1 are switched places? What do the methods return?

推荐答案

这是一个棘手的情况,抱歉文档不够.

This is a tricky situation, sorry that docs are not sufficient.

当适配器内容更改(并且您调用notify***())时,RecyclerView请求新的布局.从那时起,直到布局系统决定计算新的布局(<16 ms),由于布局尚未反映适配器的更改,因此布局位置和适配器位置可能不匹配.

When adapter contents change (and you call notify***()) RecyclerView requests a new layout. From that moment, until layout system decides to calculate a new layout (<16 ms), the layout position and adapter position may not match because layout has not reflected adapter changes yet.

在您的用例中,由于您的数据与适配器的内容有关(并且我假设数据与适配器的更改同时发生了更改),因此您应该使用adapterPosition.

In your use case, since your data is related to your adapter contents (and I assume that data is changed at the same time with adapter changes), you should be using adapterPosition.

但是,如果要调用notifyDataSetChanged(),请小心,因为它会使所有内容无效,因此在计算下一个布局之前,RecyclerView不会知道ViewHolder的适配器位置.在这种情况下,getAdapterPosition()将返回RecyclerView#NO_POSITION(-1).

Be careful though, if you are calling notifyDataSetChanged(), because it invalidates everything, RecyclerView does not know that ViewHolder's adapter position until next layout is calculated. In that case, getAdapterPosition() will return RecyclerView#NO_POSITION (-1).

但是可以说,如果您调用了notifyItemInserted(0),先前位于位置0的ViewHolder的getAdapterPosition()将立即开始返回1.因此,只要您调度细粒度的通知事件,您就始终处于良好状态(即使尚未计算新的布局,我们也知道适配器的位置).

But lets say if you've called notifyItemInserted(0), the getAdapterPosition() of ViewHolder which was previously at position 0 will start returning 1 immediately. So as long as you are dispatching granular notify events, you are always in good state (we know adapter position even though new layout is not calculated yet).

另一个示例,如果您正在执行用户点击操作,如果getAdapterPosition()返回NO_POSITION,则最好忽略该点击,因为您不知道用户点击了什么(除非您有其他机制,例如稳定的) id来查找项目).

Another example, if you are doing something on user click, if getAdapterPosition() returns NO_POSITION, it is best to ignore that click because you don't know what user clicked (unless you have some other mechanism, e.g. stable ids to lookup the item).

在版面位置合适时进行编辑

假设您正在使用LinearLayoutManager,并且想访问当前单击的项目上方的ViewHolder.在这种情况下,您应该使用布局位置将项目移到上方.

Lets say you are using LinearLayoutManager and want to access the ViewHolder above the currently clicked item. In that case, you should use layout position to get the item above.

mRecyclerView.findViewHolderForLayoutPosition(myViewHolder.getLayoutPosition() - 1)

您必须使用布局位置,因为它与用户当前在屏幕上看到的内容匹配.

You have to use layout position because it matches what user is currently seeing on the screen.

这篇关于RecyclerView.ViewHolder-getLayoutPosition与getAdapterPosition的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆