Is it possible to check if a notification is visible or canceled?

AndroidNotifications

Android Problem Overview


I would like to update notification data, but the only way I found is to launch a new one with the same Id.

The problem is that I don't want to raise a new one if the original has beed canceled. Is there a way to tell if a notification is visible or canceled? Or a way to update a notification only if it exists?

Android Solutions


Solution 1 - Android

If you're app has a minimum API >= 23 can use this method to get active notification:

NotificationManager mNotificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
StatusBarNotification[] notifications = mNotificationManager.getActiveNotifications();
for (StatusBarNotification notification : notifications) {
  if (notification.getId() == 100) {
    // Do something.
  }
}

Solution 2 - Android

This is how I solved it:

	private boolean isNotificationVisible() {
	Intent notificationIntent = new Intent(context, MainActivity.class);
	PendingIntent test = PendingIntent.getActivity(context, MY_ID, notificationIntent, PendingIntent.FLAG_NO_CREATE);
	return test != null;
}

This is how I generate the notification:

	/**
 * Issues a notification to inform the user that server has sent a message.
 */
private void generateNotification(String text) {

	int icon = R.drawable.notifiaction_icon;
	long when = System.currentTimeMillis();
	NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
	Notification notification = new Notification(icon, text, when);
	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, MY_ID, notificationIntent, 0);
	notification.setLatestEventInfo(context, title, text, intent);

	notification.flags |= Notification.FLAG_AUTO_CANCEL; //PendingIntent.FLAG_ONE_SHOT

	notificationManager.notify(MY_ID, notification);
}

Solution 3 - Android

I think you can use deleteIntent of Notification class.

I remember in one of my application I use use to fire a Broadcast (custom Broadcast) when a notification is cancelled or the Notification tray was cleared.

Solution 4 - Android

An alternative to the deleteIntent is the following which has proved beneficial in my own app:

Basically, you create an intent with your notification that starts an IntentService (or any other service) and in onHandleIntent you can set a flag indicating whether the notification is active.
You can set this intent to be fired when the user taps the notification (contentIntent) and/or when the user clears it from the list (deleteIntent).

To illustrate it, here is what I do in my own app. When building the notification I set

Intent intent = new Intent(this, CleanupIntentService.class);
Notification n = NotificationCompat.Builder(context).setContentIntent(
        PendingIntent.getActivity(this, 0, intent, 0)).build();

When the notification is tapped, my CleanupIntentService is launched, setting a flag (in the service that created the notification):

@Override
public int onStartCommand(Intent intent, int flags, int startId) {
    super.onCreate(); // If removed, onHandleIntent is not called
    return super.onStartCommand(intent, flags, startId);
}


@Override
protected void onHandleIntent(Intent intent) {
    OtherService.setNotificationFlag(false);
}

Solution 5 - Android

In my situation, I wanted to check if a Notification was already shown before showing another. And it turns out there's a simple way to do it without listening to when the Notification was deleted or dismissed with .setAutoCancel(true) on NotificationManagerCompat.Builder.

 private val NOTIF_ID = 80085
 private val CHANNEL_ID = "com.package.name.ClassName.WhatNotifycationDoes"  
 private lateinit var mNotificationManagerCompat: NotificationManagerCompat
 private lateinit var mNotificationManager: NotificationManager // this is for creating Notification Channel in newer APIs

override fun onCreate() {
    super.onCreate()
    
    mNotificationManagerCompat = NotificationManagerCompat.from(this)

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O)
       mNotificationManager = getSystemService(NotificationManager::class.java)

    showNotification()
    startWatching()
}

private fun showNotification() {
        val contentIntent = Intent(this, MainActivity::class.java)
                .apply { flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK }
        val contentPendingIntent = PendingIntent.getActivity(this, 1, contentIntent, 0)

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        val name = getString(R.string.app_name)
        val importance = NotificationManager.IMPORTANCE_HIGH
        val channel = NotificationChannel(CHANNEL_ID, name, importance)
        channel.description = getString(R.string.your_custom_description)
        mNotificationManager.createNotificationChannel(channel)
    }

    val mNewStatusNotificationBuilder = NotificationCompat.from(this)
    mNewStatusNotificationBuilder = NotificationCompat.Builder(this, CHANNEL_ID)
            .setContentTitle(getString(R.string.app_name))
            .setContentText(getString(R.string.simple_text))
            .setPriority(NotificationCompat.PRIORITY_DEFAULT)
            .setContentIntent(contentPendingIntent)
            .setAutoCancel(true) // This dismisses the Notification when it is clicked
            .setOnlyAlertOnce(true) //this is very important, it pops up the notification only once. Subsequent notify updates are muted. unless it is loaded again    

    if (Build.VERSION.SDK_INT > Build.VERSION_CODES.LOLLIPOP)
        mNewStatusNotificationBuilder.setSmallIcon(R.drawable.ic_notification)

    notification = mNewStatusNotificationBuilder.build()
        
    mNotificationManagerCompat.notify(NOTIF_ID, notification)
}

Solution 6 - Android

You can check as follow in Kotlin:

  val mNotificationManager: NotificationManager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
    val notifications: Array<StatusBarNotification> = mNotificationManager.activeNotifications

    if(notifications.isNotEmpty())
    {
      //you don't have notifications 
    }
    else
    {
      //you have notifications 
    }

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionAsaf PinhassiView Question on Stackoverflow
Solution 1 - AndroidSayed Abolfazl FatemiView Answer on Stackoverflow
Solution 2 - AndroidAsaf PinhassiView Answer on Stackoverflow
Solution 3 - AndroidVishal VyasView Answer on Stackoverflow
Solution 4 - AndroidstemadsenView Answer on Stackoverflow
Solution 5 - AndroidLekeOpeView Answer on Stackoverflow
Solution 6 - AndroidOsama IbrahimView Answer on Stackoverflow