I have a GCMIntentService class, in which i get some messages returned from my server. I want to be able to start a certain activity when a certain message arrives at my app. For example if in my onMessage() method (onMethod() is the method, and the first place, in the app, that receives the messages from the server) arrives the string = "tomatoe", i want to start a specific activity. The way i know right now to start an activity, is this:
Intent resactivity = new Intent(getApplicationContext(), ResponseActivity.class);
resactivity.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(resactivity);
The problem is that GCMIntentService, is not a class that extends activity, and i believe that i can't use this code for this purpose. Is there some way to initiate an activity from a class that is not an activity, by creating an intent inside that class?
The problem is that GCMIntentService, is not a class that extends activity, and i believe that i can't use this code for this purpose.
GCMIntentService inherits from Context, which is where startActivity() is defined.
Bear in mind, though, that your users may attack you with pitchforks or machine guns for popping up activities at random points in time, perhaps in the middle of something else that they are doing. Please make this behavior configurable, or else make very very certain that your users will appreciate these interruptions.
I post the method I usually use to start an activity when a notification arrives in my apps. Take a look to all the configurations and remove those you are not interested in:
#Override
protected void onMessage(Context context, Intent intent) {
String app_name = context.getString(R.string.app_name);
String message = intent.getStringExtra("payload");
String ns = Context.NOTIFICATION_SERVICE;
NotificationManager notificationManager = (NotificationManager) context.getSystemService(ns);
int icono = R.drawable.ic_stat_notify;
long time = System.currentTimeMillis();
Notification notification = new Notification(icono, app_name, time);
notification.defaults |= Notification.DEFAULT_SOUND;
Intent notificationIntent = new Intent(context, ResponseActivity.class);
PendingIntent pendingIntent = PendingIntent.getActivity(context, -1, notificationIntent, PendingIntent.FLAG_UPDATE_CURRENT);
notification.when = System.currentTimeMillis();
notification.flags |= Notification.FLAG_AUTO_CANCEL;
notification.setLatestEventInfo(context, app_name, message, pendingIntent);
notificationManager.notify(0, notification);
}
You should be able to do it as such:
getApplication().startActivity(resactivity);
Related
I have implemented smooch. https://smooch.io/
And my issue is that when I get the notification from smooch. If I'm in the background, I set a "unread messages" long that I use in my main activity on the smooch button.
The issue is that when I press on the notification, and the ConversationActivity is started from there. I need to set the unread messages to 0, because the ConversationActivity is opened. How can I know when this happens?
I cannot modify ConversationActivity.class from the smooch library.
I thought about making the notification myself, and changing the smooch created one with this one using this code:
private static void generateNotificationSmooch(final Context context, String title, String message) {
if (title == null)
title = context.getString(R.string.passenger_name);
Intent notificationIntent = new Intent(context, ConversationActivity.class);
notificationIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
int iUniqueId = (int) (System.currentTimeMillis() & 0xfffffff);
PendingIntent intent = PendingIntent.getActivity(context, iUniqueId, notificationIntent, PendingIntent.FLAG_UPDATE_CURRENT);
NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(context);
mBuilder.setContentTitle(title).setContentText(message).setSmallIcon(R.drawable.notification_icon);
mBuilder.setContentIntent(intent);
Notification notification = mBuilder.build();
notification.flags |= Notification.FLAG_AUTO_CANCEL;
NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
notificationManager.notify(0, notification);
}
But I need to set the unread to 0 when the notification is pressed, and not when I create the notification. And I can't put it in pending intent
You have a few options.
Use the onSmoochShown delegate callback.
This callback will be triggered when the conversation is shown, so you will be able to update your unread count.
Use the onUnreadCountChanged delegate callback
.
This delegate will be called whenever the unread count changes for current user. You can use this callback to update your long accordingly.
Since you will need to be listening to these delegate callbacks when a notification is tapped, it may be best to set your delegate in your Application’s onCreate, after you initialize Smooch.
Is it possible not launch new activity if we receive a push notification while the app is running?
My activity works with fragments and I want to do transition to a determinate fragment when the notification is received. My activity have data that I need to show the fragments. The problem is that when I receive the push notification while the app is running the method onDestroy is called and here I clear the data and then the app crash because the data are null. How can I do to not create new activity when the app receive a push notification while is running? In case the app is running I want that if you click the notification do a transition fragment, not create again the activity.
Thanks in advance.
First of all, I think that you mean "notification" to be a "message", but not android.app.Notification class.
And second, I don't think it's a best practise to raise new GUI when receiving a message, which would interrupt the user interaction. For details, please refer to: http://developer.android.com/training/notify-user/index.html and http://developer.android.com/design/patterns/notifications.html.
At last, if you really wanna do what you stated in your thread, I wonder why the data used to generate the show-data fragment is held in the activity. Try holding the data in an android.app.IntentService object, and then generate transfer the data to new activity, and then use android.app.Fragment.setArguments method to transfer the data from activity to fragment.
I think that this code will help you. This which you need is PendingIntent, it make transaction to desired activity.
/**
* Issues a notification to inform the user that server has sent a message.
*/
private static void generateNotification(Context context, String title,
String message) {
//get the default notification sound URI
Uri uriNotificationSound = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
//make intent to the application. if the application is opened just maximize it.
Intent homeIntent = new Intent(context, 'your desired activity');
homeIntent.addFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
PendingIntent contentIntent = PendingIntent.getActivity(context, 0,
homeIntent, 0);
NotificationCompat.Builder mBuilder =
new NotificationCompat.Builder(context)
.setSmallIcon(R.drawable.ic_launcher)
.setContentTitle("eCommCongress")
.setContentText(message)
.setLights(Color.GREEN, 1500, 1500)
.setSound(uriNotificationSound)
.setAutoCancel(true)
.setContentIntent(contentIntent);
NotificationManager mNotificationManager =
(NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
// mId allows you to update the notification later on.
mNotificationManager.notify(counter, mBuilder.build());
counter++;
}
It is perfectly possible and I do such a thing in one of my apps. First, you need to declare your activity as android:launchMode="singleTop",
Then, when you build you must configure your pending intent not to fire a new instance of your activity:
mNotificationManager = (NotificationManager)
this.getSystemService(Context.NOTIFICATION_SERVICE);
Intent intent = new Intent("YOUR ACTION HERE");
intent.setClassName(this, MainActivity.class.getName());
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);
PendingIntent resultPendingIntent = PendingIntent.getActivity(getApplicationContext(), 0, intent, PendingIntent.FLAG_CANCEL_CURRENT);
NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(this);
mBuilder.setContentIntent(resultPendingIntent);
Notification notification = mBuilder.build();
notification.defaults |= Notification.DEFAULT_VIBRATE | Notification.DEFAULT_LIGHTS;
notification.flags |= Notification.FLAG_SHOW_LIGHTS | Notification.FLAG_AUTO_CANCEL;
mNotificationManager.notify(idNotificacion,notification);
Now all you have to do is to override your onNewIntent inside your Activity and do whatever you want with your fragment:
#Override
protected void onNewIntent(Intent intent) {
MiLog.i(getApplicationContext(),"IntentShit","new intent received");
MiLog.i(getApplicationContext(),"IntentShit","Action: "+intent.getAction());
if(intent.getAction()!=null && intent.getAction().equals("YOUR ACTION HERE"){
//DO your stuff here
}
}
You should also take a look at this page for more info:
http://www.intridea.com/blog/2011/6/16/android-understanding-activity-launchmode
I try to make my notification(from Service) updating or refreshing in every five minutes. How can I do this? This is, what i want to update.
if (...){
int icon = R.drawable.updatedImage1;
long when = System.currentTimeMillis();
NotificationManager notificationManager = (NotificationManager) this
.getSystemService(Context.NOTIFICATION_SERVICE);
CharSequence message = "II Tydzień";
Notification notification = new Notification(icon, message, when );
String title = this.getString(R.string.app_name); // Here you can pass the value of your TextView
Intent notificationIntent = new Intent(this, MainActivity.class);
notificationIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP );
PendingIntent intent = PendingIntent.getActivity(this, 0, notificationIntent, 0);
notification.setLatestEventInfo(this, title, message, intent);
notification.flags |= Notification.FLAG_NO_CLEAR;
notificationManager.notify(0, notification);
} else { ...other notification }
Condition is period of time, so I need to change notification depending on what time is it.
You can use AlarmManager to schedule your notification repeatedly at different time intervals. The docs mention that:
This class provides access to the system alarm services. These allow you to schedule your application to be run at some point in the future. When an alarm goes off, the Intent that had been registered for it is broadcast by the system, automatically starting the target application if it is not already running
You might be able to use setRepeating function for your purpose.
so we have an iOS app and an Android app that each utilize their respective notification method frameworks... iOS has push and Android has C2DM (until we bring it up to GCM)... all is well on iOS, but i'm looking for a method of detecting if the app was launched by clicking a C2DM message (similar to the functionality of didFinishLaunchingWithOptions on iOS).
Currently, when the push message is received on Android, i do whatever processing that i need to do based on the data contained within the message's payload... so when the user launches the app their experience is determined by what was in that push message. This is the case regardless of whether they launch by pressing the icon on the home screen/history or push message. Ideally we'd like this to happen only if they select that message, and if they select the app from the home/history screen then it should launch normally.
You can save some data in the SharedPreferences on your onMessage listener in the GCMIntentService intent class. The GCM listener belongs to your package app after all.
What you save depends on your app and your message payload, but it may be whatever you want.
Then on your onCreate function of the Activity launched when clicking on the notification, you read the Shared Preferences to see whether you come from the GCM notification or not. Remember to clear the variable you save in the SharedPreferences so that next time that the user opens the app, it displays the content properly.
You have an example here. Unfortunately I cannot try it right now but it's useful to see the idea. It's quite similar to G2DM so you have to look for the equivalent in your case.
public class GCMIntentService extends GCMBaseIntentService {
/*... other functions of the class */
/**
* Method called on Receiving a new message
* */
#Override
protected void onMessage(Context context, Intent intent) {
Log.i(TAG, "Received message");
String message = intent.getExtras().getString("your_message");
// notifies user
generateNotification(context, message);
}
/**
* Issues a notification to inform the user that server has sent a message.
*/
private static void generateNotification(Context context, String message) {
int icon = R.drawable.ic_launcher;
long when = System.currentTimeMillis();
NotificationManager notificationManager = (NotificationManager)
context.getSystemService(Context.NOTIFICATION_SERVICE);
Notification notification = new Notification(icon, message, when);
// Save your data in the shared preferences
SharedPreferences prefs = getSharedPreferences("YourPrefs", MODE_PRIVATE);
SharedPreferences.Editor prefEditor = prefs.edit();
prefEditor.putBoolean("comesFromGCMNotification", true);
prefEditor.commit();
String title = context.getString(R.string.app_name);
Intent notificationIntent = new Intent(context, MainActivity.class);
// set intent so it does not start a new activity
notificationIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP |
Intent.FLAG_ACTIVITY_SINGLE_TOP);
PendingIntent intent =
PendingIntent.getActivity(context, 0, notificationIntent, 0);
notification.setLatestEventInfo(context, title, message, intent);
notification.flags |= Notification.FLAG_AUTO_CANCEL;
// Play default notification sound
notification.defaults |= Notification.DEFAULT_SOUND;
// Vibrate if vibrate is enabled
notification.defaults |= Notification.DEFAULT_VIBRATE;
notificationManager.notify(0, notification);
}
}
I'm trying to create a notification when an alarm fires. No problem so far.
A notification is shown. The problem is on my device (2.1 Update 1) it is displayed as an ongoing notification. While on another device (2.2) it is working fine and is actually shown as a one time only notification. Has anyone experienced this behaviour, and more important has anyone been able to fix it. It seems like 2.1 is not respecting the FLAG_ONLY_ALERT_ONCE or any flags for that mather. See my code below. Any help would be appreciated.
public class AlarmHandler extends BroadcastReceiver {
NotificationManager nm;
#Override
public void onReceive(Context context, Intent intent) {
Debug.log("Alarm notification received");
nm = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
CharSequence from = intent.getStringExtra("AlarmType");
CharSequence message = intent.getStringExtra("AlarmType");
Intent newIntent = new Intent(context, Splashscreen.class);
PendingIntent contentIntent = PendingIntent.getActivity(context, intent.getIntExtra("RequestCode", 0),
newIntent, Intent.FLAG_ACTIVITY_NEW_TASK);
Notification notif = new Notification(R.drawable.icon,
null, System.currentTimeMillis());
notif.setLatestEventInfo(context, from, message, contentIntent);
notif.flags |= Notification.FLAG_ONLY_ALERT_ONCE | Notification.FLAG_AUTO_CANCEL;
Debug.log("flags: "+notif.flags);
Debug.log("Defaults: "+notif.flags);
nm.notify(intent.getIntExtra("RequestCode", 0), notif);
}
}
Please find below values and definition for each one. Hope you can get idea from this.
FLAG_ONLY_ALERT_ONCE = 8
Definition : It should be set if you want the sound and/or vibration play each time the notification is sent, even if it has not been canceled before that.
FLAG_ONGOING_EVENT = 2
Definition: It should be set if this notification is in reference to something that is ongoing, like a phone call. It should not be set if this notification is in reference to something that happened at a particular point in time, like a missed phone call.
FLAG_AUTO_CANCEL = 16
Definition: The notification should be canceled when it is clicked by the user
Also you if you want to cancel the notification manually then use below code
nm.cancel(id);