Notification being cancelled by another one in Android Lollipop - android

I create a notification in Service (launched from the BroadcastReceiver) this way:
this.notification = new NotificationCompat.Builder(getApplicationContext())
.setContentTitle("Foo")
.setContentText("Bar")
.setSmallIcon(R.drawable.logo)
.setContentIntent(pIntent)
.build();
this.initializeNotificationSound(volumne, Uri.parse(melody));
this.initializeNotificationVibration();
notification.flags = Notification.FLAG_INSISTENT;
this.notificationManager.cancelAll();
this.notificationManager.notify(0, notification);
This notification is set when a particular SMS is received. I want to create a notification which will play a defined melody and will not be interrupted by the standard SMS notification.
This functionality works pretty good, however in lollipop, following scenario happens:
SMS is received
My notification is launched
After some time, notification sound is stopped and default SMS ringtone is played
This happens only when ringtone mode is silent. Otherwise, it works as expected, because of the cancelAll() method, which interrupts the SMS notification.
Thanks in advance for your response.

You can not change that. If you notice, when more than one notifications are created at the same time, even from a sole application(e.g. Facebook), the sound they make is played simultaneously. This has to do with the notification management of android system itself. Maybe the problem you are facing happens due to some code changes made to the specific Android system version (API level), maybe to the cancelAll() method. One solution would be to find the appropriate line of code for checking current system version. For example:
if(System_version <= lollipop) {
//code works fine. Keep as it is
}
else{
//find the appropriate method and call it here.
}

Related

How to send a notification without waking the screen on Android

I have a foreground service in my app, whose persistent notification has a timer in it, which means that the notification is sent once per second to update the timer that is shown in the notification. This means that on some devices, where notifications are set to either wake the screen entirely or show a dark version on the screen briefly, the screen is constantly awake.
Is there a way to send the notification in a way that it won't wake up the screen? Setting it as a silent notification on the device fixes this, but the point of a foreground service notification is that it's prominent on the device, so this isn't a great solution, and not all users would know to do that.
This is how I'm building the notification:
NotificationCompat.Builder(this, CHANNEL_ID)
.setContentTitle("Currently Reading")
.setSound(null)
.setContentIntent(TaskStackBuilder.create(this).run {
addNextIntentWithParentStack(timerIntent)
getPendingIntent(
0,
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
)
})
.setSmallIcon(R.drawable.ic_launcher_foreground)
.setPriority(NotificationCompat.PRIORITY_DEFAULT)
.setAutoCancel(true)
Have you tried updating the notification instead? And use setOnlyAlertOnce()
"You can optionally call setOnlyAlertOnce() so your notification interupts the user (with sound, vibration, or visual clues) only the first time the notification appears and not for later updates."
Check this link
https://developer.android.com/training/notify-user/build-notification.html#Updating
setPriority(NotificationCompat.PRIORITY_DEFAULT)?
lower it, so wont be shown on lockscreen (android 7 and up)
and here we go with a small fix for this part:
setPriority(NotificationCompat.PRIORITY_LOW)
you can also add:
setVisibility(NotificationCompat.VISIBILITY_PRIVATE)
but it'll also remove notification from lockscreen...
docs:
https://developer.android.com/training/notify-user/build-notification.html#lockscreenNotification
https://developer.android.com/training/notify-user/channels#importance
hope this helps =]

How to make a sound-only notification?

There seem to be several other questions related to this topic, but each one I've found has a solution that either doesn't use notifications or doesn't work on recent Android versions. The reason I want to use notifications is to ensure the volume for the sound corresponds to the user's notification volume.
Q: How can I play the default notification sound, that doesn't display anything to the user, and responds to the notification volume level?
One solution, which used to work, was to build a notification but leave off the icon, title, and content. This worked on older Android versions (with an error in the log E/NotificationService: WARNING: In a future release this will crash the app:), but is no longer an option.
Other solutions use MediaPlayer or RingTone, but these have the down-side of different user volume controls which mean the sound level won't match that of displayed notifications. In other words, if the user has their media and ring volume set very low, then these approaches may not be heard.
Some similar questions that don't solve this:
Play notification default sound only (Android)
Android Notification to play sound only
Android Marshmallow sound only Notification?
How to play an android notification sound
This plays the right sound, but not at the notification volume:
Uri uriSound = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
try {
RingtoneManager.getRingtone(getApplicationContext(), uriSound).play();
} catch (Exception e) {
e.printStackTrace();
}
This is a sound-only notification, but only worked (contrary to documentation) on older Android versions:
Notification notification = new NotificationCompat.Builder(this, "channel_id")
.setDefaults(NotificationCompat.DEFAULT_SOUND)
.build();
An example of this working as I desire is Google's Android Messages app. When the app is open to a conversation thread and a new message is received, the notification sound is played and the sound correctly responds to the notification volume level.

