Conversation
There was a problem hiding this comment.
Pull request overview
Adds animation blending and root motion support to TombEngine’s animation, item, and renderer pipelines, including new curve math utilities and updated level serialization for the extra animation data.
Changes:
- Introduces per-animation blend settings (frame count + Bezier curve) and per-item runtime blend state used by the renderer.
- Implements root motion extraction/counteraction and applies it across rendering transforms and various gameplay queries/bounds.
- Replaces legacy “keyframe interpolation” access patterns with direct
Frames[...]/GetFrame(...)usage and renames/reshapes related structs/constants.
Reviewed changes
Copilot reviewed 48 out of 49 changed files in this pull request and generated 9 comments.
Show a summary per file
| File | Description |
|---|---|
| TombEngine/TombEngine.vcxproj | Adds BezierCurve2 sources to the build. |
| TombEngine/Specific/level.cpp | Reads new animation data (blend curves, fixed motion curves, per-frame root position). |
| TombEngine/Scripting/Internal/TEN/Objects/Moveable/MoveableObject.h | Extends Lua API to allow specifying blend frames when setting animation. |
| TombEngine/Scripting/Internal/TEN/Objects/Moveable/MoveableObject.cpp | Wires scripting animation changes to new blending-aware SetAnimation. |
| TombEngine/Scripting/Internal/TEN/Objects/Lara/LaraObject.cpp | Minor cleanup to TestLaraPosition call. |
| TombEngine/Renderer/Structures/RendererMirror.h | Formatting/whitespace normalization. |
| TombEngine/Renderer/Structures/RendererItem.h | Renames bone arrays and interpolation buffers to new constants/names. |
| TombEngine/Renderer/RendererLara.cpp | Applies root motion counteraction to Lara world matrix and updates animation update calls for new frame/blend path. |
| TombEngine/Renderer/RendererHelper.cpp | Updates animation evaluation to use FrameData + optional blend data. |
| TombEngine/Renderer/RendererFrame.cpp | Applies root motion counteraction to renderer item transforms and updates interpolation buffer handling. |
| TombEngine/Renderer/RendererEnums.h | Renames MAX_BONES/MAX_BONE_WEIGHTS to BONE_COUNT_MAX/BONE_WEIGHT_COUNT_MAX. |
| TombEngine/Renderer/RendererDrawMenu.cpp | Updates preview animation path to use Frames rather than keyframe interpolation data. |
| TombEngine/Renderer/RendererDrawEffect.cpp | Updates effect attachment/root offsets to new Frames/RootPosition fields and renamed bone buffers. |
| TombEngine/Renderer/RendererDraw.cpp | Updates skinning transforms/bone loops to new bone constants and renamed buffers. |
| TombEngine/Renderer/Renderer.h | Updates UpdateAnimation signature to new frame/blend types. |
| TombEngine/Renderer/ConstantBuffers/ItemBuffer.h | Updates constant buffer arrays to use BONE_COUNT_MAX. |
| TombEngine/Objects/Utils/object_helper.cpp | Uses new Frames container for “has > 1 frame” checks. |
| TombEngine/Objects/TR5/Entity/tr5_guard.cpp | Updates bounds query to GetFrame. |
| TombEngine/Objects/TR4/Trap/tr4_teethspike.cpp | Updates bounds query to GetFrame. |
| TombEngine/Objects/TR4/Trap/tr4_joby_spikes.cpp | Refactors flag locals and switches player height calc to OBB-based approach. |
| TombEngine/Objects/TR2/Entity/tr2_mercenary.cpp | Minor comment formatting for deterministic shooting rate logic. |
| TombEngine/Objects/Generic/Object/rope.cpp | Updates root offset access to GetFrame(...).RootPosition. |
| TombEngine/Objects/Generic/Object/Pushable/PushableStates.cpp | Updates last-frame bounds query helper. |
| TombEngine/Objects/Generic/Object/Pushable/PushableCollision.cpp | Updates root offset access to GetFrame(...).RootPosition. |
| TombEngine/Objects/Generic/Object/BridgeObject.cpp | Updates local AABB access to Frames[].LocalAabb. |
| TombEngine/Math/Objects/GameBoundingBox.cpp | Switches to GetFrame and applies root-motion counteraction translation in deprecated ctor. |
| TombEngine/Math/Objects/BezierCurve2.h | Adds new 2D Bezier curve utility type used for blending and fixed motion. |
| TombEngine/Math/Objects/BezierCurve2.cpp | Implements Bezier curve presets + evaluation (GetY via Newton-Raphson). |
| TombEngine/Math/Math.h | Exposes BezierCurve2 through the umbrella math header. |
| TombEngine/Game/pickup/pickup.cpp | Updates plinth bounds queries to Frames[...] and leaves a commented-out debug return. |
| TombEngine/Game/people.cpp | Updates target bounds queries to GetFrame. |
| TombEngine/Game/items.h | Renames/reshapes ItemInfo sub-structs; adds blending state + helpers; pulls in renderer bone constants. |
| TombEngine/Game/items.cpp | Implements blending state capture (SetAnimBlend/DisableAnimBlend) and updates OBB calculation. |
| TombEngine/Game/effects/tomb4fx.cpp | Updates bounds query to GetFrame. |
| TombEngine/Game/effects/hair.cpp | Updates bounds query to Frames[...] / GetFrame. |
| TombEngine/Game/control/box.cpp | Updates various bounds/frame queries to Frames/GetFrame. |
| TombEngine/Game/collision/collide_room.cpp | Updates collision AABB bounds query to GetFrame. |
| TombEngine/Game/collision/collide_item.cpp | Updates collision bounds queries to GetFrame/Frames[...] and formatting. |
| TombEngine/Game/Lara/lara_initialise.cpp | Renames EntityAnimationData to MoveableAnimData in backup globals/copy. |
| TombEngine/Game/Lara/lara_helpers.cpp | Updates many SetAnimation calls to include blend parameters/curves. |
| TombEngine/Game/Lara/lara_flare.cpp | Refactors flare object/anim assignment (currently introduces an AnimObjectID mismatch). |
| TombEngine/Game/Lara/lara_fire.cpp | Updates bounds query to GetFrame. |
| TombEngine/Game/Lara/lara_collide.cpp | Updates several SetAnimation calls to blend-aware overloads and tweaks comments. |
| TombEngine/Game/Lara/lara.h | Adds default player animation blend frame count constant. |
| TombEngine/Game/Lara/lara.cpp | Adds a debug block forcing root-motion flags on Lara animations; updates a fall transition to blend. |
| TombEngine/Game/Animation/Commands.h | Renames command base type and “MoveOrigin” -> “MoveRoot”. |
| TombEngine/Game/Animation/Commands.cpp | Updates move-root execution and uses OBB-based height for Lara room update. |
| TombEngine/Game/Animation/Animation.h | Reworks animation data model (frames, dispatch ranges, curves, flags) and updates API signatures. |
| TombEngine/Game/Animation/Animation.cpp | Implements fixed motion + root motion extraction/counteraction and blending integration into animation updates. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| { | ||
| auto interpData = GetKeyframeInterpolationData(frameNumber); | ||
| return ((interpData.Alpha <= 0.5f) ? interpData.Keyframe0 : interpData.Keyframe1); | ||
| const auto& rootOrient = Frames[frameNumber].BoneOrientations.front(); | ||
| const auto& prevRootOrient = Frames[frameNumber - 1].BoneOrientations.front(); | ||
| auto rootRot = rootOrient - prevRootOrient; | ||
|
|
||
| rot = EulerAngles( | ||
| (Flags & (int)AnimFlags::RootMotionRotationX) ? rootRot.x : ANGLE(0.0f), | ||
| (Flags & (int)AnimFlags::RootMotionRotationY) ? rootRot.y : ANGLE(0.0f), | ||
| (Flags & (int)AnimFlags::RootMotionRotationZ) ? rootRot.z : ANGLE(0.0f)); |
There was a problem hiding this comment.
AnimData::GetRootMotion() computes rootRot via rootOrient - prevRootOrient and then treats the quaternion components as Euler angles. Quaternion subtraction is not a valid way to derive relative rotation and will yield incorrect/root-motion rotations. Compute a delta rotation (e.g., delta = rootOrient * Inverse(prevRootOrient)), convert that delta to EulerAngles, then mask axes via the flags.
Checklist
Links to issue(s) this pull request concerns (if applicable)
N/A
Description of pull request
Introduces the following new features:
TODO:
Related TE PR: TombEngine/Tomb-Editor#1095