Ausnahmebedingung "IllegalStateException: Diese Aktion kann nach onSaveInstanceState nicht ausgeführt werden"
Habe ich eine Live-Android-Anwendung, und vom Markt, die ich erhielt folgende stack-trace und ich habe keine Ahnung, warum Ihr passiert, als nicht geschehen, im code der Anwendung, aber immer verursacht, die von einigen oder andere Ereignis aus der Anwendung (Annahme)
Ich bin nicht mit Fragmenten, noch gibt es einen Hinweis der FragmentManager.
Wenn jeder Körper kann werfen etwas Licht auf einige verborgene Tatsachen zu vermeiden, diese Art von Problem:
java.lang.IllegalStateException: Can not perform this action after onSaveInstanceState
at android.app.FragmentManagerImpl.checkStateLoss(FragmentManager.java:1109)
at android.app.FragmentManagerImpl.popBackStackImmediate(FragmentManager.java:399)
at android.app.Activity.onBackPressed(Activity.java:2066)
at android.app.Activity.onKeyDown(Activity.java:1962)
at android.view.KeyEvent.dispatch(KeyEvent.java:2482)
at android.app.Activity.dispatchKeyEvent(Activity.java:2274)
at com.android.internal.policy.impl.PhoneWindow$DecorView.dispatchKeyEvent(PhoneWindow.java:1668)
at android.view.ViewGroup.dispatchKeyEvent(ViewGroup.java:1112)
at android.view.ViewGroup.dispatchKeyEvent(ViewGroup.java:1112)
at android.view.ViewGroup.dispatchKeyEvent(ViewGroup.java:1112)
at android.view.ViewGroup.dispatchKeyEvent(ViewGroup.java:1112)
at android.view.ViewGroup.dispatchKeyEvent(ViewGroup.java:1112)
at android.view.ViewGroup.dispatchKeyEvent(ViewGroup.java:1112)
at com.android.internal.policy.impl.PhoneWindow$DecorView.superDispatchKeyEvent(PhoneWindow.java:1720)
at com.android.internal.policy.impl.PhoneWindow.superDispatchKeyEvent(PhoneWindow.java:1258)
at android.app.Activity.dispatchKeyEvent(Activity.java:2269)
at com.android.internal.policy.impl.PhoneWindow$DecorView.dispatchKeyEvent(PhoneWindow.java:1668)
at android.view.ViewRoot.deliverKeyEventPostIme(ViewRoot.java:2851)
at android.view.ViewRoot.handleFinishedEvent(ViewRoot.java:2824)
at android.view.ViewRoot.handleMessage(ViewRoot.java:2011)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:132)
at android.app.ActivityThread.main(ActivityThread.java:4025)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:491)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:841)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:599)
at dalvik.system.NativeStart.main(Native Method)
InformationsquelleAutor der Frage dcool | 2011-09-19
Du musst angemeldet sein, um einen Kommentar abzugeben.
Dies ist der dümmste Fehler, den ich bisher begegnet sind. Ich hatte eine
Fragment
Anwendung funktioniert perfekt für API < 11undForce Closing
auf API > 11.Ich konnte nicht wirklich herausfinden, was Sie verändert, im inneren des
Activity
Lebenszyklus im AufrufsaveInstance
aber ich hier ist, wie ich das Problem gelöst :Ich einfach nicht den Aufruf zu
.super()
und alles funktioniert Super. Ich hoffe, dass dies Zeit zu sparen.EDIT: nach einigen mehr Forschung ist dies ein bekanntes bug in den support-Paket.
Wenn Sie die Instanz, und fügen Sie etwas zu Ihrem
outState
Bundle
können Sie die folgenden verwenden :EDIT2: dies kann auch auftreten, wenn Sie versuchen zum ausführen einer Transaktion, nachdem Ihre
Activity
ist Weg im hintergrund. Um dies zu vermeiden sollten Sie die VerwendungcommitAllowingStateLoss()
EDIT3: Die oben genannten Lösungen wurden Behebung von Problemen in der frühen Förderung.v4 Bibliotheken aus, was ich mich erinnern kann. Aber wenn Sie immer noch Probleme mit diesem MUSS Lesen Sie auch @AlexLockwood 's blog : Fragment-Transaktionen & Aktivitäts-Status-Verlust
Zusammenfassung aus dem blog-post (aber ich empfehlen Sie stark, um es zu Lesen) :
commit()
Transaktionen nachonPause()
auf pre-Waben, und dieonStop()
auf post-HoneycombActivity
lifecycle-Methoden. VerwendungonCreate()
onResumeFragments()
undonPostResume()
commitAllowingStateLoss()
nur als letzten AuswegInformationsquelleAutor der Antwort Ovidiu Latcu
Suche im Android-Quellcode auf, welche Ursachen dieses Problem gibt, Flagge mStateSaved in
FragmentManagerImpl
Klasse (Instanz verfügbar in Aktivität) hat den Wert true. Ist es auf true gesetzt, wenn der back-stack gespeichert (saveAllState) auf Anruf vonActivity#onSaveInstanceState
.Danach werden die Anrufe von ActivityThread nicht zurücksetzen dieses flag mit Hilfe der vorhandenen reset-Methoden aus
FragmentManagerImpl#noteStateNotSaved()
unddispatch()
.Die Art, wie ich es sehe gibt es einige fixes, je nachdem, was Ihre app macht und mit:
Gute Möglichkeiten
Etwas anderes vor: ich möchte werben Alex Lockwood Artikel. Dann, von dem, was ich bisher getan habe:
Für Fragmente und Aktivitäten, die nicht brauchen, um jede Status-Informationen, rufen Sie commitAllowStateLoss. Entnommen aus der Dokumentation:
Nur nach dem Abschluss der Transaktion commit (Sie hat gerade angerufen
commit()
), rufenFragmentManager.executePendingTransactions()
.Nicht empfohlen, Möglichkeiten:
Als Ovidiu Latcu oben erwähnt, nicht nennen
super.onSaveInstanceState()
. Dadurch aber verlieren Sie den ganzen Staat von Ihrer Aktivität zusammen mit Fragmenten Zustand.Überschreiben
onBackPressed
und es rufen nurfinish()
. Dies sollte in Ordnung sein, wenn Sie eine Anwendung nicht verwenden, Fragmente API, wie Sie in dersuper.onBackPressed
es ist ein Aufruf anFragmentManager#popBackStackImmediate()
.Wenn Sie beide Fragmente API und den Zustand Ihrer Aktivität ist wichtig/entscheidend ist, dann könnte man versuchen, rufen Sie mit Hilfe der reflection-API
FragmentManagerImpl#noteStateNotSaved()
. Aber dies ist ein hack, oder man könnte sagen, es ist ein workaround. Ich mag es nicht, aber in meinem Fall ist es ganz akzeptabel, da ich einen code von einem legacy-app, nutzt deprecated-code (TabActivity
und implizitLocalActivityManager
).Unten ist der code, verwendet Reflexion:
Prost!
InformationsquelleAutor der Antwort gunar
Solche Ausnahme auftreten, wenn Sie versuchen, führen Sie ein fragment der übergang nach Ihrer fragment-Aktivität
onSaveInstanceState()
aufgerufen wird.Ein Grund, warum dies passieren kann, ist wenn Sie einen
AsyncTask
(oderThread
) ausgeführt wird, wenn eine Aktivität gestoppt wird.Alle übergänge nach
onSaveInstanceState()
genannt wird, könnte möglicherweise verloren, wenn das system reaktiviert die Aktivität der Ressourcen und stellt es später.InformationsquelleAutor der Antwort FunkTheMonk
Rufen Sie einfach super.onPostResume ()bevor Sie zeigt Ihre fragment oder verschieben Sie Ihren code in onPostResume () - Methode nach dem Aufruf von super.onPostResume(). Diese lösen das problem!
InformationsquelleAutor der Antwort MJ.Ahmadi
Dies kann auch geschehen, wenn die Berufung
dismiss()
auf ein dialog-fragment, nachdem der Bildschirm gesperrt wurde\ausgeblendet und die Aktivität + dialog - Instanz Zustand gespeichert wurde. Um dieses nennen:Buchstäblich jedes einzelne mal bin ich die Entlassung ein dialog, den ich nicht kümmern, es Stand jedenfalls nicht mehr, so ist dies ok zu tun - Sie sind nicht wirklich verloren, egal welcher Zustand.
InformationsquelleAutor der Antwort Brian Dilley
Kurze Und funktionierende Lösung :
Folgen Sie Den Einfachen Schritten :
Schritt 1 : Überschreiben onSaveInstanceState-Zustand im jeweiligen fragment. Und entfernen super Methode.
Schritt 2 : Verwenden Sie CommitAllowingStateLoss(); anstatt von commit(); while fragment-Operationen.
InformationsquelleAutor der Antwort Basbous
dieser arbeitete für mich... fand diese auf meinem eigenen... hoffe es hilft dir!
1) NICHT über eine Globale "statische" FragmentManager /FragmentTransaction.
2) onCreate, IMMER initialisieren der FragmentManager wieder!
Beispiel :-
InformationsquelleAutor der Antwort kurayami88
War ich immer, wenn ich zu zeigen versucht-fragment in onActivityForResult () - Methode, so wurde das problem weiter:
Was ich gemacht habe ist die nächste:
InformationsquelleAutor der Antwort Array
Ich löste das Problem mit onconfigurationchanged. Der trick ist, dass nach android activity life cycle, wenn Sie explizit genannt, die der Absicht(Kamera-Vorsatz, oder jede andere Person); die Aktivität wird angehalten und onsavedInstance heißt in diesem Fall. Beim drehen des Geräts auf eine andere position als die anderen, während der die Aktivität aktiv war; dies fragment-Operationen, wie das fragment commit Ursachen Illegal state exception. Es gibt viele beschwert sich darüber. Es ist etwas über android activity lifecycle-management und die richtige Methode aufruft.
Um es zu lösen, ich habe dieses:
1-Überschreiben Sie die onsavedInstance-Methode Ihrer Aktivität, und Sie bestimmen die aktuelle Display-Orientierung(hoch-oder Querformat), dann legen Sie Ihre Ausrichtung des Bildschirms, um es, bevor Sie Ihre Aktivität angehalten wird. so wird die Aktivität, die Sie den Bildschirm sperren Drehung für Ihre Tätigkeit im Fall, dass es gedreht ist, durch ein anderes.
2-dann , überschreiben onresume-Methode der activity, und legen Sie die Ausrichtung Modus wird jetzt zum sensor, so dass nach onsaved-Methode aufgerufen wird, wird ein Anruf mehr Zeit onconfiguration Umgang mit der rotation richtig.
Können Sie kopieren/fügen Sie diesen code in Ihre Tätigkeit zu beschäftigen:
InformationsquelleAutor der Antwort douggynix
Ich hatte das gleiche problem, immer IllegalStateException, aber ersetzen alle meine Aufrufe von commit() mit commitAllowingStateLoss() nicht helfen.
Der Täter war ein Aufruf DialogFragment.show().
Ich umgebe es mit
und das war es. OK, habe ich nicht bekommen, um zu zeigen, der dialog, aber in diesem Fall, das war in Ordnung.
Es war der einzige Ort in meiner app wo ich zum ersten mal rief FragmentManager.beginTransaction (), aber nie aufgerufen commit() also ich habe es nicht gefunden, wenn ich gesucht "commit()".
Das lustige an der Sache ist, der Benutzer verlässt niemals die app. Statt der Mörder war ein AdMob interstitial-Anzeige angezeigt.
InformationsquelleAutor der Antwort Roger C S Wernersson
Meine Lösung für das problem war
In fragment add-Methoden:
Kann schlecht sein, aber konnte nichts finden besser.
InformationsquelleAutor der Antwort mc.dev
Hab ich das gleiche Problem in meiner App. Ich habe das gelöst, einfach den Aufruf der
super.onBackPressed();
auf der vorherigen Klasse und dem aufrufen dercommitAllowingStateLoss()
auf die aktuelle Klasse mit diesem fragment.InformationsquelleAutor der Antwort Peter
Ich denke, Lebenszyklus-Status kann helfen, zu verhindern, dass solche crash ab Android-support-lib v26.1.0 Sie können die folgenden check:
oder Sie können versuchen:
mehr Informationen hier
https://developer.android.com/reference/android/support/v4/app/Fragment.html#isStateSaved()
InformationsquelleAutor der Antwort Jamal
onSaveInstance wird aufgerufen, wenn ein Benutzer dreht den Bildschirm so, dass Sie es laden können Ressourcen im Zusammenhang mit der neuen Ausrichtung.
Es möglich, dass dieser Benutzer rotiert der Bildschirm, gefolgt vom drücken der zurück-Taste (denn es ist auch möglich, dass diese Benutzer fummelte Ihr Handy während der Verwendung der app)
InformationsquelleAutor der Antwort dols
Ich habe dieses Problem.Aber ich denke, das problem ist nicht im Zusammenhang zu Begehen und commitAllowStateLoss.
Folgende stack-trace und der Ausnahme-Meldung über commit().
Aber diese Ausnahme wurde verursacht durch die onBackPressed()
Waren Sie alle verursacht durch checkStateLoss()
mStateSaved wird wahr, nach onSaveInstanceState.
Dieses problem tritt sehr selten auf.Ich habe noch nie auf dieses problem.Ich kann nicht auftreten das problem.
Fand ich Problem 25517
Könnte es stattgefunden haben, in den folgenden Fällen
Zurück-Taste aufgerufen wird, nachdem onSaveInstanceState, aber bevor die neue Aktivität gestartet wird.
verwenden onStop() im code
Ich bin mir nicht sicher, was die Wurzel des Problems ist.
So habe ich eine hässliche Art und Weise.
InformationsquelleAutor der Antwort oO_ox
Lesen
http://chris-alexander.co.uk/on-engineering/dev/android-fragments-within-fragments/
Artikel.
fragment.isResumed() Prüfung hilft mir in onDestroyView w/o mit onSaveInstanceState-Methode.
InformationsquelleAutor der Antwort andep
Gleiche Problem von mir und nach einem Tag Analyse aller Artikel, blog-und stackoverflow habe ich eine einfache Lösung. Verwenden Sie nicht savedInstanceState an alle, dies ist der Zustand mit nur einer Zeile code. Die fragment-code:
InformationsquelleAutor der Antwort Tobia Caneschi
Dies geschieht, wenn Sie versuchen zu laden, ein fragment, aber die Aktivität hat sich verändert seinen Zustand in onPause().Dies geschieht zum Beispiel, wenn Sie versuchen, abrufen von Daten, und laden Sie Sie auf die Aktivität, sondern durch die Zeit, die der Benutzer geklickt hat, die Buttons und zog zur nächsten Aktivität.
Können Sie lösen, gibt es zwei Möglichkeiten
Können Sie mit der Transaktion.commitAllowingStateLoss() anstelle von Transaktion.commit() zum laden von fragment-aber Sie können am Ende verlieren commit-operation, die getan wird.
oder
Stellen Sie sicher, dass die Aktivität im Lebenslauf und nicht auf pause-Status beim laden ein fragment.
Erstellen Sie eine Boolesche und überprüfen, ob die Aktivität ist nicht zu onPause() Zustand.
dann beim laden von fragment-überprüfen, ob Aktivität vorhanden ist und laden nur, wenn Aktivität ist Vordergrund zu stellen.
InformationsquelleAutor der Antwort Anonymous
Gut, nach dem Versuch, alle oben genannten Lösungen, ohne Erfolg (denn im Grunde habe ich derzeit keine Transaktionen).
In meinem Fall war ich mit AlertDialogs und ProgressDialog als Fragmente, die, manchmal, bei rotation, bei der Frage für den FragmentManager, der Fehler steigt.
Ich fand einen workaround, mischen einige viele ähnliche posts:
Seine eine 3-Schritt-Lösung, alles getan auf deiner FragmentActivity (in diesem Fall, das heißt GenericActivity):
InformationsquelleAutor der Antwort Antilope
Wenn ich mit startactivity in einem fragment, bekomme ich diese exception;
Wenn ich auf die Verwendung startactivityforresult, die exception ist Weg 🙂
So der einfache Weg, um es zu beheben ist die Verwendung der startActivityForResult api 🙂
InformationsquelleAutor der Antwort Question
War ich immer zu dieser Ausnahme war, wenn ich drücken Sie die zurück-Taste, um abzubrechen intent chooser auf meiner Karte fragment-Aktivität.
Ich habe dieses Problem gelöst, indem Sie ersetzen den code, der onResume()(wo ich war initialisieren der fragment-und der Begehung der Transaktion) , onStart() und die app funktioniert jetzt gut.
Hoffe, es hilft.
InformationsquelleAutor der Antwort DCS
Dies ist fest in Android 4.2 und auch im support-library-source.[*]
Details von der Ursache (und Tricks) finden Sie auf der Google bug-report:
http://code.google.com/p/android/issues/detail?id=19917
Wenn Sie mit der support-Bibliothek, dann sollten Sie nicht zu kümmern, bug (lang)[*]. Allerdings, wenn Sie über die API direkt (also Nicht über die support-Bibliothek FragmentManager) und der Ausrichtung eines API unter Android 4.2 dann müssen Sie versuchen, eine der Tricks.
[*] In der Zeit des Schreibens der Android-SDK-Manager ist noch die Verteilung eine alte version, die Exponate dieser Fehler.
Bearbeiten ich werde einige Klarstellungen hier, weil ich habe es natürlich irgendwie verwirrt, wer down-stimmte diese Antwort.
Gibt es mehrere verschiedene (aber ähnliche) Umstände können bewirken, dass diese exception geworfen werden. Meine obige Antwort bezieht sich auf die spezifische Instanz diskutiert, die Frage also ein bug in Android, die anschließend behoben wurden. Wenn Sie diese Ausnahme für einen weiteren Grund, es ist, weil Sie sind das hinzufügen/entfernen von Fragmenten, wenn du nicht sein solltest (nach fragment Staaten gerettet wurden). Wenn man in so einer situation dann vielleicht "Verschachtelte Fragmente - IllegalStateException "Kann nicht führen Sie diese Aktion nach onSaveInstanceState"" können von nutzen für Sie.
InformationsquelleAutor der Antwort Benjamin Dobell
Auf der Suche nach ein bisschen die Lösung für dieses problem ist, um Ihre fragment begeht in der onresume.
Quelle: https://wenchaojames.wordpress.com/2013/01/12/illegalstateexception-from-onactivityresult/
InformationsquelleAutor der Antwort jai
Mein Anwendungsfall: ich habe verwendet Zuhörer das fragment zu Benachrichtigen Aktivität, die einige Sache, die passiert ist. Ich habe neue fragment commit auf callback-Methode. Dies funktioniert einwandfrei auf ersten mal. Aber auf die Ausrichtung verändern die Aktivität wiederhergestellt wird, mit der gespeicherten Instanz Staat. In diesem Fall-fragment ist nicht erstellt, wieder impliziert, dass das fragment haben die Zuhörer die alte ist zerstört Aktivität. Irgendeiner Weise die call back Methode wird ausgelöst über das Vorgehen. Es geht um zerstörte Aktivität, die das Problem verursachen. Die Lösung ist ein reset der Zuhörer das fragment mit aktuellen live-Aktivitäten. Diese lösen das problem.
InformationsquelleAutor der Antwort Ganesh Kanna
Was ich gefunden habe ist, dass wenn ein anderer app-dialog-Typ und ermöglicht es, berührt zu werden geschickt in den hintergrund app dann fast jede hintergrund-app-Absturz mit dieser Fehlermeldung.
Ich denke, wir müssen überprüfen, jedes mal, wenn eine Transaktion durchgeführt wird, wenn die Instanz gespeichert oder wiederhergestellt werden.
InformationsquelleAutor der Antwort chris
In meinem Fall, mit dem gleichen Fehler Ausnahme, ich habe die "onBackPressed()" in einer lauffähigen (Sie können jede Ihrer anzeigen):
Verstehe ich nicht, warum, aber es funktioniert!
InformationsquelleAutor der Antwort Alecs
Können Sie aufrufen fragmentManager.popBackStackImmediate(); wenn die Tätigkeit unterbrochen. Aktivität ist noch nicht beendet aber pausiert ist und nicht auf den Vordergrund. Sie brauchen, um zu überprüfen, ob die Aktivität pausiert ist oder nicht, bevor popBackStackImmediate().
InformationsquelleAutor der Antwort Murat
Dank @gunar, aber ich denke, es gibt einen besseren Weg.
Laut doc :
So verwenden
commitNow
zu ersetzen:InformationsquelleAutor der Antwort JianxinLi
Bemerkte ich etwas sehr Interessantes. Ich habe in meiner app die option, das Telefon zu öffnen Galerie und das Gerät fragt, welche app zu verwenden, da ich auf den grauen Bereich Weg von dialog und sah dieses Problem. Ich bemerkte, wie meine Aktivität geht von onPause, onSaveInstanceState zurück zu onResume, ist es nicht geschehen, zu besuchen onCreateView. Mache ich Transaktionen bei onResume. Also, was ich am Ende machen, setzen wir ein flag wird negiert onPause, aber wahr onCreateView. wenn das flag true ist onResume dann tun onCommit, sonst commitAllowingStateLoss. Ich könnte gehen auf und verschwenden so viel Zeit, aber ich wollte überprüfen der Lebenszyklus. Ich habe ein Gerät, das sdkversion 23, und ich bekomme nicht dieses Problem, aber ich habe noch eine eine, die ist 21, und da sehe ich es.
InformationsquelleAutor der Antwort Juan Mendez
können Sie FragmentActivity.onStart vor popBackStackImmediate
wie diese:
http://jorryliu.blogspot.com/2014/09/illegalstateexception-can-not-perform.html
InformationsquelleAutor der Antwort user3327339