2012-03-05 2 views
6

Ho uno strano comportamento nella mia applicazione sul cambio di orientamento.Seconda istanza di attività dopo il cambiamento di orientamento

Il comportamento normale:
Quando apro il mio app mia attività di casa inizia. Quando vado alla prossima attività (una galleria) viene avviato normalmente (con un'animazione scorrevole da destra a sinistra). Quando torno usando il tasto indietro, l'attività corrente (la galleria) è terminata (con un'animazione scorrevole da sinistra a destra).

Lo strano comportamento:

  • Quando sto iniziando l'applicazione in modalità verticale e modificare l'orientamento di paesaggio. Poi c'è qualcosa come una seconda istanza dell'attività domestica. Perché premendo il pulsante Indietro in modalità orizzontale non si chiude l'app come sarebbe senza modifica di orientamento (l'attività di casa è la prima attività nella mia app), ma rahter crea un'animazione scorrevole da sinistra a destra (come l'avvio di una nuova attività) e mostra l'attività domestica (ma penso un'altra istanza) di nuovo. Premendo il pulsante Indietro una seconda volta si chiude l'app.
  • Quando si avvia l'app in modalità orizzontale e si modifica l'orientamento in modalità verticale, premere quindi il pulsante Indietro che genera un'animazione di diapositiva da destra a sinistra (come la chiusura di un'attività) e mostra di nuovo l'attività di casa.
  • Quando avvio l'app e faccio due cambi di orientamento portrait-landscape-portrait, quindi il pulsante back chiude l'app come dovrebbe.

Quindi è come se il paesaggio e la modalità verticale fossero trattati come due attività diverse.

Non uso android:configChanges="orientation|keyboardHidden|screenSize", quindi un cambiamento di orientamento dovrebbe seguire il normale ciclo di vita di attività Android e distruggere la versione "vecchio" verticale (o orizzontale) dell'attività.
Le mie attività ereditano da FragmentActivity. Sto usando onSaveInstanceState per passare un parceable (che non contiene alcun riferimento all'attività) e sto usando onRetainCustomNonConfigurationInstance (read here) per passare più AsyncTask s. Ma tutti i riferimenti in queste attività (se ne hanno) vengono distrutti in onRetainCustomNonConfigurationInstance e ripristinati (con l'attività appena creata) dopo getLastCustomNonConfigurationInstance.

Qualche idea su cosa potrebbe causare questo comportamento?

EDIT:
Dichiarazione attività nel manifesto-File:
<activity android:name=".activities.smartphone.HomeSmartphone" android:label="@string/app_name"></activity>

HomeSmartphone estende casa
Home si estende MyFragmentActivity
MyFragmentActivity estende android.support.v4.app.FragmentActivity

In MyFragmentActivity Faccio solo alcune operazioni di registrazione/monitoraggio in onCreate, onRestart, onStart, onSaveInstanceState, onPause, onResu me, onStop, onDestroy chiamando alcuni metodi statici di una classe di monitoraggio, che contiene solo un riferimento al contesto dell'applicazione. Non per il contesto di attività.

Home è una classe astratta che viene estesa da HomeSmartphone e HomeTablet.Queste due classi eseguono solo alcune operazioni di caricamento/aggiornamento/inizializzazione speciali nei diversi layout.

La maggior parte delle attività vengono eseguite nella classe astratta casa.



    public HomeRetainedObjects retained = new HomeRetainedObjects(); 

    public boolean adIsShown = false; 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     this.setContentView(R.layout.home); 

     Log.i("DEBUG", "onCreate(Home)"); 

     if (savedInstanceState != null) { 
      this.adIsShown = savedInstanceState.getBoolean("adIsShown"); 
     } 

    // write/update values in shared preferences 
     this.initPreferences(); 

    // recover retained objects (mostly AsyncTasks) 
     this.recoverRetained(); 

    // show content/refresh content 
     this.init(); 
    } 

    @Override 
    protected void onSaveInstanceState(Bundle outState) { 
     super.onSaveInstanceState(outState); 

     outState.putBoolean("adIsShown", this.adIsShown); 

     Log.i("DEBUG", "onSaveInstanceState(Home)"); 
    } 

    public void recoverRetained() { 
     Object retained = this.getLastCustomNonConfigurationInstance(); 
     if (retained instanceof HomeRetainedObjects) { 
      this.retained = (HomeRetainedObjects) retained; 

      if (this.retained.loadMessageTask != null) { 
       this.retained.loadMessageTask.restoreContext(this); 
      } 
     } 
    } 

    @Override 
    public Object onRetainCustomNonConfigurationInstance() { 
     if (this.retained.loadMessageTask != null) { 
      this.retained.loadMessageTask.destroyContext(); 
     } 

     return this.retained; 
    } 

Spero che questo aiuti ?!

+0

ci mostrano il codice ... –

+0

... compresa la dichiarazione di attività nel vostro manifesto, plz. – Turnsole

+3

+1 per una domanda ben fatta che ci mostra i tuoi sforzi :) –

risposta

0

mi sono imbattuto in un problema simile, e sembra che la causa dei vostri problemi è prevalente onRetainCustomNonConfigurationInstance().

ho rivisto il mio oggetto di stato di ritenzione, e ha scoperto che era in possesso di un riferimento ad un Context. Ho avvolto in un WeakReference e il comportamento normale tornato e non strane doppie casi indugiato su.

Forse il vostro stato di conservazione è anche in possesso di un riferimento ad un Context?