Up to date
This page is up to date for Godot 4.2
.
If you still find outdated information, please open an issue.
Використання Дерева анімації¶
Вступ¶
Завдяки AnimationPlayer анімаційна система Godot є одною з найбільш гнучких серед ігрових рушіїв. Можливість анімувати майже будь-яку властивість будь-якого вузла, або ресурсу, а також мати виділені перетворення, криві Безьє, виклики методів, аудіо- та під-анімаційні доріжки, є майже унікальною.
Однак підтримка змішування цих анімацій в AnimationPlayer
відносно обмежена, оскільки можна встановити лише фіксований час плавного переходу.
AnimationTree (Дерево анімацій) - це новий вузол, представлений в Godot 3.1 для розширення можливих переходів. Він витісняє древній AnimationTreePlayer
, додаючи при цьому величезну кількість функцій і гнучкість.
Створення Дерева Анімацій¶
Спочатку необхідно чітко зрозуміти, що вузол AnimationTree
не містить власних анімацій. Замість цього він використовує анімацію, що міститься в вузлі AnimationPlayer
. Таким чином, ви можете редагувати свої анімації (або імпортувати їх з 3D-сцени), як зазвичай, а потім використовувати цей додатковий вузол для управління відтворенням.
Найчастіше AnimationTree
використовують в 3D-сценах. Імпортовані сцени, як правило, поставляються із вбудованою анімацією (або кількома, або розділеною при імпорті одною великою). В кінці імпортована сцена Godot буде містити анімацію в вузлі AnimationPlayer
.
Оскільки ви нечасто використовуєте імпортовані сцени безпосередньо в Godot (вони або вставляються, як екземпляри, або успадковуються), ви можете розмістити вузол AnimationTree
у новій сцені, яка містить імпортовану. Після цього вкажіть вузлу AnimationTree
вузол AnimationPlayer
, що був створений в імпортованій сцені.
Ось як це зроблено в `демонстрації стрілялки від третьої особи<https://github.com/godotengine/tps-demo>`_:
A new scene was created for the player with a CharacterBody3D
as root. Inside this scene, the original .dae
(Collada) file was instantiated
and an AnimationTree
node was created.
Створення дерева¶
Існує три основних типи вузлів, які можна використовувати в AnimationTree
:
Animation nodes, which reference an animation from the linked
AnimationPlayer
.Анімаційні кореневі вузли, які використовуються для змішування під-вузлів.
Вузли анімації Blend, які використовуються в
AnimationNodeBlendTree
як один графік змішування з кількох вхідних портів.
Доступні кілька типів кореневих вузлів у AnimationTree
:
AnimationNodeAnimation
: Вибирає анімацію зі списку та відтворює її. Це найпростіший кореневий вузол, і, як правило, не використовується безпосередньо як корінь.AnimationNodeBlendTree
: Містить багато вузлів з типом змішування, таких як mix, blend2, blend3, one shot, тощо. Це один з найбільш часто використовуваних коренів.AnimationNodeStateMachine
: Містить кілька кореневих вузлів, як дочірніх, на графіку. Кожен вузол використовується як стан і надає кілька функцій для чергування між станами.AnimationNodeBlendSpace2D
: Дозволяє розміщувати кореневі вузли в просторі 2D змішування. Керуйте позицією накладання в 2D, щоб змішувати кілька анімацій.AnimationNodeBlendSpace1D
: Спрощена версія вищенаведеного (1D).
Дерево змішування¶
AnimationNodeBlendTree
може містити як кореневі, так і звичайні вузли, які використовуються для змішування. Вузли додаються до графіка з меню:
Всі дерева суміші за замовчуванням містять вузол Output
(Вивід), і до нього потрібно підключити щось, щоб анімація відтворювалася.
Найпростіший спосіб протестувати цю функціональність - підключити безпосередньо до нього вузол Animation
:
Це просто відтворить анімацію. Для того, щоб щось сталося AnimationTree
має бути активним.
Нижче наведено короткий опис доступних вузлів:
Бленд2 / Бленд3¶
Ці вузли будуть змішувати два, або три, входи за вказаним користувачем значенням змішування:
Для складнішого змішування рекомендується замість цього використовувати простір для змішування.
При змішуванні також можна використовувати фільтри, тобто ви можете індивідуально контролювати, які доріжки проходять через функцію змішування. Це дуже корисно для накладання анімацій одної на одну.
Одним махом¶
Цей вузол виконує допоміжну анімацію, а потім повертається до основної. Час сповільнення та прискорення змішування можна налаштувати, як і фільтри.
After setting the request and changing the animation playback, the one-shot node automatically clears the request on the next process frame by setting its request
value to AnimationNodeOneShot.ONE_SHOT_REQUEST_NONE
.
# Play child animation connected to "shot" port.
animation_tree.set("parameters/OneShot/request", AnimationNodeOneShot.ONE_SHOT_REQUEST_FIRE)
# Alternative syntax (same result as above).
animation_tree["parameters/OneShot/request"] = AnimationNodeOneShot.ONE_SHOT_REQUEST_FIRE
# Abort child animation connected to "shot" port.
animation_tree.set("parameters/OneShot/request", AnimationNodeOneShot.ONE_SHOT_REQUEST_ABORT)
# Alternative syntax (same result as above).
animation_tree["parameters/OneShot/request"] = AnimationNodeOneShot.ONE_SHOT_REQUEST_ABORT
# Get current state (read-only).
animation_tree.get("parameters/OneShot/active"))
# Alternative syntax (same result as above).
animation_tree["parameters/OneShot/active"]
// Play child animation connected to "shot" port.
animationTree.Set("parameters/OneShot/request", (int)AnimationNodeOneShot.OneShotRequest.Fire);
// Abort child animation connected to "shot" port.
animationTree.Set("parameters/OneShot/request", (int)AnimationNodeOneShot.OneShotRequest.Abort);
// Get current state (read-only).
animationTree.Get("parameters/OneShot/active");
TimeSeek¶
Цей вузол може бути використаний для команди пошуку будь-яких допоміжних нащадків з анімаційного графіка. Цей тип вузла використовується для відтворення Animation
з самого початку, або певної позиції, всередині AnimationNodeBlendTree
.
After setting the time and changing the animation playback, the seek node automatically goes into sleep mode on the next process frame by setting its seek_request
value to -1.0
.
# Play child animation from the start.
animation_tree.set("parameters/TimeSeek/seek_request", 0.0)
# Alternative syntax (same result as above).
animation_tree["parameters/TimeSeek/seek_request"] = 0.0
# Play child animation from 12 second timestamp.
animation_tree.set("parameters/TimeSeek/seek_request", 12.0)
# Alternative syntax (same result as above).
animation_tree["parameters/TimeSeek/seek_request"] = 12.0
// Play child animation from the start.
animationTree.Set("parameters/TimeSeek/seek_request", 0.0);
// Play child animation from 12 second timestamp.
animationTree.Set("parameters/TimeSeek/seek_request", 12.0);
ЧасоваШкала¶
Allows scaling the speed of the animation (or reverse it) connected to the in input via the scale parameter. Setting the scale to 0 will pause the animation.
Перехід¶
Very simple state machine (when you don't want to cope with a StateMachine
node). Animations can be connected to the outputs and transition times can be specified.
After setting the request and changing the animation playback, the transition node automatically clears the request on the next process frame by setting its transition_request
value to an empty string (""
).
# Play child animation connected to "state_2" port.
animation_tree.set("parameters/Transition/transition_request", "state_2")
# Alternative syntax (same result as above).
animation_tree["parameters/Transition/transition_request"] = "state_2"
# Get current state name (read-only).
animation_tree.get("parameters/Transition/current_state")
# Alternative syntax (same result as above).
animation_tree["parameters/Transition/current_state"]
# Get current state index (read-only).
animation_tree.get("parameters/Transition/current_index"))
# Alternative syntax (same result as above).
animation_tree["parameters/Transition/current_index"]
// Play child animation connected to "state_2" port.
animationTree.Set("parameters/Transition/transition_request", "state_2");
// Get current state name (read-only).
animationTree.Get("parameters/Transition/current_state");
// Get current state index (read-only).
animationTree.Get("parameters/Transition/current_index");
Blend Простір 2D¶
BlendSpace2D
— це вузол для розширеного змішування у двох вимірах. Точки додаються до двовимірного простору, а потім положення можна контролювати, щоб визначити накладання:
The ranges in X and Y can be controlled (and labeled for convenience). By default, points can be placed anywhere (right-click on the coordinate system or use the add point button) and triangles will be generated automatically using Delaunay.
Також можна намалювати трикутники вручну, відключивши опцію автоматичного трикутника, хоча це нечасто буває необхідним:
Нарешті, можна змінити режим змішування. За замовчуванням змішування відбувається шляхом інтерполяції точок всередині найближчого трикутника. Коли ви маєте справу з 2D-анімацією (кадр за кадром), ви можете перейти в дискретний режим. Крім того, якщо ви хочете зберегти поточну позицію відтворення під час перемикання між дискретними анімаціями, існує режим Carry. Цей режим можна змінити в меню Змішувати:
Blend Простір 1D¶
Це схоже на простори 2D-змішування, але в одному вимірі (тому трикутники не потрібні).
Машина стану¶
Цей вузол діє як машина станів з кореневими вузлами як станами. Кореневі вузли можуть створюватися і з'єднуватися по лініях. Стани з'єднуються через Переходи, які є з'єднаннями зі спеціальними властивостями. Переходи є однонаправленими, але два можуть бути використані для з'єднання в обох напрямках.
Є багато типів переходів:
Негайно: Негайний перехід до наступного стану. Поточний стан завершиться і почнеться новий.
Синхронізувати: Переключиться на наступний стан негайно, але буде шукати новий стан до позиції відтворення старого стану.
На кінець: Чекатиме завершення відтворення поточного стану, а потім переключиться на початок анімації наступної стану.
Переходи також мають кілька властивостей. Натисніть будь-який перехід, і вони будуть відображатися на панелі інспектора:
Switch Mode- це тип переходу (див. вище), його можна змінити після створення тут.
Auto Advance ввімкне автоматичний перехід, коли цей стан буде досягнуто. Найкраще працює з режимом перемикача На кінець.
Advance Condition ввімкне автоматичне просування вперед, коли буде встановлено цю умову. Це настроюване текстове поле, яке можна заповнити ім'ям змінної. Змінну можна змінити з коду (докладніше про це пізніше).
Xfade Time - це час, щоб переходу між цим станом і наступним.
Priority використовується разом з функцією
travel()
з коду (докладніше про це пізніше). Переходи з нижчим пріоритетом мають перевагу під час переходу по дереву.Disabled дозволяє відключити цей перехід (він не буде використовуватися під час переходів, чи автоматичного просування).
For better blending¶
In Godot 4.0+, in order for the blending results to be deterministic (reproducible and always consistent), the blended property values must have a specific initial value. For example, in the case of two animations to be blended, if one animation has a property track and the other does not, the blended animation is calculated as if the latter animation had a property track with the initial value.
When using Position/Rotation/Scale 3D tracks for Skeleton3D bones, the initial value is Bone Rest.
For other properties, the initial value is 0
and if the track is present in the RESET
animation,
the value of its first keyframe is used instead.
For example, the following AnimationPlayer has two animations, but one of them lacks a Property track for Position.
This means that the animation lacking that will treat those Positions as Vector2(0, 0)
.
This problem can be solved by adding a Property track for Position as an initial value to the RESET
animation.
Примітка
Be aware that the RESET
animation exists to define the default pose when loading an object originally.
It is assumed to have only one frame and is not expected to be played back using the timeline.
Also keep in mind that the Rotation 3D tracks and the Property tracks for 2D rotation with Interpolation Type set to Linear Angle or Cubic Angle will prevent rotation of more than 180 degrees from the initial value as blended animation.
This can be useful for Skeleton3Ds to prevent the bones penetrating the body when blending animations. Therefore, Skeleton3D's Bone Rest values should be as close to the midpoint of the movable range as possible. This means that for humanoid models, it is preferable to import them in a T-pose.
You can see that the shortest rotation path from Bone Rests is prioritized rather than the shortest rotation path between animations.
If you need to rotate Skeleton3D itself more than 180 degrees by blend animations for movement, you can use Root Motion.
Рух кореня¶
При роботі з 3D-анімацією популярна техніка полягає в тому, щоб аніматори використовували кореневу кістку скелета, щоб рухати увесь скелет. Це дозволяє анімувати персонажі таким чином, щоб кроки справді відповідали підлозі нижче. Це також дозволяє точно взаємодіяти з об'єктами під час кінематографії.
Під час відтворення анімації в Godot можна вибрати цю кістку як доріжку руху кореня. Це скасує візуальне перетворення кісток (анімація залишиться на місці).
Після цього фактичний рух можна отримати через API AnimationTree, як перетворення:
# Get the motion delta.
animation_tree.get_root_motion_position()
animation_tree.get_root_motion_rotation()
animation_tree.get_root_motion_scale()
# Get the actual blended value of the animation.
animation_tree.get_root_motion_position_accumulator()
animation_tree.get_root_motion_rotation_accumulator()
animation_tree.get_root_motion_scale_accumulator()
// Get the motion delta.
animationTree.GetRootMotionPosition();
animationTree.GetRootMotionRotation();
animationTree.GetRootMotionScale();
// Get the actual blended value of the animation.
animationTree.GetRootMotionPositionAccumulator();
animationTree.GetRootMotionRotationAccumulator();
animationTree.GetRootMotionScaleAccumulator();
This can be fed to functions such as CharacterBody3D.move_and_slide to control the character movement.
Існує також вузол інструменту RootMotionView
, який може бути розміщений на сцені і виступати в якості спеціальної підлоги для вашого персонажа та анімації (цей вузол за замовчуванням вимикається під час гри).
Контроль з коду¶
Після побудови дерева та його попереднього перегляду залишилося єдине питання: "Як все це контролюється з коду?".
Майте на увазі, що анімаційні вузли є лише ресурсами і, таким чином, вони поділяються між усіма екземплярами. Встановлення значень у вузлах безпосередньо вплине на всі екземпляри сцени, яка використовує це Дерево Анімації AnimationTree
. Загалом це не бажано, однак є деякі круті випадки для використання, наприклад, ви можете копіювати та вставляти частини дерева анімації, або повторно використовувати вузли зі складним макетом (наприклад, машина станів, або простір для змішування) у різних анімаційних деревах.
Фактичні дані анімації містяться в вузлі AnimationTree
і доступні за допомогою властивостей. Перевірте розділ вузла Parameters, щоб побачити всі параметри, які можна змінити в режимі реального часу:
Це зручно, тому що це дає можливість анімувати їх з``AnimationPlayer`` , або навіть самого AnimationTree
, що дозволяє реалізувати дуже складну логіку анімації.
Щоб змінити ці значення з коду, потрібно отримати шлях властивості. Для цього досить навести курсор мишки на будь-який з параметрів:
Маючи шлях можна встановлювати їх, або читати:
animation_tree.set("parameters/eye_blend/blend_amount", 1.0)
# Simpler alternative form:
animation_tree["parameters/eye_blend/blend_amount"] = 1.0
animationTree.Set("parameters/eye_blend/blend_amount", 1.0);
Переходи машини станів¶
One of the nice features in Godot's StateMachine
implementation is the ability to travel. The graph can be instructed to go from the
current state to another one, while visiting all the intermediate ones. This is done via the A* algorithm.
If there is no path of transitions starting at the current state and finishing at the destination state, the graph teleports to the destination state.
Щоб скористатися переходами, слід спочатку отримати об'єкт AnimationNodeStateMachinePlayback з вузла AnimationTree
(він експортується як властивість).
var state_machine = animation_tree["parameters/playback"]
AnimationNodeStateMachinePlayback stateMachine = (AnimationNodeStateMachinePlayback)animationTree.Get("parameters/playback");
Після отримання його можна використовувати, викликавши одну з багатьох функцій, які він пропонує:
state_machine.travel("SomeState")
stateMachine.Travel("SomeState");
Державна машина повинна спочатку запуститися перед відтворенням переходів. Обов'язково викличте start()
, або виберіть на вузлі Autoplay on Load.