javaandroidandroid-recyclerviewandroid-runonuithread

setClickListener from runnable not working


I am working on an Android application that downloads images from a server and displays them in a Recycler view. I am having issues enabling the onclick for each of the images.

In my MyRecyclerViewAdapterClass:

public class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
    public TextView myTextView;
    public ImageView myImage;

    ViewHolder(View itemView) {
        super(itemView);
        myTextView = (TextView) itemView.findViewById(R.id.info_text);
        myImage = (ImageView) itemView.findViewById(R.id.image_test);
        itemView.setOnClickListener(this);
    }

    @Override
    public void onClick(View view) {
        if (mClickListener != null) mClickListener.onItemClick(view, getAdapterPosition());
    }
}

    void setClickListener(ItemClickListener itemClickListener) {
        this.mClickListener = itemClickListener;
    }

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

    String getItem(int id){
        return mData[id];
    }
    public void onItemClick(View view, int position){
        Log.i("TAG","You clicked number" + getItem(position));
}

In my main activity:

public void postImage() {
    runOnUiThread(new Runnable() {
        @Override
        public void run() {

            //RecyclerView.
            RecyclerView recyclerView = (RecyclerView) findViewById(R.id.rvNumbers);
            recyclerView.setLayoutManager(new GridLayoutManager(context, numberOfColumns));
            MyRecyclerViewAdapter.ItemClickListener itemClickListener;
            adapter = new MyRecyclerViewAdapter(context,data,file_payload);

            **adapter.setClickListener(this);**
            adapter.mData = data;
            adapter.PAYLOADS = allPayloads;
            adapter.DATES = allDates;
            recyclerView.setAdapter(adapter);

        }
    });}

When I call adapter.setListener(this) I get an error:

setClickListener in my RecyclerView cannot be applied, anonymous.java.lang.Runnable

I have tried creating a itemClickListener in the runnable as you can see in the code, using that for the call adaptersetClickListener(itemClickListener), however I get an error because itemClickListener is not initialised.

If I do not call the setClickListener method, the mClickListener is never set and is always null. When debugging, I noticed the click is registered but nothing happens because mClickListener is null.


Solution

  • When I call adapter.setListener(this) I get an error:

    Because here this indicate a Runnable instance you implemented and you are passing a Runnable instance not MyRecyclerViewAdapter.ItemClickListener in adapter.

    I think you are trying to pass a MyRecyclerViewAdapter.ItemClickListener instance to ViewHolder. If i am correct,

    For that:

    1. You have to implement MyRecyclerViewAdapter.ItemClickListener in MainActivity
    2. Pass that instance to Adapter.
    3. And from Adapter pass that instance to ViewHolder.

    In MainActivity:

    MyRecyclerViewAdapter.ItemClickListener listener = new MyRecyclerViewAdapter.ItemClickListener() {
      @Override
      public void onItemClick(View view, int position) {
         Log.i("TAG","You clicked number" + position);
      }
    };
    
    adapter = new MyRecyclerViewAdapter(context,data,file_payload);
    adapter. setItemClickListener( listener);
    

    In Adapter

    public interface ItemClickListener {
        void onItemClick(View view, int position);
     }
    
    ItemClickListener listener;
    
    public void setItemClickListener(ItemClickListener listener){
       this.listener = listener;
    }
    
    @Override 
     public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        View v = LayoutInflater.from(parent.getContext()).inflate(itemLayout, parent, false);
        ViewHolder viewHolder =  new ViewHolder(v);
        viewHolder.setItemClickListener(listener);
        return viewHolder;
     }
    

    In your ViewHolder:

    public class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
    public TextView myTextView;
    public ImageView myImage;
    MyRecyclerViewAdapter.ItemClickListener itemClickListener;
    
    ViewHolder(View itemView) {
        super(itemView);
        myTextView = (TextView) itemView.findViewById(R.id.info_text);
        myImage = (ImageView) itemView.findViewById(R.id.image_test);
        itemView.setOnClickListener(this);
    }
    
    @Override
    public void onClick(View view) {
        if (itemClickListener != null) itemClickListener.onItemClick(view, getAdapterPosition());
     }
    
    
    void setItemClickListener(MyRecyclerViewAdapter.ItemClickListener itemClickListener) {
        this.itemClickListener = itemClickListener;
     }
    
    
      String getItem(int id){
        return mData[id];
       }
    }