Resume application from service notification - android

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.

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);

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);

I resolve this issue by saving top activity intent in onResume method of BaseActivity like below:
Intent currentActivityIntent = new Intent(this, getClass());
currentActivityIntent.addFlags(FLAG_ACTIVITY_NEW_TASK);
currentActivityIntent.addFlags(FLAG_ACTIVITY_SINGLE_TOP);
App.setCurrentActivityIntent(currentActivityIntent);
I get top activity intent after clicking on push.
All you need is to get intent of last top activity with the two flags
FLAG_ACTIVITY_NEW_TASK and FLAG_ACTIVITY_SINGLE_TOP.

Related

Not opening specific activity on notification click when the app is in background/not running

The notification-click starts specified activity only when the app is opened up and the notification-click is performed. If the app is in background/not running and the notification-click is performed, the application's MainActivity opens up. In short, it is like the app opens normally following the activity stack instead of opening the specified activity in the PendingIntent.
I want to redirect the notification clicks to two different Activities (ApprovalDetailActivity and ConversationDetailActivity), based on their type.
I am using FCM for Push notifications. I am pasting my Manifest file and my FCMListener file here. Please help me out.
sendNotification() function in MyFirebaseMessagingService.java
private void sendNotification(String messageBody)
{
Intent intent;
System.out.println("----message body: " + messageBody);
if(notificationBundle.getCategory().equalsIgnoreCase(Master.KEY_PUSH_NOTIFICATION_CONVERSATION))
{
intent = new Intent(this, ConversationDetailActivity.class);
/*Conversation conversation = Master.notificationBundle.getConversation();
Master.conversationsList = new ArrayList<>();
Master.conversationsList.add(conversation);*/
}
else
{
intent = new Intent(this, ApprovalDetailActivity.class);
if(notificationBundle.getApprovalType().equals("I"))
intent.putExtra(Master.KEY_WHICH_APPROVAL, Master.KEY_VERIFICATIONS);
else if(notificationBundle.getApprovalType().equals("A"))
intent.putExtra(Master.KEY_WHICH_APPROVAL, Master.KEY_APPROVALS);
else
intent.putExtra(Master.KEY_WHICH_APPROVAL, Master.KEY_COMPLETED);
intent.putExtra(Master.KEY_IS_FROM_CONVERSATION, false);
}
intent.putExtra(Master.KEY_PUSH_NOTIFICATION_POST_ID , notificationBundle.getPostID());
intent.putExtra(Master.KEY_IS_FROM_PUSH_NOTIFICATION, true);
intent.putExtra(Master.KEY_POSITION, 0);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent,
PendingIntent.FLAG_ONE_SHOT);
Uri defaultSoundUri= RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)
.setSmallIcon(R.drawable.mnet_icon)
.setContentTitle(getString(R.string.app_name))
.setContentText(messageBody)
.setAutoCancel(true)
.setSound(defaultSoundUri)
.setContentIntent(pendingIntent);
NotificationManager notificationManager =
(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
int random = (int) ((new Date().getTime() / 1000L) % Integer.MAX_VALUE);
notificationManager.notify(random, notificationBuilder.build());
}
AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest
xmlns:android="http://schemas.android.com/apk/res/android"
package="mnet.mediaware.com.m_net">
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<application
android:name=".MnetApplication"
android:allowBackup="true"
android:icon="#drawable/mnet_icon"
android:label="#string/app_name"
android:supportsRtl="true"
android:theme="#style/AppTheme">
<activity
android:name=".activities.LoginActivity"
android:configChanges="orientation|keyboardHidden|screenSize"
android:label="#string/app_name"
android:launchMode="singleTask"
android:theme="#style/Theme.AppCompat.Light.NoActionBar.FullScreen">
<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:configChanges="orientation|keyboardHidden|screenSize"
android:label="#string/title_activity_main"
android:launchMode="singleTask"
android:theme="#style/AppTheme.NoActionBar" />
<activity
android:name=".activities.ConversationDetailActivity"
android:configChanges="orientation|keyboardHidden|screenSize"
android:label="#string/title_activity_conversation_detail"
android:parentActivityName=".activities.MainActivity"
android:theme="#style/AppTheme.NoActionBar"
android:launchMode="singleTask"
android:windowSoftInputMode="stateHidden|adjustResize">
<intent-filter>
<action android:name="mnet.mediaware.com.m_net.activities.ConversationDetailActivity" />
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<data android:scheme="http" />
</intent-filter>
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="mnet.mediaware.com.m_net.activities.MainActivity" />
</activity>
<activity
android:name=".activities.ApprovalDetailActivity"
android:configChanges="orientation|keyboardHidden|screenSize"
android:label="#string/title_activity_approval_detail"
android:parentActivityName=".activities.MainActivity"
android:theme="#style/AppTheme.NoActionBar"
android:windowSoftInputMode="stateHidden|adjustResize">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="mnet.mediaware.com.m_net.activities.MainActivity" />
</activity>
<activity
android:name=".activities.NewConversationActivity"
android:configChanges="orientation|keyboardHidden|screenSize"
android:label="#string/title_activity_new_conversation"
android:parentActivityName=".activities.MainActivity"
android:theme="#style/AppTheme.NoActionBar"
android:windowSoftInputMode="stateHidden|adjustResize">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="mnet.mediaware.com.m_net.activities.MainActivity" />
</activity>
<activity
android:name=".activities.NotificationActivity"
android:configChanges="orientation|keyboardHidden|screenSize"
android:label="#string/title_activity_notification"
android:parentActivityName=".activities.MainActivity"
android:theme="#style/AppTheme.NoActionBar"
android:windowSoftInputMode="stateHidden|adjustResize">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="mnet.mediaware.com.m_net.activities.MainActivity" />
</activity>
<activity
android:name=".activities.ProfileActivity"
android:label="#string/title_activity_profile"
android:configChanges="orientation|keyboardHidden|screenSize"
android:parentActivityName=".activities.MainActivity"
android:theme="#style/AppTheme.NoActionBar">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value="mnet.mediaware.com.m_net.activities.MainActivity" />
</activity>
<service
android:name=".utils.firebase.MyFirebaseMessagingService">
<intent-filter>
<action android:name="com.google.firebase.MESSAGING_EVENT"/>
</intent-filter>
</service>
<service
android:name=".utils.firebase.MyFirebaseInstanceIDService">
<intent-filter>
<action android:name="com.google.firebase.INSTANCE_ID_EVENT"/>
</intent-filter>
</service>
</application>
</manifest>
As per Firebase Cloud Messaging documentation-If Activity is in foreground then onMessageReceived will get called. If Activity is in background or closed then notification message is shown in the notification center for app launcher activity.
For More information Check this link
Only this thing worked for me. The thing work for me is simple. Make sure you add this in the activity that you want to open directly.
<intent-filter>
<action android:name="MainActivity" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
And from the push notification you must add a new payload: click_action
it will looks like this -
"notification": {
"title": "hello",
"body": "test message",
"click_action": "MAIN_ACTIVITY"
},
Note: You can name it as you want MAIN_ACTIVITY but must be same in both place.
Notification messages delivered when your app is in the background. In this case, the notification is delivered to the device’s system tray. A user tap on a notification opens the app launcher by default.
Messages with both notification and data payload, when received in the background. In this case, the notification is delivered to the device’s system tray, and the
data payload is delivered in the extras of the intent of your launcher Activity.
if (getIntent().getExtras() != null) {
for (String key : getIntent().getExtras().keySet()){
String value = getIntent().getExtras().getString(key);
Log.d(TAG, "Key: " + key + " Value: " + value);
}}
use this code to get intent datas
I think I got the exact answer for you.
TaskStackBuilder Usage and Definition
Please don't overlook the awesome video into the above link.
TaskStackBuilder taskStackBuilder = TaskStackBuilder.create(getContext());
taskStackBuilder.addNextIntentWithParentStack(intent);
PendingIntent pendingIntent = taskStackBuilder.getPendingIntent(0, PendingIntent.FLAG_UPDATE_CURRENT);
when app is in background Firebase push notification data payload deliver to Launcher Activity,
So, in Launcher Activity you can get simply check and open appropriate screen
if (intent.hasExtra("data")) {
}
Get bundle(for push notification data payload) from intent at launcher activity then start your specific activity.

