Resume application from service notification

Refresh

February 2019

Views

716 time

1

Let me start by saying I know this is a very similar question to others that have been answered, but they aren't helping me to solve my problem.

The question Resume application and stack from notification is exactly the same problem as mine, but the selected answer doesn't work for me and I don't quite understand why it even would?

Simply enough, I want to be able to resume my app from a notification click and regardless of what activity was open I want it to return to the last activity open. So if I'm in activity F, then press the home button and a couple minutes later I press the notification.. I want to return back to activity F. I cannot go back to the MainActivity as the user is sometimes forced to stay on a certain activity.

This answer - https://stackoverflow.com/a/5502950/4662037 is shown below:

final Intent notificationIntent = new Intent(context, YourActivity.class);
notificationIntent.setAction(Intent.ACTION_MAIN);
notificationIntent.addCategory(Intent.CATEGORY_LAUNCHER);

It seems to be correct as so many people have accepted it but what exactly is "YourActivity" in this case?.. I don't want to set it to a specific activity!

EDIT: Updated code for notification

private void setForegroundService(){
    CharSequence text = getString(R.string.app_name);

    PackageManager pm = getPackageManager();

    Intent notificationIntent = pm.getLaunchIntentForPackage("com.example.xxxx.xxxxx");
    notificationIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
    PendingIntent contentIntent = PendingIntent.getActivity(getApplicationContext(), 0,
            notificationIntent, 0);

    // Create the notification
    Notification notification = new NotificationCompat.Builder(this)
            .setContentText(text)
            .setSmallIcon(R.drawable.nurse_call_app_icon)
            .setContentTitle(text)
            .setContentIntent(contentIntent).build();

    notification.flags = Notification.FLAG_AUTO_CANCEL | Notification.FLAG_ONGOING_EVENT;

    //  Start the actual service
    startForeground(Integer.MAX_VALUE, notification);
}

Manifest code:

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.xxxxx.xxxxxx"
    android:versionCode="1"
    android:versionName="0.0.1" >

<uses-sdk android:minSdkVersion="14" />

<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.WAKE_LOCK" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.PROCESS_OUTGOING_CALLS" />
<uses-permission android:name="android.permission.VIBRATE" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.FLASHLIGHT" />
<uses-permission android:name="android.permission.CALL_PHONE" />
<uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission android:name="android.permission.RECORD_AUDIO" />
<uses-permission android:name="android.permission.BLUETOOTH" />
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />

<uses-feature android:name="android.hardware.Camera" />
<uses-feature
    android:name="android.hardware.bluetooth_le"
    android:required="false" />

