Making an animated character throw an object

Now that your animated character is ready, you might want to coordinate his actions with his animation states. In this recipe, we will exemplify this by making the character throw an object when the player presses the appropriate button. Also, we will make sure that the action corresponds to the character's animation.

Getting ready

For this recipe, we have prepared a project named MixamoProject, containing several assets such as levels, animated characters, and props. You can find it inside the 0423_05_codes folder.

How to do it...

To make an animated character throw an Easter egg(!), follow these steps:

  1. Open the MixamoProject project, and then open the level named 05_06 (in the Levels folder).
  2. Play the level and press the F key on your keyboard. The character will move as if he's throwing something with his right hand.
  3. In the Project view, create a new C# script named ThrowObject.cs.
  4. Open the script and add the following code:
    using UnityEngine;
    using System.Collections;
    
    public class ThrowObject : MonoBehaviour {
        public GameObject projectile;
        public Vector3 projectileOffset;
        public Vector3 projectileForce;
        public Transform charactersHand;
        public float lenghtPrepare;
        public float lenghtThrow;
        public float compensationYAngle = 20.0f;
        private bool prepared = false;
        private bool threw = false;
        private Animator animator;
        public void Start(){
            animator = GetComponent<Animator>();
        }
        public void LateUpdate(){
            AnimatorStateInfo stateInfo = animator.GetCurrentAnimatorStateInfo(1);
    
            if(stateInfo.IsName("UpperBody.Grenade")){
    
                if(stateInfo.normalizedTime >= lenghtPrepare * 0.01 && !prepared)
                    Prepare();
    
                if(stateInfo.normalizedTime >= lenghtThrow * 0.01 && !threw)
                    Throw();
    
            } else {
            prepared = false;
            threw = false;
        }
    }
    
        public void Prepare () {
            prepared = true;
            projectile = Instantiate(projectile, charactersHand.position, charactersHand.rotation) as GameObject;
            if(projectile.GetComponent<Rigidbody>())
                Destroy(projectile.rigidbody);
    
            projectile.GetComponent<SphereCollider>().enabled = false;
            projectile.name = "projectile";
            projectile.transform.parent = charactersHand;
            projectile.transform.localPosition = projectileOffset;
            projectile.transform.localEulerAngles = Vector3.zero;
        }
        public void Throw () {
            threw = true;
            Vector3 dir = transform.rotation.eulerAngles;
            dir.y += compensationYAngle;
            projectile.transform.rotation = Quaternion.Euler(dir);
            projectile.transform.parent = null;
            projectile.GetComponent<SphereCollider>().enabled = true;
            projectile.AddComponent<Rigidbody>();
            Physics.IgnoreCollision(projectile.collider, collider);
            projectile.rigidbody.AddRelativeForce(projectileForce);
        }
    }
  5. Save and close the script.
  6. Attach the ThrowObject.cs script to the game object named Swat.
  7. Select the Swat object. In the Inspector view, check out its Throw Object component. From the Project view, drag the Prefab named EasterEgg (available in the Props folder) into the Projectile field.
  8. In the Characters Hand field, select the swat:RightHand transform.
  9. As we are still on the Throw Object component, fill in the variables as follows: Projectile Offset: X: -0.07, Y: -0.04, Z: 0; Projectile Force: X: 0, Y: 200, Z: 500.
  10. We need to find out the values that should go into the Length Prepare and Length Throw fields. In the Project view, select Swat@toss_grenade.
  11. In the Inspector view, select the clip toss_grenade and drag the playhead through the timeline. Observe how the character starts preparing for the throw by grabbing the grenade at 11 seconds (12 percent of the length). This is shown in the following screenshot:
    How to do it...

    Likewise, it finishes the throw movement around 1:24 (57 percent of the length), as shown in the following screenshot:

    How to do it...
  12. Again, in the Hierarchy view, select the Swat game object.
  13. In the Inspector view, change the values in the Length Prepare and Length Throw fields to 12 and 57 respectively.
  14. Finally, change the value of Compensation YAngle to -45.
    How to do it...
  15. Play your scene. Your character should now be able to throw an Easter egg when you press the F key.

How it works...

Once the toss_grenade animation reaches 12 percent of its length, our script detects it and calls the function named Prepare().This function instantiates a Prefab, now named projectile, into the character's hand. The values specified under Projectile Offset are used to fine-tune its position, making it respect the character's hierarchy. Also, it disables the Prefab's collider and destroys its Rigidbody component, provided it has one.

Later, when the toss_grenade animation reaches 57 percent of its length, the Throw() function is called, which enables the projectile's collider, adds a Rigidbody component to it, and makes it independent of the Character object. Finally, it adds a relative force to the projectile's Rigidbody component so it behaves as if it was thrown by the character. Compensation YAngle is used to adjust the direction of the grenade.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.223.206.69