In this homework we will continue Lab 8 to implement the game Key Master.
This game will be composed of 5 levels. In each level, the player moves through a maze and must open a door. In order to open a door, the player must acquire first a key. Both the key and the door's positions are randomized in the maze. An opponent NPC will also chase the player and if they catch them, the level is lost and can be restarted. In Level 1, we start with a large maze, and in each new level, it shrinks down to make it more challenging to escape the opponent.
Note. I have added .blend versions of the objects we use in this program to Canvas - Files - Week 10, in case you want to make modifications.
Create another scene called end, similar to start but displaying the keyWon image instead. The caption on the button should say "New Game". The action can be the same as for the first scene. Add a text mesh (any kind) object displaying the credits.
If you have not set the aspect of the game and a matching application window size in the lab, set the aspect of the whole game to 3:2 and the size of the application window to 750x500. If you've already set these, you can use those settings instead. Arrange the quads in the start and end scene so that they cover the entire viewport.
a. Add a feature to the PlayerController.cs class such that when the player moves to the left and right, the creature is rotated that way, and when it moves backwards, it faces the screen. Hint: check the values of the player's speed in Update or FixedUpdate. Normally, the rotation is stored in the transformation in quaternions. To apply a rotation to the player using the 3 angles for x, y, and z, you can do
transform.eulerAngles = new Vector3(0f, 90f, 0f);
b. Add public variables of type GameObject to the GameManager class and back in Unity, connect them to the key and the door objects.
Declare a function void InitLevel(). In this function, check the level number and for level 1, initialize mazeWidth, and mazeHeight with 30 both. For each next level remove 5 from these sizes. Then call the function MakeMaze with the values of these variables.
Then in the function Start, replace the call to MakeMaze with a call to InitLevel.
Add another function to the class called Point RandomSpace(). This function should generate a random integer r between 0 and mazeWidth and c between 0 and mazeHeight, and check if the cell in maze at that position is a space. Repeat the procedure until you find a space. Then return Point(r, c) from the function.
Going back to the function InitLevel, call the function above to generate a space position for the key and for the door. Use the functions Col2X and Row2Y to get world coordinates for these objects, then apply them to X and Z in their transform. You may have to add or subtract half of the scale over X of the brick prefab from these coordinates. This should place the key and door properly in the maze. Tag the key with the tag "key" and the door with the tag "door". Add a bool variable called hasKey initialized as false in the function InitLevel.
Add a collision function the player: void OnCollisionEnter(Collision colInfo). If the object it collided with has the tag "key" (colInfo.collider.tag), apply a scale of like 0.5 to the object (colInfo.collider). Assign a position to the key based on the current position of the player, with some small translation to make the key visible. Then make the key a child of the player so that it follows its movement. For example, if the objects are key and the target object of the script is the player, then you'd attach it by doing
key.transform.parent = transform;
Then also assign true to the flag hasKey.
In the same collision function, add another test for the tag being "door". If the player collides with the door, check if the flag hasKey is true. If it is, then play a cheerful sound and wait for a short delay. After the delay, increase the level number, and if it's less than or equal to 5, then reload the scene. If not, then load the end scene.
To implement a short delay, declare a boolean class variable endLevel initialized as false in InitLevel, and another class variable float countDown. When a game end condition occurs, set endLevel to true and countDown to the number of seconds you want.
Then in the function Update, check if endLevel is true, and if it is, then subtract Time.deltaTime from countDown. If the countDown is <= 0, then reload the current scene or switch to the end scene based on the level number, as described before.
Add a text box of any kind displaying the level number. When the game is won or lost, make it display that information.
Add an opponent creature to the scene. You can use the following or your own:
Add a tag "enemy" to this object, a rigidbody with similar settings to the player, and a collider. Add a reference to it in the GameMaster script and connect it in Unity. Randomize its starting position as you did for the key and door.
Add a case to the player's collision function where if the tag is "enemy", you display the message that the game is lost, play some sad sound, and restart the scene without changing the level after some delay.
Add a function in GameMaster to have the enemy object try to follow the player. You can set its velocity over x and z to move towards the player. Like, if the X coordinate of the player is less than the X of the enemy, set its x velocity with a negative value, otherwise with a positive value. The same for z. Call this function from Update.
You can try to make it more clever by using the information in the maze. Like, if its velocity.x is negative but the maze at its position -1 over the column is not a space, set velocity.x to 0. The same for z. Use the functions X2Col and Y2row to map its current coordinates to the maze array (except that you should use z in place of y as parameter).
Create a zip file containing a Windows executable and the script files that you have changed. Also take a screen shot of the running application and save it as a png or jpg. Make sure that the zip file includes the following:
Submit the zip file containing the Windows executable and the script files to Canvas, Assignments - Homework 8.