在onSaveInstanceState()中设置标志以确定onDestroy()中的退出类型

时间:2013-01-21 05:06:02

标签: android android-activity

对于在线游戏,很高兴知道Android Activity的onDestroy()是否仅被调用,因为Android将重新创建它(例如设备轮换)或者如果用户选择退出游戏。

我的计划是在Android可能正在重新创建Activity时在onSaveInstanceState() Activity设置一个标记:

private boolean mDestroyedForReCreation;
...
protected void onSaveInstanceState() {
    ...
    mDestroyedForReCreation = true;
}

如果您这样做,可以查看mDestroyedForReCreation中的onDestroy()

  • 如果设置了标志(true),请不要将用户从在线游戏中解雇。
  • 如果未设置标志(false),则将用户从在线游戏中解雇,因为他自愿退出游戏。

这是正确的做法吗?如果是,是推荐还是有更好的解决方案?我希望如此,因为我不喜欢那个解决方案...

6 个答案:

答案 0 :(得分:5)

我建议你从活动的生命周期中删除这种游戏逻辑。创建服务。如果没有人绑定 - 所有活动都已死亡。有人绑定 - 继续工作。

如果您不想创建服务,可以使用onRetainNonConfigurationInstance方法。 Here is example

您应该使用onRetainNonConfigurationInstance,因为系统会调用它,作为因配置更改而销毁活动的一部分,当知道新实例立即为新配置创建时。 onSaveInstanceState在android要杀死活动时调用,有时可能还原或者可能没有恢复。

答案 1 :(得分:3)

通过代码处理此配置更改,您可以简单地避免重新启动轮换。您可以在Manifest.xml中执行此操作:

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

因此,如果键盘打开/关闭,您的应用程序将无法在轮换时重新启动。

我认为这个解决方案要简单得多。

在这种情况下,您几乎不需要处理onSaveInstanceState()退出,除非您启动另一个需要保存游戏状态的意图/活动。请注意,通话也会中断您的代码。我知道一些有趣的错误的游戏,时间被重置但不是分数。

答案 2 :(得分:2)

我只是简化整个事情,并设置一个在用户退出游戏时切换的标志,如:

void exitGame() {
   mUserExited = true;
   finish();
}

(或者,如果您需要销毁多个活动,则可能需要更多逻辑)

然后检查onDestroy()中的标志。

您对配置更改(轮换等)的任何逻辑都与退出游戏标志无关。

另外,请记住,“后退”按钮的默认行为是完成()当前活动(如果没有其他内容) - 在这种情况下不会被视为“退出”。这里的行为取决于你。

答案 3 :(得分:2)

Activity有一个名为isFinishing()的方法,可能就是你要找的。

请参阅:https://stackoverflow.com/a/9621078/445348

答案 4 :(得分:1)

如果您需要了解这一点,您应该考虑自己处理轮换和其他配置更改事件,而不是让系统执行此操作。如果在清单中设置活动处理configChanges,它将在旋转时调用onConfigChange而不是销毁并重新创建活动。大量的应用程序都是这样做的,在Android上进行的旋转破坏和重新创建是绝对迟钝的。

答案 5 :(得分:0)

如果在恢复/重新创建时,将调用

onRestoreInstanceState(),如果活动如果被android杀死它会保存其活动UI状态,并且某些值可以覆盖onSaveInstanceState 但是因为不能保证调用onSaveInstanceState(),所以你应该只使用它来记录活动的瞬态(UI的状态) - 你永远不应该使用它来存储持久数据。相反,您应该使用onPause()来存储用户离开活动时的持久数据(例如应保存到数据库的数据)。当当前活动重新显示给用户时,onStop()之后也将调用onRestart。因此,你可以将你的状态保存在onPause /如果onRestart被调用它就像它被重新显示一样,而如果在没有onRestart的情况下调用onCreate则会重新创建它。其他解决方案是使用onInwIntent的singleInstance和override方法,如果活动没有被破坏,而是像重新启动新意图那样被调用。