获取已点击的项目及其在RecyclerView中的位置

Xci*_*egn 94 android listview recycler-adapter android-recyclerview

我正在替换我ListViewRecyclerView,列表显示确定,但我想知道如何获得点击项目及其位置,类似于OnItemClickListener.onItemClick(AdapterView parent, View v, int position, long id)我们使用的方法ListView.

谢谢你的想法!

Xci*_*egn 164

基于链接:为什么RecyclerView没有onItemClickListener()?和RecyclerView如何与Listview不同?,还有@Duncan的总体想法,我在这里提出我的解决方案:

  • 定义一个接口,RecyclerViewClickListener用于将消息从适配器传递到Activity/ Fragment:

    public interface RecyclerViewClickListener {
        public void recyclerViewListClicked(View v, int position);
    }
    
    Run Code Online (Sandbox Code Playgroud)
  • Activity/ Fragment实现接口,并将侦听器传递给适配器:

    @Override
    public void recyclerViewListClicked(View v, int position){... ...}
    
    //set up adapter and pass clicked listener this
    myAdapter = new MyRecyclerViewAdapter(context, this);
    
    Run Code Online (Sandbox Code Playgroud)
  • AdapterViewHolder:

    public class MyRecyclerViewAdapter extends RecyclerView.Adapter<MyRecyclerViewAdapter.ItemViewHolder> {
       ... ... 
       private Context context;
       private static RecyclerViewClickListener itemListener;
    
    
       public MyRecyclerViewAdapter(Context context, RecyclerViewClickListener itemListener) {
           this.context = context;
           this.itemListener = itemListener;
           ... ...
       }
    
    
       //ViewHolder class implement OnClickListener, 
       //set clicklistener to itemView and, 
       //send message back to Activity/Fragment 
       public static class ItemViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener{
           ... ...
           public ItemViewHolder(View convertView) {
               super(convertView);
               ... ...
               convertView.setOnClickListener(this);
           }
    
           @Override
           public void onClick(View v) {
               itemListener.recyclerViewListClicked(v, this.getPosition());     
    
           }
       }
    }
    
    Run Code Online (Sandbox Code Playgroud)

经过测试,它运行正常.


[ 更新 ]

从API 22开始,RecyclerView.ViewHoler.getPosition()不推荐使用,所以改为使用getLayoutPosition().

  • 使用getLayoutPosition()方法,因为getPosition()现在已被删除. (20认同)
  • upvote for deprecation notice. (3认同)
  • 感谢这段代码:)只有一个提示:在构造函数中以静态方式引用静态`private static RecyclerViewClickListener itemListener;`. (2认同)
  • 您不应该在此处使用 Wea​​kReference:“new MyRecyclerViewAdapter(context, this)”吗?这可能会导致内存泄漏 (2认同)
  • public void recyclerViewListClicked(View v,int position);修饰符public对接口方法是多余的 (2认同)

Uda*_*ale 30

public class MyRvAdapter extends RecyclerView.Adapter<MyRvAdapter.MyViewHolder>{
    public Context context;
    public ArrayList<RvDataItem> dataItems;

    ...
    constructor
    overrides
    ...

    class MyViewHolder extends RecyclerView.ViewHolder{
        public TextView textView;
        public Context context;

        public MyViewHolder(View itemView, Context context) {
            super(itemView);

            this.context = context;

            this.textView = (TextView)itemView.findViewById(R.id.textView);

            // on item click
            itemView.setOnClickListener(new View.OnClickListener(){
                @Override
                public void onClick(View v) {
                    // get position
                    int pos = getAdapterPosition();

                    // check if item still exists
                    if(pos != RecyclerView.NO_POSITION){
                        RvDataItem clickedDataItem = dataItems.get(pos);
                        Toast.makeText(v.getContext(), "You clicked " + clickedDataItem.getName(), Toast.LENGTH_SHORT).show();
                    }
                }
            });
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 谢谢.getAdapterPosition()就是我所需要的. (4认同)

Gil*_*rra 13

以下是设置Click Listener的示例.

Adapter extends  RecyclerView.Adapter<MessageAdapter.MessageViewHolder> {  ...  }

 public static class MessageViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
        public TextView     tv_msg;
        public TextView     tv_date;
        public TextView     tv_sendTime;
        public ImageView    sharedFile;
        public ProgressBar sendingProgressBar;

        public MessageViewHolder(View v) {
            super(v);
            tv_msg =  (TextView) v.findViewById(R.id.tv_msg);
            tv_date = (TextView)  v.findViewById(R.id.tv_date);
            tv_sendTime = (TextView)  v.findViewById(R.id.tv_sendTime);
            sendingProgressBar = (ProgressBar) v.findViewById(R.id.sendingProgressBar);
            sharedFile = (ImageView) v.findViewById(R.id.sharedFile);

            sharedFile.setOnClickListener(this);

        }

        @Override
        public void onClick(View view) {
        int position  =   getAdapterPosition();


            switch (view.getId()){
                case R.id.sharedFile:


                    Log.w("", "Selected"+position);


                    break;
            }
        }

    }
Run Code Online (Sandbox Code Playgroud)


小智 11

将此代码放在您在活动中定义Recycler视图的位置.

