Ответ 1
Вам необходимо использовать NotificationChannel для Android O API 26 и выше, иначе вы получите ошибку, с которой вы столкнулись. См. Следующее выражение в документах Android - Создание и управление каналами уведомлений:
Начиная с Android 8.0 (уровень API 26), все уведомления должны быть назначены каналу.
Вот выдержка (возьмите из нее то, что вам нужно) из метода, который я использую для создания уведомлений в средствах массовой информации. Вы можете видеть, что есть проверка для устройств Android O с определенным методом обработки этого случая:
private fun compileNotification(context: Context, action: NotificationCompat.Action, mediaSession: MediaSessionCompat, controller: MediaControllerCompat, mMetadata: MediaMetadataCompat, art: Bitmap?, mPlaybackState: PlaybackStateCompat) {
val description = mMetadata.description
// https://stackoverflow.com/questions/45395669/notifications-fail-to-display-in-android-oreo-api-26
@TargetApi(26)
if(Utils.hasO()) {
val channelA = mNotificationManager?.getNotificationChannel(NotificationChannelID.MEDIA_SERVICE.name)
if(channelA == null) {
val channelB = NotificationChannel(NotificationChannelID.MEDIA_SERVICE.name,
"MediaService",
NotificationManager.IMPORTANCE_DEFAULT)
channelB.setSound(null, null)
mNotificationManager?.createNotificationChannel(channelB)
}
}
val notificationBuilder = if(Utils.hasLollipop()) {
NotificationCompat.Builder(context, NotificationChannelID.MEDIA_SERVICE.name)
} else {
NotificationCompat.Builder(context)
}
notificationBuilder
.setStyle(android.support.v4.media.app.NotificationCompat.MediaStyle()
// Show actions 0,2,4 in compact view
.setShowActionsInCompactView(0,2,4)
.setMediaSession(mediaSession.sessionToken))
.setSmallIcon(R.drawable.logo_icon)
.setShowWhen(false)
.setContentIntent(controller.sessionActivity)
.setContentTitle(description.title)
.setContentText(description.description)
.setLargeIcon(art)
.setVisibility(NotificationCompat.VISIBILITY_PUBLIC)
.setOngoing(mPlaybackState.state == PlaybackStateCompat.STATE_PLAYING)
.setOnlyAlertOnce(true)
if(!Utils.hasLollipop()) {
notificationBuilder
.setStyle(android.support.v4.media.app.NotificationCompat.MediaStyle()
// Show actions 0,2,4 in compact view
.setShowActionsInCompactView(0,2,4)
.setMediaSession(mediaSession.sessionToken)
.setShowCancelButton(true)
.setCancelButtonIntent(MediaButtonReceiver.buildMediaButtonPendingIntent(context,
PlaybackStateCompat.ACTION_STOP)))
// Stop the service when the notification is swiped away
.setDeleteIntent(MediaButtonReceiver.buildMediaButtonPendingIntent(context,
PlaybackStateCompat.ACTION_STOP))
}
notificationBuilder.addAction(NotificationCompat.Action(
R.drawable.exo_controls_previous,
"Previous",
MediaButtonReceiver.buildMediaButtonPendingIntent(context,
PlaybackStateCompat.ACTION_SKIP_TO_PREVIOUS)))
notificationBuilder.addAction(NotificationCompat.Action(
R.drawable.ic_replay_10_white_24dp,
"Rewind",
MediaButtonReceiver.buildMediaButtonPendingIntent(context,
PlaybackStateCompat.ACTION_REWIND)))
notificationBuilder.addAction(action)
notificationBuilder.addAction(NotificationCompat.Action(
R.drawable.ic_forward_10_white_24dp,
"Fast Foward",
MediaButtonReceiver.buildMediaButtonPendingIntent(context,
PlaybackStateCompat.ACTION_FAST_FORWARD)))
notificationBuilder.addAction(NotificationCompat.Action(
R.drawable.exo_controls_next,
"Next",
MediaButtonReceiver.buildMediaButtonPendingIntent(context,
PlaybackStateCompat.ACTION_SKIP_TO_NEXT)))
(context as MediaService).startForeground(NOTIFICATION_ID, notificationBuilder.build())
}
В onStop()
вам нужно вызвать stopSelf()
в службе. Затем, когда вы onDestroy()
метод onDestroy()
вам нужно очистить несколько вещей (применительно к вашему делу) следующим образом:
override fun onDestroy() {
super.onDestroy()
abandonAudioFocus()
unregisterReceiver(mNoisyReceiver)
//Deactivate session
mSession.isActive = false
mSession.release()
NotificationManagerCompat.from(this).cancelAll()
if(mWiFiLock?.isHeld == true) mWiFiLock?.release()
stopForeground(true)
}
Я не включил детали для некоторых из вышеперечисленных методов, но имена методов должны быть самокомментирующими - сообщите мне, могу ли я включить более подробную информацию. Некоторые из них могут быть излишними, но в вашем случае это может решить проблему.
Я уверен, что это решит вашу проблему. Если это не так, у меня есть еще несколько идей.