I have added two action button to the notification but I'm not able to handle the click event in background.
Intent ok = new Intent(mContext, MainActivity.class);
ok.putExtra("OK",true);
PendingIntent intentOK = PendingIntent.getActivity(mContext, 0 , ok, PendingIntent.FLAG_UPDATE_CURRENT);
mBuilder.addAction(R.drawable.ic_ok, delivered(), intentOK);
mBuilder.addAction(R.drawable.ic_ko, notdelivered(), intentKO);
The actions needs an intent that force my app in foreground.
I need to post user choice to a remote server without popping up the app.
Related
I have a custom notification bar in my application that has 2 buttons. I found a way to make the buttons work by using contentView.setOnClickPendingIntent in my notification class and then handle the functionality in separate activity but I have a problem. Here is the code in Notification class.
//Handle the button for showing bookmarks on custom notification
Intent buttonsIntent2 = new Intent(context, NotificationBarButtonActivityHandler.class);
buttonsIntent2.putExtra(PENDING_ACTION, REGISTER_BOOKMARK);
contentView.setOnClickPendingIntent(R.id.notificationBarShowBookmarksButton, PendingIntent.getActivity(context, 0, buttonsIntent2, 0));
//Handle the button for adding bookmark on custom notification
Intent buttonsIntent = new Intent(context, NotificationBarButtonActivityHandler.class);
buttonsIntent.putExtra(PENDING_ACTION, SHOW_BOOKMARKS);
contentView.setOnClickPendingIntent(R.id.notificationBarAddBookmarkFromChromeButton, PendingIntent.getActivity(context, 0, buttonsIntent, 0));
The problem is that no matter which button is pressed, the button handler activity always receives REGISTER_BOOKMARK when I am pressing both button.
String action = (String) getIntent().getExtras().get(NotificationBarService.PENDING_ACTION);
Could someone please explain to me why is this happening? Also, is this the optimal way to handle button presses in the notification bar?
I have implemented push notification for the app. When notification is tapped, How to start the application from splash screen if the app is already killed. I want to start from Splash screen if the app is already killed and start from Inside landing screen if the app is already in the background. How to handle this? Please help me.
Add this code to your create notification method:
Intent resultIntent = new Intent(this, SplashActivity.class);
resultIntent.addFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT | Intent.FLAG_ACTIVITY_SINGLE_TOP);
resultIntent.setAction(Intent.ACTION_MAIN);
resultIntent.addCategory(Intent.CATEGORY_LAUNCHER);
PendingIntent resultPendingIntent = PendingIntent.getActivity(getApplicationContext(), 0, resultIntent, PendingIntent.FLAG_UPDATE_CURRENT);
mBuilder.setContentIntent(resultPendingIntent);
Play around with the intent flags [resultIntent.addFlags(/*intent flag here*/)], if you want to:
start from Splash screen if the app is already killed and start from
Inside landing screen if the app is already in the background.
Hope this helps!
Use pendingIntent to specify the action which should be performed once the user select the notification.
Example tutorial Here
I'm configuring my notifications to open a new instance of ActivityDetail on click:
Intent resultIntent = new Intent(getApplicationContext(), ActivityDetail.class);
resultIntent.putExtra("object_id", objectId);
...
TaskStackBuilder stackBuilder =TaskStackBuilder.create(getApplicationContext());
stackBuilder.addNextIntentWithParentStack(resultIntent);
resultIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
PendingIntent resultPendingIntent =
stackBuilder.getPendingIntent(0, PendingIntent.FLAG_CANCEL_CURRENT);
I build each notifications with a different id, as clicking will populate the ActivityDetail with results unique to the notification.
When I receive two notifications, the first one will open ActivityDetail correctly. Clicking the second notification, however, does nothing (except dismiss it), whether I remain on the ActivityDetail screen or not. Specifying the activity launch mode as "singleTop" makes no difference.
I don't seem to have any problems if there is only one notification displayed at a time, but if there are two, the second one always fails to open a new instance of the ActivityDetail on click. Any help would be appreciated.
I think this is happening because you are sending static request code '0' in 'getPendingIntent' method while obtain pending intent. send a separate value for each notification instead of '0'. it will work.
You need to do like this:
PendingIntent resultPendingIntent =stackBuilder.getPendingIntent(SEPARATE_INT_VALUE, PendingIntent.FLAG_CANCEL_CURRENT);
// Now change value of 'SEPARATE_INT_VALUE'
I'm building an android-app with wear-support and having the following problem when I add a notification with the voice-action specified here:
http://developer.android.com/training/wearables/notifications/voice-input.html
// Create an intent for the reply action
Intent replyIntent = new Intent(mainActivity, VoiceActivity.class);
replyIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent replyPendingIntent =
PendingIntent.getActivity(mainActivity, 0, replyIntent,
PendingIntent.FLAG_UPDATE_CURRENT);
// Create the reply action and add the remote input
NotificationCompat.Action voice_action =
new NotificationCompat.Action.Builder(R.drawable.ic_action_mic,
getString(R.string.label_voice), replyPendingIntent)
.addRemoteInput(remoteInput)
.build();
Everytime the wearable calls the voice action / pending intent(?) my activity starts in onCreate() and opens my MainActivity-UI on the phone! But the thing is, the user is working simultaneously on the phone and don't want to get interrupted by a simple voice-action.
Any ideas how to pretend the voice-command from opening the app on phone when it's "minimized"?
My question is a bit complicated so I am going to describe it briefly what I want to achieve. My application receives messages from GCM without any issue. When application is running and is visible to the user I am not displaying notification in Action Bar, I am displaying this message in dialog alert. I use BroadcastReceiver to achieve this.
The main issue is that, when app gets a few notifications in no time. When main activity is visible to the user, the first notification will be shown in dialog alert. And next will be placed in Action Bar as usual Android notifications. And at this moment user disposes the dialog alert and is going to choose a next notification from Action Bar. At this moment I am using in my CloudService (extends IntentService) intent with flag Intent.FLAG_ACTIVITY_CLEAR_TOP and also PendingIntent.FLAG_UPDATE_CURRENT flag for pendingIntent. PendingIntent is just the contentIntent for my NotificationCompat.Builder.
It works in this way that for each user click on the notification from Action Bar, my activity is refreshing (floats to the lower device edge and then floats from the upper edge with dialog alert with message - I am getting the extras from the intent in onResume method). This action is quite OK. Activity has only one instance in that case - I don't have to break through the few instances of the same activity while I have opened few notifications. But the big problem is that when user chooses any of the notifications in each case the last one will open in dialog alert. Activity seems to has the same intent despite of PendingIntent.FLAG_UPDATE_CURRENT.
There are two methods in CloudService which handle cloud messages:
private void showNotification(Bundle extras) {
notificationManager = (NotificationManager) this.getSystemService(Context.NOTIFICATION_SERVICE);
String message = extras.getString(CloudMetaData.MESSAGE);
if (App.isMyActivityVisible() && !CloudMessageDialogFragment.isAttached()) {
sendBroadcast(message, NOTIFICATION_ID);
} else {
Intent intent = new Intent(this, MyParentActivity.class);
intent.putExtra(CloudMetaData.MESSAGE, message);
intent.putExtra(CloudMetaData.NOTIFICATION_ID, NOTIFICATION_ID);
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
NotificationCompat.Builder builder = new NotificationCompat.Builder(this);
builder.setSmallIcon(R.drawable.ic_launcher);
builder.setContentTitle(getString(R.string.app_name));
builder.setStyle(new NotificationCompat.BigTextStyle().bigText(alert));
builder.setContentText(alert);
builder.setAutoCancel(true);
builder.setDefaults(Notification.DEFAULT_SOUND);
builder.setContentIntent(contentIntent);
notificationManager.notify(NOTIFICATION_ID, builder.build());
}
NOTIFICATION_ID++;
}
And method which send broadcast is just like that:
private void sendBroadcast(String message, int notificationId) {
Intent intent = new Intent();
intent.setAction(ACTION_FROM_CLOUD_SERVICE);
intent.putExtra(CloudMetaData.MESSAGE, message);
intent.putExtra(CloudMetaData.NOTIFICATION_ID, notificationId);
sendBroadcast(intent);
}
In which way can I achieve similar solution? But it is important for user of course to open notification from Action Bar and shown him its correct message.
EDIT
I have switched my dialog alert into the dialog activity. This is its definition in AndroidManifest:
<activity
android:name="com.myapp.activity.CloudMessageDialogActivity"
android:theme="#android:style/Theme.Dialog"
android:parentActivityName="com.myapp.activity.MyParentActivity"/>
But the result is still the same - when app receives a few notifications, clicking on one of them will open the dialog with the intent for the last received notification.
But the big problem is that when user chooses any of the notifications in each case the last one will open in dialog alert. Activity seems to has the same intent despite of PendingIntent.FLAG_UPDATE_CURRENT.
That's because you are using the same request code (i.e., 0) for all PendingIntents here:
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, intent,
PendingIntent.FLAG_UPDATE_CURRENT);
By doing so, you are ultimately receiving the same intent, because the platform is failing to see the difference between the intents and delivering the same object everytime:
... it is important to know when two Intents are considered to be the same for purposes of retrieving a PendingIntent. A common mistake people make is to create multiple PendingIntent objects with Intents that only vary in their "extra" contents, expecting to get a different PendingIntent each time. This does not happen. The parts of the Intent that are used for matching are the same ones defined by Intent.filterEquals. If you use two Intent objects that are equivalent as per Intent.filterEquals, then you will get the same PendingIntent for both of them.
So, instead of a constant value, please use a unique request code. For e.g. change the above line with:
PendingIntent contentIntent = PendingIntent.getActivity(this, NOTIFICATION_ID,
intent, PendingIntent.FLAG_UPDATE_CURRENT);
Hope this helps.