Спойлер

Спойлером называется раскрытие интриги, влияющее на восприятие сюжета книги или фильма. В детективах, к примеру, спойлером является имя убийцы. Чтобы не портить удовольствие от предстоящего чтения или просмотра фильма текст спойлера прячут, оставляя возможность его просмотреть тем, кто хочет узнать подробности сюжета.

В HTML5 для создания спойлеров или информации, которую не следует сразу показывать, используется элемент <details>, внутри которого располагается заголовок <summary>. В исходном виде отображается только заголовок, по щелчку на который раскрывается и закрывается содержимое <details> (рис. 1).

Вид содержимого <details>

Рис. 1. Вид содержимого <details>

В примере 1 показано использование элемента <details> для создания спойлеров.

Пример 1. Спойлер, сделанный через <details>

<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>Спойлер</title> </head> <body> <details> <summary>Внимание, спойлер!</summary> <p>Убийца — дворецкий!</p> </details> </body> </html>

В браузерах IE и Edge элементы <summary> и <details> не работают, текст спойлера в них отображается сразу же. Поэтому для универсальности рассмотрим альтернативную реализацию через псевдокласс :checked.

Вместо <details> будем использовать элемент <div> с классом spoiler, заголовок сделаем через <label>, а содержимое спойлера опять же через <div> (пример 2). Для реализации функции открытия-закрытия добавим <input type="checkbox"> и свяжем его с <label> через атрибуты id и for.

Пример 2. Структура спойлера

<div class="spoiler">
  <input type="checkbox" id="spoiler1">
  <label for="spoiler1">Внимание, спойлер!</label>
  <div>Убийца — дворецкий!</div>
</div>

Сперва прячем <input> и текст спойлера через свойство display со значением none.

.spoiler input, .spoiler div  { 
  display: none; 
}

А затем показываем его через псевдокласс :checked с помощью всё того же свойства display.

.spoiler :checked ~ div {
  display: block;
}

Этого уже достаточно, чтобы при щелчке по <label> ниже расположенный <div> отображался и скрывался. Всё остальное это косметические детали для оформления. Добавим перед заголовком стрелку, как это реализовано в <summary>, через псевдоэлемент ::before и свойство content, значением которого будет символ стрелки, направленной вправо или вниз.

/* Закрытый спойлер */
.spoiler label::before {
  content: '►'; 
  margin-right: 5px;
}
/* Открытый спойлер */
.spoiler :checked + label::before {
  content: '▼';
}

Окончательный код продемонстрирован в примере 3.

Пример 3. Спойлер, сделанный через :checked

<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>Спойлер</title> <style> .spoiler input, .spoiler div { display: none; /* Скрываем содержимое */ } .spoiler label::before { content: '►'; /* Текст перед заголовком */ margin-right: 5px; /* Расстояние до текста */ } /* Открытый спойлер */ .spoiler :checked + label::before { content: '▼'; } .spoiler :checked ~ div { display: block; /* Показываем спойлер */ padding: 10px; /* Поля вокруг текста */ } </style> </head> <body> <div class="spoiler"> <input type="checkbox" id="spoiler1"> <label for="spoiler1">Внимание, спойлер!</label> <div>Убийца — дворецкий!</div> </div> </body> </html>

Результат данного примера в браузере Internet Explorer показан на рис. 2.

Вид спойлера

Рис. 2. Вид спойлера

Теперь наш спойлер работает во всех основных браузерах. К недостаткам метода следует отнести громоздкий код HTML — при добавлении нескольких спойлеров каждому <input> внутри spoiler надо давать уникальный id и это же значение затем писать в атрибуте for для <label>.

Автор: Влад Мержевич
Последнее изменение: 20.02.2024