【问题标题】:Restoring state of TextView after screen rotation?屏幕旋转后恢复TextView的状态?
【发布时间】:2011-03-03 10:47:21
【问题描述】:

在我的应用程序中,我有 TextViewEditText。两者都有数据。当屏幕方向改变时,EditText 中的数据仍然存在,但TextView 中的数据被清除。

有人能帮我找到一种方法来保留TextView 中的数据吗?

【问题讨论】:

    标签: android android-layout android-orientation onconfigurationchanged


    【解决方案1】:

    如果您想强制 TextView 保存其状态,您必须添加 freezesText 属性:

    <TextView 
         ... 
         android:freezesText="true" />
    

    来自freezesText 上的文档:

    如果设置,文本视图将在其冻结的冰柱内包含其当前完整文本,以及当前光标位置等元数据。默认情况下这是禁用的;当文本视图的内容未存储在诸如内容提供者之类的持久位置时,它会很有用

    【讨论】:

    • 为什么文本默认情况下不像其他属性(文本选择、光标位置等)那样“冻结/保存”?换句话说,在什么情况下有人会更喜欢文本保存?
    • @Gautam 我的猜测是,TextView 通常是由存储在 XML 中的静态字符串构建的,在这种情况下,系统记住这些值是多余的。
    • 实际上,一旦您给 EditText 或 TextView 一个 id,该值将在屏幕旋转事件期间持续存在。
    • @jegesh - 不幸的是,TextViews 至少在某些设备上不是这种情况(Jellybean)
    • 对我不起作用,至少在 API 17 设备上不起作用
    【解决方案2】:

    为了保留有关方向变化的数据,您需要实现两种方法:

    @Override
    protected void onRestoreInstanceState(Bundle savedInstanceState) {
        super.onRestoreInstanceState(savedInstanceState);
        // Read values from the "savedInstanceState"-object and put them in your textview
    }
    
    @Override
    protected void onSaveInstanceState(Bundle outState) {
        // Save the values you need from your textview into "outState"-object
        super.onSaveInstanceState(outState);
    }
    

    【讨论】:

    • 当同一个包在 onCreate 中可用时,为什么要使用 onRestoreInstanceState ?
    • @slott 检查此文档。 developer.android.com/training/basics/activity-lifecycle/… 这是推测,但我怀疑这是因为系统会跟踪它是创建新活动还是重新创建旧活动。 onRestorySavedInstance 仅在极少数情况下调用 - 由于内存限制,配置更改和活动破坏。
    【解决方案3】:

    1) 并非所有具有 ID 的视图都会保存其状态。带有 ID 的 Android 小部件,其状态可由用户更改,似乎在软杀时保存其状态。所以 EditText 保存了它的状态,但是 TextView 在软杀时没有保存它的状态。

    “AFAIK,Android 只会为预期的事情保存状态 改变。这就是为什么它将文本保存在 EditText (用户是 可能会改变)并且可能不会保存 TextView 的状态(通常保持静态)"

    马克M

    所以你可以选择在onSaveInstanceState中保存textview的状态,你可以选择在onCreate中恢复textview的状态。

    2) 最佳做法是保存“内部”非视图实例状态,即使您声明

    android:configChanges= "orientation|keyboardHidden" 
    

    来自文档:

    “但是,您的应用程序应该始终能够在其先前状态完好无损的情况下关闭和重新启动。不仅因为您无法阻止重新启动应用程序的其他配置更改,而且还为了处理事件,例如当用户接听来电,然后返回到您的应用程序。”

    日航

    【讨论】:

      【解决方案4】:

      Android 不会为您处理这类事情。您已手动保存所有数据。

      您可以在活动中使用来保存值

      @Override
          public Object onRetainNonConfigurationInstance() {
              HashMap<String, Object> savedValues = new HashMap<String, Object>();
              savedValues.put("someKey", someData);           
              return savedValues;
          }
      

      并在活动的 oncreate 方法中使用类似的东西来加载保存的对象

      HashMap < String, Object> savedValues 
           = (HashMap<String, Object>)this.getLastNonConfigurationInstance();
      

      您还可以为活动选择禁用方向更改

      <activity android:name=".Activity" android:screenOrientation="portrait" >
          <intent-filter>
              <action android:name="android.intent.action.MAIN" />
          </intent-filter>
      </activity>
      

      【讨论】:

      • 无法覆盖android.support.v4.app.fragmentActivity中的onRetainNonConfigurationInstance();被覆盖的方法是最终的!!
      【解决方案5】:

      修改您在 AndroidManifest.xml 中的活动以通过将其添加到您的活动/活动来覆盖方向更改行为:

      android:configChanges="orientation|keyboardHidden"
      

      它应该看起来像这样:

          <activity android:name=".activity.LoginActivity"
                    android:configChanges="orientation|keyboardHidden"
                    android:label="@string/app_name">
          </activity>
      

      【讨论】:

      【解决方案6】:

      将这些添加到 AndroidManifest.xml
      将您的活动名称放在 Activity_Name

      的位置
      <activity android:name="Activity_Name"
              android:screenOrientation="sensor"
              ...
              android:configChanges="orientation|keyboardHidden|screenSize">
      

      这也适用于更改 TextField 的值。

      【讨论】:

        【解决方案7】:

        添加

        android:configChanges="orientation|screenSize"
        

        到 AndroidManifest.xml 中的 Activity。

        【讨论】:

          【解决方案8】:

          默认情况下,当配置更改时,Android 会重新启动您的活动。要更改这一点,您应该覆盖 onConfigurationChanged() 方法。此外,您应该将android:configChanges 添加到您的清单文件中。

          您可以阅读更多here

          【讨论】:

            【解决方案9】:

            我也用过

            android:configChanges="orientation"
            

            它没有用。

            但后来我找到了解决办法。

            验证您的最目录中是否正确包含以下行:

            <uses-sdk android:minSdkVersion="11" android:targetSdkVersion="11" />
            

            确保它没有读取类似

            的内容
            <uses-sdk android`:minSdkVersion="11" android:targetSdkVersion="15" />`
            

            我一开始是第二种方式,但是当我更正它时,状态被保留了。

            【讨论】:

            • 这是完全不同的事情。 Target SDK 旨在使您的应用程序与大多数 Android 操作系统兼容。这不是答案,从某种意义上说,这可能对您的情况有效,但这不是一个合适的解决方案。
            猜你喜欢
            • 2011-01-31
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多