Friday, June 21, 2013

Blending Between Walk and Run Animations

In most games, walk and run animations can be blended together by holding analog stick. Depending on how much analog stick is pressed, two animations (usually walk and run) start blending. There is a problem in blending between walk and run animations and that is these two animations has different timings. Blending between walk and run results an unexpected motion. In this post I want to talk about how we can blend between two animations with different timings like walking and running.

Before going further, let’s consider human jogging. Jogging is a movement between run and walk. It's not as slow as walk and not as fast as run. We can say that jogging is partially run and partially walk so the gait and hands should not move as long as they move in running and should not move as short as they move in walking. We can say that the transform of bones are averaged between run and walk in jogging. That's actually what we are doing in animation blending. Obviously, animation blending is a weighted average of different animations keyframes. So for now we know that jogging actual poses can be achieved by blending between run and walk animations. One another thing should be considered is that jogging speed value is also between run and walk speed. This means that jogging is slower than run and faster than walk. To achieve a jog animation by blending between walk and run, we also need to blend between speeds of two animations.

Now let’s consider how we should blend between walk and run to make a jog animation. First it comes from animators. They should animate walk and run with same normalized time. For example, if in walk animation, left foot starts planting on the ground at normalized time 0.5 then the left foot in run animation should start planting on the ground at normalized time 0.5 too and if the right foot in walk, starts planting on the ground at normalized time 0 and 1 (loop poses) then the right foot in run animation should start planting on the ground at time 0 and 1 too.

After making walk and run animations with the rules I mentioned, you can blend the speed of two animations with the same blend factor used for animation blending:

a = blend_factor        where  0 <= blend_factor <=1

T1 = walk_length     (in seconds)

T2  = run_length       (in seconds)

T1>T2

At the most times we need to blend animations with each other linearly so if we use linear animation blending then we need to blend speeds of walk and run animations linearly as well. For this reason I wrote a linear equation to show the time length of jog animation:

jog_length = (T2 -T1)  * a + T1       where jog animation is the result of blending between walk and run animations with blend factor ‘a’ linearly and jog_length is the time length for jog animation.

At the final step we should change the playback rate of both walk and run animations to achieve a blended speed:

Walk.PlayBackRate = T1 / Jog_length
Run.PlayBackRate = T2 / Jog_length

For avoiding some problems like round-off errors in floating points you can set the Run.NormalizedTime to Walk.NormalizedTime instead of setting the Run.PlayBackRate.

Make sure to change the speed of both animations before calling your blend function, otherwise you will face unexpected results.