CSS

CSS: анимации

📚 20 вопросовПройти тест →
Лекция

CSS: анимации

CSS

CSS: анимации

Введение: движение, которое объясняет интерфейс

Хорошая анимация в UI работает как жест руками в разговоре: не отвлекает, а помогает быстрее понять смысл.
Если элементы двигаются осознанно, пользователь сразу считывает, что произошло и что делать дальше.
Без анимаций интерфейс может казаться "мертвым", а без правил анимации - хаотичным и утомляющим.
Поэтому CSS-анимации важны не как украшение, а как инструмент понятного UX.
💡 Совет: Сначала определяйте смысл движения, потом подбирайте эффект.
Вывод: Анимация в CSS должна усиливать понятность, а не создавать шум.

Проблема -> решение

Проблема: Элементы появляются резко, пользователь не замечает изменения состояния, а бесконечные эффекты начинают раздражать.
Решение: Строить анимацию по правилам: сценарий через @keyframes, управляемые параметры animation-*, осознанные длительности и обязательный учет prefers-reduced-motion.
Вывод: Системная анимация снижает когнитивную нагрузку и делает интерфейс предсказуемым.

Чем помогает и как работает

CSS-анимации помогают:
  • показать причинно-следственную связь: "нажал -> изменилось";
  • подсветить важные изменения без агрессивного визуала;
  • снизить ощущение "подвисания" при загрузке;
  • сделать интерфейс целостным за счет единого ритма движения.
Как это работает:
  • Шаг 1: определяете пользовательский сценарий, где движение реально полезно.
  • Шаг 2: описываете ключевые кадры (@keyframes) или выбираете transition для простого перехода.
  • Шаг 3: задаете длительность и кривую скорости, чтобы движение было читабельным.
  • Шаг 4: ограничиваете повторы и избегаете бесконечной анимации без необходимости.
  • Шаг 5: проверяете влияние на UX: не мешает ли движение читать и выполнять действия.
  • Шаг 6: добавляете prefers-reduced-motion и fallback-поведение.
  • Шаг 7: фиксируете motion-правила в дизайн-системе команды.
Вывод: Анимация полезна только тогда, когда встроена в сценарий и контролируется правилами.

Ключевые термины (простыми словами)

  • Animation (анимация) - изменение CSS-свойств во времени по сценарию.
  • @keyframes (ключевые кадры) - этапы анимации от старта к финалу.
  • Duration (длительность) - сколько времени длится один цикл.
  • Delay (задержка) - пауза перед началом.
  • Timing function (кривая скорости) - как ускоряется и замедляется движение.
  • Iteration count (число повторов) - сколько раз проигрывается анимация.
  • Direction (направление) - в одну сторону или туда-обратно.
  • Fill mode (сохранение состояния) - что остается до/после анимации.
  • Play state (состояние проигрывания) - идет анимация или на паузе.
  • Reduced motion (уменьшение движения) - режим доступности для пользователей, которым тяжело от motion.

1. @keyframes - сценарий анимации

Назначение: Описать, как именно элемент меняется на разных этапах.
Простыми словами: Это "раскадровка" движения: от какого состояния к какому идет элемент.
Для новичка: Если не задать @keyframes, то CSS не понимает, какую последовательность менять.
Аналогия: Как сценарий фильма с ключевыми сценами.
Пример:
@keyframes pulse {  0% { transform: scale(1); opacity: 1; }  100% { transform: scale(1.06); opacity: 0.75; }}
🔎 Как это происходит на практике:
  • Команда решает, что бейдж "Новый" должен мягко привлекать внимание.
  • Дизайнер задает начальное и конечное состояние.
  • Разработчик переносит это в keyframes.
Характеристики:
  • ✅ позволяет строить сложный сценарий;
  • ✅ поддерживает промежуточные кадры 25/50/75%;
  • ✅ дает полный контроль над движением.