Resume activity from notification calling onCreate

I am trying to resume my activity from a notification, but it is recreating the activity and not resuming.
As all posts regarding this issue, mention creating a PendingIntent and setting this with the appropriate flags (as shown in code below), and adding the singleTop|singleInstance to the AndroidManifest.
Notification Code:
NotificationManager mNotifyMan = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
mNotifyMan.cancelAll();
Notification.Builder mNB = new Notification.Builder(this);
mNB.setOngoing(true);
Intent intent = new Intent(parentContext, main.class);
intent.setFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT);
PendingIntent pendingIntent = PendingIntent.getActivity(parentContext, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
mNB.setContentIntent(pendingIntent);
mNB.setSmallIcon(R.drawable.ic_notify_icon);
mNB.setLargeIcon(BitmapFactory.decodeResource(getResources(), R.mipmap.ic_noti_large));
mNB.setContentTitle(Title);
mNB.setContentText(Message);
mNB.setColor(0);
mNotifyMan.notify(777, mNB.build());
I understand one must pass an intent with the current context.
When resuming an activity via the onPause() on onResume(), it resumes and restores the last activity state, i.e. a thread counter running has incremented values.
Problem:
When resuming from the notification (i.e. clicking on the notification), the activity is recreated. I have attempted to resolve this by
when onPause() is executed, sending the current activity state via base class to the notification, thus recreating the notification with the current state.
Here is my AndroidManifest:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.cynetstudios.wifimanager">
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<uses-feature android:name="android.hardware.wifi" />
<application
android:allowBackup="true"
android:icon="#mipmap/ic_launcher"
android:label="#string/app_name"
android:supportsRtl="true"
android:theme="#style/AppTheme"
android:launchMode="singleInstance">
<activity android:name="com.cynetstudios.frequencyselector.main" android:configChanges="orientation|screenSize|keyboardHidden">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<service android:name="com.cynetstudios.frequencyselector.serviceWifiFreqManager" android:exported="false"/>
</application>
</manifest>
I might be missing something trivial, any advice?
You can set your Activity's launchMode SingleTask, SingleTop or SingleInstance depending on how you want your activity to act.
Later you can handle your activity's onNewIntent method if your activity is open when user clicks your active notification.
Also you need to define activity's launchMode in that atcitvity's part. I edited your xml.
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.cynetstudios.wifimanager">
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<uses-feature android:name="android.hardware.wifi" />
<application
android:allowBackup="true"
android:icon="#mipmap/ic_launcher"
android:label="#string/app_name"
android:supportsRtl="true"
android:theme="#style/AppTheme">
<activity android:name="com.cynetstudios.frequencyselector.main"
android:configChanges="orientation|screenSize|keyboardHidden"
android:launchMode="singleInstance">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<service android:name="com.cynetstudios.frequencyselector.serviceWifiFreqManager" android:exported="false"/>
</application>
</manifest>
I hope this'll help you.
launchMode should be used in Activity section (not application)
Intent intent = new Intent(Intent.ACTION_MAIN);
intent.addCategory(Intent.CATEGORY_LAUNCHER);
intent.setClass(this, main.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);
startActivity(intent);
You can try this Intent. Such an intent is used by system app launcher, which will just show(no recreate) your activity if it is not killed.
Try
Intent.FLAG_ACTIVITY_CLEAR_TOP
with
Intent.FLAG_ACTIVITY_NEW_TASK
Set them as flags for the intent
Try this it may help you:
intent.setFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
and as #Alexander says put android:launchMode="singleTop" into activity tag

After throwing an Intent to a PDF app, my activity is finished

I'm having an issue trying to open files (can be .jpg or .pdf, mostyl .pdf) this is the code that I use to launch the Intent:
public static void openFile(Context context, File aFile) throws ActivityNotFoundException {
MimeTypeMap myMime = MimeTypeMap.getSingleton();
mLogger.info("Opening file " + aFile.getName());
Intent newIntent = new Intent(Intent.ACTION_VIEW);
String[] nameParts = aFile.getName().split("\\.");
String namePart = nameParts[nameParts.length - 1];
mLogger.info("Searching activity for MIME type " + namePart);
String mimeType = myMime.getMimeTypeFromExtension(namePart);
newIntent.setDataAndType(Uri.fromFile(aFile), mimeType);
newIntent.setFlags(Intent.FLAG_ACTIVITY_MULTIPLE_TASK);
context.startActivity(newIntent);
}
I've already tried changing the flags like:
No flags at all.
newIntent.setFlags(Intent.FLAG_ACTIVITY_MULTIPLE_TASK);
newIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
newIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_MULTIPLE_TASK);
The weird thing is that somethimes works (doesn't close the Activity from where I launched the intent) and some times does (I press back being in the PDF app, and then when I come back, I'm in the Activity previous to the one where I lauched the intent)
I don't know what other thing I can do, I'm starting to think that is some device related problem. My device is a Moto G.
BTW, this happens with the two kind of files, jpg. and pdf. It's the same, I'm mean, I'm pretty sure that the problem is in the way that I'm setting the flags or It's some kind of device related problem. I don't think that this is a problem related to the applications that I use to open the files.
EDIT
Added the manifest
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="TOP_SECRET_SORRY">
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.WRITE_INTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_INTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission android:name="android.permission.BROADCAST_STICKY" />
<!-- Optional permission for reliable local dispatching on non-Google Play devices -->
<uses-permission android:name="android.permission.WAKE_LOCK" />
<application
android:name=".app.NAME"
android:allowBackup="true"
android:icon="#mipmap/ic_launcher"
android:label="#string/app_name"
android:theme="#style/AppTheme">
<meta-data
android:name="com.google.android.gms.version"
android:value="#integer/google_play_services_version" />
<!-- Optionally, register AnalyticsReceiver and AnalyticsService to support background
dispatching on non-Google Play devices -->
<receiver
android:name="com.google.android.gms.analytics.AnalyticsReceiver"
android:enabled="true">
<intent-filter>
<action android:name="com.google.android.gms.analytics.ANALYTICS_DISPATCH" />
</intent-filter>
</receiver>
<service
android:name="com.google.android.gms.analytics.AnalyticsService"
android:enabled="true"
android:exported="false" />
<activity
android:name=".app.activities.LoginActivity"
android:label="#string/title_login"></activity>
<activity
android:launchMode="singleTask"
android:name=".app.activities.MainActivity"
android:label="#string/app_name">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".app.activities.DisclaimerActivity"
android:label="#string/title_disclaimer"></activity>
<activity
android:name=".app.activities.SubCategoriesListActivity"
android:label="#string/title_file_categories"></activity>
<activity
android:name=".app.activities.SubCategoriesDetailActivity"
android:label="#string/online_file_list">
</activity>
<activity
android:name=".app.activities.UatTestingActivity"
android:label="#string/title_uat_testing"></activity>
<service
android:name=".app.services.SyncService"
android:process="com.SOME_COMPANY.SOME_APP.app.services.SyncService" />
<receiver
android:name=".app.receivers.Boot">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
</intent-filter>
</receiver>
<provider
android:name=".utils.MultiProcessShared"
android:authorities="com.COMPANY.SOME_APP.PREFERENCE_AUTHORITY"
android:exported="false" />
</application>
</manifest>
SubcategoryDetailActivity is the one whose context I use to launch the intent.
The problem was solved when I used this flag:
newIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
IDK why but if someone can explain it to me I'll gladly accept that answer.

