[Перевод] Кнопки «Закрыть»: паттерны и антипаттерны
На модальных окнах, на рекламных объявлениях, на других подобных всплывающих элементах веб-страниц часто можно найти кнопку «Закрыть» с соответствующим символом. Эти кнопки позволяют пользователям (по крайней мере — некоторым из них) закрывать окна. Возможность щёлкнуть по кнопке «Закрыть» часто доступна только тем посетителям веб-страниц, у которых есть мышь. Дело в том, что большинство реализаций подобных кнопок далеко не идеально. В материале, перевод которого мы сегодня публикуем, будет рассмотрено 11 проблемных паттернов, которые используются при создании кнопок «Закрыть», а также — способы решения проблем этих паттернов. Здесь же речь пойдёт и об удачных способах создания кнопок «Закрыть».
Неудачные паттерны
▍Паттерн №1: элемент div и фоновое изображение
Взглянем на HTML-код, используемый для создания кнопки «Закрыть»:
Вот стили:
.close::after {
background: url("close.png");
content: "";
}
Проблемы и их решение
Ниже приведён список проблем, которые характерны для данного варианта реализации кнопки «Закрыть». Зная об этих проблемах, можно наметить пути их решения.
- Элемент — это элемент, которым пользуются в крайнем случае, тогда, кода для решения некоей задачи просто нет другого, более подходящего элемента. Использованиевместо более подходящих элементов ведёт к плохой доступности проекта.
- Событие
click
элементавызывается только в том случае, если по нему щёлкают мышью. А, например, такое же событие элементавызывается и по щелчку мыши, и по нажатию клавиш
Enter
иПробел
на клавиатуре.- Элемент
не поддерживает получение фокуса с клавиатуры.- Здесь нет текстовой альтернативы фоновому изображению.
- Средства для чтения с экрана не «озвучивают» этот элемент.
▍Паттерн №2: элемент div и иконка
Вот разметка:✕Проблемы и их решение
- Значок ✕ не является чем-то таким, что можно напрямую соотнести с командой «Закрыть». Этот значок используется для записи математических выражений, в которых одно число умножается на другое (вроде 2✕2). Не стоит использовать его для оформления кнопки «Закрыть».
- О минусах использования элемента при оформлении кнопок «Закрыть» читайте в разделе «Паттерн №1».
- Средства для чтения с экрана «озвучат» этот значок, использовав какое-нибудь слово, имеющее отношение к умножению (вроде «multiplication x» или «times»).
▍Паттерн №3: иконки из Font Awesome
Вот HTML-разметка:
Вот CSS-код:.fa-times::before { content: '\f00d'; }
Проблемы и их решение
- Средства для чтения с экрана могут озвучить содержимое, сгенерированное средствами CSS.
- В документации к Font Awesome рекомендуется семантически скрывать иконки, например, пользуясь атрибутом
aria-hidden=«true»
элемента.
- Font Awesome добавляет на страницу Unicode-содержимое с помощью псевдоэлемента
::before
. Ассистивные технологии могут озвучить Unicode-эквивалент соответствующей иконки, что в данном примере приведёт к сообщению о том, что тут имеется символ умножения («times»). Дело в том, что fa-times — это не символ-крестик, а знак умножения. Обратите внимание на то, что Talkback и VoiceOver при обработке подобного кода вообще ничего не «говорят». - Элемент
представляет собой фрагмент текста, который, при использовании средств для чтения с экрана, должен озвучиваться другим голосом или с другой интонацией. То есть это — фрагмент, который система должна «прочитать» не так, как обычный текст. Если всё, что нужно — это текст, набранный курсивом, рекомендуется использовать CSS-стиль
font-style: italic;
. - О недостатках элемента читайте в разделе «Паттерн №1».
▍Паттерн №4: ссылка «Закрыть»
Вот HTML-код:
Вот стили:a::after { font-size: 28px; display: block; content: "×"; }
Проблемы и их решение
- Если у элемента
есть атрибут
href
, он представляет собой ссылку на некий ресурс — вроде другой веб-страницы или PDF-документа. - Цель элемента из этого примера заключается в вызове на той же самой странице действия, выполняемого средствами JavaScript. В такой ситуации лучше подойдёт элемент
, атрибут
type
которого установлен в значениеbutton
. Дело в том, что такой элемент, по умолчанию, не выполняет никаких действий. Он создан специально для того, чтобы вызывать выполнение каких-то действий в ответ на события пользовательского ввода. - Если вы не уверены в том, какой именно элемент использовать,
или
, посмотрите это видео.
- Средства для чтения с экрана могут «прочитать» то, что будет сгенерировано с помощью CSS. Значок, используемый в этом примере, как и в предыдущих примерах, это не значок «закрыть», а значок, символизирующий умножение. Его не стоит использовать для оформления кнопок «Закрыть».
- Средства для чтения с экрана, разбирая этот код, могут сообщить о значке умножения и о ссылке, но не о кнопке «Закрыть».
▍Паттерн №5: ссылка «Закрыть» с текстом
Вот HTML-код этого паттерна:Close
Вот CSS-код:.close::before { content: "\e028"; }
Проблемы и их решение
- Это, на самом деле, не так уж и плохо, но тут, всё же используется ссылка, а не кнопка.
- Почитайте то, о чём говорится в разделе «Паттерн №4» относительно элементов
и содержимого, генерируемого средствами CSS.
- Средства для чтения с экрана могут «озвучить» подобный элемент как «link, times close».
▍Паттерн №6: ссылка «Закрыть» без атрибута href
Вот разметка:×
Проблемы и их решение
- Перед нами ещё один пример, который нельзя признать очень уж плохим, но тут у ссылки нет атрибута
href
, и это, опять же, ссылка, а не кнопка. - Если у элемента
нет атрибута
href
, это значит, что элемент представляет собой местозаполнитель элемента, куда могла бы быть вставлена реальная ссылка. - Если вы обрабатываете событие щелчка на ссылке-местозаполнителе, то вам, возможно, стоит использовать не такую ссылку, а ссылку с атрибутом
href
, или элемент. Это зависит от того, что именно происходит при щелчке по подобному элементу.
- Ссылки-местозаполнители не могут получать фокус.
- Если вы не знаете точно о том, что именно вам нужно, элемент
или
, обратитесь к этому видео.
- Средства для чтения с экрана могут «прочитать» этот элемент как «times, clickable».
▍Паттерн №7: ссылка-местозаполнитель и элемент img
Вот HTML-код этого паттерна:Проблемы и их решение
- Тут нет текстовой альтернативы изображению.
- Об особенностях ссылок-местозаполнителей читайте в разделе «Паттерн №6».
- Средства для чтения с экрана могут «прочитать» в такой ситуации имя файла, например, выдать что-то вроде «close.png, image».
▍Паттерн №8: радиокнопка
Вот HTML-код:
Вот применяемый здесь стиль:[type="radio"] { display: none; }
Проблемы и их решение
- Когда люди, которые продвигают идеи доступности контента, говорят о том, что нужно просто использовать кнопки, они имеют в виду элемент
, а не радиокнопки.
- Радиокнопки используются в группах, описывающих наборы взаимосвязанных опций.
- У SVG-изображения нет текстовой альтернативы. Вот хорошая статья о доступности SVG-изображений.
- Средства для чтения с экрана могут никак не «озвучить» такой элемент.
▍Паттерн №9: кнопка с иконкой
Как обычно, сначала рассмотрим разметку:Проблемы и их решение
- Значок ✕, с которым мы уже встречались, это не символ закрытия чего-либо. Это знак, символизирующий умножение. Не стоит использовать его для оформления кнопки «Закрыть».
- Средства для чтения с экрана могут «прочитать» эту кнопку как «times, button».
▍Паттерн №10: кнопка с SVG-изображением
HTML-код:Проблемы и их решение
- Здесь нет текстовой альтернативы SVG-изображению. О доступности таких изображений читайте здесь.
- Средства для чтения с экрана могут сообщить о том, что тут имеется «button», не «сказав» больше ничего.
▍Паттерн №11: старый добрый символ X
Вот HTML-код, реализующий этот паттерн:XПроблемы и их решение
- Учитывая то, что существует элемент
, в явной настройке семантики кнопки с использованием атрибута
role
необходимости нет. - Если пользоваться элементом
, не нужно применять атрибут
tabindex
. HTML-кнопки, по умолчанию, рассчитаны на возможность получения ими фокуса ввода. - О минусах читайте в разделе «Паттерн №1».
- Символ, представляющий букву X, это не иконка для закрытия чего-либо.
- Средства для чтения с экрана могут «озвучить» этот элемент как «X».
Вот что по этому поводу сказал Макс Бок: «Использовать символ x для кнопок закрытия — это как сыпать соль в кофе только из-за того, что она выглядит так же, как сахар».Вот CodePen-проект, в котором собраны неудачные паттерны создания кнопок «Закрыть»
Альтернативы неудачным паттернам
▍Решение №1: кнопка с видимым текстом без иконки
Вот разметка, применяема в этом решении:Особенности
- Здесь используется только текст. Такую кнопку просто реализовать, её назначение понятно пользователям.
- Средства для чтения с экрана могут «озвучить» такую кнопку как «Close, button».
▍Решение №2: кнопка с видимым текстом и с иконкой, скрытой от ассистивных технологий
HTML-код:Особенности
- Если вам и правда нужно пользоваться иконкой, которая, в обычных условиях, используется как символ умножения, её стоит скрыть от средств для чтения с экрана, поместив в элемент
с атрибутом
aria-hidden=«true»
. - Средства для чтения с экрана могут сообщить о том, что это «Close, button».
▍Решение №3: кнопка со скрытым текстом и со значком, который видим на экране, но скрыт от ассистивных технологий
Вот HTML-код этого решения:
Вот стиль:.sr-only { position: absolute; white-space: nowrap; width: 1px; height: 1px; overflow: hidden; border: 0; padding: 0; clip: rect(0 0 0 0); clip-path: inset(50%); margin: -1px; }
Особенности
- К сожалению, нет стандартного способа скрытия элементов, при использовании которого они не видны, но остаются доступными для ассистивных технологий. Эта задача решается здесь с помощью стиля класса
.sr-only
. - Средства для чтения с экрана могут «озвучить» эту кнопку как «Close, button».
▍Решение №4: ещё один вариант кнопки со скрытым текстом и со значком, который видим на экране, но скрыт от ассистивных технологий
Вот HTML-разметка:Особенности
- Если вам не хочется выводить текст — назначьте иконке или SVG-изображению текстовую альтернативу, воспользовавшись атрибутом кнопки
aria-label
. - Средства для чтения с экрана могут сообщить о том, что перед нами «Close, button».
▍Решение №5: использование Font Awesome
Вот, ради полноты изложения, удачный пример кнопки «Закрыть», при создании которой используется Font Awesome:▍Общие замечания
Иногда имеет смысл использовать метки с более подробными описаниями действий, вроде «Закрыть окно», или «Закрыть галерею», или «Закрыть рекламу».Если вы применяете решения сторонних разработчиков для оформления модальных окон, диалоговых окон и прочего подобного, пожалуйста, перед включением их в состав своего сайта, поинтересуйтесь тем, как именно реализованы эти решения. Не стоит слепо доверять другим в вопросах качества кода и обеспечения доступности контента.
Здесь можно найти примеры реализации удачных паттернов кнопок «Закрыть».
Как сделаны кнопки «Закрыть», которые используются в ваших проектах?
- Если у элемента
- Событие