14

Ich habe eine Anwendung, die Benachrichtigungen ausgibt, die bei Auswahl eine Aktivität starten. Laut den Android-Dokumenten kann ich mit NavUtils.shouldUpRecreateTask überprüfen, ob die Aktivität direkt (d. H. Aus der Benachrichtigung) oder über einen normalen Aktivitätsstapel gestartet wurde. Es gibt jedoch die falsche Antwort. Ich teste das auf JellyBean, aber benutze die Support-Bibliothek.NavUtils.shouldUpRecreateTask schlägt auf JellyBean fehl

Grundsätzlich gibt shouldUpRecreateTask immer false zurück, auch wenn die Aktivität aus der Benachrichtigung gestartet wurde.

Irgendwelche Ideen, warum shouldUpRecreateTask nicht die richtige Antwort geben kann?

+0

Hallo Clyde, funktioniert shouldUpRecreateTask für Sie vor Jellybean? Ich werde immer falsch auf dem Emulator, egal ob ich meine App direkt vor dem Öffnen der Benachrichtigung getötet habe. – Maragues

+0

Ich habe eigentlich genau das gleiche Problem. AFAIK, es scheint kaputt zu sein. –

+0

Siehe http://stackoverflow.com/questions/14602283/up-navigation-broken-on-jellybean – riwnodennyk

Antwort

5

Ich weiß immer noch nicht warum shouldUpRecreateTask fehlschlägt - Blick auf den Quellcode dafür hilft nicht viel. Aber die Lösung ist ziemlich einfach - ich füge nur einen zusätzlichen Flag-Wert zur Absicht hinzu, die der Benachrichtigung angehängt ist, und überprüfe dies in onCreate(). Wenn es gesetzt ist, wurde die Aktivität von der Benachrichtigung aus aufgerufen, so dass der Rückstapel neu erstellt werden muss.

Der Code sieht wie folgt aus:

@Override 
public void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    Bundle b = getIntent().getExtras(); 
    fromNotification = b.getInt("fromNotification") == 1; 
    setContentView(R.layout.threadlist); 
} 

@Override 
public boolean onHomeButtonPressed() { 
    if(fromNotification) { 
     // This activity is not part of the application's task, so create a new task 
     // with a synthesized back stack. 
     TaskStackBuilder tsb = TaskStackBuilder.from(this) 
       .addNextIntent(new Intent(this, COPAme.class)); 
     tsb.startActivities(); 
    } 
     // Otherwise, This activity is part of the application's task, so simply 
     // navigate up to the hierarchical parent activity. 
    finish(); 
    return true; 
} 
+1

Dies wird nicht helfen, wir würden den echten Backstack zerstören, falls wir die Anwendung bereits benutzen würden. Es ist in Ordnung, wenn unsere App geschlossen ist. – Maragues

+0

@Maragues Wenn die Aktivität bereits geöffnet ist, wird onCreate nicht aufgerufen - onNewIntent wird stattdessen aufgerufen, daher wird fromNotification nicht festgelegt, sodass der Backstack intakt bleibt. Wenn die Aktivität nicht geöffnet ist, dann ist es genau das, was ich möchte, den vorhandenen Backstack zu zerstören. – Clyde

+0

warum verwenden Sie getInt ("fromNotification") == 1 wenn Sie etwas wie getBoolean ("fromNotification", false) verwenden können? – ademar111190

4

Dies ist nicht korrekt! Wenn Sie aus der Meldung beginnen müssen Sie den Stapel erstellen, wenn die Meldung Aufbau wie hier erklärt: http://developer.android.com/guide/topics/ui/notifiers/notifications.html#NotificationResponse

Deshalb, wenn die Benachrichtigung Erstellen Sie, dies zu tun haben:

Intent resultIntent = new Intent(this, ResultActivity.class); 
// ResultActivity is the activity you'll land on, of course 
TaskStackBuilder stackBuilder = TaskStackBuilder.create(this); 
// Adds the back stack 
stackBuilder.addParentStack(ResultActivity.class); 
// Adds the Intent to the top of the stack 
// make sure that in the manifest ResultActivity has parent specified!!! 
stackBuilder.addNextIntent(resultIntent); 
// Gets a PendingIntent containing the entire back stack 
PendingIntent resultPendingIntent = 
     stackBuilder.getPendingIntent(0, PendingIntent.FLAG_UPDATE_CURRENT); 

und dann, wenn Sie Klicken Sie auf die Schaltfläche AUF, Sie benötigen den regulären Code, der lautet:

if (NavUtils.shouldUpRecreateTask(this, intent)) { 
    // This activity is NOT part of this app's task, so 
    // create a new task when navigating up, with a 
    // synthesized back stack. 
    TaskStackBuilder.create(this) 
    // Add all of this activity's parents to the back stack 
      .addNextIntentWithParentStack(intent) 
      // Navigate up to the closest parent 
      .startActivities(); 
} else { 
    NavUtils.navigateUpTo(this, intent); 
} 

Dies funktioniert perfekt für mich.

+0

+1, das scheint mir die beste/richtigste Antwort zu sein. Vielen Dank. – akent

+1

TaskStackBuilder.getPendingIntent setzt das Flag FLAG_ACTIVITY_CLEAR_TASK auf intent, was dazu führt, dass onNewIntent() NICHT wie oben erwartet aufgerufen wird 2.3. Vergessen Sie in meinen Opinions TaskStackBuilder nicht den normalen PendingIntent. – jiashie

3

Ich hatte das gleiche Problem wie OP. NavUtils.shouldUpRecreateTask schien immer false zurückzugeben. (JellyBean auch) nutzte ich folgendes um die gleiche Funktionalität zu erreichen.

case android.R.id.home: 
Intent upIntent = new Intent(this,ParentActivity.class); 
upIntent.addFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT); 
startActivity(upIntent); 
finish(); 
return true; 

Die "Eltern" Absicht konnte auf diese Weise statt der harten Codierung abgerufen werden.

Intent upIntent = NavUtils.getParentActivityIntent(this);