Когда использовать: Когда эффект нельзя выразить одним изменением состояния.
Вывод: @keyframes - фундамент любой осознанной CSS-анимации.

2. animation-name, animation-duration и шорткат animation

Назначение: Подключить сценарий к элементу и задать длительность.
Простыми словами: Вы "назначаете" элементу анимацию и говорите, как быстро ее проигрывать.
Для новичка: Без duration анимация может быть незаметной или выглядеть как резкий скачок.
Аналогия: Выбрали трек и установили его длину.
Пример:
.badge {  animation-name: pulse;  animation-duration: 800ms;} .loader {  animation: spin 1s linear infinite;}
🔎 Как это происходит на практике:
  • В UI-компоненте создают библиотечный класс .is-loading.
  • Через шорткат animation задают сценарий одним выражением.
  • Эффект переиспользуется в разных частях приложения.
Характеристики:
  • ✅ быстрое подключение keyframes;
  • ✅ шорткат сокращает код;
  • ✅ удобно стандартизировать длительности.
Когда использовать: Всегда при запуске keyframes-анимации на элементе.
Вывод: name + duration - обязательный минимум для управляемой анимации.

3. animation-timing-function - характер скорости

Назначение: Определить, как ощущается движение во времени.
Простыми словами: Можно сделать эффект ровным, мягким или более резким.
Для новичка: ease обычно безопаснее, чем linear, для интерфейсных микроэффектов.
Аналогия: Как разгон и торможение автомобиля: плавно или без амортизации.
Пример:
.card {  animation: fade-in 280ms ease-out;} .accent {  animation: pulse 700ms cubic-bezier(0.2, 0.8, 0.2, 1);}
🔎 Как это происходит на практике:
  • Дизайнер жалуется: "анимация слишком механическая".
  • Разработчик меняет linear на ease-out.
  • Эффект начинает восприниматься естественно.
Характеристики:
  • ✅ влияет на эмоциональное восприятие;
  • ✅ помогает согласовать motion-стиль бренда;
  • ✅ при плохом выборе кривая делает UI дерганым.
Когда использовать: Для всех анимаций, где важен "характер" движения.
Вывод: Одна и та же анимация с разной кривой ощущается как разные интерфейсы.

4. animation-delay и последовательности (stagger)

Назначение: Запускать элементы не одновременно, а в логичном порядке.
Простыми словами: Сначала появляется первый блок, потом второй, потом третий.
Для новичка: Небольшая задержка (50-150ms между элементами) часто делает появление чище.
Аналогия: Выход участников на сцену по очереди, а не всей толпой.
Пример:
.card {  animation: fade-in 300ms ease forwards;} .card:nth-child(2) { animation-delay: 80ms; }.card:nth-child(3) { animation-delay: 160ms; }
🔎 Как это происходит на практике:
  • Каталог курсов рендерит 12 карточек.
  • Без stagger интерфейс "вспыхивает" сразу.
  • С задержками пользователь легче считывает структуру.
Характеристики:
  • ✅ улучшает визуальный ритм;
  • ✅ помогает иерархии контента;
  • ✅ в избытке может замедлять UX.
Когда использовать: При поочередном появлении списков, меню, карточек.
Вывод: Delay полезен, когда помогает чтению интерфейса, а не тормозит его.

5. Повторы и управление: animation-iteration-count, direction, play-state

Назначение: Контролировать количество циклов, направление и паузу анимации.
Простыми словами: Можно крутить бесконечно, ограничить в 3 раза или поставить на паузу при hover.
Для новичка: Если эффект не про загрузку, бесконечный цикл чаще вреден.
Аналогия: Музыка: можно повторять трек один раз, по кругу или ставить на паузу.
Пример:
.hint {  animation: pulse 700ms ease-in-out 3 alternate;} .hint:hover {  animation-play-state: paused;}
🔎 Как это происходит на практике:
  • Подсказка должна привлечь внимание и успокоиться.
  • Команда ставит 3 повтора вместо infinite.
  • На hover эффект ставится на паузу, чтобы прочитать текст.
