English | 简体中文 | 繁體中文 | Русский язык | Français | Español | Português | Deutsch | 日本語 | 한국어 | Italiano | بالعربية

Android RecyclerView multiple item selection implementation code

Following the channel selection of the NetEase News client's reading preferences, let's first take a look at the implemented page:


Directly to the code:

import android.content.res.Resources;
import android.content.res.TypedArray;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.DefaultItemAnimator;
import android.support.v7.widget.GridLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.support.v7.widget.helper.ItemTouchHelper;
import android.util.Log;
import android.util.SparseBooleanArray;
import android.view.View;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
public class RecyclerViewActivity extends AppCompatActivity {
  private RecyclerView recycler;
  private RecyclerAdapter mAdapter;
  private List<PreferCustomizableChannel> channels = new ArrayList<>();
  private List<PreferCustomizableChannel> channelsSelected;
  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_recycler_view_acitivity);
    initData();
    initUI();
    findViewById(R.id.resultBTN).setOnClickListener(new View.OnClickListener() {
      @Override
      public void onClick(View v) {
        int lens = channelsSelected.size();
        for (int i = 0; i < lens; i++) {
          PreferCustomizableChannel customizableChannel = channelsSelected.get(i);
          if (customizableChannel.isSelected()) {
            Log.i("RecyclerViewActivity", "onClick: ");+customizableChannel.toString());
          }
        }
      }
    );
  }
  private void initData() {
    Resources resources = getResources();
    TypedArray array = resources.obtainTypedArray(R.array.prefer_channel_icon);
    int len = array.length();
    String[] name = resources.getStringArray(R.array.prefer_channel_name);
    for (int i = 0; i < len; i++) {
      PreferCustomizableChannel customizableChannel = new PreferCustomizableChannel();
      customizableChannel.setChannel(name[i]);
      customizableChannel.setResId(array.getResourceId(i, 0));
      customizableChannel.setSelected(false);
      customizableChannel.setId(i * 100);
      channels.add(customizableChannel);
    }
    array.recycle();
    channelsSelected = channels;
  }
  private void initUI() {
    recycler = (RecyclerView) findViewById(R.id.recycler);
    final GridLayoutManager manager = new GridLayoutManager(this, 3)
    recycler.setLayoutManager(manager);
    recycler.setHasFixedSize(true);
    recycler.setItemAnimator(new DefaultItemAnimator());
    mAdapter = new RecyclerAdapter(RecyclerViewActivity.this, channels);
    recycler.setAdapter(mAdapter);
    mAdapter.setClickListener(new OnRecyclerViewItemClickListener() {
      @Override
      public void onItemClick(View view, int position) {
        SparseBooleanArray selecteds = mAdapter.getSelectedItem();
        int len = channels.size();
        for (int i = 0; i < len; i++) {
          if (selecteds.get(i)) {
            channelsSelected.get(position).setSelected(true);
          }
        }
      }
    );
  }
}

The layout file's RecyclerView is both horizontal and vertical 'match_parent', otherwise the gridView will automatically scroll up a certain distance when clicked.

The implementation of the adapter:

