Saving scroll state of NestedScrollView

自作多情 提交于 2020-08-24 06:27:26

问题


My application revolves around a HomeActivity which contains 4 tabs at the bottom. Each of these tabs is a fragment, all of them are added (not replaced) from the start, and they are hidden/shown upon tapping the appropriate tab.

My problem is that whenever I change tab, the state of my scroll is lost. Each fragment which exhibits that issue uses a android.support.v4.widget.NestedScrollView (see below for an example).

Note: My fragments that use a RecyclerView or ListView keep their scroll state for some reason.

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <include layout="@layout/include_appbar_title" />

    <android.support.v4.widget.NestedScrollView
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <!-- Content -->

    </android.support.v4.widget.NestedScrollView>

</LinearLayout>

I read several posts regarding saving the instance state (this one, that one for example), and their solution either don't work in my scenario, or are not practical to implement given I have 4-12 different fragments I'd need to modify to make it work.

What is the best way to have a Nested Scroll View keep its scroll position on fragment changes ?


回答1:


One solution I found on inthecheesefactory is that fragments, by default, have their state saved (from the input in a EditText, to the scroll position), but ONLY if an ID is given to the xml element.

In my case, just adding an ID to my NestedScrollView fixed the problem:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <include layout="@layout/include_appbar_title" />

    <android.support.v4.widget.NestedScrollView
        android:id="@+id/NestedScrollView"
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <!-- Content -->

    </android.support.v4.widget.NestedScrollView>

</LinearLayout>



回答2:


You can manage the instance state (which includes the scroll state) by yourself by first making the corresponding methods public:

class SaveScrollNestedScrollViewer : NestedScrollView {
    constructor(context: Context) : super(context)

    constructor(context: Context, attributes: AttributeSet) : super(context, attributes)

    constructor(context: Context, attributes: AttributeSet, defStyleAttr: Int) : super(context, attributes, defStyleAttr)


    public override fun onSaveInstanceState(): Parcelable? {
        return super.onSaveInstanceState()
    }

    public override fun onRestoreInstanceState(state: Parcelable?) {
        super.onRestoreInstanceState(state)
    }
}

Then use it in your view with (YOUR_NAMESPACE is the namespace of the SaveScrollNestedScrollViewer class):

<YOUR_NAMESPACE.SaveScrollNestedScrollViewer
     android:id="@+id/my_scroll_viewer"
     android:layout_width="match_parent"
     android:layout_height="match_parent">
</YOUR_NAMESPACE.SaveScrollNestedScrollViewer>

and then in the activity which displays it, save / recover the state as needed. For example, if you want to recover the scroll position after navigating away use the following:

class MyActivity : AppCompatActivity() {

    companion object {
        var myScrollViewerInstanceState: Parcelable? = null
    }

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.my_activity)

        if (myScrollViewerInstanceState != null) {
            my_scroll_viewer.onRestoreInstanceState(myScrollViewerInstanceState)
        }
    }

    public override fun onPause() {
        super.onPause()
        myScrollViewerInstanceState = my_scroll_viewer.onSaveInstanceState()
    }
}


来源:https://stackoverflow.com/questions/44407092/saving-scroll-state-of-nestedscrollview

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!