Menu

1 Nov 2016

PixelHorrorJam Retrospective: Spooky Scary Gamedev

The #PixelHorrorJam:

So for the past month or so I've been putting a bit of work into an entry for the Pixel Horror Jam on itch.io, and last night was the release. The guidelines were to create a horror game that conveys a story and has a pixel art aesthetic. My final product for submission is Motel 666:



In Motel 666 you play as a traveller who had to stop for the night at The Starlight Motel. After checking in and going to bed you awaken in the night to find things aren't quite right. The staff are hazy, violent, and grotesque, and the motel itself has become like a trap.

Development Notes:

I developed Motel 666 in the Unity Engine, and it's available for download on both Windows and OS X. I may port it to the Razer Forge TV and post it to the Cortex store at some point after the voting phase of the Jam wraps up. Speaking of which, if you're reading this, please check out some of the other entries in the jam and please remember to rate any you've played!

My objective in developing Motel 666 was to craft an experience that would cross the atmosphere, story-telling, and mechanics of survival horror classics like Resident Evil, Silent Hill, and Alone in the Dark with the aesthetics of The Legend of Zelda: A Link to the Past and Graal Online (All of which I played far too much in my youth). The end results wasn't exactly what I'd set out to make when I first came up with the game and wrote out my designs, but time constraints on a game jam being what they are I'm very happy with the final product and I think it does its job quite well.

I had a great time developing Motel 666, if you're interested in the tools used to create the assets for Motel 666 you should read my entry Assets, Assets, Assets... which details how I make sprites, music, and sound effects. The short version is I used a combination of Piskel and Paint.NET to make the sprites, props, menus, and settings; and I used PulseBoy to make the chiptune music and sound effects.

On the Subject of the Sountrack:

Below are the three main songs from Motel 666, including the introduction music from the splash cards and menu, the boss battle music, and the closing music from the ending. 

Thanks so much to any of you who decided to give Motel 666 a try and I really hope you enjoyed it. If you have any feedback or comments about the game please feel free to let me know on Twitter @AdamBoyce4 or throw up a comment on the Game's submission page on itch.io

Thanks again everyone!



22 May 2016

Entity Component System

Entities, Components, and Systems

To start I've created a C# class library solution to store the basic class and interfaces for the implementation of the ECS pattern. It contains the Entity class, which consists of an Id value and a collection of components. The components implement IComponent, an interface that describes the common behaviours of all component classes. Likewise the systems all implement the interface ISystem, which outlines a set of methods to ensure all of our systems are fulfilling their appropriate role in a given program. 

Entity is a very simple class. As I stated in the first entry on ECS, entities are really just an ID value and a set of components, as seen here:

Entity - An ID with a List Of Components
In addition to a constructor and properties the Entity class also contains a few utility methods for getting and setting Components in a couple of different ways. The interfaces are fairly simple as well, each only declaring a few methods, here's IComponent:

IComponent - All Components will have Activate, Deactivate, and Update methods
...and ISystem:
ISystem - All Systems register their components of interest from a set of entities and update those components on iteration

These three building blocks are part of a solution called "RushECS" that can be downloaded from the GitHub repository linked at the end of this post. The project builds a C# class library DLL file that can also be found in the repo and downloaded for use in any projects you so desire. Before I get into the actual implementation of this library, I'd like to talk briefly about how these pieces are meant to interact...

Avoiding Component Instantiation During Runtime

It's important to avoid making a habit of constructing and destroying objects in the midst of execution if a game is to run at a reasonable pace. Having your framerate slow down randomly because memory is being reallocated unnecessarily can make games look janky and poorly made. This is why IComponent contains a method declaration for Activate and Deactivate, rather than simply having a constructor in the implementing class handle those responsibilities. This doesn't prohibit writing a constructor aside from the default, but it does provide a clear pattern to implement the management of Component states during runtime without eating up any extra RAM.

IComponent contains one other method, Update. This is the other behaviour common to all Components and it's used to expose the specific functionality of a given implementing object to it's corresponding system. In the example to follow, an InputComponent's Update method will be used to notify the InputSystem of any Key presses that map to a set of commands.

Obtaining and Iterating Through a Component Collection

The way ISystem's methods are laid out is a combination of essential system behaviour and accomodating my preferred order of object instantiation when the program is starting up. I want to create all of my entities first, then add components to them, and then finally to register those components with the appropriate systems. As such, systems built using this library register components by going over a collection of Entity objects and checking each for the components they're interested in. This also affords the ability to give the system an association between the entities and their components during gameplay without having to check our entities over and over.