Характеристики:
  • ✅ точный контроль жизненного цикла эффекта;
  • ✅ меньше раздражения от постоянного движения;
  • ✅ помогает управлять вниманием пользователя.
Когда использовать: Для подсказок, бейджей, акцентных индикаторов и hover-пауз.
Вывод: Управление циклами и паузой критично для "здорового" motion.

6. animation-fill-mode - что остается после проигрывания

Назначение: Сохранить начальное или конечное состояние после анимации.
Простыми словами: Элемент может "остаться в финале", а не прыгнуть обратно.
Для новичка: Для анимации появления часто нужен forwards.
Аналогия: Финальный кадр презентации остается на экране.
Пример:
@keyframes fade-in {  from { opacity: 0; transform: translateY(8px); }  to { opacity: 1; transform: translateY(0); }} .card--enter {  animation: fade-in 300ms ease forwards;}
🔎 Как это происходит на практике:
  • Карточка курса появляется при фильтрации.
  • Без forwards элемент может визуально "откатиться".
  • С fill-mode финальное состояние фиксируется.
Характеристики:
  • ✅ устраняет визуальные скачки после анимации;
  • ✅ полезен для enter/exit сценариев;
  • ✅ снижает количество дополнительных стилей.
Когда использовать: Когда финальное состояние должно сохраниться после проигрывания.
Вывод: fill-mode управляет "послевкусием" анимации и стабилизирует UI.

7. Производительность: что анимировать безопаснее

Назначение: Снизить риск подтормаживаний и "тяжелых" эффектов.
Простыми словами: Лучше анимировать transform и opacity, а не свойства, которые сильно пересчитывают layout.
Для новичка: Если анимация начинает лагать, сначала проверьте, какие свойства меняются.
Аналогия: Легче двигать предметы на колесиках, чем перестраивать весь шкаф.
Пример:
.item {  transition: transform 200ms ease, opacity 200ms ease;} .item:hover {  transform: translateY(-4px);  opacity: 0.95;}
🔎 Как это происходит на практике:
  • На странице 50 карточек, и hover тормозит.
  • Команда убирает анимацию ширины/позиционирования.
  • После перехода на transform/opacity интерфейс работает плавнее.
Характеристики:
  • ✅ лучше масштабируется на длинных списках;
  • ✅ меньше визуальных артефактов;
  • ✅ проще поддерживать единый motion-стандарт.
Когда использовать: Всегда, когда нужно анимировать много элементов или сложные списки.
Вывод: Правильный выбор анимируемых свойств важнее, чем "красивый" эффект.

8. Доступность: prefers-reduced-motion как обязательный стандарт

Назначение: Уважать настройки пользователей, которым тяжело от движения.
Простыми словами: Если человек просит меньше движения, интерфейс должен это учитывать.
Для новичка: Reduced-motion - не опция "по желанию", а базовый слой доступности.
Аналогия: Как приглушить свет в комнате, если яркость вызывает дискомфорт.
Пример:
@media (prefers-reduced-motion: reduce) {  .loader,  .badge,  .card--enter {    animation: none !important;    transition: none !important;  }}
🔎 Как это происходит на практике:
  • QA включает reduced-motion в системе.
  • Команда проверяет, что пульсации и вращения отключаются.
  • Интерфейс остается функциональным без движения.
Характеристики:
  • ✅ улучшает комфорт и доступность;
  • ✅ снижает риск негативной реакции на motion;
  • ✅ показывает зрелость продукта.
Когда использовать: В любом проекте, где есть анимации и переходы.
Вывод: Хорошая анимация всегда учитывает сценарий "без анимации".

