Open ghost opened 9 months ago
My plan for the user-facing API was
AnimationGraphPlayer
component or in an animation graph (open to discussion).AnimationGraphPlayer
component, without automatically applying it.
Users can then add a system to read the root motion deltas every frame and apply them as needed, since they may need be applied differently depending on how you structured your character controller and which physics engine (if any) you're using.That said I haven't developed this idea into anything yet, and in particular I haven't figured out what the best way of extracting the root motion internally would be. Options I can think of are:
Currently I'm leaning towards option 2, since it should be easiest to implement and I can't think of a use case for having root motion data available to the animation graph.
Of course, feedback/discussion is appreciated, as it will help to better understand the requirements others have and, honestly, I don't really know that much about this :) In any case, I'm hoping to work on this after the animation graph editor (which I'm currently working on), animation events and state machines.
Neat! I also don't know much about this but it's really fun to think about. I've fallen down the Bobby Anguelov link.
Regarding extracting the root motion internally, it seems like how Bobby is doing it is from the blended pose from the animation graph. Imagine blending a walk and run animation. The blended root motion joint delta is the instantaneous velocity. Minute 38 of the YouTube link talks about how this is configurable in the transition node.
Having said that, calculating the root motion delta for nodes seems tricky and like it's easy to make an incorrect decision.
Bobby has a root motion override node that I think is your option 3 for internal management.
https://github.com/BobbyAnguelov/Esoterica/blob/main/Code/Engine/Animation/AnimationRootMotion.cpp
Around minute 21, 28, and 38, and 1:34 https://www.youtube.com/live/R-T3Mk5oDHI?feature=shared
Edit:
1:34 of the video talks about getting the "root motion from the graph and not calculated by the pose". Reading into this more with the below links it turns out that it's configurable based on the graph behavior. it's a little confusing to follow, but it can blend or not blend, and then it can override behavior after that.
Nice, thank you for looking into this! It seems that Bobby does include root motion deltas as part of the pose data available to the graph, which was what I wasn't sure about. It looks like he does some combination of options 1 and 3? He extracts the root motion from the animation clip and propagates it through the graph. When blending two poses he just does either a linear or additive blend to the root motion deltas of either pose, depending on some configuration:
I'll go through the code you sent in a bit more detail this weekend when I have more time, but I think we can get away with a very similar solution here. Very cool :)
In your planning list I saw you were considering using bone masks to specify which bones are kinematically driven and which are simulated. Similarly, there is a concept called root motion that uses a joint (typically pelvis in humanoid) to drive the character in the physics engine using velocity, acceleration, and/or impulses. Have you considered how root motion data could be exposed and zero'd for kinematic motion?
https://github.com/bevyengine/bevy/pull/8102 https://docs.unity3d.com/Manual/RootMotion.html