Настройка триггеров запуска анимации в коде игр
Animator.SetTrigger — один из самых частых источников трудноуловимых анимационных багов. Тот самый сценарий: персонаж атакует, вы вызываете SetTrigger("Attack"), но анимация не воспроизводится. Или воспроизводится с кадровой задержкой. Или запускается дважды подряд. И всё это потому, что trigger в Animator Controller имеет специфическое поведение: если его некому «потребить» в текущем кадре, он остаётся в очереди и выстреливает в следующем состоянии — там, где вы его уже не ждёте.
Это не баг Unity, это архитектурное решение. Но оно требует понимания, иначе Animator State Machine превращается в источник непредсказуемого поведения.
Почему SetTrigger ломается в типичных сценариях
Trigger + Any State переход. Если у вас есть Any State → Attack с Trigger "Attack", и персонаж находится в состоянии Stunned, которое также имеет Any State → Stunned с более высоким приоритетом — SetTrigger("Attack") будет потреблён переходом в Stunned, если оба триггера выставлены в один кадр. Порядок приоритетов переходов из Any State критичен и часто не документируется в проекте.
ResetTrigger в неправильный момент. Если код вызывает animator.ResetTrigger("Attack") в OnStateEnter атакующего состояния «для надёжности» — вы гарантированно теряете повторный запрос на атаку, если игрок успел нажать кнопку во время анимации. Правильное место сброса — конец анимации через StateMachineBehaviour.OnStateExit.
Animator не активен или culled. Если Animator.cullingMode = AlwaysAnimate отключён и объект вышел за пределы Camera Frustum — Animator перестаёт обновляться. SetTrigger не теряется, но применяется с задержкой при возвращении в frustum. Для персонажей за краем экрана, которые должны реагировать на игрока — это неожиданное поведение.
Правильные паттерны запуска анимаций
Bool вместо Trigger для длительных состояний. Стрельба, бег, прицеливание — не Trigger, а Bool. SetBool("IsRunning", true/false) даёт предсказуемое поведение и не теряется при смене состояния. Trigger используем только для одноразовых импульсных событий: прыжок, удар, смерть.
Integer-параметры для комбо. Если у персонажа есть цепочка атак, ComboIndex: int — надёжнее набора триггеров Attack1/Attack2/Attack3. Переход проверяет ComboIndex == 1, ComboIndex == 2. Код инкрементирует счётчик и сбрасывает по таймауту. Это устраняет целый класс проблем с «потерянными» триггерами.
Animation Events для синхронизации геймплея. Запуск хитбокса, звука удара, спавна снаряда — через Animation Event, а не через coroutine с таймером. Animation Event гарантирует привязку к конкретному кадру анимации независимо от скорости воспроизведения. Если вы умножаете animator.speed для slow-motion — событие всё равно сработает в правильный кадр.
Реальный кейс: файтинг, 6 персонажей, у каждого по 3–5 атак с разными хитбоксами. Первоначальная реализация через SetTrigger + coroutine-таймеры для хитбоксов. Проблема: при изменении скорости анимации (через animator.speed) хитбокс активировался в неправильный момент — раньше или позже удара. Переход на Animation Events + StateMachineBehaviour для активации/деактивации хитбоксов полностью устранил рассинхронизацию. Бонус: стало возможным легко настраивать тайминг хитбоксов через Animation Window без правки кода.
Animator vs Playables API
Для сложных сценариев — кат-сцены, процедурные анимации, динамический blend — Unity Playables API даёт больше контроля, чем Animator State Machine. AnimationMixerPlayable позволяет микшировать несколько анимаций с явными весами в коде. AnimatorControllerPlayable позволяет использовать существующий Animator Controller внутри Playables графа.
Это не значит, что нужно переписывать всё под Playables. Но для системы кат-сцен или кастомного IK-решения — Playables API правильнее, чем попытки сломать Animator State Machine.
Инструменты диагностики
Animator Window в Play Mode — базовый инструмент. Показывает текущее состояние, активные переходы, значения параметров в реальном времени. Включаем через Window → Animation → Animator.
Profiler → Animation module — показывает, сколько CPU времени тратит Animator на обновление. Если Animation Evaluation > 3 мс с 10 персонажами — проблема в архитектуре: слишком сложные State Machine, слишком много Layers с full-body масками.
Frame Debugger — для проверки, что анимация применяется в правильный кадр рендера.
Процесс настройки системы анимационных триггеров
Аудит существующей State Machine: количество состояний, переходов, параметров, Layers. Документирование логики переходов (часто её нет — только в голове разработчика). Выявление проблемных мест через Play Mode тестирование с включённым Animator Window.
Разработка спецификации: какие параметры, какие типы (Trigger/Bool/Int/Float), кто и когда их устанавливает, где сбрасывает. Это предотвращает конфликты между разными системами (AI, Input, Network).
| Масштаб задачи | Ориентировочные сроки |
|---|---|
| Отладка конкретной анимационной проблемы | 1–3 дня |
| Настройка системы триггеров для одного персонажа | 3–7 дней |
| Разработка архитектуры анимаций для всей игры | 2–5 недель |
Стоимость определяется после анализа сложности персонажей и требований к анимационной системе.





