Domanda

E 'possibile avviare un'attività in pila, cancellare tutta la storia prima di esso?

La situazione

Ho una pila un'attività che o va A-> B-> C o B-> C (schermo A seleziona gli utenti gettone, ma molti utenti hanno solo un singolo token).

Nella schermata C l'utente possono intraprendere un'azione che rende schermo B valido, quindi l'applicazione vuole portarli a schermo A, indipendentemente dal fatto che è già in pila. Schermo A dovrebbe quindi essere l'unico punto all'ordine del pila nella mia applicazione.

Note

Ci sono molte altre domande simili, ma non ho trovato nulla che risponde a questa domanda esatta. Ho provato a chiamare getParent().finish() - questo si traduce sempre in un'eccezione di puntatore nullo. FLAG_ACTIVITY_CLEAR_TOP funziona solo se l'attività è già in pila.

È stato utile?

Soluzione

Nel livello di API 11 una nuova bandiera Intent è stato aggiunto proprio per questo: Intent.FLAG_ACTIVITY_CLEAR_TASK

Giusto per chiarire, usare questo:

Java

intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);

Kotlin

intent.flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK

Purtroppo per API lvl <= 10, non ho ancora trovato una soluzione pulita per questo. I "DontHackAndroidLikeThis" soluzione è davvero pura aggiustamenti. Non dovresti farlo. :)

Modifica Come da commento @ Ben Pearson s ', per l'API <= 10 ora si può usare IntentCompat classe per lo stesso. Si può usare la bandiera IntentCompat.FLAG_ACTIVITY_CLEAR_TASK al compito chiaro. Così si può sostenere il livello pre API 11 pure.

Altri suggerimenti

Caso 1: Solo due attività di A e B:

Qui il flusso di attività è A-> B .On clic BackButton da B abbiamo bisogno di chiudere l'applicazione poi mentre a partire Activity B da A solo finitura call () questo impedirà Android di memorizzazione Attività A alla Backstack.eg per attività di A è Caricamento in corso / schermata iniziale di applicazione.

Intent newIntent = new Intent(A.this, B.class);
startActivity(newIntent);
finish();

Caso 2: Più di due activitiy:

Se c'è un flusso come A-> B-> C-> D> B e facendo clic sul pulsante indietro nel Activity B venendo da attività D.In quel caso dovremmo usare.

Intent newIntent = new Intent(D.this,B.class);
newIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); 
newIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(newIntent);

qui Attività B verrà avviato dal backstack, piuttosto che una nuova istanza a causa di Intent.FLAG_ACTIVITY_CLEAR_TOP e Intent.FLAG_ACTIVITY_NEW_TASK cancella lo stack e la rende la parte superiore one.So quando premiamo il pulsante di nuovo l'intera applicazione verrà terminata.

Con Android più recente versione> = 16 API uso finishAffinity()

approccio è adatto per> = 16 API.

Intent mIntent = new Intent(mContext,MainActivity.class);
finishAffinity();
startActivity(mIntent);
  • Il suo è stessa partendo nuova attività, e cancellare tutti stack.
  • O Riavvia per MainActivity / FirstActivity.

ho trascorso un paio d'ore anche su questo ... e sono d'accordo che i suoni FLAG_ACTIVITY_CLEAR_TOP come quello che ci si vuole: cancellare l'intero stack, fatta eccezione per l'attività in fase di lancio, in modo che il pulsante Indietro chiude l'applicazione. Eppure, come detto Mike Repass, FLAG_ACTIVITY_CLEAR_TOP funziona solo quando l'attività che stai lanciando è già in pila; quando l'attività non c'è, la bandiera non fa nulla.

Che fare? Mettere l'attività dell'essere lancio nello stack con FLAG_ACTIVITY_NEW_TASK, che rende l'attività che l'inizio di una nuova attività sullo stack storia. Quindi aggiungere il flag FLAG_ACTIVITY_CLEAR_TOP.

Ora, quando FLAG_ACTIVITY_CLEAR_TOP va a trovare la nuova attività nello stack, sarà lì e si fermò prima di tutto viene cancellato.

Ecco la mia funzione di logout; il parametro View è il tasto a cui della funzione allegata.

public void onLogoutClick(final View view) {
    Intent i = new Intent(this, Splash.class);
    i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
    startActivity(i);
    finish();
}

Non si dovrebbe cambiare la pila. pulsante indietro Android dovrebbe funzionare come in un browser web.

mi viene in mente un modo per farlo, ma è piuttosto un hack.

  • Fai la tua attività singleTask aggiungendolo al AndroidManifest Esempio:

    <activity android:name=".activities.A"
              android:label="@string/A_title"
              android:launchMode="singleTask"/>
    
    <activity android:name=".activities.B"
              android:label="@string/B_title"
              android:launchMode="singleTask"/>
    
  • Estendere Application che terrà la logica di dove andare.

Esempio:

public class DontHackAndroidLikeThis extends Application {

  private Stack<Activity> classes = new Stack<Activity>();

  public Activity getBackActivity() {
    return classes.pop();
  }

  public void addBackActivity(Activity activity) {
    classes.push(activity);
  }
}

Da A a B:

DontHackAndroidLikeThis app = (DontHackAndroidLikeThis) getApplication();
app.addBackActivity(A.class); 
startActivity(this, B.class);

Da B a C:

DontHackAndroidLikeThis app = (DontHackAndroidLikeThis) getApplication();
app.addBackActivity(B.class); 
startActivity(this, C.class);

In C:

If ( shouldNotGoBackToB() ) {
  DontHackAndroidLikeThis app = (DontHackAndroidLikeThis) getApplication();
  app.pop();
}

e gestire il pulsante Indietro per pop() dallo stack.

Ancora una volta, non si dovrebbe fare questo:)

Subito dopo aver avviato una nuova attività, utilizzando startActivity, assicuratevi di chiamare finish() in modo che l'attività in corso non è accatastato dietro quella nuova.

Prova questo:

Intent logout_intent = new Intent(DashboardActivity.this, LoginActivity.class);
logout_intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
logout_intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
logout_intent.setFlags(Intent.FLAG_ACTIVITY_NO_HISTORY);
startActivity(logout_intent);
finish();
Intent i = new Intent(MainPoliticalLogin.this, MainActivity.class);
i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
startActivity(i);

Prova sottostante Codice,

Intent intent = new Intent(ManageProfileActivity.this, LoginActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP|
                Intent.FLAG_ACTIVITY_CLEAR_TASK| 
                Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);

Per me non dei metodi di cui sopra non funziona.

Basta fare questo per cancellare tutte le attività precedenti :

finishAffinity() // if you are in fragment use activity.finishAffinity()
Intent intent = new Intent(this, DestActivity.class); // with all flags you want
startActivity(intent)

ho trovato troppo semplice mod solo fare questo nuovo elemento aggiuntivo in AndroidManifest come: -

<activity android:name=".activityName"
          android:label="@string/app_name"
          android:noHistory="true"/>

il android:noHistory cancellerà la tua attività indesiderate da Pila.

A volte il vostro emulatore di forza di Android non riesce a strumento di connessione eclissi DDMS e chiedere ADB per l'avvio manuale. In questo caso è possibile avviare o interrompere l'adb utilizzando il prompt dei comandi.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top