Developing a puzzle game over a weekend
Back in mid-July I set out to make a quick game in Unity. I didn’t have any sort of plan, other than to try to learn the basic’s for the engine, and develop a simple game.
I consider a basic game to have Win/Lose Conditions at the very least. With that in mind, I came up with the following list:
- Set up Main menu
- Make at least 3 levels.
- Have an animated character move around and interact with the environment
- Have Victory/Lose screens
Basic Movement:
Starting off, I didn’t really have a main game idea for development. I only wanted to start with having a cube I could move around, and then added a ball to see
C# and the art of Duck-taping Spaghetti
I won’t even pretend to know C#. In fact I still don’t have knowledge of the language for the most part. But I have enough of a background in C++/Java to make educated guess on what I need to program enough of the project. For the most part, I relied on the engine was capable of handling most of what I needed. The most complicated code I wrote was for Mico to move and fall with gravity. Everything else just had fairly basic flags to check for collisions, and control whether the object would be active or not.
There’s also some code with the camera so that it will fit within the stages. I briefly flirted with the idea to design the camera to rotate around the character, and zoom in and out. This was a mistake. I retreated from that idea as soon as I could. I suspect I would need to have some basic understanding of the arcane knowledge of Linear Algebra in order to pull something like that off.
Recycling decades old Animation
I opted to reuse Mico for this project for a couple of reasons. The Model is fairly basic, and can be quickly imported into any sort of project, and it has a fairly simple skeleton for animating. It was a little tricky to convert the old animation strips from an older version blender, to a newer version, and then importing that into Unity. But it I found that it just naturally fell into place within a few hours. From there it was just a matter of using Unity’s built in animation state system to use the defined animation strip.
Organically Grown Level Design
First Level: The Basics
First level followed a very simple design. Four walls, a goal, a ball, the character, and a teleporter. Push the ball into the goal, and that activates the portal for the next level. The very basic design is also to allow the player to familiarize themselves with the controls, and what the goals of the game are.
Second Level: Remixing a Modular Grid
With the second level I started breaking down the components from the first level with the goal of having modular components that I could drag and drop into the Unity editor. I used Blender to break down the walls and floors into power’s of ‘2’ for use in a grid. The reason for this to future proof when add further components so that all parts can fit together cleanly. The smallest parts were 4×4 meters, and the largest components were 8×8 meters.
Once the components were broken down, I then went into the process of using those components to remix the first level. Adding walls around the character, and ball, then forcing the player to navigate the level to push the ball into the goal.
Third Level: Expanded Toolbox
Once I had the basic rules of the grid locked down, the next step was to expand that toolbox. I decided to add a bridge, and a second level should the player fall. Ramps were created to traverse between the levels.
If you don’t fall, then the level is fairly basic, but if you wind up having to use the ramps, it’s surprisingly difficult. If I return to developing the game, then I’d probably redesign this level. Not sure whether to make it easier or harder.
An Unexpected Challenge: The Pause Screen.
The hardest part of this project was strangely the pause screen.
The easy part was to design a basic menu through Unity’s engine. Drag and dropping each button, renaming the labels and then writing basic scripts behind each button. The hard part was hiding that menu, and ensuring that there was a proper separation between user inputs between the normal game, and the menu.
Keeping an element disabled or hidden until needed would be the obvious solution to the problem. But unity has a quirk where if any game element is disabled, then it’s garbage collector will automatically run through and delete all of those objects. Hiding the element was also a bit of a challenge since you’d need to know ‘which’ element from the menu you’d need to hide. Despite the simple drag and drop appearance Unity presents, in true Object Oriented fashion, the engine is adding a lot more elements to the screen. Strangely though you can’t hide the Parent ‘Menu’ that you add, but you would need to hide the specific nested ‘Panel’ it creates once the game is started. Once I had figured that out, the next hurdle was to control how input was handled.
First part Disabling the user input for the Game elements. Each element in the game has the potential to have some level of user input applied to it, so rather than cornering myself into a corner, I opted instead to just stop the game timer. Unity has two timers that it keeps track of, one for the game, and one for the engine. So long as you clearly define which elements in the game should belong to each timer, then you are free to stop and start each timer as needed. All elements still accept user input, but the user should not be able to notice changes until you Pause or UnPause. From there, I had an empty Game object checking user input for ‘Esc’ then made a basic ‘state’ engine to enable mouse input on the menu.
I was honestly surprised there wasn’t a built in State Machine for ingame functions. When I was in the process of creating my own engine, I had began implementing a feature just to handle the pause screen for my games. Perhaps there is, and I’m just not aware at this time, but without that feature built in I would imagine setting up Dialogue boxes, inventory screens, in-game cutscene’s, and other components that may exist would present a similar challenge, and would require a deeper knowledge of C#.
Losing and handling an impossible Death.
This is a basic puzzle game designed with no enemies or hazards. But there is a fundamental rule with software development. Never underestimate the user’s ability to exploit the system. I noted in this build the player was capable of glitching on top of the ball, and could theoretically fall out of the level. So I made a simple check that if the player falls below a threshold to display they had ‘died’ and then offer the option to restart. I also added another ‘death’ if the player should wander into the ‘goal’ and get sucked into it, which performs the same check described above.
I then proceeded to add a check for the ball that if ‘it’ fell below a certain threshold, then it would display an alternate message that you’d lost, but offer the option to restart the level.
Wrapping up and Future plans
From there, I threw together a basic Main Menu screen, and Final victory screen after you complete the third level.
I don’t really have plans to continue development, but if I were to continue development for this game, then I would continue to develop in the same method mentioned above, but grow it to 10 levels. I would work towards improving the art style, adding sound effects, as well as developing music. If you’re interested in trying the the current pre-alpha build I developed, feel free to try it out. The current build is for Windows 64.
Leave a Reply