I have read plenty of examples ,but if I wish to maintain my scroll position after a ListView
is updated from JSON
,then can I do that without using an
If you're using an ArrayAdapter (or a subclass of it), the problem may be caused by that the adapter updates the list when you clean it before adding the new items:
adapter.clear();
adapter.addAll(...);
You can fix it by wrapping the code that modifies the adapter like this:
adapter.setNotifyOnChange(false); // Disable calling notifyDatasetChanged() on modification
adapter.clear();
adapter.addAll(...); // Notify the adapter about that data has changed. Note: it will re-enable notifyOnChange
adapter.notifyDataSetChanged();
For overall picture:
In your API response callback, call this function(example) below:
MyAdapter mAdapter;
ArrayList<Users> mUsers;
private void updateListView(ArrayList<Users> users) {
mUsers.addAll(users);
if(mAdapter == null) {
mAdapter = new MyAdapter(getContext(), mUsers);
mListView.setAdapter(mAdapter);
}
mAdapter.notifyDataSetChanged(); // Add this one
}
listview.setSelection( i );
this will help you to set particular row at top
It is easier to maintain scroll position by calling notifydatasetchanged() only. The problem there is that you are creating a new adapter every time the data gets updated... you should do something like this:
if(listView.getAdapter()==null)
listView.setAdapter(myAdapter);
else{
myAdapter.updateData(myNewData); //update adapter's data
myAdapter.notifyDataSetChanged(); //notifies any View reflecting data to refresh
}
This way, your listview will mantain the scrolling position.
In case you want to scroll to a new position, use:
list.smoothScrollToPosition(int position);
list.smoothScrollToPosition(int position); //my favorite :)
It may also help you to scroll nice'n'smooth to a particular item
In case for some reason you don't want to call notifyDataSetChanged(), the you can maintain the position by using setSelectionFromTop()
Before updating the adaptor:
lastViewedPosition = listView.getFirstVisiblePosition();
//get offset of first visible view
View v = listView.getChildAt(0);
topOffset = (v == null) ? 0 : v.getTop();
After updating the adaptor:
listView.setSelectionFromTop(lastViewedPosition, topOffset);