web-dev-qa-db-fra.com

attraper sur glisser pour ignorer l'événement

J'utilise une notification Android pour alerter l'utilisateur une fois le service terminé (succès ou échec) et je souhaite supprimer les fichiers locaux une fois le processus terminé.

Mon problème est que, en cas d’échec, je veux laisser à l’utilisateur une option "réessayer". et s'il choisit de ne pas réessayer et de rejeter la notification, je souhaite supprimer les fichiers locaux enregistrés aux fins du processus (images, etc.).

Existe-t-il un moyen de détecter l'événement de balayage de la notification?

73
Dror Fichman

DeleteIntent : DeleteIntent est un objet PendingIntent qui peut être associé à une notification et qui est déclenché lorsque la notification est supprimée, si:

  • Action spécifique à l'utilisateur
  • Utilisateur Supprimer toutes les notifications.

Vous pouvez définir l'intention en attente sur un récepteur de diffusion, puis exécuter l'action de votre choix.

  Intent intent = new Intent(this, MyBroadcastReceiver.class);
  PendingIntent pendingIntent = PendingIntent.getBroadcast(this.getApplicationContext(), 0, intent, 0);
  Builder builder = new Notification.Builder(this):
 ..... code for your notification
  builder.setDeleteIntent(pendingIntent);

MyBroadcastReceiver

public class MyBroadcastReceiver extends BroadcastReceiver {
      @Override
      public void onReceive(Context context, Intent intent) {
             .... code to handle cancel
         }

  }
129
Mr.Me

Une réponse entièrement vidé (avec un merci à M. Me pour la réponse):

1) Créez un récepteur pour gérer l'événement de balayage:

public class NotificationDismissedReceiver extends BroadcastReceiver {
  @Override
  public void onReceive(Context context, Intent intent) {
      int notificationId = intent.getExtras().getInt("com.my.app.notificationId");
      /* Your code to handle the event here */
  }
}

2) Ajoutez une entrée à votre manifeste:

<receiver
    Android:name="com.my.app.receiver.NotificationDismissedReceiver"
    Android:exported="false" >
</receiver>

3) Créez l'intention en attente en utilisant un identifiant unique pour l'intention en attente (l'identifiant de notification est utilisé ici), sans quoi les mêmes extras seront réutilisés pour chaque événement de renvoi:

private PendingIntent createOnDismissedIntent(Context context, int notificationId) {
    Intent intent = new Intent(context, NotificationDismissedReceiver.class);
    intent.putExtra("com.my.app.notificationId", notificationId);

    PendingIntent pendingIntent =
           PendingIntent.getBroadcast(context.getApplicationContext(), 
                                      notificationId, intent, 0);
    return pendingIntent;
}

4) Construisez votre notification:

Notification notification = new NotificationCompat.Builder(context)
              .setContentTitle("My App")
              .setContentText("hello world")
              .setWhen(notificationTime)
              .setDeleteIntent(createOnDismissedIntent(context, notificationId))
              .build();

NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
notificationManager.notify(notificationId, notification);
77
Chris Knight

Une autre idée:

si vous créez une notification normalement, vous avez également besoin des actions une, deux ou trois. J'ai créé un "NotifyManager" qui crée toutes les notifications dont j'ai besoin et reçoit tous les appels d'intention. Ainsi, je peux gérer toutes les actions ET aussi attraper l’événement de licenciement à UN endroit. 

public class NotifyPerformService extends IntentService {

@Inject NotificationManager notificationManager;

public NotifyPerformService() {
    super("NotifyService");
    ...//some Dagger stuff
}

@Override
public void onHandleIntent(Intent intent) {
    notificationManager.performNotifyCall(intent);
}

pour créer le deleteIntent, utilisez ceci (dans le NotificationManager):

private PendingIntent createOnDismissedIntent(Context context) {
    Intent          intent          = new Intent(context, NotifyPerformMailService.class).setAction("ACTION_NOTIFY_DELETED");
    PendingIntent   pendingIntent   = PendingIntent.getService(context, SOME_NOTIFY_DELETED_ID, intent, 0);

    return pendingIntent;
}

et QUE j’utilise pour définir l’intention de suppression comme ceci (dans le NotificationManager):

private NotificationCompat.Builder setNotificationStandardValues(Context context, long when){
    String                          subText = "some string";
    NotificationCompat.Builder      builder = new NotificationCompat.Builder(context.getApplicationContext());


    builder
            .setLights(ContextUtils.getResourceColor(R.color.primary) , 1800, 3500) //Set the argb value that you would like the LED on the device to blink, as well as the rate
            .setAutoCancel(true)                                                    //Setting this flag will make it so the notification is automatically canceled when the user clicks it in the panel.
            .setWhen(when)                                                          //Set the time that the event occurred. Notifications in the panel are sorted by this time.
            .setVibrate(new long[]{1000, 1000})                                     //Set the vibration pattern to use.

            .setLargeIcon(BitmapFactory.decodeResource(context.getResources(), R.mipmap.ic_launcher))
            .setSmallIcon(R.drawable.ic_white_24dp)
            .setGroup(NOTIFY_GROUP)
            .setContentInfo(subText)
            .setDeleteIntent(createOnDismissedIntent(context))
    ;

    return builder;
}

et enfin, dans le même NotificationManager, se trouve la fonction perform:

public void performNotifyCall(Intent intent) {
    String  action  = intent.getAction();
    boolean success = false;

    if(action.equals(ACTION_DELETE)) {
        success = delete(...);
    }

    if(action.equals(ACTION_SHOW)) {
        success = showDetails(...);
    }

    if(action.equals("ACTION_NOTIFY_DELETED")) {
        success = true;
    }


    if(success == false){
        return;
    }

    //some cleaning stuff
}
0
HowardS