Notifications. Канали
В Android Oreo (API 26) з'явилася можливість створювати канали для сповіщень. У цьому уроці розберемося, як це робити і навіщо це потрібно.
Для кожної програми користувач може налаштувати сповіщення. Для цього треба зайти в налаштування системи, там вибрати Apps, знайти в списку і відкрити потрібний застосунок і вибрати розділ Notifications.
За замовчуванням налаштування виглядають так:

Налаштувань небагато, і вони торкнуться всіх повідомлень від цієї програми.
Канали дають змогу розширити ці налаштування і застосовувати їх вибірково. Розробник застосунку створює канал і вказує його ID під час створення повідомлень. Користувач у системних налаштуваннях програми бачить цей канал і може налаштувати його: важливість, звук, вібру тощо. У підсумку всі сповіщення, які належать цьому каналу, відображатимуться з цими налаштуваннями.
Тобто створюючи канал, розробник дає користувачеві можливість налаштувати поведінку певної групи повідомлень.
Давайте створимо канал:
NotificationManager notificationManager =
(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
NotificationChannel channel = new NotificationChannel(CHANNEL_ID, "My channel",
NotificationManager.IMPORTANCE_HIGH);
channel.setDescription("My channel description");
channel.enableLights(true);
channel.setLightColor(Color.RED);
channel.enableVibration(false);
notificationManager.createNotificationChannel(channel);
}
Канали актуальні тільки для Android Oreo і вище, тому використовується перевірка версії Android. Далі я не буду включати цю перевірку в приклади, щоб не захаращувати код.
У конструкторі NotificationChannel вказуємо ID, ім'я та важливість. Далі вказуємо інші дані та налаштування. За назвою методів усе зрозуміло.
Методом createNotificationChannel створюємо канал.
Тепер Notifications налаштування застосунку мають такий вигляд:

З'явилися два канали: дефолтний і наш створений My channel. Налаштування дефолтного будуть використані для повідомлень, для яких не було вказано канал.
Відкриємо налаштування My channel:

Зверніть увагу, що пункт Vibrate вимкнений. Ми явно вказали це під час створення каналу, використовуючи метод enableVibration(false).
Тепер під час створення сповіщень ви можете вказати ID каналу, і сповіщення буде відображено відповідно до налаштувань цього каналу.
NotificationCompat.Builder builder =
new NotificationCompat.Builder(this, CHANNEL_ID)
.setSmallIcon(R.mipmap.ic_launcher)
.setContentTitle("Title")
.setContentText("Notification text");
ID каналу вказується в конструкторі білдера повідомлення. І тепер цей конструктор не буде закреслено як Deprecated, якщо ви використовуєте бібліотеку appCompat версії 26 і вище.
У який момент створювати канал? Можна під час старту програми. Навіть якщо канал уже був раніше створений, то просто нічого не станеться. Але судячи з того, що користувач не може видаляти канали, я думаю, можна використати якийсь прапор, який ми встановимо в true після першого створення каналів, і надалі він буде говорити нам про те, що канали вже створені.
Група
Розглянемо приклад поштового додатка. Припустимо, що він уміє працювати не тільки з поштою, а й з календарем. Тобто він може нам надсилати повідомлення двох типів: листи і події.
Відповідно, ми можемо створити два канали - один для повідомлень про листи, інший - для подій. У результаті, користувач сам зможе налаштувати під себе окремо повідомлення про листи й окремо про події. Це зручно.
Але наш застосунок підтримує кілька облікових записів. І під кожен обліковий запис нам необхідно створювати два канали для повідомлень.
При створенні 4-х каналів налаштування будуть виглядати так:

Можна це поліпшити, використовуючи групи. Група - це просто спосіб візуально розділити канали в налаштуваннях.
Створюється група так:
NotificationManager notificationManager =
(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
notificationManager.createNotificationChannelGroup(
new NotificationChannelGroup(GROUP_ID, "Group 1"));
У конструкторі вказуємо ID та ім'я.
Далі, при створенні каналу використовуємо метод setGroup, щоб вказати, якій групі буде належати канал.
NotificationChannel channel = new NotificationChannel(...);
// ...
channel.setGroup(GROUP_ID);
notificationManager.createNotificationChannel(channel);
Таким чином, для кожного облікового запису нашого застосунку ми можемо створити групу і вказати її під час створення каналів повідомлень цього облікового запису:
User A (group)
Mail (channel)
Events (channel)
User B (group)
Mail (channel)
Events (channel)
Тепер налаштування мають кращий вигляд:
Канали згруповані за обліковими записами.
Отримання інформації про канал
У будь-який момент після створення каналу, ви можете отримати інформацію про нього.
NotificationChannel channel = notificationManager.getNotificationChannel(CHANNEL_ID);
Метод getNotificationChannel поверне вам об'єкт NotificationChannel або null, якщо канал із зазначеним ID не було знайдено. Використовуючи різні get-методи каналу, ви зможете дізнатися, як користувач налаштував ваш канал. Але ви не зможете переналаштувати його, set-методи просто не працюватимуть.
Єдине, що ви можете змінити - це ім'я каналу і його опис (description). Для цього необхідно просто перестворити канал із новими параметрами і тим самим ID.
Якщо ви рахували налаштування каналу і з якихось причин вирішили, що користувач не правий, то ви можете попросити його змінити налаштування.
Наприклад, якщо користувач вимкнув відображення повідомлень для каналу, відкриваємо налаштування цього каналу.
NotificationChannel channel = notificationManager.getNotificationChannel(CHANNEL_ID);
if (channel.getImportance() == NotificationManager.IMPORTANCE_NONE) {
Intent intent = new Intent(Settings.ACTION_CHANNEL_NOTIFICATION_SETTINGS);
intent.putExtra(Settings.EXTRA_CHANNEL_ID, channel.getId());
intent.putExtra(Settings.EXTRA_APP_PACKAGE, getPackageName());
startActivity(intent);
}
Якщо getImportance дорівнює IMPORTANCE_NONE, це означає, що канал був вимкнений користувачем. Створюємо Intent із зазначенням ID каналу та package додатка і запускаємо Activity.
Зрозуміло, у реальному застосунку треба діяти не так незграбно, а спершу поцікавитися думкою користувача і пояснити, чому ви хочете, щоб він змінив налаштування каналу.
Видалення каналу
Щоб видалити канал, використовуйте метод deleteNotificationChannel
notificationManager.deleteNotificationChannel(CHANNEL_ID);
Технічно ви, звичайно, можете використовувати видалення, а потім створення каналу, щоб відновити ваші налаштування. Але так робити не рекомендується. До того ж у налаштуваннях, у самому низу, користувач бачитиме, скільки каналів було видалено.

І він зрозуміє, що ви просто перестворюєте канал і скидаєте його налаштування.
Importance vs Priority
Якщо ви пам'ятаєте, при створенні повідомлення, ми можемо в білдері вказати пріоритет. Починаючи з Android Oreo пріоритети сповіщень були оголошені застарілими і замінені параметром каналу - важливість.