Reputation: 197
I tried, by several means, to restore data of a listview when the user rotate his phone..However, I have some difficulties due to the fact that when I turn the screen once, it works, but when I turn it over another time, it no longer works. In addition, I tried to restore the scroll position but without success.
So I would like to know the best way to do this.
My code:
private ListView item_container;
private ArrayList<Song.Hits> values;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
item_container = findViewById(R.id.bottom_popup_container);
}
And when I finish to retrieve data from an API, I load them into the listview (and I save the data):
@Override
public void onRequestFinish(ArrayList<Song.Hits> hits) {
if (!hits.isEmpty()) {
CAdapter adapter = new CAdapter(hits);
item_container.setAdapter(adapter);
values = adapter.getHits();
};
}
Finally, I overwrite these 2 methods to save the position and the items of the listview.
@Override
protected void onSaveInstanceState(@NonNull Bundle outState) {
outState.putParcelableArrayList("list", values);
outState.putParcelable("pos", item_container.onSaveInstanceState());
super.onSaveInstanceState(outState);
}
@Override
protected void onRestoreInstanceState(@NonNull Bundle savedInstanceState) {
super.onRestoreInstanceState(savedInstanceState);
ArrayList<Song.Hits> values = savedInstanceState.getParcelableArrayList("list");
if (values != null) {
CAdapter adapter = new CAdapter(values);
item_container.setAdapter(adapter);
item_container.onRestoreInstanceState(savedInstanceState.getParcelable("pos"));
}
}
Upvotes: 0
Views: 516
Reputation: 81568
To an unrelated degree, you should probably be using RecyclerView
instead of ListView
, which nowadays also supports a custom state restoration policy so that the scroll state is automatically preserved until data is set.
Anyways, following current approach, should be as simple as
@Override protected void onRestoreInstanceState(@NonNull Bundle savedInstanceState) { super.onRestoreInstanceState(savedInstanceState); ArrayList<Song.Hits> values = savedInstanceState.getParcelableArrayList("list");
should be
@Override
protected void onRestoreInstanceState(@NonNull Bundle savedInstanceState) {
super.onRestoreInstanceState(savedInstanceState);
values = savedInstanceState.getParcelableArrayList("list");
Upvotes: 1
Reputation: 74
You should do the same checking but on onCreate
because onRestoreInstanceState
is not always called, is kind of tricky.
You can check this from the documentation:
This method is called after
onStart()
when the activity is being re-initialized from a previously saved state, given here insavedInstanceState
. Most implementations will simply useonCreate(Bundle)
to restore their state, but it is sometimes convenient to do it here after all of the initialization has been done or to allow subclasses to decide whether to use your default implementation. The default implementation of this method performs a restore of any view state that had previously been frozen byonSaveInstanceState(Bundle)
.
Move your logic to onCreate
and you'll be fine
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
item_container = findViewById(R.id.bottom_popup_container);
if (savedInstanceState != null) {
ArrayList<Song.Hits> values = savedInstanceState.getParcelableArrayList("list");
if (values != null) {
CAdapter adapter = new CAdapter(values);
item_container.setAdapter(adapter);
item_container.onRestoreInstanceState(savedInstanceState.getParcelable("pos"));
}
}
}
Upvotes: 0
Reputation: 208
You should also update the OnCreate method or override OnPostCreate method and add the logic you used in onRestoreInstanceState upon checking if savedInstanceState!=null
Upvotes: 0