Android activity 能够承受屏幕旋转但不能最小化

Android activity able to survive screen rotation but not minimizing

好的,所以我的应用程序可以正常工作,这样当屏幕方向改变时,它会将所有重要的变量信息存储在 savedInstanceState 包中,然后它会在创建时读回activity 再次没有问题。这有点棘手,因为我使用的是自定义对象的 ArrayList,所以我在我的自定义 class 中实现了 Serializable。这有助于它适用于屏幕旋转,但是当我单击主页按钮或以任何方式最小化应用程序时,它会崩溃。

这是抛出的错误:

01-23 10:50:54.961  19756-19756/com.example.spencers.arcgisgeodb E/AndroidRuntime﹕ FATAL EXCEPTION: main
    java.lang.RuntimeException: Parcelable encountered IOException writing serializable object (name = com.example.spencers.arcgisgeodb.agGDBFeatureTable)
            at android.os.Parcel.writeSerializable(Parcel.java:1285)
            at android.os.Parcel.writeValue(Parcel.java:1233)
            at android.os.Parcel.writeMapInternal(Parcel.java:591)
            at android.os.Bundle.writeToParcel(Bundle.java:1646)
            at android.os.Parcel.writeBundle(Parcel.java:605)
            at android.app.ActivityManagerProxy.activityStopped(ActivityManagerNative.java:2318)
            at android.app.ActivityThread$StopInfo.run(ActivityThread.java:3100)
            at android.os.Handler.handleCallback(Handler.java:730)
            at android.os.Handler.dispatchMessage(Handler.java:92)
            at android.os.Looper.loop(Looper.java:137)
            at android.app.ActivityThread.main(ActivityThread.java:5103)
            at java.lang.reflect.Method.invokeNative(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:525)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:737)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553)
            at dalvik.system.NativeStart.main(Native Method)
     Caused by: java.io.NotSerializableException: com.esri.core.geodatabase.GeodatabaseFeatureTable
            at java.io.ObjectOutputStream.writeNewObject(ObjectOutputStream.java:1364)
            at java.io.ObjectOutputStream.writeObjectInternal(ObjectOutputStream.java:1671)
            at java.io.ObjectOutputStream.writeObject(ObjectOutputStream.java:1517)
            at java.io.ObjectOutputStream.writeObject(ObjectOutputStream.java:1481)
            at java.io.ObjectOutputStream.writeFieldValues(ObjectOutputStream.java:979)
            at java.io.ObjectOutputStream.defaultWriteObject(ObjectOutputStream.java:368)
            at java.io.ObjectOutputStream.writeHierarchy(ObjectOutputStream.java:1074)
            at java.io.ObjectOutputStream.writeNewObject(ObjectOutputStream.java:1404)
            at java.io.ObjectOutputStream.writeObjectInternal(ObjectOutputStream.java:1671)
            at java.io.ObjectOutputStream.writeObject(ObjectOutputStream.java:1517)
            at java.io.ObjectOutputStream.writeObject(ObjectOutputStream.java:1481)
            at android.os.Parcel.writeSerializable(Parcel.java:1280)
            at android.os.Parcel.writeValue(Parcel.java:1233)
            at android.os.Parcel.writeMapInternal(Parcel.java:591)
            at android.os.Bundle.writeToParcel(Bundle.java:1646)
            at android.os.Parcel.writeBundle(Parcel.java:605)
            at android.app.ActivityManagerProxy.activityStopped(ActivityManagerNative.java:2318)
            at android.app.ActivityThread$StopInfo.run(ActivityThread.java:3100)
            at android.os.Handler.handleCallback(Handler.java:730)
            at android.os.Handler.dispatchMessage(Handler.java:92)
            at android.os.Looper.loop(Looper.java:137)
            at android.app.ActivityThread.main(ActivityThread.java:5103)
            at java.lang.reflect.Method.invokeNative(Native Method)

根本问题似乎是这一行:

Caused by: java.io.NotSerializableException:com.esri.core.geodatabase.GeodatabaseFeatureTable

class 是我正在使用的外部库,不可编辑。

存储在 savedInstanceState 包中的我的自定义 class 的一部分:

public class agGDBFeatureTable implements Serializable {
    private static final long serialVersionUID = 1L;
    private GeodatabaseFeatureTable geodatabaseFeatureTable = null;
    private boolean active = true;
    private agLegendSymbol legendSymbols;

这是我的 onSaaveInstanceState 方法代码:

@Override
    public void onSaveInstanceState(Bundle savedInstanceState) {
        super.onSaveInstanceState(savedInstanceState);
        Log.i("Saved Instance", "onSaveInstanceState");
        for (int i = 0; i<gdbList.size(); i++) {
            savedInstanceState.putSerializable(i + "", gdbList.get(i));
        }
        savedInstanceState.putInt("NUMBEROFLAYERS",gdbList.size());
     }

现在,我的问题是,为什么我的自定义对象可以序列化、存储在包中并在屏幕旋转时重新启动,但是当应用程序最小化并通过同样的过程,它崩溃并抛出该错误?我该如何解决?

实现 Serializable 的 class 的所有字段也必须是可序列化的。显然(例外情况),GeodatabaseFeatureTable 不是。如果一个字段不可序列化,它必须被标记为瞬态的,像这样:

private transient GeodatabaseFeatureTable geodatabaseFeatureTable = null;

这样你就不会得到异常。现在你可以确定这个对象在反序列化后不会被持久化并再次为 null,或者你可以执行以下操作之一:

  1. 扩展 GeodatabaseFeatureTable class 并在那里实现 Serializable,然后使用扩展的 class - 注意:当然,如果 class 是最终的,这不是一个选项
  2. 通过覆盖 writeObject 和 readObject 方法并从 GeodatabaseFeatureTable 对象内部访问相关信息,在您的 agGDBFeatureTable class 中处理该对象的序列化 - 注意:很可能并非您需要的所有内容可从外部访问

希望对您有所帮助。祝你好运!