Captain! Our Shields are Failing!
Objective: allow the Player’s shield to sustain multiple hits before failing, with visual feedback after each hit to indicate diminishing shield effectiveness.
In my current version of the GameDevHQ Space Shooter Unity 2D Game Project, my Player occasionally gets an opportunity to collect “shield” powerups. This shield, once activated, permits the Player to survive unscathed a collision with an enemy ship or a hit from hostile laser weapons. Upon collision detection, the shield deactivates rendering the Player vulnerable to damage.
My goal in this article is to beef up the resistance of the shield. It will be able to take 3 impacts of any kind before deactivating. After each impact, I’ve opted to alter the Alpha channel of the Player’s shield to imply a weakened state.
I started out by declaring two private variables in my PlayerScript attached to my Player game object. The first one is an integer I use to track how many times the shield, when active, gets hit. The second one is a float allowing me to adjust the alpha channel of the sprite renderer.
To put things in context, one of my previous articles introduced the powerup system in my game project (find the article here), and used a Switch Statement to activate “pickups” (collisions). As seen below, when the Player collides with the game object having the _powerUpID 2 (case 2:), it calls the ShieldActivate() method in the PlayerScript script.
We can see below the ShieldActivate() function. I added three new lines to ensure that every time a shield powerup is collected, it resets all parameters to their default values.
This way, if the Player currently has shields, but they’ve been hit a couple of times and weakened, collecting a new shield powerup “regenerates” the shields and offers the Player renewed protection.
The way I adjusted the visuals is by altering the Alpha channel of the Sprite Renderer. Now at first, I tried to hard-code the existing RGB values of the shield into the new Color (R, G, B, A), but doing so would alter the original tints slightly. If on the other hand, I left RGB as (1f, 1f, 1f) and only altered the Alpha channel, then I was getting the results I wanted. I’m not quite sure why, but I’m presenting here what worked for me 🤔.
So my implementation works this way: every time the Player’s Damage() method gets called, I check to see if the shield is activated.
If it isn’t, then the Player gets the full impact of the collision which results in damage or loss of life.
If it is, then I increment my _shieldHits by 1. I then run a Switch Statement comparing the value of _shieldHits, and depending on the results, I store a new float value into the _playerShieldAlpha variable. Once this is done, I set the new color of the material using the following line:
This results in the opacity of the sprite changing, becoming more transparent as the hits increase until the third hit deactivates the shields.
The results are as follows:
There you have it. The effect looks fairly nice. Along the way, I figured out a simple way to manipulate the transparency of a sprite without altering or needing to replace the animation in order to give the Player a convincing visual cue that his shields are failing.
I hope you’ve enjoyed this short article and will find it useful as you play around with your own Unity game project. Thanks for reading :)