In any implementation of ISystem, there will need to be some determination of how frequently to run the UpdateComponents method. That's how a system regulates it's components behaviour and it's important to ensure that each system is updating with an appropriate frequency, such as a graphics system having a frequency of update that ensures smooth image rendering.

The implementation example below isn't going to have anything as complex as rendering graphics though, as it's just meant to demonstrate how Entities, Components, and Systems can work together to give a strong design base for a game.

The Example: Input and Display

The basic structure of the example project (which can be found in it's entirety on the GitHub repo mentioned earlier) is to run a console application that will receive specific key presses using InputComponents, these components then notify the InputSystem using a ReceivedInputEvent, and the system in turn notifies any other components that would be concerned with that input using a DispatchCommand method. In this case there's only going to be one other type of component to notify, a DisplayComponent, which will put messages into a queue to be printed to the console by the DisplaySystem during update iterations.

Looking at the actual execution of the program (found in Program.cs) you can see what I described earlier; several Entity objects are created and are each given a pair of InputComponents and DisplayComponents, followed by the instantiation of an InputSystem and a DisplaySystem. The entities are grouped in a List and passed into each system's RegisterComponents method, as shown below:

The first portion of the example's runtime code
The components then call Activate in turn and the systems are started, followed by an intentional infinite loop to just keep the program running until it's closed.

The Systems and Components During Runtime

When the InputSystem registers a component, it attaches a reference to a method called DispatchCommand, as you can see in the RegisterComponents method here:

The RegisterComponents method in InputSystem
During the aforementioned infinite loop, the systems both have a Timer object running that calls their UpdateComponents method according to an Elapsed event. These systems are really simple, so the only thing happening in their UpdateComponents methods are direct calls to the Update methods of their component lists. When InputSystem executes an update on InputComponent, there's an attempt to get any key input from the console, which is then compared against the set of InputCommands specified in the component's builder methods seen in Program.cs. In the event that the key entered matches one of the keys in the component, a ReceivedInputEvent is raised:

The Update method in InputComponent
Which then triggers the DispatchCommand method...

The DispatchCommand method in InputSystem
In this instance all DispatchCommand has to do is format a message string and send it off to a DisplayComponent, which it finds using the supplied Entity ID value. In a real world implementation there are a plethora of other potential command objects that could be created and sent off to components, because an input system and it's components are responsible for communicating player action into game world effect. For the example though, it sends off a message using QueueOutput which adds the message to a List called OutputQueue to await processing by the Update method, with the oldest messages being displayed first:

The Update method in DisplayComponent

In Summary...

So that's it in a nutshell, the program features an Entity Component System architecture composed of:

  • Entities - An ID value and a set of Components
  • Components - An Object mapped to Entities which define various properties and behaviours 
  • Systems - An Object which iterates over a set of Components defined by a logical domain and manages their behaviours
The Entity objects each have an InputComponent, which watches for keyboard inputs and notifies the InputSystem, which in turn passes off display instructions to a related DisplayComponent and the message is then queued up for printing out to the console. In action it looks like this:

Runtime execution of the ECSInputExample project
I hope this is a helpful breakdown of the Entity Component System pattern. If you have any questions or comments feel free to leave them in the comment section below or contact me on twitter @AdamBoyce4

As promised earlier the GitHub repository for the class library and example project can be found by following this link. Thanks very much for reading and I hope you'll come back for the next entry.

25 Jan 2016

LibGDX Jam Retrospective: Always Have A Plan

I recently entered the LibGDX Jam on itch.io, and I've decided to do a write up on my experiences working with the engine and with developing in the month-long jam in general. I wound up with a great learning experience for the LibGDX engine and reinforcing some general software design lessons, which all in all made for a very worthwhile thirty days. With that out of the way, it's time to dissect my experiences developing for the jam and relay those important lessons!

Planning is Essential

This is the first and most important lesson of this jam, and basically any project: Always have a plan, make a design for your project before you begin coding. The design may change while you're working if you find parts of it unworkable, but it's important to have a blueprint with a feasible set of deliverable features that you can work off of. Without that, development can quickly become disjointed, muddled, and disorganized. Relating this specifically to my project, this was my first time using LibGDX in any capacity and I haven't written any Java in years. So I downloaded Android Studio, set up my LibGDX project and started following some simple tutorials on setting up a Gradle desktop build. 

I learned how the LibGDX project was laid out and how to use various engine features like Screen interfaces and the Gdx object, but I didn't enter with a solid design for what I was going to make. One of the rules of the jam was that all source code has to be open sourced and linked to the jam submission page. My Github repository can be found here


Plan within your means

If you play Antares Trail and then look at the code in my repository, something you might notice quickly is that there are building blocks for a number of unimplemented features in the game. You see, Antares Trail was originally conceived as an amalgam of classic Galaxian shooters like Galaga or Gradius, and Oregon Trail which was a popular American educational game about crossing the old American west in a horse drawn wagon to reach Oregon. The player would sele
ct one of three ships and stock up on supplies for the journey, and then fly ahead of the transport ship fighting space pirates between stops en route to a colony in the Antares system.

In the released version of the game, the player chooses one of three ships and then flies between a few locations fighting space pirates before finally arriving at your destination. The purchasing of items for the passengers on the transport, the possibility that passengers would become sick or otherwise injured during space travel, and the requirement to manage the passengers in between space flight levels during stops all wound up not in the game. They are in the code, though:

This is the GameData JSON object in a save file for Antares Trail
As you can see above, the save data for an Antares Trail game tracks a bunch of information about fuel, food, passengers, money, etc. All kinds of things that would've been important to the management side of the game that I didn't get to put in, which brings me to the point about planning within your means:

If I could say anything to myself circa 18th of December, 2015 it would be this: "You only have a month". Over the course of the jam were holidays with family, a day job, home upkeep, and generally everything else that can come up in day-to-day life. This was my first time using LibGDX and I had also decided to personally create all of the assets for my game (aside from the font). I planned a very ambitious game for my first outing with a new engine, and I didn't do myself any favours with a thirty day deadline.

It's very important to be realistic in setting goals for a project. Weigh out the deadline, what features you want, what your level of skill and knowledge is with the technologies involved, and build your design accordingly.

Make Plans From the Ground-Up

One issue that came about in developing my project was that what plans I had all revolved around a set of gameplay features, but didn't account for making a good object-oriented design using patterns. The result was a set of features haphazardly implemented in the order I learned to implement them, and (thanks to a lack of familiarity with Java) some bizarre looking design choices later in development. The most glaring among these choices came in the refactoring of my ISpaceship interface, which was helping to build code for enemies and the player around behaviours rather than one concrete implementation, in a Spaceship  parent class from which all others derived. This all would have been avoided if I'd been aware of Java's "instance of" keywords. Alas, I only knew of ".getClass()".

The reason that bit of code was so important was for collision detection. Every object in the space flight portions of the game implemented an ICollidable interface, and had a Rectangle object used to check for overlapping objects in the CollisionSystem during gameplay. The colliders needed to be able to report what type of object they were attached to in order to call it's appropriate methods when their "OnCollision()" method was called. I refactored the interface into a parent class because ".getClass()" always failed checks against ISpaceship, as it wasn't a class at all. This cost a lot of time and made for a lot of incongruity in the way each object type was being designed. 

Getting back to the point, the lesson here is to make your design using the building blocks of what your finished project will be. That may sound pretty obvious, but it's very easy to overlook the importance of selecting a set of patterns that will be the foundation of your design. It's also extremely easy to become overwhelmed at the first sign of difficulty and to abandon a better design for something that seems more obvious in the moment. Which leads into the next teachable moment of my jam development...

You're Probably Not Going Back To Fix That Thing

This is the code of someone in denial

Looking at my project now, I can count the times writing a class that I hard-coded a value and said to myself "It's fine, I'll go back and fix it later. This is just to see how it works", I'm not going to count them though, because I did it a lot. Past-me was in serious denial about going back and correcting a poor practice later, and should've just made variables in every instance. Instead I wound up with code that was more and more difficult to expand upon because every time I had to update a value in testing it had to be updated in several different places. 

This applies to more than just variables. As I mentioned earlier, there's a lot of groundwork code present in the project files for unimplemented features. Starting with the core components of a game (or any application, really) and adding optional features later is a much better way to go, rather than throwing out a series of half-baked ideas and determining to finish them up later when there's time. There might not be time, especially when you're looking at a one month development cycle.

Use Patterns

Originally I'd planned to use the Strategy pattern to separate behaviours from the objects implementing them using interfaces. I wound up using a Component pattern later in development than I should have to get collision detection working. The game would've benefited from using Component from the start, specifically Entity Component System, but really any pattern oriented design would've helped keep things simpler and cleaner. Patterns make life better by making code easier to maintain as development wears on, and they should be kept in mind whether a project is using unfamiliar tools or your favourite language.

In Summary

Plan. Always plan. If you don't have a design plan, make one immediately. Make sure to consider at least a few options for tackling development goals, and then make a plan using the one that seems best. Planning out projects ahead of time is essential to good, maintainable development that can be used and reused going forward. 

With all of that said, I made a bunch of assets for the jam, including music. So to cap off the retrospective, here's the soundtrack of Antares Trail. Thanks for reading!