2015-07-21 51 views
6

我的理解是所有具有ID的标准视图都应该自动保存它们的状态,并且通过对这个例子的尝试我发现它很混乱。TextView(带ID)为什么不自动保存它的状态?

我只有1个活动和主要布局如下所示。
当我通过单击按钮来更改TextView的文本,然后旋转屏幕时,TextView确实会保存它的状态,但在再次旋转时,它会重置为默认状态。

如果我在横向和旋转时编辑它,也会发生同样的情况:第一次旋转后仍然保存它的状态,但在另一次旋转后(除非我再次更改文本)它会重置为默认值。

我现在很困惑。有人可以向我解释这种行为吗?我无法找到解释此特定行为的任何其他问题(或答案)。

activity_main.xml中:

<RelativeLayout 
    xmlns:android="http://schemas.android.com/apk/res/android" 
    xmlns:tools="http://schemas.android.com/tools" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    android:paddingBottom="@dimen/activity_vertical_margin" 
    android:paddingLeft="@dimen/activity_horizontal_margin" 
    android:paddingRight="@dimen/activity_horizontal_margin" 
    android:paddingTop="@dimen/activity_vertical_margin" 
    tools:context=".MainActivity"> 

    <TextView 
     android:id="@+id/activity_main_textView" 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content" 
     android:maxLines="2" 
     android:text="test" 
     android:textSize="50sp" 
     /> 

    <EditText 
     android:id="@+id/activity_main_editText" 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content" 
     android:layout_centerVertical="true" 
     android:maxLength="30" 
     android:maxLines="1" 
     /> 

    <Button 
     android:id="@+id/activity_main_button" 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content" 
     android:layout_alignParentBottom="true" 
     android:text="Set text" 
     /> 

</RelativeLayout> 

MainActivity.java:

package com.example.viewstatetest; 

import android.os.Bundle; 
import android.support.v7.app.AppCompatActivity; 
import android.view.View; 
import android.widget.EditText; 
import android.widget.TextView; 

public class MainActivity extends AppCompatActivity { 

    private TextView textView; 
    private EditText editText; 
    private View button; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 

     textView = (TextView) findViewById(R.id.activity_main_textView); 
     editText = (EditText) findViewById(R.id.activity_main_editText); 
     button = findViewById(R.id.activity_main_button); 


     button.setOnClickListener(new View.OnClickListener() { 
      @Override 
      public void onClick(View v) { 
       textView.setText(editText.getText()); 
      } 
     }); 
    } 
} 
+0

试试这个可能:http://stackoverflow.com/questions/5123407/losing-data-when-rotate-screen – Zarwan

+0

谢谢,但那个节目如何保存状态。我知道如何手动保存状态,但想知道为什么某些视图(有时候!)不会自动保存它们的状态。 – SuperLemon

回答

3

如果你看一下TextView来源(尤其是TextView#onSaveInstanceState()),您将看到文本在两种情况下仅保存:

  1. 当用户明确要求通过设置freezeText国旗true通过android:freezesText="true"TextView#setFreezesText(true)
  2. 当TextView中的文本有选择。

在您的情况下,这两种情况都是错误的,所以您的文本在方向更改期间重置为默认状态。

简单的改变你的布局将解决这一问题:

<TextView 
    android:id="@+id/activity_main_textView" 
    android:layout_width="match_parent" 
    android:layout_height="wrap_content" 
    android:freezesText="true" 
    android:maxLines="2" 
    android:text="test" 
    android:textSize="50sp" 
    /> 
+0

非常感谢!冻结它并手动保存和恢复文本有什么实际区别吗? 又如何在我的例子中,状态通过第一个方向改变保存,并且只在第二个之后复位? 再次感谢! – SuperLemon

+0

@SuperLemon我不认为你需要重新发明手动保存状态的轮子,所以我会使用已有的功能。至于为什么它在第一次方向改变时保存状态 - 我真的不知道:)我用你的布局创建了一个测试项目,并试图重现这种行为 - 在第一次方向改变时我失去了我的textview状态 –