有一种方法可以处理点击元素:
override fun onListItemClick(itemIndex: Int, itemCode: String) {
presenter.onItemClick(adapter.getItem(itemIndex))
}
但问题是用户以某种方式设法点击了 -1 元素。是什么给了我错误:
"backtrace" => "[\"java.lang.ArrayIndexOutOfBoundsException: length\u003d25; index\u003d-1\",\" 在 java.util.ArrayList.get(ArrayList.java:310)\",\" 在 com.project.android.features.common.base_list.AbstractListAdapter.getItem(AbstractListAdapter.kt :20)\",\" 在 com.project.android.features.categories.selector.CategorySelectDialog.onListItemClick(CategorySelectDialog.kt:59)\",\" 在 com.project.android.features.categories.selector.CategorySelectItemViewHolder $1.onClick(CategorySelectItemViewHolder.kt:32)\",\" 在 android.view.View.performClick(View.java:4856)\",\" 在 android.view.View$PerformClick.run(View.java: 19956)\",\" 在 android.os.Handler.handleCallback(Handler.java:739)\",\" 在 android.os.Handler.dispatchMessage(Handler.java:95)\",\"
这怎么可能?以及如何排除用户点击-1列表项的那一刻?
在我使用此方法的地方之一:
titleView.setOnClickListener { listener?.onListItemClick(adapterPosition, "") }
我去了 adapterPosition 的实现,看到了以下内容:
/** * 返回此 ViewHolder 所表示的项目的 Adapter 位置。*
* 请注意,这可能与 {@link #getLayoutPosition()} 不同,如果有 * 挂起的适配器更新但尚未发生新的布局传递。*
* RecyclerView 在下一次布局遍历之前不会处理任何适配器更新。这 * 可能会在用户在屏幕上看到的内容与 * 适配器内容之间产生暂时的不一致。这种不一致并不重要,因为它会小于 * 16 毫秒,但如果您想使用 ViewHolder 位置访问 * 适配器,则可能会出现问题。有时,您可能需要获取确切的适配器位置以执行一些响应用户事件的操作。在这种情况下,您应该使用此方法 * 将计算 ViewHolder 的适配器位置。*
* 请注意,如果您调用了 {@link RecyclerView.Adapter#notifyDataSetChanged()},直到 * 下一次布局传递,此方法的返回值将为 {@link #NO_POSITION}。* * @return 项目的适配器位置(如果它仍然存在于适配器中)。* {@link RecyclerView#NO_POSITION} 如果项目已从适配器中移除, * {@link RecyclerView.Adapter#notifyDataSetChanged()} 已在最后一次 * 布局传递后调用或 ViewHolder 已被回收。*/
也许某处有问题?因为正是在这个方法中返回了 -1。
public final int getAdapterPosition() {
if (mOwnerRecyclerView == null) {
return NO_POSITION;
}
return mOwnerRecyclerView.getAdapterPositionFor(this);
}
通过方法获取适配器列表中的位置时
getAdapterPosition()
,可能会出现适配器RecyclerView
返回NO_POSITION值(常量值 -1)的情况,例如,在更新列表时单击项目时。这种情况需要单独处理,比如像这样(只有当position不等于NO_POSITION时才执行点击item的动作):或使用方法
getLayoutPosition()
,它也有其缺点(在某些情况下,位置并不总是与实际位置相对应)。有关详细信息,请参阅离线文档(RecyclerView 中的位置部分)
在确定问题之前,我建议将方法包装在 try-catch 中:
通常,最好在 catch 块中显示错误日志,例如:
e.log()
并且已经在其中实现了一个接收错误的方法(类似这样)。