protected void displayNotification(String response) {
Intent intent = new Intent(context, testActivity.class);
PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intent, Intent.FLAG_ACTIVITY_NEW_TASK);
Notification notification = new Notification(R.drawable.icon, "Upload Started", System.currentTimeMillis());
notification.setLatestEventInfo(context, "Upload", response, pendingIntent);
nManager.notify((int)System.currentTimeMillis(), notification);
}
Esta función se llamará varias veces. Me gustaría que cada uno notification
iniciara testActivity cuando se hace clic en él. Desafortunadamente, solo la primera notificación inicia testActivity. Al hacer clic en el resto, la ventana de notificación se minimiza.
Información adicional: la función displayNotification()
está en una clase llamada UploadManager
. Context
se pasa UploadManager
desde el activity
que instancia. La función displayNotification()
se llama varias veces desde una función, también en UploadManager, que se ejecuta en un AsyncTask
.
Edición 1: Olvidé mencionar que estoy pasando la respuesta de cadena Intent intent
como un extra
.
protected void displayNotification(String response) {
Intent intent = new Intent(context, testActivity.class);
intent.putExtra("response", response);
PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
Esto hace una gran diferencia porque necesito la "respuesta" adicional para reflejar cuál era la respuesta de cadena cuando se creó la notificación. En su lugar, el uso de PendingIntent.FLAG_UPDATE_CURRENT
la "respuesta" adicional refleja a qué fue la respuesta de String en la última llamada displayNotification()
.
Sé por qué esto es por leer la documentación en FLAG_UPDATE_CURRENT
. Sin embargo, no estoy seguro de cómo solucionarlo en este momento.
fuente
Estaba luchando con
RemoteViews
y varios diferentesIntents
para cada unoButton
enHomeScreen
Widget. Funcionó cuando se agregaron estos:1.
intent.setAction(Long.toString(System.currentTimeMillis()));
2.
PendingIntent.FLAG_UPDATE_CURRENT
PackageManager pm = context.getPackageManager(); Intent intent = new Intent(context, MyOwnActivity.class); intent.putExtra("foo_bar_extra_key", "foo_bar_extra_value"); intent.setAction(Long.toString(System.currentTimeMillis())); PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT); RemoteViews views = new RemoteViews(context.getPackageName(), R.layout.widget_layout); views.setOnClickPendingIntent(my_button_r_id_received_in_parameter, pendingIntent);
fuente
setAction
setAction
, lo que puedes hacer esaddCategory
.PendingIntent
se utilizaIntent.filterEquals
para comprobar la igualdad de la acción, los datos, el tipo, la clase y las categorías. developer.android.com/reference/android/content/…Establecer acción Resolvió esto por mí. Aquí está mi comprensión de la situación:
Tengo varios widgets que tienen un PendingIntent adjunto a cada uno. Siempre que uno se actualizaba, todos se actualizaban. Las banderas están ahí para describir lo que sucede con PendingIntents que son exactamente iguales.
La descripción de FLAG_UPDATE_CURRENT se lee mucho mejor ahora:
Si ya existe el mismo PendingIntent que está creando, actualice todos los antiguos al nuevo PendingIntent que está creando.
La definición de exactamente lo mismo se aplica a todo el PendingIntent EXCEPTO los extras. Por lo tanto, incluso si tiene diferentes extras en cada intento (para mí, estaba agregando el appWidgetId) y luego en Android, son lo mismo.
Agregar .setAction con una cadena única ficticia le dice al sistema operativo. Estos son completamente diferentes y no actualizan nada. Al final, aquí está mi implementación que funciona como quería, donde cada widget tiene su propia configuración Intent adjunta:
Intent configureIntent = new Intent(context, ActivityPreferences.class); configureIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, appWidgetId); configureIntent.setAction("dummy_unique_action_identifyer" + appWidgetId); PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, configureIntent, PendingIntent.FLAG_UPDATE_CURRENT);
ACTUALIZAR
Una solución aún mejor en caso de que esté trabajando con transmisiones. Los PendingIntents únicos también se definen mediante códigos de solicitud únicos. Esta es mi solución:
//Weee, magic number, just want it to be positive nextInt(int r) means between 0 and r int dummyuniqueInt = new Random().nextInt(543254); PendingIntent pendingClearScreenIntent = PendingIntent.getBroadcast(context, dummyuniqueInt, clearScreenIntent, PendingIntent.FLAG_UPDATE_CURRENT);
fuente
Veo respuestas pero no explicaciones. Además, ninguna de las respuestas aborda todas las posibles soluciones, así que intentaré aclararlo.
Documentación:
Causa del problema:
Creas 2 notificaciones con 2 intenciones pendientes. Cada intento pendiente está asociado con un intento:
Intent intent = new Intent(context, testActivity.class);
Sin embargo, estos 2 intentos son iguales, por lo tanto, cuando llegue su segunda notificación, lanzará el primer intento.
Solución:
Tienes que hacer que cada intento sea único, para que ningún intento pendiente sea igual. ¿Cómo haces que las intenciones sean únicas? No por los extras que pones
putExtra()
. Incluso si los extras son diferentes, las intenciones pueden ser iguales. Para que cada intención sea única, debe establecer un valor único para la acción, los datos, el tipo, la clase, la categoría o el código de solicitud de la intención: (cualquiera de ellos funcionará)intent.setAction(...)
intent.setData(...)
intent.setType(...)
intent.setClass(...)
intent.addCategory(...)
PendingIntent.getActivity(context, YOUR_UNIQUE_CODE, intent, Intent.FLAG_ONE_SHOT);
Nota : Establecer un código de solicitud único puede ser complicado porque necesita un int, mientras que
System.currentTimeMillis()
devuelve long, lo que significa que se eliminarán algunos dígitos. Por lo tanto, recomendaría ir con la categoría o la acción y establecer una cadena única.fuente
Tuve el mismo problema y pude solucionarlo cambiando la bandera a:
PendingIntent contentIntent = PendingIntent.getActivity(context, 0, notificationIntent, PendingIntent.FLAG_UPDATE_CURRENT);
fuente
Como la documentación dijo, use un código de solicitud único:
fuente
Fwiw, he tenido más suerte con
PendingIntent.FLAG_CANCEL_CURRENT
que conPendingIntent.FLAG_UPDATE_CURRENT
.fuente
Tuve el mismo problema y lo solucioné siguiendo los pasos a continuación
1) Borrar cualquier bandera de intención
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
2) inserte intent.setAction con el siguiente código
intent.setAction(Long.toString(System.currentTimeMillis()));
3) para Pendingintent, inserte el siguiente código
PendingIntent Pintent = PendingIntent.getActivity(ctx,0, intent,PendingIntent.FLAG_UPDATE_CURRENT);
Espero trabajar contigo
fuente
PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intent, Intent.FLAG_ACTIVITY_NEW_TASK);
En PendingIntent hay dos parámetros int, el segundo y el último. El segundo es el "código de solicitud" y debe ser un número único (por ejemplo, la identificación de su notificación), de lo contrario, si (como en su ejemplo, es igual a cero, siempre se sobrescribirá).
fuente
// Use pending Intent and also use unique id for display notification.... // Get a PendingIntent containing the entire back stack PendingIntent notificationPendingIntent = stackBuilder.getPendingIntent(0,PendingIntent.FLAG_UPDATE_CURRENT); NotificationManager mNotificationManager = (NotificationManager) sqlitewraper.context.getSystemService(Context.NOTIFICATION_SERVICE); // Issue the notification mNotificationManager.notify(id, builder.build());
fuente
para enviar datos extra correctamente, debe enviar con intención pendiente la identificación de notificación como esta: PendingIntent pendienteIntent = PendingIntent.getActivity (context, (int) System.currentTimeMillis () , intent, PendingIntent.FLAG_UPDATE_CURRENT);
fuente
Tengo el mismo problema y uso PendingIntent.html.FLAG_UPDATE_CURRENT para solucionarlo.
He comprobado el código fuente. En ActivityManagerService.java , el método clave es el siguiente. Cuando la bandera es PendingIntent.FLAG_UPDATE_CURRENT y updateCurrent es verdadero. Algunos extras serán reemplazados por nuevos y obtendremos un PendingIntent reemplazado.
IIntentSender getIntentSenderLocked(int type, String packageName, int callingUid, int userId, IBinder token, String resultWho, int requestCode, Intent[] intents, String[] resolvedTypes, int flags, Bundle bOptions) { // ... omitted final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT |PendingIntent.FLAG_UPDATE_CURRENT); PendingIntentRecord.Key key = new PendingIntentRecord.Key( type, packageName, activity, resultWho, requestCode, intents, resolvedTypes, flags, bOptions, userId); WeakReference<PendingIntentRecord> ref; ref = mIntentSenderRecords.get(key); PendingIntentRecord rec = ref != null ? ref.get() : null; if (rec != null) { if (!cancelCurrent) { if (updateCurrent) { if (rec.key.requestIntent != null) { rec.key.requestIntent.replaceExtras(intents != null ? intents[intents.length - 1] : null); } if (intents != null) { intents[intents.length-1] = rec.key.requestIntent; rec.key.allIntents = intents; rec.key.allResolvedTypes = resolvedTypes; } else { rec.key.allIntents = null; rec.key.allResolvedTypes = null; } } return rec; } rec.canceled = true; mIntentSenderRecords.remove(key); }
fuente
Tuve el mismo problema y pude solucionarlo cambiando la bandera a:
LayoutInflater factory = LayoutInflater.from(this); final View textEntryView = factory.inflate(R.layout.appointment, null); AlertDialog.Builder bulider= new AlertDialog.Builder(PatientDetail.this); final AlertDialog alert=bulider.create(); bulider.setTitle("Enter Date/Time"); bulider.setView(textEntryView); bulider.setPositiveButton("Save", new DialogInterface.OnClickListener() { public void onClick(DialogInterface dialog, int which) { EditText typeText=(EditText) textEntryView.findViewById(R.id.Editdate); EditText input1 =(EditText) textEntryView.findViewById(R.id.Edittime); getDateAndTime(typeText.getText().toString(),input1.getText().toString()); } }); bulider.setNegativeButton("Cancel", new DialogInterface.OnClickListener() { public void onClick(DialogInterface dialog, int which) { dialog.cancel(); } }); bulider.show(); }
fuente