安卓本地通知不适用于三星银河



很长一段时间以来,我一直在努力处理Android上的复杂本地通知。

我有一个事件列表。用户可以选择他/她希望何时收到通知:

  • 活动当天
  • 活动开始前一天
  • 活动开始前两天

他/她还可以设置他/她想要收到通知的时间。每一次都是可能的。他/她也只能收到不同类型的事件的通知。

发生的事情是,它适用于除三星Galaxy手机以外的所有设备。用户告诉我,他们只收到一次通知(当他们设置它们时(,然后就再也不会收到通知了。

我几乎尝试了一切,我没有想法了。看起来三星在通知方面存在一些问题,但它适用于其他一些应用程序。那么他们的代码和我的代码有什么区别。

也许其他人知道这个问题,可以帮助我。这太神奇了!

这是我的代码:

public int setEventNotifications(List<Event> chosenEvents) {
SharedPreferences settings = context.getSharedPreferences(Constants.PREFS_EVENT_SETTINGS, 0);
AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
ArrayList<PendingIntent> intentArray = new ArrayList<>();
// To cancel an existing pending intent you need to recreate the exact same and cancel it -__-
// So pending intents need to be stored in the database
deleteOldGarbagePendingIntents();
// get notification settings from shared prefs
int hours = 0;
int minutes = 0;
String time = settings.getString(Constants.PREFS_EVENT_TIME, "00:00");
String parts[] = time.split(":");
try {
hours = Integer.parseInt(parts[0]);
minutes = Integer.parseInt(parts[1]);
} catch (Exception e) {
Log.e(TAG, "Invalid time. Cannot be parsed: " + time);
}
String interval = settings.getString(Constants.PREFS_EVENT_INTERVAL, "");
String communeId = settings.getString(Constants.PREFS_EVENT_COMMUNE_ID, "");
String regionId = settings.getString(Constants.PREFS_EVENT_REGION_ID, "");
for (Event event : chosenEvents) {
// check if date is in the future
Intent intent = new Intent(context, AlarmGarbageReceiver.class);
intent.putExtra("request_code", Integer.parseInt(event.getId()));
intent.putExtra("event_type", event.getGarbageType().getType());
intent.putExtra("event_date", event.getPickupDateAsDate().getTime());
// calculate trigger time
long triggerTime = calculateTriggerTime(event.getPickupDateAsDate(), hours, minutes, interval);
Calendar alarmCalendar = Calendar.getInstance();
alarmCalendar.setTimeInMillis(triggerTime);
try {
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, Integer.parseInt(event.getId()), intent, FLAG_UPDATE_CURRENT);
if (alarmManager != null) {
alarmManager.set(AlarmManager.RTC_WAKEUP, alarmCalendar.getTimeInMillis(), pendingIntent);
} else {
Log.e(TAG, "Alarmmanager is null");
}
intentArray.add(pendingIntent);
// save intents in database
dbHelper.insertEventData(event.getId(), event.getEventType().getType(), String.valueOf(event.getPickupDateAsDate().getTime()), event.getLocation(), event.getEventType().getColor(), communeId, regionId);
} catch (SecurityException securityException) {
Log.e(TAG, "Security Exception");
securityException.printStackTrace();
} catch (Exception exception) {
Log.e(TAG, "Exception");
exception.printStackTrace();
}
}
return intentArray.size();
}

AlarmEventReceiver 类:

public class AlarmEventReceiver extends BroadcastReceiver {
private static final String NOTIFICATION_CHANNEL_NAME = "xxx_events";
private static final String NOTIFICATION_CHANNEL_ID = "xxx_events_1";
@Override
public void onReceive(Context context, Intent intent) {
if(intent.getExtras() != null) {
Log.e(TAG, AlarmEventReceiver.class.getSimpleName() + " request code: " + intent.getExtras().getInt("request_code"));
}
int eventId = intent.getExtras().getInt("request_code");
String eventType = intent.getExtras().getString("event_type");
long pickupDate = intent.getExtras().getLong("event_date");
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(pickupDate);
calendar.set(Calendar.HOUR, 6);
calendar.set(Calendar.MINUTE, 0);
long finalDate = calendar.getTimeInMillis();
NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
NotificationCompat.Builder builder;
Intent resultIntent = new Intent(context, EventCalendarActivity.class);
TaskStackBuilder stackBuilder = TaskStackBuilder.create(context);
stackBuilder.addParentStack(EventCalendarActivity.class);
stackBuilder.addNextIntent(resultIntent);
PendingIntent resultPendingIntent = stackBuilder.getPendingIntent(0, PendingIntent.FLAG_UPDATE_CURRENT);
if (notificationManager == null) {
notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
}
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
builder = new NotificationCompat.Builder(context, NOTIFICATION_CHANNEL_ID);
NotificationChannel notificationChannel = new NotificationChannel(NOTIFICATION_CHANNEL_ID, NOTIFICATION_CHANNEL_NAME, NotificationManager.IMPORTANCE_DEFAULT);
notificationChannel.enableVibration(true);
notificationChannel.setVibrationPattern(new long[]{100, 200, 300, 400, 500, 400, 300, 200, 400});
if (notificationManager != null) {
notificationManager.createNotificationChannel(notificationChannel);
} else {
Log.e(TAG, "Notification Manager is NULL");
}
if (eventType != null) {
builder.setChannelId(NOTIFICATION_CHANNEL_ID)
.setDefaults(Notification.DEFAULT_ALL)
.setContentTitle("Erinnerung")
.setContentText(eventType)
.setWhen(finalDate)
.setContentIntent(resultPendingIntent)
.setAutoCancel(false)
.setVibrate(new long[]{100, 200, 300, 400, 500, 400, 300, 200, 400});
}
} else {
builder = new NotificationCompat.Builder(context);
builder.setContentTitle("Erinnerung")
.setDefaults(Notification.DEFAULT_ALL)
.setContentText(eventType)
.setWhen(finalDate)
.setContentIntent(resultPendingIntent)
.setAutoCancel(false)
.setVibrate(new long[]{100, 200, 300, 400, 500, 400, 300, 200, 400})
.setPriority(Notification.PRIORITY_DEFAULT);
}
Notification notification = builder.build();
if (notificationManager != null) {
notificationManager.notify(eventId, notification);
} else {
Log.e(TAG, "notificationManager is NULL");
}
}
}

