Android RecyclerView: Change layout file LIST to GRID onOptionItemSelected
I found solution with the starting of activity I have set LinearLayoutManager
like:
mLayoutManager = new LinearLayoutManager(this);
mProductListRecyclerView.setLayoutManager(mLayoutManager);
after that onOptionsItemSelected
written like:
case R.id.menu_product_change_view:
isViewWithCatalog = !isViewWithCatalog;
supportInvalidateOptionsMenu();
//loading = false;
mProductListRecyclerView.setLayoutManager(isViewWithCatalog ? new LinearLayoutManager(this) : new StaggeredGridLayoutManager(2, StaggeredGridLayoutManager.VERTICAL));
mProductListRecyclerView.setAdapter(mAdapter);
break;
and changing view in onCreateViewHolder
like:
@Override
public ProductRowHolder onCreateViewHolder(ViewGroup viewGroup, int i) {
View v = LayoutInflater.from(viewGroup.getContext()).inflate(isViewWithCatalog ? R.layout.product_row_layout_list : R.layout.product_row_layout_grid, null);
ProductRowHolder mh = new ProductRowHolder(v);
return mh;
}
From Starting to Ending you have to manage isViewWithCatalog variable for displaying which layout first.
Switch between RecyclerView layouts when click on AlertDialog item list
No need to use multiple Recyclerview
for this
You can achieve this using single Recyclerview
with Multiple viewType
When you want to change the layout of Recyclerview
just change the LayoutManager
and viewType
of your Recyclerview
it will work
SAMPLE CODE
Try this way
First Create a Three layout for your Multiple viewType
grid_layout
<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="150dp"
android:layout_height="150dp"
app:cardElevation="10dp"
app:cardUseCompatPadding="true">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<ImageView
android:layout_width="match_parent"
android:layout_height="150dp"
android:adjustViewBounds="true"
android:contentDescription="@string/app_name"
android:scaleType="centerCrop"
android:src="@drawable/dishu" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:background="#6a000000"
android:gravity="center"
android:padding="10dp"
android:text="dummy text"
android:textColor="@android:color/white" />
</RelativeLayout>
</android.support.v7.widget.CardView>
cardlist_layout
<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:cardElevation="10dp"
app:cardUseCompatPadding="true">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:orientation="vertical">
<ImageView
android:layout_width="match_parent"
android:layout_height="150dp"
android:adjustViewBounds="true"
android:contentDescription="@string/app_name"
android:scaleType="centerCrop"
android:src="@drawable/dishu" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingStart="5dp"
android:paddingEnd="10dp"
android:text="Dummy Title"
android:textColor="@android:color/black"
android:textStyle="bold" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingStart="5dp"
android:paddingEnd="10dp"
android:text="Dummy Tex" />
</LinearLayout>
</android.support.v7.widget.CardView>
title_layout
<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:cardElevation="10dp"
app:cardUseCompatPadding="true">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center">
<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:orientation="vertical">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingStart="5dp"
android:paddingEnd="5dp"
android:text="dummy text"
android:textColor="@android:color/black"
android:textStyle="bold" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="start"
android:paddingStart="5dp"
android:paddingEnd="5dp"
android:text="I have three different layouts cardsListLayout , titleLayout , cardMagazineLayoutand there may be more in the future, which used as a views on onCreateViewHolder method." />
</LinearLayout>
<ImageView
android:layout_width="wrap_content"
android:layout_height="150dp"
android:adjustViewBounds="true"
android:contentDescription="@string/app_name"
android:scaleType="centerCrop"
android:src="@drawable/dishu" />
</LinearLayout>
</android.support.v7.widget.CardView>
DataAdapter
package neel.com.recyclerviewdemo;
import android.content.Context;
import android.support.annotation.NonNull;
import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
public class DataAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
public static final int ITEM_TYPE_GRID = 0;
public static final int ITEM_TYPE_CARD_LIST = 1;
public static final int ITEM_TYPE_TITLE_LIST = 2;
private Context mContext;
private int VIEW_TYPE = 0;
public DataAdapter(Context mContext) {
this.mContext = mContext;
}
public void setVIEW_TYPE(int viewType) {
VIEW_TYPE = viewType;
notifyDataSetChanged();
}
@NonNull
@Override
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View view = null;
// check here the viewType and return RecyclerView.ViewHolder based on view type
switch (VIEW_TYPE) {
case ITEM_TYPE_GRID:
// if VIEW_TYPE is Grid than return GridViewHolder
view = LayoutInflater.from(mContext).inflate(R.layout.grid_layout, parent, false);
return new GridViewHolder(view);
case ITEM_TYPE_CARD_LIST:
// if VIEW_TYPE is Card List than return CardListViewHolder
view = LayoutInflater.from(mContext).inflate(R.layout.cardlist_layout, parent, false);
return new CardListViewHolder(view);
case ITEM_TYPE_TITLE_LIST:
// if VIEW_TYPE is Title List than return TitleListViewHolder
view = LayoutInflater.from(mContext).inflate(R.layout.title_layout, parent, false);
return new TitleListViewHolder(view);
}
return new GridViewHolder(view);
}
@Override
public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int position) {
final int itemType = getItemViewType(position);
// First check here the View Type
// than set data based on View Type to your recyclerview item
if (itemType == ITEM_TYPE_GRID) {
if (holder instanceof CardViewHolder) {
GridViewHolder viewHolder = (GridViewHolder) holder;
// write here code for your grid list
}
} else if (itemType == ITEM_TYPE_CARD_LIST) {
if (holder instanceof CardViewHolder) {
CardListViewHolder buttonViewHolder = (CardListViewHolder) holder;
// write here code for your grid list
}
} else if (itemType == ITEM_TYPE_TITLE_LIST) {
if (holder instanceof CardViewHolder) {
TitleListViewHolder buttonViewHolder = (TitleListViewHolder) holder;
// write here code for your TitleListViewHolder
}
}
}
@Override
public int getItemCount() {
return 40;
}
// RecyclerView.ViewHolder class for gridLayoutManager
public class GridViewHolder extends RecyclerView.ViewHolder {
public GridViewHolder(@NonNull View itemView) {
super(itemView);
}
}
// RecyclerView.ViewHolder class for Card list View
public class CardListViewHolder extends RecyclerView.ViewHolder {
public CardListViewHolder(@NonNull View itemView) {
super(itemView);
}
}
// RecyclerView.ViewHolder class for Title list View
public class TitleListViewHolder extends RecyclerView.ViewHolder {
public TitleListViewHolder(@NonNull View itemView) {
super(itemView);
}
}
}
MainActivity
package neel.com.recyclerviewdemo;
import android.content.DialogInterface;
import android.os.Bundle;
import android.support.v7.app.AlertDialog;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.GridLayoutManager;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
public class MainActivity extends AppCompatActivity {
DataAdapter dataAdapter;
private RecyclerView myRecyclerView;
private LinearLayoutManager linearLayoutManager;
private GridLayoutManager gridLayoutManager;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
myRecyclerView = findViewById(R.id.myRecyclerView);
myRecyclerView.setHasFixedSize(true);
linearLayoutManager = new LinearLayoutManager(this);
gridLayoutManager = new GridLayoutManager(this, 3);
myRecyclerView.setLayoutManager(gridLayoutManager);
dataAdapter = new DataAdapter(this);
myRecyclerView.setAdapter(dataAdapter);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.home_menu, menu);
// return true so that the menu pop up is opened
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
if (item.getItemId() == R.id.action_dialog) {
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle("Please choose a layout");
String[] layouts = {"Title Layout", "Cards List", "Grid View"};
builder.setItems(layouts, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int index) {
switch (index) {
case 0: // Title layout
dataAdapter.setVIEW_TYPE(2);
myRecyclerView.setLayoutManager(linearLayoutManager);
myRecyclerView.setAdapter(dataAdapter);
break;
case 1: // Cards List
dataAdapter.setVIEW_TYPE(1);
myRecyclerView.setLayoutManager(linearLayoutManager);
myRecyclerView.setAdapter(dataAdapter);
break;
case 2: // Grid Layout
dataAdapter.setVIEW_TYPE(0);
myRecyclerView.setLayoutManager(gridLayoutManager);
myRecyclerView.setAdapter(dataAdapter);
}
}
});
builder.show();
}
return super.onOptionsItemSelected(item);
}
}
activity_main layout
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".MainActivity">
<android.support.v7.widget.RecyclerView
android:id="@+id/myRecyclerView"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</LinearLayout>
OUTPUT
https://youtu.be/L3slKTy2bzI
Recyclerview keep scrolling position after changing layout
You have to remember the firstVisibleItem
and scroll to that position after changing the LayoutManager it works fine I just tried it out by myself:
E.g. Button
click to change LayoutManager
:
btn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
int i = ((LinearLayoutManager) rcView.getLayoutManager()).findFirstVisibleItemPosition();
if(rcView.getLayoutManager() instanceof GridLayoutManager) {
rcView.setLayoutManager(new LinearLayoutManager(MainActivity.this));
} else {
rcView.setLayoutManager(new GridLayoutManager(MainActivity.this, 3));
}
rcView.scrollToPosition(i);
}
});
RecyclerView: how to clear cached/recycled views?
Ok now I understand. You use both layouts? There is a method to return the viewtype for a list/grid element (id/position). You have too implement this method correctly that the adapter can recycle the correct layout for the new view.
Do you understand what I mean? :)
Related Topics
Android 'Debuggable' Default Value
Nexus 5X Reverse Landscape Sensor Fix in a Android Camera Preview App
Creating Different Layout for Android Phone and Tablet
How to Break Styled Text into Pages in Android
Set Language to French in Android Datepickerdialog
Failure [Install_Failed_Older_Sdk] Android-L
Android Change Text Color of Items in Spinner
How to Detect Android CPU Speed
Writing Text File to Sd Card Fails
Can Not Set Debuggable Flag in Androidmanifest.Xml
How to Use Broadcast Receiver in Different Applications in Android
Android - Build Separate APKs for Different Processor Architectures
How to Make Zoomable Linearlayout
Why There's a Separate Mutablelivedata Subclass of Livedata
Change Navigationview Items When User Is Logged
How to Handle Oncontextitemselected in a Multi Fragment Activity