Must-know факты (часто спрашивают и часто путают)

  • Без @keyframes CSS-анимация не знает сценарий движения.
  • animation и transition решают разные задачи: сценарий vs переход состояния.
  • transition: all часто ухудшает предсказуемость и производительность.
  • Бесконечная анимация допустима в основном для загрузчиков и системных индикаторов.
  • forwards в fill-mode нужен, когда финальное состояние должно сохраниться.
  • Motion нужно тестировать вместе с keyboard/focus сценариями.
  • prefers-reduced-motion - обязательная часть доступности.
  • Если движение не помогает понять действие, его лучше убрать.
Вывод: Эти восемь правил закрывают большинство практических ошибок по CSS-анимации.

Сравнение: transition vs animation

ПодходКогда использоватьПлюсыРиск
transitionПростая смена состояния (hover/focus)Легко внедрить, мало кодаСложные сценарии трудно описать
animation + @keyframesСценарное движение с этапамиГибкость и контрольЛегко переусложнить
Бесконечная анимацияЗагрузка/статус процессаЯсный сигнал "идет работа"Раздражение, если использовать везде
Reduced-motion fallbackЛюбой motion в продуктеДоступность и комфортБез проверки может быть нерабочим

Часто спрашивают на собеседованиях

  1. Когда выбрать transition, а когда @keyframes?
  2. Почему transition: all считают плохой практикой?
  3. Какие свойства безопаснее анимировать и почему?
  4. Зачем нужен animation-fill-mode: forwards?
  5. Когда допустима бесконечная анимация в UI?
  6. Как правильно внедрять prefers-reduced-motion?
  7. Какие типовые ошибки чаще всего встречаются в motion-дизайне на фронте?
Вывод: На собеседованиях обычно проверяют связь анимации с UX, производительностью и доступностью.

Типичные ошибки

Ошибка 1: Анимация без цели

Неправильно: Добавлять движение "просто чтобы красиво".
Правильно: Анимировать только те изменения, которые помогают понять состояние.
Почему: Лишний motion отвлекает и ухудшает читаемость интерфейса.

Ошибка 2: transition: all

Неправильно: Анимировать все свойства подряд.
Правильно: Явно указывать целевые свойства (transform, opacity).
Почему: all создает непредсказуемое и часто тяжелое поведение.

Ошибка 3: Бесконечная пульсация всего экрана

Неправильно: Ставить infinite на обычные карточки и кнопки.
Правильно: Ограничивать количество повторов или включать цикл только в загрузчиках.
Почему: Постоянное движение быстро раздражает пользователя.

Ошибка 4: Нет prefers-reduced-motion

Неправильно: Всегда проигрывать анимации независимо от системных настроек.
Правильно: Отключать или упрощать motion в режиме reduce.
Почему: Это важный стандарт доступности.

Ошибка 5: Резкие длительности и кривые

Неправильно: Слишком быстрые или дерганые эффекты без теста UX.
Правильно: Использовать умеренные duration и согласованные timing-function.
Почему: Характер движения напрямую влияет на восприятие качества продукта.

Ошибка 6: Забыт fill-mode при enter-анимации

Неправильно: Элемент появляется и "откатывается" обратно.
Правильно: Для сценариев появления использовать forwards или both.
Почему: Иначе финальное состояние не фиксируется и UI выглядит сломанным.

Best Practices

  • Держите motion-гайд: длительности, кривые, допустимые эффекты.
  • Для микроинтеракций начинайте с transform и opacity.
  • Используйте анимацию как объяснение состояния, а не украшение ради украшения.
  • Проверяйте сценарии reduced-motion в каждом релизе.
  • Ограничивайте бесконечные эффекты только функциональными индикаторами.
  • Если эффект сложно объяснить, вероятно он не нужен.

Заключение

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

Ключевые мысли

  • Анимация должна объяснять, а не отвлекать.
  • @keyframes и animation-* дают полный контроль над сценарием.
  • Доступность и производительность обязательны для любого motion-решения.
🎯

Проверьте знания

Закрепите материал — пройдите тест по теме «CSS: анимации»

Пройти тест →