我曾经有机会在三星手机上运行它,我想我记得有某种安全异常,因为手机无法更新通知。只有 500 个通知的容量,如果尝试更新它们,旧通知不会被删除,但会创建新的通知。因此,您很快就会达到 500 个通知,这就是抛出 SecurityException 的时候。但是我再也找不到这个的来源了...

我过去浏览过一个相关问题,它发生在Galaxy Note上,尽管我不确定它会有所帮助。

mNotificationManager.cancel(notificationId);
mNotificationManager.notify(++notificationId, notification);

每次必须创建新通知时,请手动取消前一个通知,并每次更新通知 ID。

它工作正常,经过Samsung Galaxy s7 edge测试

fun showDownloadNotification() {
try {
// val selectedUri = Uri.parse(Environment.getExternalStorageState())
val notiIntent = Intent(DownloadManager.ACTION_VIEW_DOWNLOADS)
notiIntent.flags = Intent.FLAG_ACTIVITY_NEW_TASK
//            startActivity(intent);
val pendingIntent: PendingIntent = PendingIntent.getActivity(baseActivity, 0, notiIntent, PendingIntent.FLAG_CANCEL_CURRENT)
val builder = NotificationCompat.Builder(baseActivity, "")
.setSmallIcon(notificationIcon)
.setContentTitle("Subject Topic downloaded")
.setContentText(fileName)
.setAutoCancel(true)
.setContentIntent(pendingIntent)
.setPriority(NotificationCompat.PRIORITY_DEFAULT)
val notificationManager: NotificationManagerCompat = NotificationManagerCompat.from(baseActivity)
// notificationId is a unique int for each notification that you must define
notificationManager.notify(1, builder.build())
} catch (e: Exception) {
// Log.e(FragmentActivity.TAG, "Notification $e")
}
}

可能会有所帮助!

我在三星设备上也遇到了类似的问题,这就是我所做的:

考虑一下:

builder = new NotificationCompat.Builder(context, NOTIFICATION_CHANNEL_ID);

在上面的行中,我们已经通过了NOTIFICATION_CHANNEL_ID.

现在在稍后的代码中也添加了它:

builder.setChannelId(NOTIFICATION_CHANNEL_ID)     // don't call this method

我们已经通过构造函数将通道 ID 提供给构建器,我们不需要再次传递它。 删除builder.setChannelId(NOTIFICATION_CHANNEL_ID)。它也可以在三星设备上工作。

最新更新