2

I am using GridLayoutManager as LayoutManager for RecyclerView inside a fragment , and RecyclerView adapter get populated by loader. I tried to store and restore state of GridLayoutManager on device rotation but not working and still get back to the initial state "first element in RecyclerView".

onSaveInstanceState method:

    @Override
public void onSaveInstanceState(Bundle outState) {
    mRecylcerViewParecelable = mGridView.getLayoutManager().onSaveInstanceState();
    outState.putParcelable(GRID_LAYOUT_PARCEL_KEY, mRecylcerViewParecelable);
    super.onSaveInstanceState(outState);
}

onViewStateRestored method:

    @Override
public void onViewStateRestored(@Nullable Bundle savedInstanceState) {
    if(savedInstanceState!=null){
        mRecylcerViewParecelable = savedInstanceState.getParcelable(GRID_LAYOUT_PARCEL_KEY);
    }
    super.onViewStateRestored(savedInstanceState);
}

onLoadFinished method:

    @Override
public void onLoadFinished(Loader<Cursor> loader, Cursor data) {
    mMovieAdapter.swapCursor(data);
  mGridView.getLayoutManager().onRestoreInstanceState(mRecylcerViewParecelable);}
Orwa kassab
  • 111
  • 1
  • 9

1 Answers1

2

Try to wrap onRestoreInstanceState() inside Handler:

new Handler().postDelayed(new Runnable() {
            @Override public void run() {
                mGridView.getLayoutManager().onRestoreInstanceState(listState);
            }
        }, 300);

It's a hack to delay the onRestoreInstanceState. I've experienced the same issue, IMO it looks like the RecyclerView keeps going back to initial state because the data in Adapter still being populated when we call the onRestoreInstanceState.

zephyrine
  • 51
  • 4
  • Nice one - this small addition of a delay resolved my issue (with a recyclerview in a fragment) with an adaptor containing a large number of records. – CoastalB Aug 16 '18 at 20:23
  • In general you must restore after you set the data – Gainder Apr 18 '20 at 21:21
  • Why do we need `Handler`? – IgorGanapolsky Jan 21 '21 at 21:00
  • @IgorGanapolsky there's a good answer here: https://stackoverflow.com/a/13954718/4447757 and here https://stackoverflow.com/a/1921759/4447757, and here in Android dev: https://developer.android.com/reference/android/os/Handler Basically you need to wrap the Runnable with Handler – zephyrine Jan 24 '21 at 09:39
  • It is only for cross-thread and cross-context. For everything else, use Kotlin Coroutines. – IgorGanapolsky Jan 24 '21 at 23:41