Hi.
I've been working on-and-off since the spring on a little zelda-like adventure game. I thought id share what i have so far, maybe that will start a discussion, maybe not at all.
I've mostly been working on the foundations of the engine and tools. I have zero gameplay element, that will come next. Everything you see if obviously a placeholder (my character is a litteral crash test dummy to make this extra clear). I am not an artist in the slightest. I eventually hope to reach a point where I have enough of a game to partner up with a real artist to make this look real nice.
So here is what i've got so far. I'll cover some of the details of each in this post:
Before i start rambling on, thanks to everyone who answered my questions. Thanks to Sour for Mesen, aka the greatest development tool, after visual studio.
4 way scrolling
Using vertical mirroring and assuming an overscan of 8px on the top and bottom of the screen, that leaves us with 16px to hide all of the attributes defects. This mean that if we are pixel-perfect, we can get really nice 4-way scrolling without using any special mapper (I use an MMC3)
Here is it running in a small C# version of the game I use for debugging. I use black bars to hide the overscan. When I switch to the debugging mode, there is 2 sets of red lines, one with the overscan and one without. Notice how all the artefacts are kept outside of the visible area. Note that the red/yellow squares are kept on screen for a few milliseconds, i'm not updating that many tiles.
Same thing, in Mesen.
It is a small level but it has been tested on huge maps and supports up to 8 screens on each axis (assuming you have the ROM/RAM to hold the data).
If you are planning to reproduce this, I *highly* advise that you create yourself a reference version in a language that is more "flexible" than ASM. The final ASM version is about 2000 lines of codes (including the code to prime the screen initially, and render some background animations). There are some nasty edge cases to handle, especially when it comes to stitching the attributes of the top and bottom rows, and on edges of name/att tables. Doing this directly in assembly would have been very time-consumming.
Basic assets
Here is a quick overview of all my asset types.
Here is what each of them are:
More gameplay-related assets will be added in the future, this like text, dialog, music, etc.
Basic editor
If you every worked in the game industry, you know how tools are much more important than whatever fancy tech you may have. That's why engines like Unreal are so popular. Their tech is by no mean outstanding, but their toolsets are super flexible and allows artists to have total control over their content. So I decided to spend some times on tools.
The tools handles all the packing in CHR ROM, updates everything automatically. You can safely delete stuff without worrying about your level being completely messed up. It works pretty well.
While you *can* paint sprites and stuff in my tools, there is no way I am going to be able to compete with Photoshop. So I added support for copy and pasting images from external applications. It automatically creates sprites, assigns palettes, detects flips, etc. Here it is in action. Notice how it detects that the hat is a flipped version of the same sprite and how it matches the rest of the body to existing sprints.
You can also compile and launch the game from the level editor:
When you export the data from the editor, you simply need to include a couple of ".inc" file in your code and you are ready to go.
Scripting
My game will not be 100% systemic. By this I mean I want to be able to create unique moments like in Zelda games. Things like:
So i added a little scripting language (it is BASIC-inspired, the first language I learned as a kid). It compiles to some bytecode i made up. It supports a bunch of stuff (loops, arrays, complex math expressions and conditions, etc.) and can also make calls to "engine functions" which are implemented in ASM.
This also allows me to prototypes functionality that I am still not sure how it is going to work. Here is an example of me using it to prototype a door opening and a room transition. As the character hit the trigger next to the keypad, it plays a background animation of a door opening (thus changing the collision) and the room transition is done by another trigger.
Please understand: NOBODY IN THEIR RIGHT MIND would use scripting to open a door and do a room transition like this if you are going to have 3 doors in every room. Of course you would want to make that code part of the engine. But is it good enough for a quick prototype? Absolutely.
The level has 3 types of objects that the script knows about: locators, routes and areas which are respectively 0D, 1D and 2D objects.
A script is assigned to a level. It can have global variables that are kept alive as long as you are in that level. The script can only react to specific events. I dont want any kind of scripting to run on every single frame. Right now the only 2 events I have are:
More will be added as I go along.
Anyway, that's it for now. Hopefully I will keep working on it a have more to report.
-Mat
I've been working on-and-off since the spring on a little zelda-like adventure game. I thought id share what i have so far, maybe that will start a discussion, maybe not at all.
I've mostly been working on the foundations of the engine and tools. I have zero gameplay element, that will come next. Everything you see if obviously a placeholder (my character is a litteral crash test dummy to make this extra clear). I am not an artist in the slightest. I eventually hope to reach a point where I have enough of a game to partner up with a real artist to make this look real nice.
So here is what i've got so far. I'll cover some of the details of each in this post:
- 4-way scrolling (100% artefact free)
- basic assets (metasprites/tiles, animations, levels, etc.)
- basic editor
- small scripting language
Before i start rambling on, thanks to everyone who answered my questions. Thanks to Sour for Mesen, aka the greatest development tool, after visual studio.
4 way scrolling
Using vertical mirroring and assuming an overscan of 8px on the top and bottom of the screen, that leaves us with 16px to hide all of the attributes defects. This mean that if we are pixel-perfect, we can get really nice 4-way scrolling without using any special mapper (I use an MMC3)
Here is it running in a small C# version of the game I use for debugging. I use black bars to hide the overscan. When I switch to the debugging mode, there is 2 sets of red lines, one with the overscan and one without. Notice how all the artefacts are kept outside of the visible area. Note that the red/yellow squares are kept on screen for a few milliseconds, i'm not updating that many tiles.
Same thing, in Mesen.
It is a small level but it has been tested on huge maps and supports up to 8 screens on each axis (assuming you have the ROM/RAM to hold the data).
If you are planning to reproduce this, I *highly* advise that you create yourself a reference version in a language that is more "flexible" than ASM. The final ASM version is about 2000 lines of codes (including the code to prime the screen initially, and render some background animations). There are some nasty edge cases to handle, especially when it comes to stitching the attributes of the top and bottom rows, and on edges of name/att tables. Doing this directly in assembly would have been very time-consumming.
Basic assets
Here is a quick overview of all my asset types.
Here is what each of them are:
- Animation: A series of keyframe, each of them being a Metasprite.
- AnimationSet: A bunch of animation together. This both represents a 1KB switchable bank of CHR ROM and the PRG ROM data for the keyframes.
- BackgroundAnimation: Allows animating the background.
- Bank: Represents an switchable 8KB bank of PRG ROM. You can dump assets in there as long as you dont go over 8KB. Right now only 8 are displayed because I have so little content. Ultimately all 64 might be there.
- Level: More of a "room" than a level really. Comes with things litle triggers and scripts. More on that later.
- Metasprite: Bunch of sprites stuck together.
- MetaTile: a 4x4 grid of sprites. So my metatiles are 16x16.
- MetaTileSet: a bunch of MetaTiles togheter. This both represents a 2KB switchable bank of CHR ROM and the PRG ROM data.
- Palette: Duh
- Sprite: Duh
More gameplay-related assets will be added in the future, this like text, dialog, music, etc.
Basic editor
If you every worked in the game industry, you know how tools are much more important than whatever fancy tech you may have. That's why engines like Unreal are so popular. Their tech is by no mean outstanding, but their toolsets are super flexible and allows artists to have total control over their content. So I decided to spend some times on tools.
The tools handles all the packing in CHR ROM, updates everything automatically. You can safely delete stuff without worrying about your level being completely messed up. It works pretty well.
While you *can* paint sprites and stuff in my tools, there is no way I am going to be able to compete with Photoshop. So I added support for copy and pasting images from external applications. It automatically creates sprites, assigns palettes, detects flips, etc. Here it is in action. Notice how it detects that the hat is a flipped version of the same sprite and how it matches the rest of the body to existing sprints.
You can also compile and launch the game from the level editor:
When you export the data from the editor, you simply need to include a couple of ".inc" file in your code and you are ready to go.
Scripting
My game will not be 100% systemic. By this I mean I want to be able to create unique moments like in Zelda games. Things like:
- You enter a room, the music changes, a big bad guy appear, you kill him, them a chest appear in the corner, etc.
- In a room you have 3 switches on the wall, if you dont press them in the right order, a monster appear, if you solve the puzzle, a door opens.
So i added a little scripting language (it is BASIC-inspired, the first language I learned as a kid). It compiles to some bytecode i made up. It supports a bunch of stuff (loops, arrays, complex math expressions and conditions, etc.) and can also make calls to "engine functions" which are implemented in ASM.
This also allows me to prototypes functionality that I am still not sure how it is going to work. Here is an example of me using it to prototype a door opening and a room transition. As the character hit the trigger next to the keypad, it plays a background animation of a door opening (thus changing the collision) and the room transition is done by another trigger.
Please understand: NOBODY IN THEIR RIGHT MIND would use scripting to open a door and do a room transition like this if you are going to have 3 doors in every room. Of course you would want to make that code part of the engine. But is it good enough for a quick prototype? Absolutely.
The level has 3 types of objects that the script knows about: locators, routes and areas which are respectively 0D, 1D and 2D objects.
- Locators are simple points, simply to represent a coordinate
- Routes are paths, which will be used to assign path to AIs, for example.
- Areas are rectangles, which can be used as trigger (and other stuff later).
A script is assigned to a level. It can have global variables that are kept alive as long as you are in that level. The script can only react to specific events. I dont want any kind of scripting to run on every single frame. Right now the only 2 events I have are:
- on_level_init: Called after a level is loaded, but before it is rendered. This is where I will be spawning AIs, setting up the inital state of things like doors.
- on_trigger_touched: Called when the hero enters a trigger. The id of the trigger is passed as an argument.
More will be added as I go along.
Anyway, that's it for now. Hopefully I will keep working on it a have more to report.
-Mat