import android.support.v7.widget.RecyclerView;
import android.util.SparseBooleanArray;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.RelativeLayout;
import android.widget.TextView;
import com.entity.PreferCustomizableChannel;
import com.listener.OnRecyclerItemClickListener;
import java.util.List;
import ButterKnife.BindView;
import ButterKnife;
public class PreferChannelAdapter extends RecyclerView.Adapter<PreferChannelAdapter.PreferChannelHolder>{
  private List<PreferCustomizableChannel> lists;
  private OnRecyclerItemClickListener listener;
  private SparseBooleanArray selectLists = new SparseBooleanArray();
  public PreferChannelAdapter() {
  }
  public void setDatas(List<PreferCustomizableChannel> lists) {
    this.lists = lists;
    notifyDataSetChanged();
  }
  public void setOnItemClickListener(OnRecyclerItemClickListener listener) {
    this.listener = listener;
  }
  @Override
  public PreferChannelHolder onCreateViewHolder(ViewGroup parent, int viewType) {
    View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.prefer_channel_item, null);
    return new PreferChannelHolder(view);
  }
  @Override
  public void onBindViewHolder(final PreferChannelHolder holder, final int position) {
    PreferCustomizableChannel channelItem = lists.get(position);
    holder.channelItemTV.setText(channelItem.getChannel());
    holder.channelItemImg.setImageResource(channelItem.getResId());
    if (!selectLists.get(position)) {
      holder.selectedMarkImg.setVisibility(View.GONE);
    } else {
      holder.selectedMarkImg.setVisibility(View.VISIBLE);
    }
    holder.preferChannelItemLayout.setOnClickListener(new View.OnClickListener() {
      @Override
      public void onClick(View view) {
        if (holder.selectedMarkImg.getVisibility() == View.GONE) {
          holder.selectedMarkImg.setVisibility(View.VISIBLE);
          selectLists.put(position, true);
        } else if (holder.selectedMarkImg.getVisibility() == View.VISIBLE) {
          holder.selectedMarkImg.setVisibility(View.GONE);
          selectLists.put(position, false);
        }
        listener.onRecyclerClick(position);
      }
    );
  }
  @Override
  public int getItemCount() {}}
    return lists.size();
  }
  public class PreferChannelHolder extends RecyclerView.ViewHolder {
    @BindView(R.id.preferChannelItemLayout)
    RelativeLayout preferChannelItemLayout;
    @BindView(R.id.channelItemTV)
    TextView channelItemTV;
    @BindView(R.id.channelItemImg)
    ImageView channelItemImg;
    @BindView(R.id.selectedMarkImg)
    ImageView selectedMarkImg;
    public PreferChannelHolder(View itemView) {
      super(itemView);
      ButterKnife.bind(this, itemView);
    }
  }
  public SparseBooleanArray getSelectedItem() {
    return selectLists;
  }
}

Please also paste the item layout:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:id="@"+id/preferChannelItemLayout"
  android:gravity="center"
  android:layout_gravity="center"
  android:layout_marginTop="10dp
  android:layout_width="wrap_content"
  android:layout_height="wrap_content">
  <!--android:gravity="center"
  android:layout_gravity="center"-->
  <ImageView
    android:id="@"+id/channelItemImg"
    android:scaleType="centerInside"
    android:layout_width="68dp
    android:layout_height="wrap_content"/>
  <TextView
    android:id="@"+id/channelItemTV"
    android:gravity="center"
    android:layout_marginLeft="20dp"
    android:layout_marginRight="20dp"
    android:layout_marginBottom="20dp"
    android:layout_marginTop="8dp
    android:layout_below="@id/channelItemImg"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content" />
  <ImageView
    android:id="@"+id/selectedMarkImg"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_centerVertical="true"
    android:visibility="gone"
    android:layout_alignRight="@id/channelItemImg"
    android:src="@mipmap/prefer_selected"/>
</RelativeLayout>

Other points to note:

SpareBooleanArrary.size() returns the length of the items already set to true, for example, if one is selected, it returns1It selects10It returns10But when selecting10When removing one from the back, size() does not return9But still10This is something to note, so there is no use of size() to get the length when traversing.

That's all for this article, I hope it will be helpful to everyone's learning, and I also hope everyone will support the Shouting Tutorial more.

Declaration: The content of this article is from the Internet, and the copyright belongs to the original author. The content is contributed and uploaded by Internet users spontaneously. This website does not own the copyright, does not edit the content manually, and does not assume any relevant legal liability. If you find any content suspected of copyright infringement, please send an email to notice#w3Please report via email to codebox.com (replace # with @ when sending email) and provide relevant evidence. Once verified, this site will immediately delete the infringing content.

You May Also Like