web-dev-qa-db-ja.com

RecyclerView.AdapterでonBindViewHolder()内のonItemClickListenerを設定します

私はカスタムオブジェクトを持っています:

Student.class

_public class Student {
  private String name;
  private String age;

  public String getName() {
    return name;
  }

  public void setName(String name) {
    this.name = name;
  }

  public String getAge() {
    return age;
  }

  public void setAge(String age) {
    this.age = age;
  }
}
_

次に、このように_RecyclerView.Adapter_を実装します。

MyAdapter.class

_public class MyAdapter extends RecyclerView.Adapter<MyAdapter.ViewHolder> {

  private Context context;
  private ArrayList<Student> students = new ArrayList<>();

  public MyAdapter(Context mContext, ArrayList<Student> mStudents) {
    this.context = mContext;
    this.students = mStudents;
  }

  @Override public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
    View v = LayoutInflater.from(context).inflate(R.layout.item_row, parent, false);
    return new ViewHolder(v);
  }

  @Override public void onBindViewHolder(ViewHolder holder, int position) {

    final Student student = students.get(position);

    holder.name.setText(student.getName());
    holder.age.setText(student.getAge());

    holder.setClickListener(new ItemClickListener() {
      @Override public void onClickItem(int pos) {
        Toast.makeText(context, "CLICK : " + student.getName(), Toast.LENGTH_SHORT).show();
      }

      @Override public void onLongClickItem(int pos) {
        Toast.makeText(context, "LONG CLICK : " + student.getName(), Toast.LENGTH_SHORT).show();
      }
    });
  }

  @Override public int getItemCount() {
    return students.size();
  }

  public static class ViewHolder extends RecyclerView.ViewHolder
      implements View.OnClickListener, View.OnLongClickListener {

    private TextView name;
    private TextView age;
    private ItemClickListener mListener;

    public ViewHolder(View itemView) {

      super(itemView);
      name = (TextView) itemView.findViewById(R.id.tv_name);
      age = (TextView) itemView.findViewById(R.id.tv_age);

      itemView.setOnClickListener(this);
      itemView.setOnLongClickListener(this);
    }

    public void setClickListener(ItemClickListener listener) {
      this.mListener = listener;
    }

    @Override public void onClick(View view) {
      mListener.onClickItem(getLayoutPosition());
    }

    @Override public boolean onLongClick(View view) {
      mListener.onLongClickItem(getLayoutPosition());
      return true;
    }
  }

  public interface ItemClickListener {
    void onClickItem(int pos);

    void onLongClickItem(int pos);
  }
}
_

onBindViewHolder()でわかるように、ホルダーにonItemClickListener()を設定します。

_@Override public void onBindViewHolder(ViewHolder holder, int position) {

    final Student student = students.get(position);
    holder.name.setText(student.getName());
    holder.age.setText(student.getAge());

    holder.setClickListener(new ItemClickListener() {
      @Override public void onClickItem(int pos) {
        Toast.makeText(context, "CLICK : " + student.getName(), Toast.LENGTH_SHORT).show();
      }

      @Override public void onLongClickItem(int pos) {
        Toast.makeText(context, "LONG CLICK : " + student.getName(), Toast.LENGTH_SHORT).show();
      }
    });
  }
_

しかし、新しいアイテムがビューにスクロールするたびにonBindViewHolder()メソッドが呼び出されることを知っています。したがって、onBindViewHolder()内でクリックリスナーを呼び出すと、内部で負荷の高い操作が発生します。

この問題を解決するにはどうすればよいですか?

11
green.android

ViewHolderのビューでonClickListener()に設定する必要があります。つまり、ケースのitemViewです。完全なビュー、つまりルートビュー(この場合はitemView)をクリックするとすぐに、onClick()メソッドが呼び出されます

ルートの子、つまり名前と年齢にonClickListener()を設定することもできます。

ViewHolder(View itemView)コンストラクター内:

_itemView.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    Toast.makeText(mContext,"clicked="+ getPosition(),Toast.LENGTH_SHORT).show();         

                }
            });
_

同様に、onLongClickListner()も呼び出すことができます。子ビューでもname.setOnClickLisner()も。

8
Baqir

以下のように、親ビューにonClickListenerを実装できます。

//holder.view - parent layout inside recyclerView item
holder.view.setTag(position);
holder.view..setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            int pos = (int) v.getTag();
            Student student = students.get(pos);
            // Do your operation

        }
    });

[〜#〜]または[〜#〜]

onItemClickListenerが初期化されているactivity/fragmentからrecyclerViewを設定する場合は、次のリンクをたどることができます。 http://www.littlerobots.nl/blog/Handle -Android-RecyclerView-Clicks /

2
himanshu1496

特定のオーディエンスに対してイベントOnclickを設定できます。

例えば:

 holder.layout.setClickListener(new ItemClickListener() {
  @Override public void onClickItem(int pos) {
    Toast.makeText(context, "CLICK : " + student.getName(), Toast.LENGTH_SHORT).show();
  }
1
Quang Doan

最も簡単な方法はアダプタ内に単一のItemClickListenerを保持:

public class WalletListRecyclerAdapter extends RecyclerView.Adapter<WalletListRecyclerAdapter.ViewHolder> {
    private List<Wallet> wallets;
    private ItemClickListener itemClickListener;

    @Override
    public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
        Wallet wallet = wallets.get(position);

        holder.root.setOnClickListener(v -> {
            if (itemClickListener != null)
                itemClickListener.onClick(holder.root, wallet);
        });
    }

    static class ViewHolder extends RecyclerView.ViewHolder {
        View root;

        public ViewHolder(View v) {
            super(v);
            root = v;
        }
    }


    public void setItemClickListener(ItemClickListener itemClickListener) {
        this.itemClickListener = itemClickListener;
    }

    public interface ItemClickListener {
        void onClick(View view, Wallet wallet);
    }
}

活動中:

walletsAdapter = new WalletListRecyclerAdapter();
walletsAdapter.setItemClickListener((view, wallet) -> {
    Intent intent = new Intent(this, WalletActivity.class);
    intent.putExtra(Const.KEY_WALLET, wallet);
    startActivity(intent);
});
1
Grigory Azaryan

このコードを置き換え、

        @Override public void onBindViewHolder (ViewHolder holder,int position){

            final Student student = students.get(position);
            holder.name.setText(student.getName());
            holder.age.setText(student.getAge());


            holder.v.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    Toast.makeText(context, "CLICK : " + student.getName(), Toast.LENGTH_SHORT).show();
                }
            });

            holder.v.setOnLongClickListener(new View.OnLongClickListener() {
                @Override
                public boolean onLongClick(View v) {
                    Toast.makeText(context, "CLICK : " + student.getName(), Toast.LENGTH_SHORT).show();
                    return false;
                }
            });
        }
0