Code style / correct structure android

Hello fellow programmers,
I cant find a proper way to route my application, I would like one file to decide which activity has to be started
I am building an android application that in general contains:
-2 ways to start up
-3 activity's
The application can be launched by clicking the icon (standard launch)
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
And an activity is started when there is an incoming call
<action android:name="android.intent.action.PHONE_STATE" />
In the first setup there was 2 activity's one to register and one to use the application. In this
setup I added an extra activity to check if a token was present and route to the right activity.
In the setup that I have now, all the actions are in the of a broadcast receiver. I tried implementing the logic of the extra activity.
The problem I am facing is the check of the incoming call, it is always launching the same activity CallHandler,
I think routing the application within a broadcast receiver might be bad practice, but I can not find a better way of routing the application, and the current code does not work.
Your help is very much appreciated, the following pieces of code might help explain my issue:
Manifest:
<?xml version="1.0" encoding="utf-8"?>
<uses-permission android:name="android.permission.CALL_PHONE" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.GET_ACCOUNTS" />
<uses-permission android:name="android.permission.READ_PROFILE" />
<uses-permission android:name="android.permission.READ_CONTACTS" />
<application
android:allowBackup="true"
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
android:theme="#style/AppTheme" >
<receiver android:name=".RoutingCallReceiver">
<intent-filter>
<action android:name="android.intent.action.PHONE_STATE" />
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</receiver>
<activity
android:name=".RegisterActivity"
android:label="#string/app_name"
android:windowSoftInputMode="adjustResize|stateVisible" >
</activity>
<activity
android:name=".CallHandler"
android:label="#string/title_activity_main" >
</activity>
<activity
android:name=".CreateCallActivity"
android:label="#string/title_activity_create_call" >
</activity>
</application>
RoutingCallReceiver:
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.telephony.PhoneStateListener;
import android.telephony.TelephonyManager;
import android.util.Log;
public class RoutingCallReceiver extends BroadcastReceiver {
TelephonyManager telephony;
Intent in;
public void onReceive(Context context, Intent intent) {
PrimePhoneStateListener phoneListener = new PrimePhoneStateListener();
telephony = (TelephonyManager) context
.getSystemService(Context.TELEPHONY_SERVICE);
telephony.listen(phoneListener, PhoneStateListener.LISTEN_CALL_STATE);
if(telephony.getCallState()== 1){
in = new Intent(context, CallHandler.class);
in.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(in);
}
else {
TokenIO tokenHandler = new TokenIO();
String token = tokenHandler.getToken(context);
Log.d("AAfter", "Token");
if(token.equals("") || token.equals(null)){
in = new Intent(context, RegisterActivity.class);
in.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(in);
}
else{
in = new Intent(context, CreateCallActivity.class);
in.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(in);
}
}
}
// when finish your job, stop listen to changes
public void onDestroy() {
telephony.listen(null, PhoneStateListener.LISTEN_NONE);
}
}
you can make change in your xml file
<?xml version="1.0" encoding="utf-8"?>
<uses-permission android:name="android.permission.CALL_PHONE" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.GET_ACCOUNTS" />
<uses-permission android:name="android.permission.READ_PROFILE" />
<uses-permission android:name="android.permission.READ_CONTACTS" />
<application
android:allowBackup="true"
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
android:theme="#style/AppTheme" >
<receiver android:name=".RoutingCallReceiver">
<intent-filter>
<action android:name="android.intent.action.PHONE_STATE" />
</intent-filter>
</receiver>
<activity
android:name=".RegisterActivity"
android:label="#string/app_name"
android:windowSoftInputMode="adjustResize|stateVisible" >
</activity>
<activity
android:name=".CallHandler"
android:label="#string/title_activity_main" >
</activity>
<activity
android:name=".CreateCallActivity"
android:label="#string/title_activity_create_call" >
</activity>
</application>
and put this tag into main activity
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
and i hope that will work fine.