    rv_list.addOnItemTouchListener(
            new RecyclerItemClickListener(activity, new RecyclerItemClickListener.OnItemClickListener() {
                @Override
                public void onItemClick(View v, int position) {

                    Toast.makeText(activity, "" + position, Toast.LENGTH_SHORT).show();
                }
            })
    );
Run Code Online (Sandbox Code Playgroud)

然后创建单独的类并放入此代码:

import android.content.Context;
import android.support.v7.widget.RecyclerView;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.view.View;
public class RecyclerItemClickListener implements RecyclerView.OnItemTouchListener {

    private OnItemClickListener mListener;
    public interface OnItemClickListener {
        public void onItemClick(View view, int position);
    }
    GestureDetector mGestureDetector;
    public RecyclerItemClickListener(Context context, OnItemClickListener listener) {
        mListener = listener;
        mGestureDetector = new GestureDetector(context, new GestureDetector.SimpleOnGestureListener() {
            @Override
            public boolean onSingleTapUp(MotionEvent e) {
                return true;
            }
        });
    }
    @Override
    public boolean onInterceptTouchEvent(RecyclerView view, MotionEvent e) {
        View childView = view.findChildViewUnder(e.getX(), e.getY());
        if (childView != null && mListener != null && mGestureDetector.onTouchEvent(e)) {
            mListener.onItemClick(childView, view.getChildAdapterPosition(childView));
        }
        return false;
    }

    @Override
    public void onTouchEvent(RecyclerView view, MotionEvent motionEvent) {
    }

    @Override
    public void onRequestDisallowInterceptTouchEvent(boolean disallowIntercept) {

    }
}
Run Code Online (Sandbox Code Playgroud)


Maz*_*oid 7

使用以下代码创建java文件

public class RecyclerItemClickListener implements RecyclerView.OnItemTouchListener {
private OnItemClickListener mListener;

public interface OnItemClickListener {
    public void onItemClick(View view, int position);
}

GestureDetector mGestureDetector;

public RecyclerItemClickListener(Context context, OnItemClickListener listener) {
    mListener = listener;
    mGestureDetector = new GestureDetector(context, new GestureDetector.SimpleOnGestureListener() {
        @Override public boolean onSingleTapUp(MotionEvent e) {
            return true;
        }
    });
}

@Override public boolean onInterceptTouchEvent(RecyclerView view, MotionEvent e) {
    View childView = view.findChildViewUnder(e.getX(), e.getY());
    if (childView != null && mListener != null && mGestureDetector.onTouchEvent(e)) {
        mListener.onItemClick(childView, view.getChildLayoutPosition(childView));
        return true;
    }
    return false;
}

@Override public void onTouchEvent(RecyclerView view, MotionEvent motionEvent) { }

@Override
public void onRequestDisallowInterceptTouchEvent(boolean disallowIntercept) {

}
Run Code Online (Sandbox Code Playgroud)

只需在您的 RecyclerView 对象上使用侦听器。

recyclerView.addOnItemTouchListener(  
new RecyclerItemClickListener(context, new RecyclerItemClickListener.OnItemClickListener() {
  @Override public void onItemClick(View view, int position) {
    // TODO Handle item click
  }
}));
Run Code Online (Sandbox Code Playgroud)


Ama*_*ila 5

如果你想从活动/片段而不是适配器中回收循环查看事件,那么你也可以使用以下捷径.

recyclerView.setOnTouchListener(new View.OnTouchListener() {
            @Override
            public boolean onTouch(View v, MotionEvent event) {
                final TextView txtStatusChange = (TextView)v.findViewById(R.id.txt_key_status);
                txtStatusChange.setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        Log.e(TAG, "hello text " + txtStatusChange.getText().toString() + " TAG " + txtStatusChange.getTag().toString());
                        Util.showToast(CampaignLiveActivity.this,"hello");
                    }
                });
                return false;
            }
        });
Run Code Online (Sandbox Code Playgroud)

您还可以使用其他很长的方式,如使用界面