My journey becoming a Unity game developer: Introduction to Physics in Unity. Adding a Triple Shot for Galaxy Invaders
Objective: Give the Player a special shooting mechanism called a Triple Shot after they collect the Triple Shot Powerup. Also, give a simple explanation on using Unity’s Physics engine system to manipulate objects that have a Rigidbody component attached to them.
We will begin with creating an Empty game object in the Hierarchy named Triple Shot. Reset its Transform to zero on the Position and Rotation axes. Grab the Laser sprite from the Sprites folder and drag it onto the Triple Shot object making it a child of the Triple Shot game object.
Adjust the 1st Laser object to shoot in front of the ship’s middle cannon without touching the cannon. Adjust the height of the Laser object through its Scale on the Y-axis if needed. Duplicate the Laser object and place the laser on one side of the ship’s back wings. Duplicate this Laser object once more and change the X-axis Position to either a negative or positive number depending on which side you positioned the 2nd laser first.
Once all 3 Laser objects are positioned, drag the Triple Shot object into the Prefabs folder making it officially a prefab. Delete the Triple Shot object from the Hierarchy as we will produce this game object through code when the Spacebar is pressed and the Triple Shot Powerup is collected.
In the Player’s script, create 2 new variables with the 1st one being set to have a Public Access Identifier. This is just for testing purposes as we will change this to Private later on. Its Type will be a Bool and the name of the variable will be tripleShotActive to check if the Triple Shot is active for the player to use.
The 2nd variable will be a SerializeField Type GameObject name tripleShotPrefab. We will attach the Triple Shot game object itself the player will be shooting to this script’s component.
Inside the FireLaser() method, we will check IF the Spacebar key has been pressed. If True then we will check IF the tripleShotActive is True as well. If tripleShotActive is True, we will Instantiate the tripleShotPrefab at the Player’s position. Last, set the Quaternion to not rotate the lasers using the Identity method. If the tripleShotActive is False, we will use Else to Instantiate the regular laserPrefab.
Back in the Hierarchy with the Player object selected, drag the Triple Shot prefab into the Triple Shot Prefab slot in the script’s component. Play the game, turn on Triple Shot Active and use the Triple Shot against your enemies. Notice the lasers are instantiating from the positions we set the Laser objects to shoot from.
Next, we need to create the Triple Shot Powerup by dragging its sprite into the Hierarchy or Scene. Scale down its size to an appropriate size according to the other ships in the game size. Add a 2D Box Collider and Rigidbody to the sprite allowing it to use Unity engine’s 2D Physics system.
Inside the Box Collider 2D, adjust the collider’s size around the powerup object using Edit Collider and turn on Is Trigger. Inside the Rigidbody 2D, set Gravity Scale to zero as we don’t want gravity used on the powerup.
Rename this sprite game object to Triple_Shot_PowerUp, and place it into the Prefabs folder making this a prefab. Now create a new C# script name PowerUps, attach it to the Triple Shot PowerUp prefab, and open it.
Before we write code for our powerup, I want to show some of the features that can be used with the Unity Physics engine through the Rigidbody properties.
First, we’re going to set the Mass on the Triple Shot PowerUp to 2 and Gravity Scale to 1. This will make it heavier than the Enemy ships which are set to 1, and drop the powerup onto the Enemy with gravity applied. Second, turn off Is Trigger on both of theirs Box Colliders as we want the 2 objects to collide and not go through each other. Third, press Play and watch the Triple Shot PowerUp knock the Enemy object into a rotation offscreen.
If we want it to stop rotating, using the Constraints properties turn on the Freeze Rotation on the Z-axis. It has an Angular Drag preset to 0.05 that will effect its rotational movement, but let’s set the Linear Drag to 0.05 as well to effect its positional movement. Notice that the Enemy ship’s motion has slowed down because of the damping effects from the values assigned. The higher the values, the more the object will slow down even with Gravity applied. If you set the Drags to zero, there will be no damping applied.
We will use the default Dynamic Body Type which is designed to move under simulation with a full set of properties available to it such as finite mass and drag which is also affected by gravity and forces. A Dynamic body will collide with every other body type and is the most interactive of the body types. This is the default body type for a Rigidbody because it is the most common body type for things that need to move, and is the most expensive performance of the body types. Collision Detection’s default is set to Discrete which allow game objects with Rigidbody 2D and Collider 2D to overlap or pass through each other during a physics update if they are moving fast enough. Kinematic Body Type is designed to move under simulation as well, but only under very explicit user control. While a Dynamic Rigidbodies are affected by gravity and forces, Kinematic Rigidbodies aren’t. For this reason, it’s fast and has a lower demand on system resources than a Dynamic Rigidbody. Kinematic Rigidbodies can still move using its velocity, but the velocity will not be affected by forces or gravity. A Static Rigidbody is designed to not move under simulation at all. If anything collides with it, a Static Rigidbody behaves like an immovable object as though it has infinite mass.
These Rigidbody properties are great to use without having to code and get great effects added onto your game objects from Unity’s Physics system. If you do decide to use code for your physics movements, it’s highly recommended to use the properties and methods assigned to the Rigidbody component. We will be using the preset property values assigned to a Rigidbody component with the Enemies and PowerUp. As we’re keeping these game objects movements simple for now, we can use simple code to control the objects movements.