HTML5 details и summary: аккордеон без JavaScript — практическое руководство
HTML5 <details> и <summary>: аккордеон без JavaScript — практическое руководство
Запрос «HTML5 details summary аккордеон без JavaScript» популярен у начинающих и практикующих верстальщиков, потому что эти элементы позволяют быстро сделать раскрывающиеся блоки (FAQ, спойлеры, разделы документации) без JS и с отличной поддержкой доступности. Ниже — пошаговое руководство, кодовые примеры и лучшие практики стилизации и UX.
Что такое <details> и <summary>
<details> — контейнер для скрытого по умолчанию контента. <summary> — заголовок, по нажатию на который блок раскрывается. Браузеры автоматически добавляют управление клавиатурой, роль и состояние для скринридеров, так что это по умолчанию доступное решение.
<details>
<summary>Что такое HTML5 Details?</summary>
<p>Это нативный способ делать сворачиваемые блоки без JavaScript.</p>
</details>
Чтобы показать блок раскрытым по умолчанию, используйте булев атрибут open:
<details open>
<summary>Открыто при загрузке</summary>
<p>Контент виден сразу.</p>
</details>
Пример: FAQ‑аккордеон без JS
Соберём секцию часто задаваемых вопросов на HTML5 details/summary и аккуратно её стилизуем. Добавим читаемый маркер, плавное раскрытие и фокус для клавиатуры.
<section class="faq">
<h2>FAQ: Аккордеон на HTML5</h2>
<details class="faq-item" open>
<summary>Как работает элемент <code>details</code>?</summary>
<div class="content">
<div class="content-inner">
<p>По клику на <summary> браузер сам скрывает/показывает контент и обновляет состояние для доступности.</p>
</div>
</div>
</details>
<details class="faq-item">
<summary>Можно ли стилизовать маркер?</summary>
<div class="content">
<div class="content-inner">
<p>Да. Скрываем стандартный маркер и рисуем свой через псевдоэлемент.</p>
</div>
</div>
</details>
<details class="faq-item">
<summary>Будет ли это решение доступным?</summary>
<div class="content">
<div class="content-inner">
<p>Да, элементы поддерживают клавиатуру и скринридеры из коробки.</p>
</div>
</div>
</details>
</section>
.faq { max-width: 720px; margin: 2rem auto; padding: 0 1rem; }
.faq-item { border: 1px solid #e5e7eb; border-radius: 12px; background: #fff; box-shadow: 0 1px 2px rgba(0,0,0,.04); }
.faq-item + .faq-item { margin-top: 12px; }
/* Сводим маркер к нулю и делаем кликабельную шапку */
.faq-item summary { list-style: none; cursor: pointer; display: flex; align-items: center; gap: .75rem; padding: 1rem 1.25rem; font-weight: 600; }
.faq-item summary::-webkit-details-marker { display: none; }
/* Кастомный индикатор раскрытия */
.faq-item summary::before { content: '▸'; display: inline-block; transition: transform .2s ease; color: #6b7280; }
.faq-item[open] summary::before { transform: rotate(90deg); }
/* Фокус и hover состояния */
.faq-item summary:hover { background: #f9fafb; }
.faq-item summary:focus-visible { outline: 3px solid #93c5fd; outline-offset: 2px; border-radius: 10px; }
/* Плавное раскрытие контента (CSS Grid trick) */
.faq-item .content { display: grid; grid-template-rows: 0fr; transition: grid-template-rows .25s ease; }
.faq-item[open] .content { grid-template-rows: 1fr; }
.faq-item .content-inner { overflow: hidden; }
.faq-item .content-inner { padding: 0 1.25rem 1rem; color: #374151; }
Трюк с grid-template-rows даёт плавное открытие/закрытие без JS. Внутренний контейнер .content-inner не даёт контенту «выпрыгнуть» во время анимации.
Доступность (a11y) и UX‑советы
- <summary> должен быть кратким и информативным — это интерактивный заголовок секции.
- Не вкладывайте в <summary> другие кнопки/ссылки: кликабельная область должна быть единой и предсказуемой.
- Не дублируйте aria-атрибуты (aria-expanded и т. п.) — браузер делает это сам.
- Заголовки h1–h6 нельзя помещать внутрь <summary> (они не относятся к «phrasing content»). Используйте жирный текст или подходящий стиль CSS, если нужен «вид» заголовка.
- Клавиатура: проверьте Tab/Enter/Space. Фокус-стиль делайте заметным (пример выше).
Продвинутая стилизация: тени, разделители, состояния
/* Разделитель между вопросом и ответом */
.faq-item[open] summary { border-bottom: 1px solid #f3f4f6; }
/* Состояние «открыт»: меняем цвет заголовка */
.faq-item[open] summary { color: #111827; }
/* Тёмная тема (пример) */
@media (prefers-color-scheme: dark) {
.faq-item { background: #111827; border-color: #1f2937; box-shadow: none; }
.faq-item summary { color: #e5e7eb; }
.faq-item .content-inner { color: #d1d5db; }
}
Частые ошибки и как их избежать
- Использование div+JS вместо нативных <details>: вы теряете доступность и усложняете код без причины.
- Забытый <summary>: без него блок не сворачивается и теряется смысл элемента.
- Иконка-маркер без индикатора состояния: обязательно показывайте «раскрыто/свернуто».
- Слишком длинный <summary>: сократите формулировки — это улучшит кликабельность и мобильный UX.
SEO: индексируется ли скрытый контент?
Да. По актуальным рекомендациям Google контент в раскрывающихся блоках (аккордеонах, вкладках) учитывается при мобильной индексации наравне с видимым, если он предназначен для удобства пользователя. Поэтому <details> подходит для FAQ, схем и длинных инструкций. Главное — не прятать «спам» и оставаться полезными.
Наследуемые и вложенные блоки
<details> можно вкладывать друг в друга, но делайте это умеренно, чтобы не запутать пользователей. Пример вложенного спойлера:
<details>
<summary>Продвинутый раздел</summary>
<p>Общее описание.</p>
<details>
<summary>Подраздел</summary>
<p>Детали для любопытных.</p>
</details>
</details>
Режим «только один пункт открыт» (необязательно)
Нативно <details> не умеет ограничивать одновременное раскрытие элементов. Если вам принципиально нужно поведение «аккордеон с одним открытым пунктом», добавьте небольшой JS (прогрессивное улучшение).
document.addEventListener('click', function(e) {
const summary = e.target.closest('summary');
if (!summary) return;
const current = summary.parentElement;
const container = current.closest('.faq');
if (!container) return;
container.querySelectorAll('details[open]').forEach(d => {
if (d !== current) d.removeAttribute('open');
});
});
Это улучшение не ломает базовую доступность: если JS отключён, элементы продолжают работать независимо друг от друга.
Практические рекомендации
- Для важных блоков оставляйте первый пункт открытым по умолчанию атрибутом
open— так повысите вовлечённость. - Тестируйте на мобильных: размер кликабельной области у <summary> должен быть не меньше 44×44 px по рекомендациям WCAG/Apple/Google.
- Подбирайте контраст для текста и иконок; добавляйте состояние :focus-visible и :hover.
- Следите, чтобы анимации были быстрыми (200–300 мс) и не мешали читабельности контента.
Где потренироваться и закрепить навыки
Хотите уверенно верстать такие блоки, собирать полноценные страницы и проекты? Посмотрите практический курс по вёрстке: Прокачать вёрстку на курсе «Вёрстка сайта с нуля 2.0» ↗ — много практики, разбор типовых паттернов и проверка домашних работ.
Итог
Элементы <details> и <summary> — простой, доступный и SEO‑дружественный способ сделать аккордеон без JavaScript. Используйте их для FAQ, спойлеров и документации, стилизуйте маркер, добавляйте аккуратную анимацию и помните о доступности. Такой подход снижает сложность кода и улучшает производительность интерфейса.
-
Создано 25.05.2026 17:01:19
-
Михаил Русаков

Комментарии (0):
Для добавления комментариев надо войти в систему.
Если Вы ещё не зарегистрированы на сайте, то сначала зарегистрируйтесь.