<application
    android:name=".xxxxxxx"
    android:allowBackup="true"
    android:icon="@drawable/xxxxxx"
    android:label="@string/app_name"
    android:theme="@style/AppTheme" >

    <service android:name=".xxxxxxService" />

    <activity
        android:name=".activities.LoginActivity"
        android:label="@string/app_name"
        android:screenOrientation="portrait" >
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />
            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>

    <activity
        android:name=".activities.MainActivity"
        android:label="@string/app_name"
        android:launchMode="singleTop"
        android:screenOrientation="portrait" >
    </activity>
    <activity
        android:name=".activities.AlarmActivity"
        android:icon="@drawable/ic_action_alarms"
        android:label="@string/alarm_details"
        android:parentActivityName=".activities.MainActivity"
        android:screenOrientation="portrait" >
        <meta-data
            android:name="android.support.PARENT_ACTIVITY"
            android:value=".activities.MainActivity" />
    </activity>
    <activity
        android:name=".activities.SettingsActivity"
        android:icon="@drawable/ic_action_settings"
        android:label="@string/settings"
        android:parentActivityName=".activities.MainActivity"
        android:screenOrientation="portrait" >
        <meta-data
            android:name="android.support.PARENT_ACTIVITY"
            android:value=".activities.MainActivity" />
    </activity>
    <activity
        android:name=".activities.MessageListActivity"
        android:icon="@drawable/ic_action_email"
        android:label="@string/title_activity_text"
        android:launchMode="singleTask"
        android:parentActivityName=".activities.MainActivity"
        android:screenOrientation="portrait" >
        <meta-data
            android:name="android.support.PARENT_ACTIVITY"
            android:value=".activities.MainActivity" />
    </activity>
    <activity
        android:name=".activities.MessageActivity"
        android:icon="@drawable/ic_action_read"
        android:label="@string/message"
        android:parentActivityName=".activities.MessageListActivity"
        android:screenOrientation="portrait" >
        <meta-data
            android:name="android.support.PARENT_ACTIVITY"
            android:value=".activities.MessageListActivity" />
    </activity>
    <activity
        android:name=".activities.BreakActivity"
        android:icon="@drawable/ic_action_person"
        android:label="@string/title_activity_break"
        android:screenOrientation="portrait" >
    </activity>
    <activity
        android:name=".activities.ContactsActivity"
        android:icon="@drawable/ic_action_group"
        android:label="@string/title_activity_contacts"
        android:parentActivityName=".activities.MainActivity"
        android:screenOrientation="portrait" >
        <meta-data
            android:name="android.support.PARENT_ACTIVITY"
            android:value=".activities.MainActivity" />
    </activity>
    <activity
        android:name=".activities.CallActivity"
        android:icon="@drawable/ic_action_call"
        android:label="@string/title_activity_call"
        android:screenOrientation="portrait" >
    </activity>

    <receiver
        android:name=".BootUpReceiver"
        android:enabled="true"
        android:exported="true" >
        <intent-filter>
            <action android:name="android.intent.action.BOOT_COMPLETED" />
            <action android:name="android.intent.action.QUICKBOOT_POWERON" />
            <category android:name="android.intent.category.DEFAULT" />
        </intent-filter>
    </receiver>
    <receiver
        android:name=".PhoneCallReceiver"
        android:enabled="true"
        android:exported="true" >
        <intent-filter>
            <action android:name="android.intent.action.NEW_OUTGOING_CALL" />
            <action android:name="android.intent.action.PHONE_STATE" />
        </intent-filter>
    </receiver>
</application>

So a quick overview of what it does:

It starts with the LoginActivity, after you login it will destroy that and the MainActivity will then become the root of everything. You can navigate up and down between stacks but never below the MainActivity unless you call a logout.

2 answers

4

Look at my question here.

This is how you are supposed to do it:

Intent notificationIntent = new Intent(getApplicationContext(), MainActivity.class);
notificationIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);

PendingIntent pendingIntent = PendingIntent.getActivity(getApplicationContext(), 0, notificationIntent, 0);

Notification notification = new Notification(R.drawable.floating2, "Click to start launcher",System.currentTimeMillis());
notification.setLatestEventInfo(getApplicationContext(), "Start launcher" ,  "Click to start launcher", pendingIntent);
notification.flags = Notification.FLAG_AUTO_CANCEL | Notification.FLAG_ONGOING_EVENT;

NotificationManager notificationManager = (NotificationManager) getApplicationContext().getSystemService(Context.NOTIFICATION_SERVICE);

notificationManager.notify(ID_NOTIFICATION,notification);
0

YourActivity is the root activity. That's the one that is defined with ACTION=MAIN and CATEGORY=DEFAULT in your manifest.

You will also need to set FLAG_ACTIVITY_NEW_TASK as well:

notificationIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

This doesn't actually start any Activity (if your app is already running). It just brings the task containing your app to the foreground in the same state it was in when it went to the background, which is what you want.


UPDATE:

Since you seem to be having problems with this, please try this alternative suggestion:

PackageManager pm = getPackageManager();
// NOTE: replace com.example.xxx.xxx with the package name from your manifest!
Intent notificationIntent = pm.getLaunchIntentForPackage("com.example.xxx.xxx");
PendingIntent contentIntent = PendingIntent.getActivity(getApplicationContext(), 0,
                                   notificationIntent, 0);