Android: onSaveInstanceState n'étant pas appelé de l'activité

j'ai une activité A qui appelle L'activité B. Dans L'activité B, quand je clique sur un bouton, finish() est appelé, qui à son tour appelle onDestroy() de L'activité B et retourne à l'activité A.

selon la documentation android, avant que onDestroy soit appelé, onSaveInstanceState (Bundle bundle) sera appelé, où je fais ce qui suit.

@Override
    public void onSaveInstanceState(Bundle outState) {

        super.onSaveInstanceState(outState);
        System.out.println("Saving webview state");
        Log.d(TAG, "In onsave");
        wv.saveState(outState);

    }

et la prochaine fois que l'Activité B est démarré à partir d'Une Activité,

dans le oncreate(), je ne l' suivantes:

onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);

if(savedInstanceState != null){
//restore webview
}else {
// code
}
}
<!-Cependant, avant de faire appel à onDestroy dans L'activité B, la méthode onSaveInstanceState n'est jamais appelée. toute aide sera grandement appréciée.

modifier: si ce n'est pas possible. S'il vous plaît laissez-moi savoir si il existe un moyen pour stocker webview état

39
demandé sur Bharath 2012-10-09 08:59:21

4 réponses

s'il vous Plaît notez que onRestoreInstanceState() est appelé lorsque l'activité est recréée mais seulement si:

il a été tué par le système d'exploitation. "Une telle situation se produit lorsque:

  • l'orientation de l'appareil change (votre activité est détruite et recréée)
  • il y a une autre activité devant la vôtre et à un moment donné L'OS tue votre activité afin de libérer la mémoire (par exemple). La prochaine fois que vous commencez votre activité onRestoreInstanceState() sera appelé."

Donc, si vous êtes dans votre activité et vous frapper le bouton de Retour sur l'appareil, votre activité est finish() ed et la prochaine fois que vous démarrez votre application, il est redémarré (il ressemble à re-créé, n'est-ce pas?) mais cette fois -sans état enregistré parce que vous l'avez quitté intentionnellement lorsque vous avez appuyé sur le bouton arrière.

49
répondu Marcin S. 2016-04-05 07:48:30

j'ai eu une situation similaire. C'était clairement un insecte dev. J'ai surchargé la méthode incorrecte:

public void onSaveInstanceState(Bundle outState, 
                                PersistableBundle outPersistentState)

correct:

protected void onSaveInstanceState(Bundle outState)
194
répondu Paweł Szczur 2016-12-12 18:10:46

voir le doc ici: http://developer.android.com/reference/android/app/Activity.html

Notez qu'il est important d'enregistrer les données persistantes dans onPause() au lieu de onSaveInstanceState(Bundle) parce que ce dernier n'est pas fait partie du cycle de vie callbacks, donc ne sera pas appelé dans chaque situation décrite dans sa documentation.

la documentation de onSaveInstanceState méthode dit,

ne confondez pas cette méthode avec les callbacks du cycle de vie de l'activité tels que onPause(), qui est toujours appelée lorsqu'une activité est placé dans le fond ou sur la voie de la destruction, ou onStop() ce qui est appelé avant la destruction. Un exemple de cas où onPause() et onStop() est appelé et non cette méthode est quand un utilisateur navigue en arrière de l'activité B activité: il n'est pas nécessaire d'appeler onSaveInstanceState(Bundle) on B parce que cette instance particulière ne sera jamais restauré, donc le système évite de l'appeler. Exemple lorsque onPause() est appelé et non onSaveInstanceState(Bundle) est lorsque l'activité B est lancée devant l'activité A: le système peut éviter d'appeler onSaveInstanceState(Bundle) à l'activité A si ce n'est pas le cas tué pendant la durée de vie de B depuis l'état de l'interface utilisateur d'Une volonté de demeurer intact.

essaye ceci:

@Override
public void onPause(){
   System.out.println("Saving webview state");
    Log.d(TAG, "In onsave");
    wv.saveState(outState);
    super.onPause();

}

and
@Override
 public void onResume(){
     //restore webview
 }

Je ne sais pas quel est le but de cette déclaration si, mais essayez ceci et voyez ce qui se passe.

5
répondu fangmobile.com 2016-09-03 08:08:00

finalement, vous allez devoir écrire l'historique du stockage persistant. Dans le cas de l'appareil à l'arrêt, comme un exemple, ainsi que d'éviter artificiel (à mon avis) exemple où vous appelez onSaveInstanceStateonPause (ce que vous devez faire pour obtenir le paquet que vous voulez passé dans onRestoreInstanceState vous pouvez ensuite passer dans restoreState).

par conséquent, en plus de reconsidérer votre conception (si l'Utilisateur a fermé votre application et vous ne faites pas un navigateur, est-ce qu'ils voulez vraiment garder la même histoire?), vous devez rechercher SharedPreferences et comment les utiliser.

malheureusement, vous ne pouvez pas mettre un paquet dans les préférences partagées, et je ne recommande pas d'essayer d'écrire le paquet via Parcelable (il est seulement destiné à L'IPC, pas au stockage persistant). Mais ce que vous pouvez faire est de stocker tous les primitifs que le bundle stocke. C'est peut-être artificiel, mais il me semble que c'est le seul moyen d'obtenir un stockage permanent.

et puis reconstruire votre paquet via le primitives stockées dans des références partagées, et passer que dans restoreState(). Vous pouvez vérifier le code source Android pour voir ce webView.saveState() en fait si (j'ai regardé le code 2.1 et il semble écrire un int, un objet sérialisable, puis un autre bundle pour le cert SSL. Le paquet SSL cert lui-même n'est que de quatre entiers). Sur le dessus de ma tête, je voudrais juste écrire toutes les primitives que vous pouvez, et puis stocker l'emplacement (chaîne) du fichier local vous écrivez les données sérialisées aussi.

Même si vous avez une certaine collection ordonnée de l'ensemble de la liste BackForward, Je ne sais pas comment traduire cela dans le goBack() et goForward() en utilisant ces valeurs (il y a une méthode protégée qui est impliquée dans l'ajout d'éléments à la liste, mais vous ne pouvez pas y accéder). À MOINS que vous ne l'utilisez restoreState(), qui est pourquoi nous allons tout le travail pour reconstruire le bundle correctement.

sérieusement cependant, à moins que mes compétences de recherche sont abysmal( entièrement possible), stocker le WebView histoire dans les endroits au-delà où saveInstanceState/restoreInstanceState pouvez faire votre travail pour vous, ne semble pas être un problème, beaucoup de gens ont couru. C'est-à-dire: peu de gens essayent de persister dans L'histoire de WebView quand l'utilisateur ferme explicitement son application, donc vous devez vous demander pourquoi vous faites cela?

excuses s'il y a un moyen vraiment facile de conserver cette information et de la recharger dans un WebView btw!

3
répondu aamit915 2012-10-09 07:42:24