I have nested RecyclerView (MainRecyclerview and ChildRecyclerview) with two Adapters(MainRecyclerviewAdapter and ChildRecyclerviewAdapter), i create an interface to handle click for childRecyclerview, but i can only access that click in MainRecyclerviewAdapter. I want to know how to handle click for items in childRecyclerview in MainActivity, thanks.
Here is my code:
//MainActivity
public class MainActivity extends AppCompatActivity {
List<Section> sectionList = new ArrayList<>();
RecyclerView mainRecyclerView;
LinearLayoutManager layoutManager;
MainRecyclerAdapter mainRecyclerAdapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_profile_properties);
initData();
initRecyclerView();
}
}
//ChildRecyclerAdapter
public class ChildRecyclerAdapter extends RecyclerView.Adapter<ChildRecyclerAdapter.ChildViewHolder> {
private final List<String> items;
private OnItemClickListener mListener;
public ChildRecyclerAdapter(List<String> items) {
this.items = items;
}
public void setOnItemClickListener(OnItemClickListener listener) {
mListener = listener;
}
@NonNull
@Override
public ChildViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.item_row, parent, false);
return new ChildViewHolder(view, mListener);
}
@Override
public void onBindViewHolder(@NonNull ChildViewHolder holder, int position) {
holder.itemTextView.setText(items.get(position));
}
@Override
public int getItemCount() {
return items.size();
}
public class ChildViewHolder extends RecyclerView.ViewHolder {
TextView itemTextView;
ChildViewHolder(final View itemView, OnItemClickListener listener) {
super(itemView);
itemTextView = itemView.findViewById(R.id.txt_item_view);
itemView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (listener != null) {
int position = getBindingAdapterPosition();
if (position != RecyclerView.NO_POSITION) {
String item = items.get(position);
listener.onItemClick(item);
}
}
}
});
}
}
}
//MainRecyclerAdapter
public class MainRecyclerAdapter extends RecyclerView.Adapter<MainRecyclerAdapter.MainViewHolder> {
List<Section> sectionList;
public MainRecyclerAdapter(List<Section> sectionList) {
this.sectionList = sectionList;
}
@NonNull
@Override
public MainViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
LayoutInflater inflater = LayoutInflater.from(parent.getContext());
View view = inflater.inflate(R.layout.section_row, parent, false);
return new MainViewHolder(view);
}
@Override
public void onBindViewHolder(@NonNull MainViewHolder holder, int position) {
Section section = sectionList.get(position);
String sectionName = section.getSectionName();
List<String> items = section.getSectionItems();
holder.sectionNameTextView.setText(sectionName);
ChildRecyclerAdapter childRecyclerAdapter = new ChildRecyclerAdapter(items);
holder.recyclerChild.setAdapter(childRecyclerAdapter);
childRecyclerAdapter.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(String item) {
// TODO: 07/02/2022 handle click
}
});
}
@Override
public int getItemCount() {
return sectionList.size();
}
public static class MainViewHolder extends RecyclerView.ViewHolder {
TextView sectionNameTextView;
RecyclerView recyclerChild;
public MainViewHolder(final View itemView) {
super(itemView);
sectionNameTextView = itemView.findViewById(R.id.txt_section_name);
recyclerChild = itemView.findViewById(R.id.child_recyclerview);
LinearLayoutManager layoutManager = new LinearLayoutManager(itemView.getContext());
recyclerChild.setLayoutManager(layoutManager);
}
}
}
//OnItemClickListener
public interface OnItemClickListener {
void onItemClick(String item);
}
CodePudding user response:
You can simple make one more interface and call it in nested adapter's onclick method.
So it will pass that data from adapter to the activity when you click any adapter items.
CodePudding user response:
I would recommend you to avoid nesting recycler views. You can add different views to an adapter to differtiate between different views in a single recycler view
class RecyclerViewAdapter(context: Context, list: ArrayList<Data>) :
RecyclerView.Adapter<RecyclerView.ViewHolder>() {
companion object {
const val VIEW_TYPE_ONE = 1
const val VIEW_TYPE_TWO = 2
}
private val context: Context = context
var list: ArrayList<Data> = list
private inner class View1ViewHolder(itemView: View) :
RecyclerView.ViewHolder(itemView) {
var message: TextView = itemView.findViewById(R.id.textView)
fun bind(position: Int) {
val recyclerViewModel = list[position]
message.text = recyclerViewModel.textData
}
}
private inner class View2ViewHolder(itemView: View) :
RecyclerView.ViewHolder(itemView) {
var message: TextView = itemView.findViewById(R.id.textView)
fun bind(position: Int) {
val recyclerViewModel = list[position]
message.text = recyclerViewModel.textData
}
}
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder {
if (viewType == VIEW_TYPE_ONE) {
return View1ViewHolder(
LayoutInflater.from(context).inflate(R.layout.item_view_1, parent, false)
)
}
return View2ViewHolder(
LayoutInflater.from(context).inflate(R.layout.item_view_2, parent, false)
)
}
override fun getItemCount(): Int {
return list.size
}
override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
if (list[position].viewType === VIEW_TYPE_ONE) {
(holder as View1ViewHolder).bind(position)
} else {
(holder as View2ViewHolder).bind(position)
}
}
override fun getItemViewType(position: Int): Int {
return list[position].viewType
}
}
This makes it a lot easier to manipulate the click listeneres and to test the code as well