Making a shortcut to a class (not the MainActivity) on the Android Homescreen

I've been looking ALL DAY to no avail..I know there are several questions on this but I haven't been able to find one that works properly for me.
Basically, I have an activity (MainActivity), with a function to add a shortcut to the home screen. When I click the shortcut, I want it to open a different activity (NewActivity). The hold up here seems to be that it doesn't work right when I try to launch a different activity than the one from which the shortcut was made.
The shortcut is successfully made, but when I click it I get an "App isn't installed" toast message from the Android system.
Here's the code for adding the shortcut:
Intent shortcutIntent = new Intent();
shortcutIntent.setClassName("com.enceladus.myApp", "com.enceladus.myApp.NewActivity");
shortcutIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
shortcutIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
Intent addIntent = new Intent();
addIntent.putExtra(Intent.EXTRA_SHORTCUT_INTENT, shortcutIntent);
addIntent.putExtra(Intent.EXTRA_SHORTCUT_NAME, "Calculator");
addIntent.putExtra(Intent.EXTRA_SHORTCUT_ICON_RESOURCE, Intent.ShortcutIconResource.fromContext(MainActivity.this, R.drawable.calc));
addIntent.setAction("com.android.launcher.action.INSTALL_SHORTCUT");
MainActivity.this.sendBroadcast(addIntent);
EDIT: Here's my manifest:
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.enceladus.myApp"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="9"
android:targetSdkVersion="15" />
<uses-permission android:name="android.permission.CAMERA"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="com.android.launcher.permission.INSTALL_SHORTCUT" />
<uses-feature android:name="android.hardware.camera" />
<uses-feature android:name="android.hardware.camera.autofocus" />
<application
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
android:theme="#style/AppTheme" >
<activity
android:name=".MainActivity"
android:label="#string/title_activity_main" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity android:name="com.enceladus.myApp.NewActivity"
android:label=""
android:screenOrientation="portrait"
android:theme="#android:style/Theme.Translucent.NoTitleBar"
android:launchMode="singleInstance"
/>
</application>
NewActivity.class functions perfectly (I know because I've debugged it a lot), so that's not the problem.
Try making your manifest look like this for the NewActivity entry:
<activity android:name="com.enceladus.myApp.NewActivity"
android:label=""
android:screenOrientation="portrait"
android:theme="#android:style/Theme.Translucent.NoTitleBar"
android:launchMode="singleInstance"
>
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
</intent-filter>
</activity>
also maybe try making the shortcut intent like this:
Intent shortcutIntent = new Intent(MainActivity.this, NewActivity.class);
shortcutIntent.setAction(Intent.ACTION_MAIN); //Not sure if you'll need this or not.
//remove the next line.
//shortcutIntent.setClassName("com.enceladus.myApp", "com.enceladus.myApp.NewActivity");
The other way that you can do this is by setting the android:exported flag to true.

Categories

Resources