Диалог — часть навигации или нет?
Введение
Не так давно я начал разработку собственной библиотеки для навигации в клиентских приложениях на Kotlin Multiplatform. Сделать такое решение подходящим под фанатзию каждого дизайнера и менеджера продукта сложно. Поэтому я начал рассказывать про библиотеку и её концепции на стадии разработки, чтобы понять как это может подойти разработчикам, особенно тем кто уже имеют большую кодовую базу. Одной из спорных тем, которая у нас появилась в рамках обсуждения: «Должен ли диалог показываться через навигацию и хранится как часть истории навигации пользователя?» Мой ответ: «Зависит от того что понимаем под диалогом и цель его показа».
Меня зовут Кирилл Розов и в этой статье я расскажу вам что понимает под диалогом в Material Design и свой взгляд как работать с диалогами в навигации
Если вам интересно следить за самыми последними новостями Android разработки и получать подборку интересных статей по этой тематике, тогда вам стоит подписаться на Телеграм-канал Android Broadcast и мой YouTube канал «Android Broadcast»
Что такое диалог
Диалог в пользовательском интерфейсе (UI — User Interface) — это всплывающее окно, панель или экран, который временно отображается поверх основного содержимого приложения или сайта.
Диалог выбора даты
Диалоги используются для привлечения внимания пользователя и обычно требуют от него какого-либо взаимодействия или ответа. Они могут выполнять различные функции, такие как подтверждение действий, ввод данных, сообщения об ошибках, уведомление о событии, настройки или параметры в рамках страницы. Диалог не занимает все пространство и под ним можно увидеть экран, чтобы понимать контекст в котором показан диалог.
Не стоит путать диалоги с окнами, которые не занимают весь экран. Например, частым приемом является показ диалога на всю площадь экрана на смартфонах, а на планшете используется режим показа в окне. Экран на планшете от этого не становится Диалогом, но имеет визуальный стиль схожий с ним, хотя Material Design называет такой случай «Полноэкранный Диалог»
Полноэкранный диалог на смартфоне и обычный на планшете
Диалог выбора в виде Bottom Sheet
В Material дизайне есть компонент Bottom Sheet (используется на смартфонах и планшетах) и Side Sheet (используется на больших экранах), которые тоже можно отнести к категории диалогов т.к. заменяют те функции для чего используются диалоги.
Side Sheet — версия Bottom Sheet для больших экранов
Контекстное меню в Android
В целом то, как что-то представляется диалогом или нет, мне показалось настолько условным, что даже контекстное меню можно отнести к диалогам.
Модальность диалога
Явное разделения по месту использования диалогов нет, но их можно разделить по влиянию на возможность взаимодействия c UI на модальные и немодальные.
Пример диалога с подтверждением действия
Модальные диалоги визуально блокируют взаимодействие с остальной частью приложения, пока не будет выполнено действие, запрашиваемое в диалоге. Например, подтверждение действия или уведомление об ошибке, которая не даёт нормально работать с приложением дальше. В отдельных случаях они позволяют закрыть его и продолжить работу с приложением дальше.
Пример немодального диалога
Немодальные диалоги позволяют продолжать работать с приложением т.к. не требуют немедленного взаимодействия с ним. Сюда относятся подсказки или уведомления. Зачастую они представлены как Баннер или Snackbar.
Диалог в навигации: быть или не быть
Под навигацией пользователя в UI я понимаю переход по Экранам приложения. История навигации возвращается после восстановления приложения. Потеря любого из такого элемента навигации критичная для пользователя.
Если рассмотреть библиотеку навигации Jetpack Navigation для Compose, то прямо в документации метода dialog () говорится:
… Эта функция предназначена для случая, если данное диалоговое окно представляет собой отдельный экран в вашем приложении, которому требуется собственный жизненный цикл и сохраненное состояние, независимые от любого другого экрана в графе навигации …
Показ Экрана в виде диалог коде Jetpack Navigation хоть и выделен функций, но это лишь визуальная обертка в Dialog и по сути имеет мало разницы с показом обычного Экрана
// Пример использования Jetpack Navigation для показа Composable
// во всплывающем окне в стиле диалога
NavHost(
navController = navController,
startDestination = startDestination,
modifier = modifier
) {
dialog{
// Показываем Composable функцию, которую обернут в диалог
}
composable {
// Показ Composable функции на всём доступном пространстве
}
}
В итоге я для себя принял ряд правил касательно экранов в навигации:
Все контекстные элементы UI не относятся к навигации, например Контекстное Меню
Все немодальные диалоги НЕ относятся к навигации приложения, так как это лишь визуальные инструменты уведомлений. Они могут относится к состоянию Экрана или быть частью глобального состояния
Диалог подтверждения и выбора не является частью навигации, так как считается визуальным инструментом предотвращения случайного действия и привязан к контексту. Могут быть частью состояния Экрана
Экран приложения, показываемый в стиле диалога, является частью навигации. Здесь диалог лишь накладываемый стиль. Такой Экран на отдельных устройствах может занимать всё доступное пространство
Контент приложения, который показывается в стиле диалога, считается частью навигации, потому что сохраняется при переходах по экранам и помещается в back stack
В своём решение навигации выделять работу с диалогами я не вижу смысла, так это лишь визуальный стиль Экрана в состоянии навигации, за который должна отвечать UI часть навигации.
Мне интересно узнать ваше мнение и как вы подходите к работе с диалогами в UI навигации. Делитесь им в комментариях и давайте искать истину вместе!