Search Unity

How to handle input combos with Animation Controller?

Discussion in 'Animation' started by JoeStrout, Oct 11, 2014.

  1. JoeStrout

    JoeStrout

    Joined:
    Jan 14, 2011
    Posts:
    9,859
    I'm noodling around with Mecanim animation today, making a little fighting game. I'm stumped on how to properly handle input combos.

    Here's the setup: I have a simple script that assigns bool parameters in my Animation Controller for each of the input buttons, including D-pad directions. So I have bools for Attack and Down (and others, but only these matter for now).

    I've defined four states: Idle, Crouch, Mid Kick, and Low Kick, with an appropriate animation for each. What I want is, if you just press Attack, then the character does a mid-level kick; but if you press Attack and Down together, then it does a low kick. And Down by itself goes into Crouch, of course.

    But I can't see how to set this up. I tried setting two conditions on each transition, i.e., both Attack and Down must be true to go to low kick, and Attack=true plus Down=false for mid kick. But (as expected), this didn't work. It's pretty much impossible to hit both keys at exactly the same time. So you get either a mid kick or a crouch.

    So, what I really expected was something like: you press Attack, and it starts the transition to the Mid Kick state; but if we very quickly see a Down input, then we switch to the Low Kick state, and do this so smoothly that the animation doesn't jitter. (Both these animations start out pretty much the same way, so this ought to work.)

    But I can't seem to make this work. In the transition inspector, I adjust the start and end of the transition so that the start is pretty much all the way to the left, and the end is shortly after that (at about 0:10). The transition animation preview looks great. Then I run, and ... Poof! The transition goes back to the way it was originally, where it doesn't even start until about 0:15. The result is that my character executes most of a mid-level kick before then switching to a low kick, and I see two kicks instead of one.

    So...
    1. What's up with the transition changing when I hit Run? Why won't it stick the way I put it? (I suspect it may have something to do with the Idle -> MidKick transition not being done yet, but I don't know what to do about that.)
    2. What's the "proper" way to handle this sort of input combo with Mecanim?
    Many thanks,
    - Joe
     
  2. JoeStrout

    JoeStrout

    Joined:
    Jan 14, 2011
    Posts:
    9,859
    I'm about ready to give up on Mecanim; it seems like it just can't do this.

    With legacy animation, I'd probably write my state machine in code. But then when entering the "kick" state, I could start both kick animations at the same time, just assigning a weight of 0.0 to the low kick, and a weight of 1.0 to mid kick. Then if we get a "down" input, I do a quick Blend of the mid kick weight to 0, and the low kick to 1. So either kick lands exactly when it would have on its own, yet I can switch from one to the other partway through.

    Maybe I can do the same thing with Mecanim, using Animator.CrossFade... though it means I have to set up a dummy state in the animator controller for every animation. But I guess it might work.

    I'm certainly open to other suggestions (especially if there's some way to handle this all within the state machine).
     
  3. JoeStrout

    JoeStrout

    Joined:
    Jan 14, 2011
    Posts:
    9,859
    Eureka! I figured out how to do this the "Mecanim way."

    The secret is to combine both kicks (and in fact, all three kicks — I've got a high one too) into a blend tree, controlled by an "Attack Height" parameter. Then, my input script sets Attack Height to Input.GetAxis("Vertical") (on which I've cranked up the Sensitivity so that it reacts faster).

    Then, in my state machine, the attack button simply transitions to this blend tree, rather than to individual kicks. Works like a charm!
     
    darknubis365 likes this.