
Кнопка или ссылка: как проверить семантику действия и перехода на странице


На карточке товара часто смешивают две разные задачи: открыть страницу с подробностями и выполнить действие прямо здесь же, например добавить товар в избранное. Из-за этого вся карточка превращается в ссылку, внутрь нее кладут иконку-сердце, а потом пытаются «починить» поведение JavaScript. Проверять такую разметку лучше не с дизайна, а с вопроса: пользователь переходит на другой адрес или меняет состояние текущей страницы?
Если нужен переход к подробностям, подойдет ссылка с href. Если нужно действие без перехода, подойдет button type="button". Дальше остается проверить две вещи: как элементы ведут себя с клавиатуры и есть ли у каждого понятное доступное имя. На этом уровне ошибка видна быстро, еще до аудита и тестирования ассистивными технологиями.
Действие и переход — это разные задачи
Семантика здесь определяется не внешним видом, а результатом нажатия. Если после активации пользователь должен попасть на страницу товара, это переход, значит нужен элемент a с адресом в href. Если после активации товар остается на месте, а страница только меняет состояние интерфейса, например помечает карточку как избранную, это действие, и его лучше отдавать кнопке.
Такой выбор полезен не только для читаемости кода. У ссылки и кнопки разное встроенное поведение: браузер по-разному включает их в навигацию, по-разному запускает их с клавиатуры и по-разному сообщает их роль вспомогательным технологиям. Когда переход маскируют под кнопку или действие маскируют под ссылку, разработчик берет на себя лишнюю работу по имитации того, что браузер уже умеет сам.
| Задача на карточке | Элемент | Что проверять |
|---|---|---|
| Открыть страницу товара | a href | Есть адрес, активация ведет на другую страницу |
| Добавить в избранное | button type="button" | Состояние меняется без перехода и без отправки формы |
Как разметить карточку товара без конфликта элементов
Здесь легко допустить структурную ошибку: сделать всю карточку ссылкой, а кнопку «в избранное» вложить внутрь. По спецификации и ссылка с href, и кнопка относятся к интерактивным элементам, а интерактивные элементы нельзя вкладывать друг в друга. Поэтому безопаснее разделить области: отдельная ссылка для контента карточки и отдельная кнопка рядом с ней.
Учебный пример. Среда — обычная HTML-страница без фреймворка. Есть карточка товара с названием, кратким описанием и действием «Добавить в избранное». Переход к подробностям должен вести на /products/trail-runner, а избранное должно переключаться прямо на странице.
<article class="product-card">
<a class="product-card__link" href="/products/trail-runner">
<h3>Кроссовки Trail Runner</h3>
<p>Легкая модель для прогулок по городу и парку</p>
</a>
<button class="product-card__favorite" type="button">
Добавить в избранное
</button>
</article>Если нужно показать работу действия, достаточно простого обработчика. Он не меняет адрес страницы и не отправляет форму, а только переключает текст кнопки. Для учебной проверки этого достаточно: мы видим разницу между переходом и действием не по теории, а по фактическому поведению.
const favoriteButton = document.querySelector('.product-card__favorite');
favoriteButton.addEventListener('click', () => {
const active = favoriteButton.dataset.active === 'true';
favoriteButton.dataset.active = String(!active);
favoriteButton.textContent = active
? 'Добавить в избранное'
: 'Убрать из избранного';
});Проверка клавиатурой: что должно происходить
Проверка клавиатурой полезна тем, что быстро показывает семантические подмены. Откройте страницу, уберите мышь и нажимайте Tab. В корректной карточке фокус должен дойти до ссылки на товар и до кнопки избранного как до двух самостоятельных элементов. Если фокус попадает только на один странный контейнер или вообще пропускает нужное действие, разметка уже подозрительна.
Дальше проверяется активация. На ссылке ожидаемо работает переход к новому адресу. На кнопке ожидаемо происходит действие на месте: меняется состояние, текст, значок, счетчик, но не открывается новая страница. Если при нажатии на «избранное» внезапно происходит переход, значит действие, скорее всего, оказалось внутри ссылки или клик всплывает не туда. Если при нажатии кнопки страница перезагружается, часто виноват отсутствующий type="button".
В учебном примере ожидаемый результат такой: первым Tab фокус получает ссылка «Кроссовки Trail Runner», следующим — кнопка «Добавить в избранное». Активация ссылки ведет на /products/trail-runner. Активация кнопки меняет ее текст на «Убрать из избранного» и оставляет пользователя на той же странице. Это уже проверяемый результат, а не просто рассуждение о семантике.
Проверка доступного имени: понятно ли назначение без догадок
Даже если элемент выбран правильно, он может быть непонятен по названию. Для учебной проверки доступного имени достаточно задать простой вопрос: можно ли по самому элементу понять, что он делает или куда ведет? У ссылки обычно таким именем становится ее текст. У кнопки — тоже текст кнопки. Поэтому вариант «Добавить в избранное» лучше, чем одинокая иконка без текстового обозначения.
На списках товаров особенно полезно проверять имена в отрыве от дизайна. Если ссылка называется только «Подробнее», спросите себя, будет ли понятна ее цель, когда на странице много одинаковых карточек. Если кнопка меняет состояние, полезно проверить и обновление имени: после добавления в избранное элемент должен сообщать уже новое понятное действие, например «Убрать из избранного», а не оставаться с прежней надписью.
- У ссылки есть текст, который описывает цель перехода.
- У кнопки есть текст, который описывает действие.
- Если на экране только иконка, у элемента все равно должно быть текстовое имя для проверки доступности.
- После изменения состояния имя кнопки не противоречит текущему состоянию.
Практический смысл у этой проверки простой: вы снижаете риск интерфейса, который выглядит аккуратно, но ведет себя неясно для пользователей клавиатуры и ассистивных технологий. Исправить название элемента на раннем этапе намного дешевле, чем потом перепроектировать карточки целиком.
Ошибки семантики и поведения по умолчанию
Самые частые ошибки повторяются из проекта в проект. Первая — ссылка без href для действия. Такая разметка не дает настоящий переход и превращает элемент в заглушку, а разработчик потом добавляет поведение скриптом. Вторая — кнопка без указанного типа. Если карточка неожиданно оказывается внутри формы, кнопка без type может начать отправлять форму по умолчанию. Третья — вложение кнопки в ссылку или ссылки в кнопку: визуально это может выглядеть удобно, но структурно конфликтует с правилами интерактивных элементов.
Отдельно стоит избегать имитации кнопки через произвольный div с обработчиком клика. Такой элемент приходится вручную делать фокусируемым, отдельно обучать клавиатуре и отдельно подписывать для доступности. Для простой карточки товара это лишняя сложность без выигрыша. Намного надежнее начать с нативного элемента и проверить его реальное поведение.
Итоговая короткая проверка выглядит так: переходы размечены ссылками с href; действия — кнопками с type="button"; фокус с клавиатуры доходит до обоих элементов; ссылка ведет по адресу, кнопка меняет состояние на месте; название каждого элемента понятно без догадок. Если все пять пунктов сходятся, семантика карточки, скорее всего, выбрана правильно.
Если хотите отдельно потренировать такие решения, в сохраненном описании каталога курса по верстке упомянуты блоки по HTML и CSS, Advanced HTML и доступности. Это полезное сочетание именно для задач, где нужно не только собрать карточку, но и проверить семантику и поведение элементов.





















