Псевдоклассы CSS
В мире веб-разработки каскадные таблицы стилей (CSS) — это не просто инструмент для задания цветов и шрифтов. Это мощный язык, позволяющий создавать интерактивные, отзывчивые и логически структурированные интерфейсы. Одним из ключевых механизмов, раскрывающих всю мощь CSS, являются псевдоклассы. Если вы хотите выйти за рамки статичного дизайна и научиться тонкому управлению элементами в зависимости от их состояния, положения или действий пользователя, то понимание псевдоклассов — это обязательный шаг.
Псевдокласс — это специальное ключевое слово, добавляемое к селектору, которое определяет его особое состояние. Это состояние может зависеть от взаимодействия с пользователем (например, наведение курсора), от положения элемента в дереве документа (например, первый дочерний элемент) или от других параметров, которые невозможно выбрать с помощью простых селекторов классов или тегов. В этой статье мы детально разберем самые важные и полезные псевдоклассы, чтобы вы могли уверенно применять их в своих проектах.
Структурные псевдоклассы
Эти псевдоклассы позволяют выбирать элементы на основе их положения в структуре HTML-документа относительно родительских и соседних элементов. Они незаменимы для сложного форматирования списков, таблиц и сеток без необходимости добавлять лишние классы.
:root
Псевдокласс :root является одним из фундаментальных инструментов в арсенале современного верстальщика. Он обращается к корневому элементу документа, которым для HTML-страниц всегда является тег <html>. Однако его ключевое преимущество заключается в более высокой специфичности по сравнению с селектором html. Чаще всего :root используется для объявления глобальных CSS-переменных (кастомных свойств). Это позволяет централизованно хранить и легко управлять такими значениями, как цветовая палитра, размеры шрифтов, отступы и т.д., по всему проекту, что значительно упрощает поддержку кода и создание тем.
/* Аналогичен селектору html */
:root {
--main-color: #3498db;
}
.button {
background-color: var(--main-color);
}
:target
Этот динамический псевдокласс применяет стили к элементу, ID которого совпадает с фрагментом в URL-адресе страницы (часть после символа #). Когда пользователь переходит по ссылке с якорем (например, <a href="#section1">Раздел 1</a>), элемент с id="section1" автоматически становится "целевым" (:target). Это открывает огромные возможности для создания интерактивных виджетов, аккордеонов, модальных окон и подсветки разделов без использования JavaScript.
:first-child
Этот псевдокласс служит для точного выбора самого первого дочернего элемента внутри своего родительского контейнера. Его основная задача — обеспечить точечное изменение стилей именно у первенца в группе, что часто требуется для корректного визуального оформления. Например, с его помощью можно убрать верхний отступ у первого заголовка на странице, задать уникальные скругления углов у первой кнопки в навигационной панели или выделить первый элемент списка. Важно помнить, что :first-child сработает только в том случае, если выбранный вами элемент действительно является первым потомком своего родителя. Если перед ним находится любой другой элемент, селектор не применится.
.block {
background: blue;
}
.block:first-child {
background: red;
}
:last-child
Логический антипод :first-child, этот псевдокласс предназначен для стилизации самого последнего элемента в группе соседних элементов, имеющих общего родителя. Он невероятно полезен для решения распространённых верстных проблем. Типичные примеры: сброс нижнего отступа у последнего параграфа в текстовом блоке (решая проблему "лишнего" отступа), визуальное отделение последнего пункта в списке или задание уникального внешнего вида крайней правой кнопки в группе. Использование :last-child позволяет отказаться от назначения дополнительных классов (вроде .last), делая HTML-разметку чище, а CSS — более логичным и независимым.
.block {
background: blue;
}
.block:last-child {
background: red;
}
:first-of-type
Псевдокласс :first-of-type - в отличие от :first-child, который требует, чтобы элемент был именно первым ребёнком, :first-of-type действует более избирательно. Он выбирает первый элемент определённого типа (тега) среди всех своих соседей внутри родителя. Это критически важно в ситуациях, когда дочерние элементы имеют разнородную структуру. Представьте статью, где структура такова: <h1>, <p>, <img>, <p>, <blockquote>. В этом случае p:first-of-type выберет самый первый параграф (<p>), несмотря на то, что перед ним находится заголовок <h1>. Этот псевдокласс идеален для стилизации первой картинки в галерее, первого абзаца с буквицей или первого блока цитаты в тексте.
.block {
background: blue;
}
.block:first-of-type {
background: red;
}
:last-of-type
Этот псевдокласс расширяет логику :first-of-type на противоположный конец списка. :last-of-type находит самый последний элемент заданного типа среди своих соседей. Он незаменим, когда вам нужно стилизовать последний элемент определённого тега в контейнере, где присутствуют элементы других типов. Например, в подвале сайта (<footer>) могут располагаться ссылки, текст и иконки. С помощью a:last-of-type вы сможете точно выбрать самую последнюю ссылку, не беспокоясь о том, что после неё может идти обычный текст (<span>) или другой элемент. Это даёт точный контроль над финальными элементами конкретного типа в любой сложной структуре.
.block {
background: blue;
}
.block:last-of-type {
background: red;
}
:only-child
Псевдокласс :only-child применяет стили к элементу только в одном-единственном случае: если этот элемент является единственным потомком своего родителя. Он не сработает, если у родителя есть два и более дочерних элементов. Это узкоспециализированный, но очень полезный инструмент для стилизации "одиночек". Типичный пример — сообщение об ошибке или уведомление, которое динамически вставляется в пустой контейнер. Вы можете сделать это сообщение шире, центрировать его или задать ему особый вид, используя :only-child, так как вы уверены, что в этом состоянии в контейнере больше ничего нет.
.block {
background: blue;
}
.block:only-child {
background: red;
}
:only-of-type
Псевдокласс :only-of-type работает точечнее, чем :only-child. Он выбирает элемент только в том случае, если внутри его родителя нет других элементов этого же типа. Элемент может быть не единственным ребёнком (у родителя могут быть другие дочерние элементы с другими тегами), но он должен быть единственным с таким тегом. Например, если внутри <div> находятся один <button>, несколько <span> и <a>, то селектор button:only-of-type успешно применится к этой кнопке, потому что других <button> там нет. Это мощный инструмент для стилизации уникальных элементов в группе.
.block {
background: blue;
}
.block:only-of-type {
background: red;
}
:nth-child()
Псевдокласс :nth-child() - это один из самых мощных и гибких псевдоклассов в CSS. Он позволяет выбирать элементы на основе арифметической формулы, переданной в качестве аргумента. Вы можете использовать ключевые слова: even (чётные) и odd (нечётные) для создания эффекта "зебры" в таблицах и списках. Или же использовать формулу an + b, где a — период цикла, n — счётчик (начиная с 0), а b — смещение. Например: :nth-child(3n) выберет каждый третий элемент, :nth-child(2n+1) — все нечётные элементы, а :nth-child(5) — строго пятый элемент. Это открывает возможности для создания сложных паттернов в сетках и галереях.
.block {
background: blue;
}
.block:nth-child(2) {
background: red;
}
:nth-last-child()
Псевдокласс :nth-last-child() - зеркальное отражение :nth-child(). Он работает по абсолютно идентичной логике и принимает те же аргументы (even, odd, an+b), но ведёт отсчёт элементов не с начала, а с конца списка дочерних элементов. Это невероятно удобно, когда вам нужно стилизовать элементы, основываясь на их положении с конца. Например, :nth-last-child(1) — это последний элемент, :nth-last-child(2) — предпоследний, а :nth-last-child(2n) — каждый второй элемент, начиная с конца.
.block {
background: blue;
}
.block::nth-last-child(2) {
background: red;
}
:nth-of-type()
Псевдокласс :nth-of-type() - как и :first-of-type, этот псевдокласс сочетает в себе логику :nth-child() с фильтрацией по типу элемента. :nth-of-type() выбирает элементы, которые являются n-ными по счёту элементами своего типа внутри родителя. Это значит, что браузер сначала отфильтрует все дочерние элементы, оставив только те, что соответствуют селектору (например, только <p>), а затем применит к этой отфильтрованной группе формулу :nth-child(). Например, img:nth-of-type(3n) выберет каждую третью картинку в блоке, игнорируя все другие элементы.
.block {
background: blue;
}
.block:nth-of-type(2) {
background: red;
}
:nth-last-of-type()
Псевдокласс :nth-last-of-type() - завершает логическую четверку, объединяя подход :nth-last-child() с фильтрацией :of-type. :nth-last-of-type() выбирает элементы, которые являются n-ными по счёту элементами своего типа, но отсчёт ведёт с конца группы. Так, li:nth-last-of-type(2) выберет предпоследний элемент списка. Это узкоспециализированный, но незаменимый инструмент для сложных селекторов, где важна позиция элемента своего типа относительно конца контейнера.
.block {
background: blue;
}
.block:nth-last-of-type(2) {
background: red;
}
:not()
Функциональный псевдокласс-отрицания :not(), который кардинально расширяет возможности селекции. :not(X) позволяет выбрать все элементы, которые не соответствуют селектору X, указанному в скобках. Аргументом может быть любой простой селектор (тег, класс, ID, другой псевдокласс). :not() невероятно полезен для создания исключений. Вместо того чтобы описывать стили для всех элементов, а затем переопределять их для одного-двух, вы можете сразу исключить ненужные. Например, input:not([type="submit"]) применит стили ко всем полям ввода, кроме кнопок отправки формы.
/* В данном примере задаем свойства для всех элементов div, кроме элемента с классом .block */
div:not(.block) { }
:empty()
Псевдокласс :empty селектирует элементы, у которых нет дочерних элементов. Сюда входят текстовые узлы (включая пробелы и переносы строк), комментарии и другие DOM-узлы. Элемент считается пустым, если в нём буквально ничего нет. Этот псевдокласс крайне полезен для борьбы с "прыгающей" вёрсткой, которая возникает, когда динамически генерируемые элементы оказываются пустыми. Например, контейнер для уведомлений, который скрыт через display: none, можно полностью скрыть с помощью .notification:empty display: none;, чтобы он не занимал место в потоке документа.
.block {
background: blue;
}
.block:empty {
background: red;
}
Псевдоклассы состояний (взаимодействие с пользователем)
Эти псевдоклассы реагируют на действия пользователя, такие как наведение курсора, клик или фокусировка, делая интерфейс интерактивным и отзывчивым.
:hover
Псевдокласс :hover - самый известный и широко используемый псевдокласс для создания интерактивности. :hover активируется, когда пользователь наводит курсор мыши на элемент, но не активирует его (не зажимает кнопку мыши). Это основа для визуальной обратной связи в интерфейсе. С его помощью кнопки меняют цвет, ссылки подчёркиваются, в карточках появляются тени и плавно меняется прозрачность. Важно помнить о доступности: на тач-устройствах нет точного курсора, поэтому :hover может срабатывать при первом тапе и "залипать", что требует осторожного использования.
.block {
background: blue;
}
.block:hover {
background: red;
}
:active
Этот псевдокласс охватывает очень короткий, но важный момент взаимодействия — он применяется к элементу в тот самый момент, когда пользователь активирует его. Для мыши это период времени, когда кнопка мыши нажата, но ещё не отпущена над элементом. :active создаёт тактильное ощущение "нажатия" или "вдавливания" элемента. Часто его используют для визуального смещения кнопки вниз (transform: translateY(1px)) или изменения её фона на более тёмный оттенок. Это микро-взаимодействие, которое значительно улучшает восприятие интерфейса.
.block {
background: blue;
}
.block:active {
background: red;
}
:link
Специализированный псевдокласс, предназначенный исключительно для стилизации элементов <a> (ссылок), которые ещё не были посещены пользователем. Он применяется ко всем ссылкам, имеющим атрибут href, и которые отсутствуют в истории браузера. :link используется для задания базового вида ссылок, отличая их от обычного текста: обычно это синий цвет и подчёркивание. Важно понимать иерархию применения псевдоклассов ссылок для корректного оформления.
a:link {
color: red;
}
:visited
Этот псевдокласс стилизует элементы <a>, которые уже присутствуют в истории браузера пользователя, то есть по которым он уже переходил. Это визуальный маркер, помогающий пользователю ориентироваться на сайте. По соображениям конфиденциальности и безопасности браузеры строго ограничивают набор CSS-свойств, доступных для :visited. Разрешено изменять только цвета (color, background-color, border-color и т.д.). Изменять размеры, шрифты или позицию через :visited невозможно.
a:visited {
color: blue;
}
:focus
Псевдокласс :focus - краеугольный камень доступности (a11y) в веб-разработке. :focus применяется к элементу, когда тот получает фокус ввода. Это происходит при навигации с помощью клавиши Tab, при клике на интерактивный элемент (вроде <input> или <button>) или при активации через JavaScript. Стилизация :focus критически важна для пользователей, которые не используют мышь. Стандартный браузерный outline часто выглядит неэстетично, поэтому его принято заменять на кастомные стили, например, outline: 2px solid blue; outline-offset: 2px;. Никогда не удаляйте индикатор фокуса полностью, это сделает сайт недоступным.
input:focus {
border: 2px solid red;
}
Псевдоклассы состояний (формы и элементы ввода)
Специализированная группа псевдоклассов, которая упрощает валидацию и стилизацию элементов форм, делая их более удобными и понятными для пользователя.
:read-write
Псевдокласс :read-write - выбирает элементы, которые открыты для редактирования пользователем. Сюда относятся текстовые поля (<input>, <textarea>), не помеченные атрибутом readonly, а также любые элементы с атрибутом contenteditable="true".
input:read-write {
border: 2px solid red;
}
:read-only
Псевдокласс :read-only - выбирает все элементы, которые пользователь не может редактировать. Это не только поля ввода с атрибутом readonly, но и большинство неделимых элементов по умолчанию, такие как <p>, <div>, <span>.
input:read-only {
border: 2px solid red;
}
:optional
Псевдокласс :optional - выбирает все поля формы, которые не помечены как required. Это позволяет, к примеру, сделать визуально менее заметными те поля, которые не являются критически важными для заполнения.
input:optional {
border: 2px solid red;
}
:required
Псевдокласс :required - выбирает поля формы, у которых установлен атрибут required. Это указывает браузеру и пользователю, что поле должно быть заполнено для успешной отправки формы. Стилизация таких полей (например, красная звёздочка или особый цвет рамки) — хорошая практика юзабилити.
input:required {
border: 2px solid red;
}
:valid
Псевдокласс :valid - активируется, когда содержимое поля соответствует всем заданным ограничениям. Это может быть корректный email, URL, значение, подходящее под pattern, или число в заданном range. Зелёная галочка или рамка — типичный пример стилизации.
input:valid {
border: 2px solid red;
}
:invalid
Псевдокласс :invalid - применяется, когда поле содержит ошибку. Красная рамка или иконка крестика мгновенно дают пользователю понять, что нужно исправить. Важно отметить, что :invalid может срабатывать сразу при загрузке страницы для обязательных полей, поэтому иногда стилизацию применяют только после взаимодействия пользователя с полем.
input:invalid {
border: 2px solid red;
}
:enabled
Псевдокласс :enabled - выбирает все активные, доступные для взаимодействия элементы формы. Это состояние по умолчанию для большинства интерактивных элементов.
input:enabled {
border: 2px solid red;
}
:disabled
Псевдокласс :disabled - выбирает элементы с атрибутом disabled, которые заблокированы для редактирования и не могут получить фокус. Стилизация таких элементов (серый фон, блеклый текст, курсор not-allowed) ясно показывает пользователю, что действие в данный момент невозможно. Часто используется для отключения кнопки "Отправить" до тех пор, пока все обязательные поля не будут заполнены корректно.
input:disabled {
border: 2px solid red;
}
:default
Этот псевдокласс выбирает элемент формы, который является установленным по умолчанию в группе похожих элементов. Например, в группе радиокнопок (<input type="radio">) он выберет ту, которая имеет атрибут checked. Для чекбоксов — тот, который отмечен по умолчанию. Для кнопок отправки формы (<input type="submit">) — кнопку, которая считается основной (часто первую в форме). Это позволяет визуально выделить вариант, который будет выбран или активирован, если пользователь не внесёт своих изменений.
input {
width: 15px;
height: 15px;
}
input:default {
width: 25px;
height: 25px;
}
:checked
Псевдокласс :checked - применяется к переключателям (radio buttons), флажкам (checkboxes) и опциям выпадающего списка (<option>), когда они отмечены или выбраны. Это ключевой инструмент для создания кастомных, стилизованных чекбоксов и радиокнопок, которые сложно изменить стандартными средствами CSS. Техника обычно involves скрытия нативного элемента (opacity: 0 или display: none) и стилизации соседнего элемента (например, <label>) с помощью комбинатора + на основе состояния :checked. Также :checked используется для построения сложных интерактивных интерфейсов, которые меняют своё содержимое или внешний вид в зависимости от выбора пользователя, например, в фильтрах или настройках.
input {
width: 15px;
height: 15px;
}
input:checked {
width: 25px;
height: 25px;
}
Заключение
Псевдоклассы CSS — это не просто дополнительные фичи, а полноценная и мощная система управления состоянием и структурой вашего веб-интерфейса. От простого визуального отклика с помощью :hover до сложной логической селекции с :nth-child() и :not() — они дают в руки разработчика инструменты для создания современного, доступного и интуитивно понятного пользовательского опыта. Глубокое понимание и умелое применение этих псевдоклассов — признак профессионализма в области фронтенд-разработки.