Дизайнеры, с которыми я работаю, часто рассматривают сообщения об ошибках в iOS как что-то очевидное. А если конкретно – как UIAlertController.
Предустановленные приложения от Apple задают такой тренд. И логично, что дизайнеры интерфейсов считают этот подход нативным и правильным.
В то же время, многие разработчики под iOS в России и СНГ самостоятельно приходят к отказу от UIAlertController, чем вызывают у меня искреннее уважение и восторг.
В этой статье я расскажу о том, к чему приводит неуместное использование UIAlertController. Поделюсь мнением об альтернативных способах сообщать пользователю об ошибках и о том, когда UIAlertController действительно необходим.
Эта статья для «опытных пользователей». Поэтому я не рассказываю о том, что такое пользовательский опыт и его прерывание, как сказывается средняя продолжительность сессии на доходах приложения и почему важно свести движения пальцем пользователя к минимуму.
Оглавление:
- Прерывание пользовательского опыта и скрытый выбор.
- Альтернативы UIAlertController.
- UIAlertController как инструмент привлечения внимания.
- Заключение и рекомендации других статей.
Прерывание пользовательского опыта и скрытый выбор
В Apple Human Interface Guidelines есть пара занимательных строк:
Minimize alerts. Alerts disrupt the user experience and should only be used in important situations like confirming purchases and destructive actions (such as deletions), or notifying people about problems. The infrequency of alerts helps ensure that people take them seriously. Ensure that each alert offers critical information and useful choices. – Apple, Human Interface Guidelines, iOS, Views, Alerts.
Минимизируйте алерты. Алерты прерывают пользовательский опыт и должны использоваться только при важных ситуациях, таких как подтверждения покупок и деструктивных действиях (например, при удалении), или оповещать людей о проблемах. Редкость алертов помогает людям относиться к ним серьезно. Убедитесь, что каждый алерт содержит важную информацию и полезные варианты выбора. – Apple, Human Interface Guidelines, iOS, Views, Alerts.
Prefer nonintrusive status messages over alerts. Alerts disrupt the user experience. List error messages inline with content instead of displaying them in alerts. – Apple, Human Interface Guidelines, Architecture, Error Handling.
Предпочтите ненавязчивые сообщения алертам. Алерты прерывают пользовательский опыт. Показывайте сообщения о ошибках вместе с контентом, вместо их отображения в алертах. – Apple, Human Interface Guidelines, Architecutre, Error Handling.
Но если вы прямо сейчас скачаете несколько приложений от небольших разработчиков, то либо вовсе не увидите сообщений об ошибках, либо увидите их в алертах.
Причина в том, что большинство дизайнеров невнимательно знакомятся с актуальными гайдлайнами от Apple перед началом разработки продуктов. А зря.
И вот почему.
Представим UIAlertController, который сообщает пользователю о том, что соединение с сервером потеряно. Он содержит две кнопки: «Попробовать еще раз» и «ОК».
Во время показа алерта пользователь не может пользоваться приложением дальше, пока не закроет алерт. Получается, что приложение блокирует действия пользователя и ставит ультиматум вынуждающий выбрать одну из кнопок алерта.
Почти все дизайнеры уверяли меня в том, что в такой ситуации у пользователя всего два выхода – как и количество кнопок в алерте. Я с этим не согласен.
У него перед глазами есть минимум еще одна кнопка – «Home».
Это и называется скрытым выбором.
В момент проблемы с соединением пользователь может решить, что вернется позже. Он просто закроет приложение и забудет о нём на ближайшие часы или дни.
В результате, с помощью алерта, мы сами снижаем среднюю продолжительность сессии и теряем доход. А это совсем не то, что нам нужно.
Альтернативы UIAlertController
Apple рекомендует показывать ошибки вместе с контентом. Посмотрим, как это выглядит на практике.
Начнем с наиболее радикальной ошибки – отсутствие соединения с интернетом.
Зачастую приложение уже успело загрузить часть контента перед потерей соединения. Когда пользователь закончит просматривать этот контент, есть вероятность, что соединение с интернетом восстановится. В таком случае он может и не догадаться о том, что проблема вообще существовала.
Зачем прерывать пользователя сообщением о ошибке, если она ему не мешает?
Правильно – незачем.
С ошибками, когда не загружена только часть контента, все еще проще. Не привлекайте к ним внимание. Лучше дайте пользователю попробовать загрузить их еще раз, если ему это необходимо.
Ещё один пример – экран входа в учетную запись. По моему опыту, это наиболее частый случай, когда ошибка вызывает неуместный UIAlertController.
Так может выглядеть ошибка, когда пользователь неверно ввел логин или пароль. Всё понятно и без алертов.
Резюмируем: чаще всего ненавязчивое отображение ошибки "внутри контента" будет лучшим решением, чем показ UIAlertController.
Однако существуют варианты, при которых алерты окажутся правильным решением.
UIAlertController как инструмент привлечения внимания
Apple рекомендует использовать UIAlertController при деструктивных действиях пользователя.
Почему? Думаю причина в том, что при удалении чего-либо пользователь обязан обратить пристальное внимание на своё действие. И здесь прерывание пользовательского опыта вполне оправдано.
Приложение как бы останавливает пользователя и говорит: «Ты уверен в том, что хочешь сделать?».
Такой алерт от Apple можно увидеть при удалении контакта в приложении «Телефон» или при удалении фотографий из приложения «Фото».
Однако, если удалять что-либо – это обычное и повседневное действие, то использование UIAlertController не обязательно. Яркий пример – приложение «Почта» на iOS.
Представьте, если бы при удалении каждого письма приложение спрашивало о том, уверены ли вы в своих действиях. Это было бы ужасно! Возможно, вы бы отказались от стандартного почтового клиента в пользу альтернативы из App Store.
В таких случаях лучше предлагать возможность отменить удаление, чем прерывать пользовательский опыт. Этим решением в стандартных приложениях на iOS также пользуются часы, заметки и напоминания.
Показывайте UIAlertController при деструктивных и безвозвратных действиях пользователя только в случае, если удаление не является одной из повседневных задач.
Заключение и рекомендации других статей
Надеюсь, что смог привлечь внимание к проблеме или подтолкнул вас к собственным размышлениям на этот счёт.
Если вы участвуете в разработке приложения, которое использует UIAlertController как основной способ демонстрации ошибок – можете для интереса внедрить аналитику, которая покажет соотношение выбора одного из вариантов действий к закрытию приложения.
Думаю, вы сильно удивитесь. Можете поделиться этой статистикой в комментариях к статье.
Также я рекомендую почитать другие статьи об ошибках в мобильных и веб-интерфейсах:
- https://developer.apple.com/design/human-interface-guidelines/carplay/architecture/error-handling/
- https://developer.apple.com/design/human-interface-guidelines/ios/views/alerts/
- https://medium.com/s/user-friendly/the-art-of-the-error-message-9f878d0bff80
- https://uxplanet.org/how-to-write-good-error-messages-858e4551cd4
- https://www.kaylaheffernan.com/blog/2014/12/9/error-messages
- https://medium.com/@thomasfuchs/how-to-write-an-error-message-883718173322
Желаю вам прекрасных проектов!
Есть вопросы или комментарии? Буду рад пообщаться!
lohmatij
Вообще было бы здорово если бы в других областях так же применялось это правило.
Допустим копирование/вставка файлов. При первой же ошибке/запросе весь процесс встаёт, хотя было бы гораздо логичнее если бы процесс продолжался и тупо пропускал файлы с ошибкой/требующих запроса. Сейчас ты ставишь на копирование огромную папку и всё минут через 5 может уткнуться в вопрос типа: «файл уже существует, что делать: заменить?/остановить весь процесс?/переименовать?». Блин, ну что мешает копировать остальные файлы дальше (если это возможно)? Пользователь вернётся, разгребет вопросы, а остальная часть копирования уже к тому времени завершится.
V1RuS
Вроде бы Total Commander так умеет, еще с версии 8.50
https://habr.com/ru/post/213287/
Файловые операции стали умнее. Копирование не будет останавливаться на нечитаемых файлах, TC сначала скопирует то, что сможет, и только потом спросит «а что делать с этим?». При этом, если файлы не читаются сразу же, диалог появится — подразумевается, что пользователь ещё не успел отойти от компьютера.
lohmatij
Тотал молодец, там это продуманно, а сколько мест где это не продуманно — тьма.
Подобные же затыки встречаются в куче разных мест: подтверждение соглашений посредине установки больших программ, ошибка в середине очереди рендеринга, скачивание больших файлов из интернета: тьма моментов когда система падает кверху лапками со стоном «не шмогла», когда логичнее тупо попытаться заново с текущей задачей или хотя бы перейти автоматически к следующей.
Так же бесит когда какое-то действие замораживает все систему напрочь. К примеру: у меня фото хранятся в облачном хранилище icloud, допустим я хочу их добавить в общий альбом или отправить кому-то по telegram. Сначала iOS должна скачать выбранные фото и только потом я могу выбрать в какой альбом их добавить или какому контакту отправить. Это тупо, так как порой скачка занимает 10-15 минут и в это время телефоном нельзя пользоваться, любое нажатие сбросит процесс. Потом ещё надо минут 5-10 ждать пока они отправятся в телеграмм или куда ты там выбрал.
Как должно быть: я выбираю фото для отправки и сразу выбираю адресата в мессенджере, а дальше система молотит все в фоне. Примерно так работает стандартная почта: я отправляю письмо, оно перемещается в исходящие, а дальше при наличии интернета оно отправляется в фоне.
Вот с мессенджерами и другими вопросами так же должно быть: нет интернета или ещё какой затык? Поставь задачу в очередь и молоти её на фоне при наличии возможности.
lohmatij
В этом плане мне очень нравится логика дропбокса или подобных облачных хранилищ. Допустим мне надо отправить кому то 50 гигабайт фото/видео со съёмки. Я делаю папку в Дропбокс (resillio sync), расшариваю её и отправляю ссылку заказчику. Параллельно ставлю на рендер фото (или видео) и ухожу по делам. Рендер закончится через час/два, потом эти файлы автоматически закачаются в облако, а при resillio sync прямо на компьютер заказчику, да ещё и с проверкой контрольных копий.
А раньше бы пришлось сначала все рендерить, потом закачивать на FTP, да ещё и следить чтобы без обрывов. А если обрыв то удалять/догружать файл, короче то что сейчас автоматизировано раньше приходилось тащить вручную. И вот везде где возможно лучше автоматизировать, не надо парить пользователя лишними подтверждениями, алертами и остановками: есть задача, так делай ее пока есть возможность, нет возможности, так делай что можешь и потом возвращайся к пропущенным задачам.
varton86
Спасибо, есть над чем задуматься. Хотя, дизайнеры скорее предпочтут кастомный вью стандартному алерту, с точки зрения хотя бы эстетики. Другое дело, что разработчикам проще использовать алерт и, возможно, это они когда-то убедили дизайнеров, что это по гайду )
Yoooriii
Все гораздо проще, дизайнеры, с которыми я работал, в глаза не видели эти самые гайды и что забавней, не имели ни малейшего желания туда заглядывать, это из серии: «платформ много, а я Д'Артаньян». Но что еще хуже, так это то что заказчики приложений, как правило не имеют ни малейшего представления об iOS и переубедить их в том, что алерт не нужен, тем более алерт типа «произошла ошибка 999» вообще из мира виндоус, Apple настойчиво рекомендует не давать подобного рода сообщения, или если давать, то что то более юзер френдли. Про текст на кнопках я вообще иногда в шоке. Что например может означать «Cancel»? Отменить последнюю операцию или спрятать алерт? Если спрятать алерт, то это как правило «Dismiss». Или что означает клавиша «ОК»? «ОК» — повторить, «ОК» — отменить, «ОК» — я вас понял или «ОК» — продолжить? Опять же у Эплов есть и на этот счет четкие инструкции плюс с какой стороны должна располагаться клавиша, слева или справа. У меня сложилось впечатление, что для пользователей виндоус невнятные алерты — это скорей норма чем исключение, ну и соответственно имеем то что имеем: экосистема виндоус просочилась даже в iOS.
andrew8712
Как предлагается показывать ошибку сервера при отправке данных с формы?
V1RuS
почему бы не показать ее там же, где ошибку ввода — рядом с формой?
вариантов действий все равно немного: повторить отправку или не повторить. для этого там уже есть кнопка.