[英]Notifications fail to display in Android Oreo (API 26)
I get this message when trying to display a notification on Android O. 尝试在Android O上显示通知时收到此消息。
Use of stream types is deprecated for operations other than volume control 对于音量控制以外的其他操作,不建议使用流类型
The notification is straight from the example docs, and displays fine on Android 25. 该通知直接来自示例文档,并在Android 25上正常显示。
Per the comments on this Google+ post : 根据对此Google+信息的评论:
those [warnings] are currently expected when using
NotificationCompat
on Android O devices (NotificationCompat
always callssetSound()
even if you never pass in custom sound). 当前在Android O设备上使用NotificationCompat
时会出现这些[警告]setSound()
即使您从不传递自定义声音,NotificationCompat
setSound()
始终调用setSound()
)。until the Support Library changes their code to use the
AudioAttributes
version ofsetSound
, you'll always get that warning. 在支持库将其代码更改为使用AudioAttributes
版本setSound
,您将始终收到该警告。
Therefore there's nothing that you can do about this warning. 因此,您无法对此警告采取任何措施。 As per the notification channels guide , Android O deprecates setting a sound on an individual notification at all, instead having you set the sound on a notification channel used by all notifications of a particular type. 根据通知渠道指南 ,Android O完全不建议在单个通知上设置声音,而是让您在特定类型的所有通知使用的通知渠道上设置声音。
Starting with Android O, you are required to configure a NotificationChannel , and reference that channel when you attempt to display a notification. 从Android O开始,您需要配置NotificationChannel ,并在尝试显示通知时引用该通道。
private static final int NOTIFICATION_ID = 1;
private static final String NOTIFICATION_CHANNEL_ID = "my_notification_channel";
...
NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
NotificationChannel notificationChannel = new NotificationChannel(NOTIFICATION_CHANNEL_ID, "My Notifications", NotificationManager.IMPORTANCE_DEFAULT);
// Configure the notification channel.
notificationChannel.setDescription("Channel description");
notificationChannel.enableLights(true);
notificationChannel.setLightColor(Color.RED);
notificationChannel.setVibrationPattern(new long[]{0, 1000, 500, 1000});
notificationChannel.enableVibration(true);
notificationManager.createNotificationChannel(notificationChannel);
}
NotificationCompat.Builder builder = new NotificationCompat.Builder(this, NOTIFICATION_CHANNEL_ID)
.setVibrate(new long[]{0, 100, 100, 100, 100, 100})
.setSound(RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION))
.setSmallIcon(R.mipmap.ic_launcher)
.setContentTitle("Content Title")
.setContentText("Content Text");
notificationManager.notify(NOTIFICATION_ID, builder.build());
A couple of important notes: 一些重要的注意事项:
NotificationChannel
override those specified in the actual Notification
. 在NotificationChannel
指定的设置(例如振动模式)会覆盖实际Notification
指定的设置。 I know, its counter-intuitive. 我知道,这违反直觉。 You should either move settings that will change into the Notification, or use a different NotificationChannel for each configuration. 您应该将将更改设置更改为Notification,或者对每个配置使用不同的NotificationChannel。 NotificationChannel
settings after you've passed it to createNotificationChannel()
. 将NotificationChannel
设置传递给createNotificationChannel()
后,您将无法对其进行修改。 You can't even call deleteNotificationChannel()
and then try to re-add it. 您甚至无法调用deleteNotificationChannel()
,然后尝试重新添加它。 Using the ID of a deleted NotificationChannel
will resurrect it, and it will be just as immutable as when it was first created. 使用已删除的NotificationChannel
的ID将重新启用它,并且它与第一次创建时一样不变。 It will continue to use the old settings until the app is uninstalled. 在卸载应用程序之前,它将继续使用旧设置。 So you had better be sure about your channel settings, and reinstall the app if you are playing around with those settings in order for them to take effect. 因此,您最好确定自己的频道设置,如果正在使用这些设置,请重新安装该应用程序,以使它们生效。 All that @sky-kelsey has described is good, Just minor additions : @ sky-kelsey所描述的一切都是好的, 只是一些小的补充 :
You should not register same channel every time if it has been already registered, so I have Utils class method that creates a channel for me: 如果已经注册了同一频道,则不应每次都注册该频道,因此我有Utils类方法可以为我创建一个频道:
public static final String NOTIFICATION_CHANNEL_ID_LOCATION = "notification_channel_location";
public static void registerLocationNotifChnnl(Context context) {
if (Build.VERSION.SDK_INT >= 26) {
NotificationManager mngr = (NotificationManager) context.getSystemService(NOTIFICATION_SERVICE);
if (mngr.getNotificationChannel(NOTIFICATION_CHANNEL_ID_LOCATION) != null) {
return;
}
//
NotificationChannel channel = new NotificationChannel(
NOTIFICATION_CHANNEL_ID_LOCATION,
context.getString(R.string.notification_chnnl_location),
NotificationManager.IMPORTANCE_LOW);
// Configure the notification channel.
channel.setDescription(context.getString(R.string.notification_chnnl_location_descr));
channel.enableLights(false);
channel.enableVibration(false);
mngr.createNotificationChannel(channel);
}
}
strings.xml: strings.xml:
<string name="notification_chnnl_location">Location polling</string>
<string name="notification_chnnl_location_descr">You will see notifications on this channel ONLY during location polling</string>
And I call the method every time before I'm going to show a notification of the type: 而且,我每次都会显示该类型的通知之前都调用该方法:
...
NotificationUtil.registerLocationNotifChnnl(this);
return new NotificationCompat.Builder(this, NotificationUtil.NOTIFICATION_CHANNEL_ID_LOCATION)
.addAction(R.mipmap.ic_launcher, getString(R.string.open_app),
activityPendingIntent)
.addAction(android.R.drawable.ic_menu_close_clear_cancel, getString(R.string.remove_location_updates),
servicePendingIntent)
.setContentText(text)
...
Another typical problem - channel default sound - described here: https://stackoverflow.com/a/45920861/2133585 另一个典型的问题-通道默认声音-在此处描述: https : //stackoverflow.com/a/45920861/2133585
In Android O it's a must to use a NotificationChannel
and NotificationCompat.Builder
is deprecated ( reference ). 在Android O中,必须使用NotificationChannel
而NotificationCompat.Builder
已过时( 参考 )。
Below is a sample code : 以下是示例代码:
NotificationCompat.Builder mBuilder =
new NotificationCompat.Builder(mContext.getApplicationContext(), "notify_001");
Intent ii = new Intent(mContext.getApplicationContext(), RootActivity.class);
PendingIntent pendingIntent = PendingIntent.getActivity(mContext, 0, ii, 0);
NotificationCompat.BigTextStyle bigText = new NotificationCompat.BigTextStyle();
bigText.bigText(verseurl);
bigText.setBigContentTitle("Today's Bible Verse");
bigText.setSummaryText("Text in detail");
mBuilder.setContentIntent(pendingIntent);
mBuilder.setSmallIcon(R.mipmap.ic_launcher_round);
mBuilder.setContentTitle("Your Title");
mBuilder.setContentText("Your text");
mBuilder.setPriority(Notification.PRIORITY_MAX);
mBuilder.setStyle(bigText);
NotificationManager mNotificationManager =
(NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
NotificationChannel channel = new NotificationChannel("notify_001",
"Channel human readable title",
NotificationManager.IMPORTANCE_DEFAULT);
mNotificationManager.createNotificationChannel(channel);
}
mNotificationManager.notify(0, mBuilder.build());
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.