目前:
我正在Adapter内的onBindViewHolder中实现单击事件,但是我注意到这样做时适配器的位置会弄乱。我进行了一些研究,发现this,他说:


  至于为什么在ViewHolder中而不是在onBindViewHolder()中更好,这是因为每个项目都调用了onBindViewHolder(),并且当您可以在ViewHolder构造函数中一次调用它时,设置单击侦听器是不必要的重复选项。


他引用的示例如下所示:

public class MyViewHolder extends RecyclerView.ViewHolder implements View.OnItemClickListener {
   public MyViewHolder(View view) {
      super(view);

      view.setOnClickListener(this);
   }

   @Override
   public void OnClick(View view) {
      // Get the item clicked
      // For this example, I'm assuming your data source is of type `List<MyObject>`
      MyObject myObject = mDataSource.get(getAdapterPosition());
      // Then you can do any actions on it, for example -
      myObject.setChecked();
   }
}


这对我来说很有意义,但是我的问题是我的ImageButton中有一个ViewHolder,他的示例仅显示了如何处理ViewHolder本身的单击事件。首先请看一下我的适配器当前的外观:

public class MyAdapter extends Adapter<MyAdapter.ViewHolder> {
    ArrayList<Bitmap> bitmapArrayList;
    Context context;
    LayoutInflater layoutInflater;
    View myLayoutView;
    ArrayList<PathModel> swingThumbPathList;
    ArrayList<PathModel> swingVideoPathList = new ArrayList();

    class ViewHolder extends android.support.v7.widget.RecyclerView.ViewHolder {
        TextView name;
        CircularImageView image;
        ImageButton viewholderOtions;

        ViewHolder(View itemView) {
            super(itemView);
        }
    }

    public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        this.myLayoutView = LayoutInflater.from(this.context).inflate(R.layout.single_item, parent, false);
        return new ViewHolder(this.myLayoutView);
    }

    public void onBindViewHolder(ViewHolder myHolder, final int position) {
        final ViewHolder holder = myHolder;
        holder.viewholderOtions = (ImageButton) myLayoutView.findViewById(R.id.viewholderOptions);
        holder.name = (TextView) this.myLayoutView.findViewById(R.id.name);
        holder.image = (CircularImageView) this.myLayoutView.findViewById(R.id.image);
        holder.name.setText(Model.getPath());
        holder.image.setImageURI(Uri.parse(Model.getPath()));

        holder.viewholderOtions.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {

                Toast.makeText(holder.itemView.getContext(), "Options was clicked", Toast.LENGTH_LONG).show();

                showPopupMenu(holder.viewholderOtions, position);

            }
        });

        holder.itemView.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                String uri = holder.name.getText().toString();

                Toast.makeText(holder.itemView.getContext(), uri, Toast.LENGTH_LONG).show();
            }


        });

    }

    private void showPopupMenu(final View view, final int position) {
        // inflate menu
        PopupMenu popup = new PopupMenu(view.getContext(), view);
        MenuInflater inflater = popup.getMenuInflater();
        inflater.inflate(R.menu.popup_menu, popup.getMenu());
        popup.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {

            @Override
            public boolean onMenuItemClick(MenuItem item) {
                switch (item.getItemId()) {
                    case R.id.delete:
                        //The correct position is being toasted
                        Toast.makeText(view.getContext(), position + "Delete", Toast.LENGTH_LONG).show();

                        return true;
                    case R.id.rename:
                        Toast.makeText(view.getContext(), "Rename", Toast.LENGTH_LONG).show();

                        return true;

                    default:

                        return true;
                }
            }

        });

        popup.show();
    }


我的问题

如何处理ViewHolder本身和ImageButton内部的ViewHolder的单击事件?

最佳答案

我回头笑了一下这个问题,所以差不多两年后回答了我自己的问题。

使用问题中提供的相同逻辑,这就是如何将点击事件设置为视图本身,以及视图内部的元素,在viewholder而不是onBindViewHolder

public class MyAdapter extends Adapter<MyAdapter.ViewHolder> {
    ArrayList<Bitmap> bitmapArrayList;
    Context context;
    LayoutInflater layoutInflater;
    View myLayoutView;
    ArrayList<PathModel> swingThumbPathList;
    ArrayList<PathModel> swingVideoPathList = new ArrayList();

    class ViewHolder extends android.support.v7.widget.RecyclerView.ViewHolder {
        TextView name;
        CircularImageView image;
        ImageButton viewholderOtions;

        ViewHolder(View itemView) {
            super(itemView);
            viewholderOtions = itemView.findViewById(R.id.viewholderOptions);
            videoName = itemView.findViewById(R.id.FilePath);
            videoThumb = itemView.findViewById(R.id.VideoThumbnail);
            //set OnClickListener's for the views we want click events for
            itemView.setOnClickListener(this);
            viewholderOtions.setOnClickListener(this);
            videoThumb.setOnClickListener(this);
        }

        @Override
        public void onClick(View v) {
            //get the tag that we have set in onBindViewHolder
            int position = (int) v.getTag();
            if (v == viewholderOtions) {
                //viewholderOtions was selected, we can use the position above to see what item, as shown below:
                Log.e("viewholderOtions at position =", String.valueOf(position);
            }
            if (v == itemView){
                //itemView was selected, we can use the position above to see what item, as shown below:
                Log.e("itemView at position =", String.valueOf(position);
            }
            if (v == videoThumbvideoThumb){
                //itemView was selected, we can use the position above to see what item, as shown below:
                Log.e("videoThumbvideoThumb at position =", String.valueOf(position);
            }
        }


    }

    public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        this.myLayoutView = LayoutInflater.from(this.context).inflate(R.layout.single_item, parent, false);
        return new ViewHolder(this.myLayoutView);
    }

    public void onBindViewHolder(ViewHolder myHolder, final int position) {
        //set a tag so we can retrieve the position via the tag
        myHolder.viewholderOtions.setTag(position);

        //Set text to holder.name
        holder.name.setText(Model.getPath());
        //a better option to below is to use a library like picasso to handle the image loading
        holder.image.setImageURI(Uri.parse(Model.getPath()));

    }

}


但老实说,我仍然将点击事件设置在onBindViewHolder内,然后将以下内容设置为RecyclerView-Activity内的recyclerView.setHasFixedSize(true);。如我的问题所述,通过这样做,职位不会变得混乱。

关于android - 处理Adapter/ViewHolder中的单击事件,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/45546739/

10-10 20:15