TaskStackBuilder, multiple distinct PendingIntents, Notifications

1.4k Views Asked by At

I have problem with combination of TaskStackBuilder and distinct PendingIntents for notifications. Let me explain what it is about.

I have an IntentService which creates notification when something comes up. Sometimes it creates several independent notification. Why I don't merge notifications like Google said? Because each notification should open the same Activity, BUT with different extras in passed Intent. So here what a do:

Create new Intent with extras:

Intent notificationIntent = new Intent(this, ItemActivity.class);
notificationIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);

notificationIntent.putExtra(ItemActivity.URL_KEY, feed.getUrl());
notificationIntent.putExtra(ItemActivity.FEED_ID, feed.get_id());
notificationIntent.putExtra(ItemActivity.TITLE, feed.getTitle());

And now is the tricky part - I want to open ItemActivity with proper back stack, this mean when I press Back button or Up in AppBar, I want to come back to parent Activity. So here's what I do (according to Google doc: http://developer.android.com/training/notify-user/navigation.html):

In AndroidManifest.xml I have:

    <activity
        android:name=".MainActivity"
        android:label="@string/app_name"
        android:launchMode="singleTask">
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />
            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>

    <activity
        android:name=".ItemActivity"
        android:label="@string/item_activity"
        android:launchMode="singleTask"
        android:parentActivityName=".MainActivity">
        <meta-data
            android:name="android.support.PARENT_ACTIVITY"
            android:value=".MainActivity" />
    </activity>

Then creating back stack:

TaskStackBuilder stackBuilder = TaskStackBuilder.create(this);
stackBuilder.addParentStack(ItemActivity.class);
stackBuilder.addNextIntent(notificationIntent);

And PendingIntent:

PendingIntent notificationPendingIntent = stackBuilder.getPendingIntent(0, PendingIntent.FLAG_UPDATE_CURRENT);

Finnaly - notfication:

NotificationCompat.Builder builder = (NotificationCompat.Builder) new NotificationCompat.Builder(this)
        (...)
        .setContentIntent(notificationPendingIntent)
        (...)
mNotifyManager.notify(feed.get_id(), builder.build());

In this scenario, app creates different notification with proper back stack, BUT with the same PendingIntent.

When I replace requestCode while getting PendingIntent with, for example, feed.get_id() (or another different number for each PendingIntent like System.currentTimeMillis()) then tapping on notification brings Activity with proper Intent (distinct PendingIntent for each notification), BUT without back stack - Back and Up buttons close the applications.

I've tried deleting android:launchMode="singleTask" from manifest, do not adding flags when I've creating new Intent, read half of Internet, hundred of StackOverflow posts and nothing.

I haven't managed working combination of this two scenario - that is: open Activity with proper Intent and back stack.

In advance please do not write something like "just override onBackPressed and start activity from there" - I want to know what I'm doing wrong here and how to achieve this with proper tools.

2

There are 2 best solutions below

0
On

use different request code Example:

declineNextPendingIntent = stackBuilder.getPendingIntent(2, PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_IMMUTABLE);
declineNextPendingIntent = stackBuilder.getPendingIntent(1, PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_IMMUTABLE);
0
On

After 4 hours of work finally i found the solution. It is very simple just you need to provide a different request codes for pending intents.

PendingIntent pendingIntent = stackBuilder.getPendingIntent((int) gcmMessage.getId() /*Unique request code for each PendingIntent*/, PendingIntent.FLAG_UPDATE_CURRENT);

Documentation for getPendingIntent() method TaskStackBuilder.getPendingIntent(int, int)