Let's make a hypercasual game: Crowd Evolution: Episode 2
We left off at a place where we had a nice modifier base class waiting to be overridden with features. First, we will create the crowd-generation mechanic.
Let’s start by creating a prefab out of our Person gameobject which. We will also make sure that the PlayerShooter.cs is attached to our Person gameobject and not to the parents. This is because we want each of our people in the crowd to shoot. separately
To create a crowd, we will need to figure out the positions where each of our Person will stay respective to their parent. We will do it in the simplest and the most configurable way possible. We will create a gameobject for each position and have reference to the gameobject so that we can spawn our Person gameobject there.
Let’s create a gameobject named Formation and under it, we will make some spheres and place them like this. The serial in the hierarchy shows the positions from person 1 to 20. The spheres are there for visualization reasons only. We will make sure these gameobjects are turned off, as they don’t have any use other than referencing the positions. As I said, it is also configurable as we can move around the positions very easily as we like.
Now, we will create a PlayerCrowd.cs script and attach it to the gameobject ‘PlayerCrowd‘. We will keep references to all of the points that we made above using a List of Transform. We will also have a reference to the PlayerShooter prefab.
Let’s now create functions to add or remove Shooter. After each spawn, we will add it to a list of shooters and we will adjust the index so that the next spawn is always done on the next free point.
Now, we can create a new function that uses the above to set the crowd size to a specific amount
We want to test out if it works correctly. Let’s create a wrapper function that will enable us to run this when playing from the Editor
It’s time to test it out
We have laid out the basic groundwork to start creating our crowd modifier. Let’s create a ModifierCrowd.cs which inherits from ModifierBase.cs and implement the Modify function. We will get the PlayerCrowd and use the AddShooter and RemoveShooter functions accordingly to add to or remove from the crowd.
The _isPositive variable simply detects if the modification is a positive or a negative one. We can use this variable to update our UI too. Here, we have a world canvas Ui with an image and text that represents our modifier
Let’s try it out now
Cool! We have a working crowd modifier
We have to fix a problem now. If we try to pass the -2 gate without going through the +3 we will see an error. It’s because we are trying to remove people who aren’t there. A simple check before adding or removing shooters shoot fix the issue. Let’s create the functions in PlayerCrowd.cs
Now, if we can not add or remove we will return early from the AddShooter and RmoveShooter functions respectively.
We are done with our crowd modifier. So let’s now think about how we should approach the Year modifier. Firstly we have a similar trigger UI on both of the trigger types. So instead of repeating the UI code, we can reuse it. How? Refactoring the UI code by sending the code to the superclass ModifierBase is an option. But, if we do that, we constrain our modifier to must have the UI. We don’t want to do that because to have a modifier behavior it’s not necessary to have a UI like this. Case in point our ModifierLog.cs
Another option is to create a separate class out of the UI-only code and then reuse that class by adding it as a separate component. That works nicely! We can add UI with the modifier. But the UI is not necessary
We create a class named ModifierView.cs and add a function named SetVisuals
We then use it from the ModifierCrowd
Now, let’s think about the year modifier. What is it really? What does the year represent? It represents better weapons which in turn means more damage per hit to the enemy.
We already have a damage per shootable variable in PlayerShooter.cs which is referenced in the Shoot function. We need to modify this when we pass the year trigger. That’s why we need to create a private variable _damagePerShootable which is set to the damagePerShootable on Start and used in place of it. We should not modify the variables which carry a default value. Now, we can modify the private value instead of the default value.
We create a new variable named year which will help us translate
year → damage per shootable
We will also need a damageAddPerYear variable that we will use for the calculation. Let’s create a function now, that updates the weapon year
In the PlayerCrowd.cs, we create a wrapper function that goes through all of the players and updates the weapon year. It also keeps count of the year itself
We can use this function, whenever we pass through the year modifier.
It’s time to create ModifierShootableYear and as expected, inherit from ModifierBase. Now, we create the Modify function
Let’s see it in action
Of course, the damage per shootable is not visible yet. But we can use the debug inspector by selecting a shootable gameobject to see that the value is indeed being modified.
To make the year visible, let’s create a UI that shows the current year. We can use the _year variable in PlayerCrowd.cs to update the UI
Finally, we have this
Great! We have created a working crowd modifier and weapon modifier. This wraps up episode 2 nicely and creates a nice groundwork for episode 3 where we will look into adding enemies. See you then!