We cover a lot in this article in adding a swing effect. We cover how to run two animations at the same time, changing the relative position of an object and how to use animation script behaviors.
We import the Sword Arc animation and create a new game object, Sword_Arc, using the first frame of the animation. This will be a child of the Player game object.
Lets create a new Animator for the Sword_Arc and we will create an Animation folder in Effects and save it there.
Dragging in the Sword_Arc animation frames to the Animation timeline. When play the animation we cannot see it in the game scene. This is due to the layer order.
We want to match the layer order of the Sprite image, which is layer 50.
Now we can see the Sword Arc when the animation is played.
This animation right now is chaotic. We will make some tweaks with the speed and rotations to get it to where we want it.
The first thing is to reduce the frame rate to 30 frames a second.
The sword swing is slow and to match it we will let the first frame of the animation hang for some time before running through the rest of the frames.
Now, we will need to adjust the rotation of the sword arc to x 66, y 48, z -80 to match the side swing of the sword. These rotations values were founded by messing around with them until it looked right.
In the Animation make sure to set Loop Time false, so the animation doesn’t continuously play.
In the Animator the Sword Arc will automatically play when the game starts.
Lets avoid this by creating an empty state with no animation we can transition from to the Sword Arc animation.
We are going to create a Trigger parameter, SwordArc, that will allow us to move from the empty state to the sword arc. Since it is a trigger, when it has be called and the animation is finished playing, it will transition back to the empty state.
The transition will not have an Exit Time or Transition Duration, so it instantly plays.
Transitioning back, we will just keep the regular transition settings.
The Player Animation script is handling all of the animations for the player. We need to get a handle of the Sword Arc Animator, so we can call the sword arc animation.
We are already getting the Animator in the Sprite game object, so we cannot simply get the animator component in children since that will only return the same Animator.
We will need to specify which child in the Player we want to get the Animator from. It is hierarchical, so Sprite Animator is Element 0 and Sword Arc is Element 1. Access the transform of the Player, GetChild and pass in the Element of the Child of Sword Arc,1, then get Animator component.
Complete a null check to ensure we have grabbed the Animator component.
Now, we can set the trigger for the sword animation in the Attack method along with the Attack animation so they will play at the same time.
Attack Animation Clean up
The Sword Arc is not matching up with the Sword Swing, so we are going to adjust the Sword Swing frames and positioning.
We are replacing the old Attack animation with Swing frames 6–8 & 10-23. This make the Attack animation much quicker to match the speed of the Sword Arc animation.
We adjust the positioning of the Sword Arc to the following position (X = 1.01, Y = -0.09, Z = -0.25).
This reposition makes the Sword Arc look great! But, it creates a new problem…when moving left the Sword Arc is out of position and facing the wrong way.
The Script Again
In the Player script, we need to get a handle on the Sword Arc sprite renderer, so we can flip the image when the player moves left and right. We cannot use the Get Component In Children since we already did that with the Player sprite. Again, we need to specify which Child we want then get the component.
In the Flip method that is using the horizontal input to determine if the player is facing left or right. When the horizontal input is less than 0, facing left, we want to flip the sword arc X & Y by setting it true. When the horizontal input is more than 0, facing right, we want to reverse the sword arc X & Y by setting flip to false.
Since we offset the x position of the sword arc, we need to rectify this when the player moves left and swings.
We create a local Vector 3 variable, newPos, that will be the sword arcs local position, which is the position of the sprite in relation to the parent game object; the Player. We just want to set the X position, so we set the newPos, which holds the current local position and set it to -1.01 (the opposite X position when facing right. Lastly, with the new X position changed, we need to set the location position to this new position.
That was for when the player is facing left, but we will do the same thing when facing right, but set the newPos.x = 1.01. This returns the sword arc back to the starting position; facing right.
The final thing is the Sword Arc image can been seen. In fixing this, we want to get a reference to the game object of the Sword Arc, complete a null check and if we assigned, we want to set the Sword Arc game object to false. This makes the entire object inactive, which includes the image.
When we call the Attack method, that will trigger the Sword Arc animation so before that happens we will activate the Sword Arc game object so we can see the image.
Once the animation is finished playing, we will want to deactivate the game object again. This is going to require a animation behavior script, but before we create this, we need a public method that will set the Sword Arc active to false so we can call it in the animation behavior script.
You can add an Animation behavior script be selecting the animation in the Animator. Click on Add Behavior and we will call this Sword Arc Behavior.
Using the OnStateExit method, which runs when the animation is finished, we get a handle on the Player Animation script and call the Swing Complete method.
Finally, the final result.