错误的状态类,期望View State但是收到了类android.widget.CompoundButton $ SavedState

时间:2016-05-09 10:08:54

标签: android android-fragments android-view

java.lang.IllegalArgumentException: Wrong state class,期待查看状态但收到class android.widget.CompoundButton$SavedState。当两个不同类型的视图在同一层次结构中具有相同的id时,通常会发生这种情况。此视图的 ID为id / 0x2 。确保其他视图不使用相同的ID。

它发生在屏幕旋转时和尝试时回到片段没有id重复plzz一些人帮助我

6 个答案:

答案 0 :(得分:3)

问题描述了为什么会发生这种情况。

  

通常会在两个不同类型的视图具有相同的ID时发生   在相同的层次结构中。

确实,将有两种具有相同ID的不同类型的视图,这可能会在动态扩展视图时发生。 就我而言,在视图膨胀之后,我有两个ViewStub,它们的视图分别为idinflatedId。应用程序进入一种状态,即视图层次结构中存在一个具有相同ID的ViewStub和其他展开视图,从而导致崩溃。

答案 1 :(得分:1)

我已经解决了....它是因为视图ID的重复,主要是当我们动态添加视图而不是设置id时(在我的情况下使用相同的单选按钮文本)

首先检查您正在动态添加的所有视图

答案 2 :(得分:1)

假设您在Fragment或DialogFragment中有一个ScrollView,其ID为:

android:id="@+id/scrollView"

您显示此片段,然后更改屏幕方向,并发生此崩溃:

E/AndroidRuntime: FATAL EXCEPTION: main
java.lang.RuntimeException: Unable to start activity ComponentInfo { com.company.MyApp/com.company.MyActivity }: 
    java.lang.IllegalArgumentException: Wrong state class, expecting View State 
    but received class android.widget.ScrollView$SavedState instead. 
    This usually happens when two views of different type have the same id 
    in the same hierarchy. This view's id is id/scrollView. Make sure other 
    views do not use the same id.
  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2325)
  at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2387)
  ...
Caused by: java.lang.IllegalArgumentException: Wrong state class...
  at android.view.View.onRestoreInstanceState(View.java:13764)
  at android.support.v4.widget.NestedScrollView.onRestoreInstanceState(NestedScrollView.java:1879)
  ...

解决方法是重命名您正在使用的ID,如下所示:

android:id="@+id/scroll_view"

我假设Android框架中的其他视图已经使用了某些ID名称,因此当视图状态恢复时,它们会被检测为重复名称。因此,您必须更改ID的名称。

答案 3 :(得分:0)

在我的情况下,我实施了onRestoreInstanceState,但未正确尝试将自定义的SavedState类发送到super.onRestoreInstanceState

我解决了它向超级调用发送savedState.getSuperState的问题。

答案 4 :(得分:0)

类似的事情发生在我身上,在我的情况下,我有一个纵向模式布局,一个横向模式布局。两者具有相似之处,但是在两个布局上都有两个具有相同ID的按钮,但是这两个按钮的类型在横向布局中是不同的。因此,当我将设备的方向更改为横向时,会发生类似的错误。解决的办法是在两种布局中使用相同类型的按钮。

答案 5 :(得分:0)

除了我没有重复的 ID 之外,我还收到了错误消息。 我的代码是这样的:

override fun onSaveInstanceState(): Parcelable {
    val bundle = Bundle()
    bundle.putString(SELECTED_KEY, selectedItemId)
    bundle.putParcelable(SUPER_STATE_KEY, super.onSaveInstanceState())
    return bundle
}

override fun onRestoreInstanceState(state: Parcelable) {
    if (state is Bundle) {
        selectedItemId = state.getString(SELECTED_KEY, null)
        selectedItemId?.let{
            views.forEach {view ->
                view.isSelected = it == view.tag
            }
        }
    }

    super.onRestoreInstanceState(state)
}

我看到有一个未解决的问题 here。当我像这样更改 super.onRestoreInstanceState 调用参数时,我设法找到了一种不会使应用程序崩溃的解决方法:

override fun onSaveInstanceState(): Parcelable {
    val bundle = Bundle()
    vgs_ring?.constraintLayoutParams()?.let {
        bundle.putParcelable(PARENT_STATE_KEY, super.onSaveInstanceState())
        bundle.putFloat(RING_POSITION_KEY, it.verticalBias)
    }
    super.onSaveInstanceState()
    return bundle
}


override fun onRestoreInstanceState(state: Parcelable) {
    var parentState : Parcelable? = null
    if (state is Bundle) {
        val curRingPosition = state.getFloat(RING_POSITION_KEY, DEFAULT_RING_POSITION)
        state.getParcelable<Parcelable?>(PARENT_STATE_KEY)?.let {
            parentState = it
        }
        vgs_ring?.constraintLayoutParams()?.let {
            it.verticalBias = curRingPosition
            calculateRingPosition()
        }
    }

    super.onRestoreInstanceState(parentState ?: super.onSaveInstanceState())
}