Android Nougat not keeping foreground service notification at top

Updated - Found out the root cause of this issue. We are showing the normal notifications as Heads up notifications as follows:
if (Build.VERSION.SDK_INT >= 21) {
notificationBuilder.setVibrate(new long[0]);
}
Whereas the foreground service notification is not Heads up, because it builds the notification every 30 seconds and we don't want that behaviour. If I remove the code for setting up the Heads up notification for normal notifications, then it works fine.
Original Question:
Our app has a foreground service for displaying the ongoing score updates for a cricket match via an ongoing notification. In every 30 seconds we hit the server API and update the notification. We are building this notification with highest priority 2.
Now whenever another normal notification of same priority comes, then the normal notification comes on top of the foreground service notification. But since we are building the foreground notification after every 30 seconds, it again comes on top.
This works fine on Marshmallow and below OS. But on Nougat and above, once a new notification comes, the foreground service notification never comes on top. This is the code I have written for building the notification.
NotificationCompat.Builder builder = new NotificationCompat.Builder(context);
builder.setSmallIcon(R.mipmap.app_notification_icon);
builder.setContentIntent(targetIntent);
builder.setDeleteIntent(dismissedIntent);
builder.setCustomBigContentView(remoteViews);
builder.setContent(remoteViews);
builder.setPriority(2);
Notification notification = builder.build();
notification.flags |= Notification.FLAG_FOREGROUND_SERVICE;
notification.flags |= Notification.FLAG_ONGOING_EVENT;
Did anyone face a similar issue? How to keep the foreground service notification always on top on Nougat and above OS.
There is one app Universal Music App in which notifications always remains on top. They come down for a moment when a new notification comes, but then again moves back to top.

Cancelling a notification received in background from GCM (Android)

I'm using Google Cloud Messaging to receive new orders into an app. I'm trying to handle cases where the same order is sent twice. I just want the second receipt to be ignored, unfortuntately when the app is in the background I dont seem to be able to cancel the notification (ie it still makes a noise and sends a message). The app works fine when in the foreground, putting cancel notification code in my GCMBrodacastreceiver doesnt seem to do anything. Am I missing something?
NotificationManager mNotify = (NotificationManager)context.getSystemService(Context.NOTIFICATION_SERVICE);
mNotify.cancelAll();
You can set the "tag" field in the notification payload. If you use this the incoming notification will just update any existing one with the same tag.
cancelAll() will dismiss the notification, but your code may not be invoked when the app is in the background as the notification will be posted without your app's code running. One option would be to have your server not send the notification if it has already sent one recently.

How to collapse Android notifications?

I'm sending a C2DM update to my Android app every 1/2 hour, which creates a Notification. Problem is, when I wake up in the morning I get 15 Notifications queued up in the status bar.
How do I only keep the latest notification, overwriting previous ones?
I tried looking at the C2DM documentation (http://code.google.com/android/c2dm/) which mentions a parameter called collapse_key, but I couldn't find an explanation for how to use it, nor am I sure the solution lies on the C2DM side.
Thanks!
If you want to cancel any previous notifications that has been set on the view you can try setting one of these flags.
PendingIntent.FLAG_CANCEL_CURRENT or PendingIntent.FLAG_UPDATE_CURRENT
Something like this should replace your old notification i believe
NotificationManager mManager= (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
Intent intent = new Intent(this,test.class);
Notification notification = new Notification(R.drawable.icon, "Notify", System.currentTimeMillis());
notification.setLatestEventInfo(this,"App Name","Description of the notification",
PendingIntent.getActivity(this.getBaseContext(), 0, intent, PendingIntent.FLAG_CANCEL_CURRENT));
mManager.notify(0, notification);
Notification has a property called number that shows a little number below the icon (for multiple notification). It lets you use the same Icon for Multiple Notification.
Use the same ID while updating your notification. :) Cheers.
In addition to the other answers, there is a parameter in your C2DM request that is called delay_while_idle. Make sure you are NOT including that or make it false. Your phone is "idle" when the screen is off (ie while you are sleeping). Google queues up all your messages on the server until the phone is not idle (ie when you turn on the screen in the morning). Then, Google sends all 15 messages at once and you display them at that time.
In the chrome to phone source, there is a method called sendNoRetry with this line:
if (delayWhileIdle) {
postDataBuilder.append("&")
.append(PARAM_DELAY_WHILE_IDLE).append("=1");
}
Make sure it is not true, then Google servers will send you your C2DM message every 30 minutes as expected.
collapse_id key should do the job. For updating any previous notification, just use the same key. To generate a new notification on device, use a different key.
For example,
* for chat notifications use the key "chat" (collapse_id = "chat")
* for invitations use the key "invite" (collapse_id = "invite")
So all the unqiue collapse_id notifications will group on device.
For more details visit: https://documentation.onesignal.com/reference#create-notification

Categories

Resources