方向变化时我的视图被重置

7
我有一个包含EditText、ImageView和按钮的小活动。当你按下按钮时,它会启动相机获取照片,返回后将ImageView更改为所拍摄的图片。

但是,当屏幕方向发生变化时,ImageView会重置回布局中的默认图片。

我尝试设置一个名为custom的布尔值,并在拍照时将其设置为true。我覆盖了onConfigurationChanged()方法,如果custom被设置为true,则恢复图像。

现在我的问题是EditText会被清除——如何在配置更改后还原EditText?我的第一次尝试是在onPause()中将其内容存储到String中,然后进行恢复,但它总是为空白。

2个回答

16
通常情况下,当UI视图无法保持其状态时,需要检查的第一件事是该UI视图是否已分配ID。如果没有ID,则视图无法恢复其状态。
 <EditText android:id="@+id/text" ... />

如果这不起作用,您需要自己保存和恢复状态。请参阅处理运行时更改。它基本上解释了您应该做什么:
为了正确处理重新启动,重要的是您的Activity通过正常的Activity生命周期来恢复其先前的状态,在其中Android在销毁Activity之前调用onSaveInstanceState(),以便您可以保存有关应用程序状态的数据。然后您可以在onCreate()onRestoreInstanceState()期间恢复状态。为了测试您的应用程序在保持应用程序状态的情况下重新启动,您应该在执行应用程序中的各种任务时调用配置更改(例如更改屏幕方向)。
当调用时,您应该覆盖onSaveInstanceState()并保存您的Acitivity状态:
@Override
protected void onSaveInstanceState(Bundle outState)
{
    super.onSaveInstanceState(outState);
    outState.putString("textKey", mEditText.getText().toString());
}

然后在onCreate()或者onRestoreInstanceState()中恢复状态:

public void onCreate(Bundle savedInstanceState)
{
    if(savedInstanceState != null)
    {
        mEditText.setText(savedInstanceState.getString("textKey"));
    }
}

如果这还不够,你可以重写 onRetainNonConfigurationInstance() 并返回任何自定义对象,该对象将传递给新的活动对象在其重新创建时。有关如何使用它的更多详细信息,请参见处理运行时更改。但是,在Android 3.0+中,FragmentActivity 中的此函数已被弃用(特别是 final)。因此,无法与 Fragment 一起使用(这没关系,它们有自己的机制来保留跨配置更改的对象)。
最后一个建议:永远不要使用android:configChanges。你必须有非常好的理由才能使用它,通常这些理由是出于性能方面的考虑。它并不是用来像现在这样被滥用:仅仅为了防止UI状态重置。如果使用了这个属性,那么是的,在配置更改时Activity UI将不会被重新设置,但是当Activity销毁并在以后重新创建时,Activity状态仍将被重置。
文档对这个选项进行了很好的解释:

注意:自己处理配置更改可能会使使用替代资源变得更加困难,因为系统不会自动为您应用它们。此技术应该被视为最后的手段,不推荐大多数应用程序使用。


好的,这听起来是一个更好的方法。我可以用它来替代位图,然后edittext就不会成为问题了——但是我应该使用哪个函数来保存图像的状态呢? - Sebastian
如果位图保存在磁盘上,则只需在onSaveInstanceState()函数中保存位图路径。如果位图在内存中,则可以使用onRetainNonConfigurationInstance()函数。 - inazaruk

6

您可以在清单文件中的活动行中添加android:configChanges="orientation",以强制您的活动在方向更改后不重新加载。


Note: 本文提供了一种解决方案,但并不推荐在所有情况下都使用此方法。只有当您确实需要处理方向更改时才应该使用它。

但是这样不会导致活动不能适应手机横屏吗? - Sebastian
这是正确的答案。防止屏幕改变方向的代码是 android:screenOrientation="portrait" - romy_ngo
4
尽管这修复了特定情况,但并未解决潜在问题。而且,“android:configChanges”被认为是最后的解决方案,通常不应使用。http://developer.android.com/guide/topics/resources/runtime-changes.html - inazaruk
仅仅因为自己处理配置更改很复杂并不意味着它不应该被使用,如果有人有勇气并且非常了解(知道自己要做什么),那么一定可以尝试。 - Alex

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接