(android) getAdapterPosition() 是否只能在 OnClick() 内工作?

问题描述

我现在很困惑,因为getAdapterPosition()

我问这个的原因是因为 getAdapterPosition() 根据呼叫位置起作用。

它适用于 Anonymous Obect's OnClick()。但是如果它存在 Anonymous Obect's Field,它就不起作用。

此时的值为-1

有什么问题吗?

这是代码

Adapter.java ( RecyclerView Adpater )

part.setonClickListener(new View.OnClickListener() {
                int position = getAdapterPosition(); // didn't work
                @Override
                public void onClick(View v) {
                    int position = getAdapterPosition(); // work well
                    if(select == false) {
                        part.setBackgroundColor(context.getResources().getColor(R.color.teal_700));;
                        select = true;
                    }
                    else {
                        part.setBackgroundColor(context.getResources().getColor(R.color.white));;
                        select = false;
                    }
                    listener.OnItemClick(v,position); // or OnItemClick(v,getAdapterPosition()) works well,too
                }
            });

DialogFragment.java(错误位置)

dialogAdapter.setonItemClickListener(new DialogItemAdapter.OnDialogItemClickListener() {
            @Override
            public void OnItemClick(View itemView,int pos) {
                Log.d(TAG,"OnItemClick: ");
                String data = dialogAdapter.getItem(pos).getPart(); // ERROR

            }
        });

这是 Java 的语法问题吗?

请帮帮我。

谢谢

解决方法

来自文档:

/**
* ...
* @return The adapter position of the item if it still exists in the adapter.
* {@link RecyclerView#NO_POSITION} if item has been removed from the adapter,* {@link RecyclerView.Adapter#notifyDataSetChanged()} has been called after the last
* layout pass or the ViewHolder has already been recycled.
*/

所以这意味着 // did not work 行在项目已从适配器中移除或 ViewHolder 已被回收时被调用。换句话说,您的 ViewHolder 当前未显示在您的回收器视图中。

// work well 行被调用时,ViewHolder 实际上在回收器视图中处于活动状态。

我怀疑您在 ViewHolder 的构造函数中设置了侦听器,并且当构造函数运行时,viewholder 尚未位于回收器视图中。如果您将点击侦听器设置在 onBindViewHolder 中,我认为它应该可以工作。

,

原因已经在源码的注释文档中提到了。

  • 请注意,如果您调用了 {@link RecyclerView.Adapter#notifyDataSetChanged()},直到 * 下一次布局传递,此方法的返回值将是 {@link #NO_POSITION}。

这意味着如果 Adapter 仍处于膨胀状态,那么 getAdapterPosition 将返回 -1 。如果您阅读评论,它用于计算 ViewHolder 的位置以对用户界面操作(点击、触摸等)做出反应。

您对匿名类所做的事情是使用 getAdapterPosition() 设置全局属性,该属性将在初始化时设置。有时可能是 -1,具体取决于适配器状态。

如果您使用 notifyItemRemoved() 也会给您带来麻烦,因为它不会更新其他位置的已保存属性。假设您在适配器中有 0..10 个项目,并且您在删除 0 后调用 notifyItemRemoved(0),您的匿名属性仍将保留 1..10,因为他们没有收到通知,最终会在 {{1 }} 。这就是为什么您应该使用 ArrayIndexOutOfBound 来计算动作时的位置。

为了安全起见,请始终检查 getAdapterPosition()

NO_POSTION

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...