Pretty banner! :)

4k Flash Game Post Mortems

Mine-X 4K Postmortem

Mine-X 4K

First Attempt
Mine-X 4K started out as a simple Asteroids variant. The first pass was a 6K game written in AS3 using standard Sprites and the display list. All of the game images were drawn with a pixel based BitmapData drawing routine that I hoped would save me time and disk space. This was not the case. Also after getting this far, I was over 6K and still had not coded the scrolling or the radar I wanted for the title. When finally I got down to coding the scrolling, it started to become a major hog byte-wise. Also, the radar map demanded that I re-draw the entire scrollable space 2x each frame. All of this code was put in and then quickly thrown out because it ballooned the game to 10K.

The pixel based drawing routine is still one that I might make use of some day. I basically defined the pixels of my sprite in a 1d array of bytes. So, for my 16×16 player ship, non thrusting frame, I had this:

sSD = [
    0,0,0,0,0,0,0,2,2,0,0,0,0,0,0,0,
    0,0,0,0,0,0,2,9,9,2,0,0,0,0,0,0,
    0,0,0,0,0,2,5,5,5,5,2,0,0,0,0,0,
    0,0,0,0,0,2,9,5,5,9,2,0,0,0,0,0,
    0,0,0,0,0,0,2,9,9,2,0,0,0,0,0,0,
    0,0,0,0,0,0,0,2,2,0,0,0,0,0,0,0,
    0,0,0,0,0,0,2,2,2,2,0,0,0,0,0,0,
    0,0,0,0,0,0,0,2,2,0,0,0,0,0,0,0,
    0,0,0,0,0,0,0,2,2,0,0,0,0,0,0,0,
    0,0,0,0,0,0,2,9,9,2,0,0,0,0,0,0,
    0,0,0,0,0,2,9,2,2,9,2,0,0,0,0,0,
    0,0,2,0,2,9,9,9,9,9,9,2,0,2,0,0,
    0,0,2,0,2,2,9,2,2,9,2,2,0,2,0,0,
    0,0,2,2,9,9,9,9,9,9,9,9,2,2,0,0,
    0,0,2,2,2,2,2,2,2,2,2,2,2,2,0,0,
    0,0,2,0,0,0,0,0,0,0,0,0,0,2,0,0
                   ];

Each of the numbers represents a color in an array of colors with 0 being a transparent pixel. These are drawn into the associated BitmapData objects with a setPixel32() call in a loop. Since all game objects (except particles and player missiles) were 16×16, I was able to build all of them in a single loop. No matter because it didn’t save me enough space and it was removed in subsequent versions.

Here is a picture of the original 4kAsteroids game:
4k Asteroids

Pretty ugly, I know. The player ship can’t even be destroyed. Each of the mines is a separate Sprite object that contains a Bitmap object. The BitmapObject rotates by running through a pre-created array of 36 frames (rotated in code before the game starts). The missiles and particles are bliitted to a single canvas, but that proved to make the radar and scrolling I needed almost impossible in the limited code space available. I needed to re-think the entire engine. There is a playable version on 8bitrocket.com if you are interested in trying it out (I didn't think so).

Second Attempt
For my next attempt, I threw out all of the code in version 1 (except the pixel drawing code that I was grasping on to for dear life) and started with a new blit based game engine I had lying around. It was already 16K with a lot of embedded bitmap objects which I had to quickly throw away. I went back to my old pixel plotting code and re-used the mine pixel layout array , but made a new player ship that I liked better. I then added in code for the radar, which was simply a second Bitmap object referencing the same BitmapData object used to draw all of the game objects. For the scrolling, I first extended my world to a 800×800 BitmapData object that was not drawn to the screen (not added to the display list). All of the game objects were updated on that BitmapData off screen.  I then simply created a 400×400 BitmapData for the viewable output. Based on the ship offset from the top left corner of the world, I started doing a copyPixels() from the world map to the 400×400 output screen on each frame tick. Because world contained everything and was updated every frame, the radar Bitmap object holder simply needed a reference to it. This created a radar screen that shows everything happening in the world, scaled down to 20%.

Here is a screen shot  of what I called 4K Scrollable Space.
4k Scrollable Space
The radar is almost invisible in the above picture, but it is in the lower right-hand portion of the 400×400 screen.
In stead of 6K, I was now up to 8K, but I had some plans to get the code to slim down. There is a playable version of this game on 8bitrocket.com if you would like to try it. The fire button in the "x" key in this version. An (ugly American) mistake  that I would soon fix in the final submitted version.

The Final Submitted Version
For the final submitted version (to drop it down 8K to 4K), instead of deleting game elements, I started deleting code. First I tried to shorten my variable names, but that did no good at all and even increased the file size in certain instances. Next I got rid of my optimized game loop and replaced it with a simple EnterFrame event. I also looked for any local variables that were used more than one time and made them global. Since blitting requires a set of Rectangle and Point objects for each copyPixels operation, I eliminated and or shared as many of those globally as possible. While doing that, I got rid of many execution speed enhancements that bloated code. I even did some things that I normally look down upon :( eg) When looping through an array instead of setting the array length to a variable and using that variable in my for loop (like I would to optimized speed), I just slapped that array.length check right into the for loop. I also rid all my event code except the key and enterFrame events. I was now at 6K. I also got rid of my two pre-calculated arrays that represented the dx and dy vector values for movement in 36 rotated directions and replaced them with in-line calculations.

I still had about 20 functions in my game file and most of them were simply called in order during the game loop. I combined almost all of them into one main switch statement and this saved me almost 500 bytes of code. Up until that time, I had left in my particle farm optimization code just in case it would fit, but that was the next to go. Originally, only 500 particles were allowed and they were pre-created in a pool to save object creation execution time. I was sad to see it go, but it allowed me to add a "thrust" frame to the player ship (score!). I then got rid of quite a few randomized elements for the mines and particles by creating one random variable (0-35) that could be used to set the initial movement vector. I then used that same random number to add to the particle life (for instance), etc instead of creating other random variables.  In some instances (if 0-35 was not the right range) I multiplied it by .5 (or 2, or .75), etc to make sure I has numbers within the correct allowable range for a certain attribute. This saved about 600 more bytes.

By eliminating  the code for object world wrapping (and life span for missiles) and replacing it with simple bounce code (and death code for missiles), I was able to save yet a another 300 bytes. My final set of optimizations were used to replace all pixel plotting with vector drawing (I finally had to let that code go). I next picked a simple pallet of 5 colors and re-used them for the entire game. I also created just one TextFormat object for all text in that game and used the "_sans" internal system font. I wanted to add in more colors and text, but there just was not enough space.

By finally figuring out a good use for the "?" operator and by using 5TonsofFlax's "-raw-metadata '' optimization,  I was able to squeeze out a few lines of text in one color and add in a some glow filter effects.

What went right in the final version
1. The radar. This was the first time I attempted to create a duplicate, scaled version of an entire game world that is updated every frame tick. Once I decided to to blit everything to one output screen, the radar became easy to do in very very few lines of code. I wanted to add more of a box around the radar screen, but I was not left with enough bytes to do anything fancy. As it stands, the radar displays the same blue outline that is around the game world and nothing more. One thing I like about the way the radar is constructed is that it shows EVERYTHING, so even the particles are visible. It is even feasible to play the game using just the radar screen. I think one of the contest reviewers didn't like this, but I consider it a feature.

2. The scrolling. I have made quite a few single screen Asteroids style games over the years, so I was happy to add scrolling to this one. In the first versions (that used display objects), I actually had a very difficult time getting it to scroll properly in limited lines of code. I was very happy when I moved to the blit version and was able to just use the world player offset to copy pixels over to the output window. This actually saved me a ton of code. Without it, I would probably have had to leave the scrolling out. With the scrolling in, it reminds me of the game Bosconian to a certain degree, although I was not able to add in the large green bosses from that classic.

3. The Glow effects. One of the final things I was able to squeeze in were the glow effects. Without them, that game was down right UGLY. With them, it is only passable, but they certainly do enough to please the eye in 4K. I had never tried to apply filters to BitmapData objects so my first attempt was to just apply one to the entire output window. This didn't do anything except make the output window look blue.  I liked it enough to apply it to the final version as the blue space background though. I was planning to change that color on each level, but ran out of space. To get a glow around the game objects, I had to re-draw them all as white and little smaller than I originally wanted. I did all of that drawing with vectors in code, then applied the glow filter and then draw them into BitmapData objects. I couldn't even get a glow to look good on the mines, so I removed it (that allowed me enough space to put the word "RADAR" over the radar screen though).  I created two GlowFilter objects whose properties I changed in-line on the fly before they were applied to the various objects. This allowed me to save a few bytes here and there. It also made it possible to change the glow on the particles from level to level (of which there are only 2 different variations – see What Went Wrong).

What went wrong (pretty much everything else)
1. Levels:
I was only able to squeak out two different enemy and even those are just the same enemy in two different colors. That made the 2 different was types, but it wasn’t what I wanted. Also, each of the two types is supposed to have different AI, but I was only able to force in some wave movement differences: One that starts in the upper left and one that starts in the lower left. I was able to flip between yellow and blue for the accent color on each subsequent level was not early enough variety. This resulted in only two different level types that alternate and get progressively more difficult. The game could have been something special if I had reserved enough space to add in the Bosconian like bases and other level features.

2. Missile speed: I simply "fat-fingered" the missile velocity for the player. The reviewers pointed out that I should have added the player velocity to the missile velocity. That certainly would have made the game much better and a little easier.

3. Transitions, end of level, start of level, etc: I built a really cool player enter and exit animation completely in code, but didn't even have enough space to put in the words "level complete" much less all of the frames needed for the animation. As it stands, the level end/start is very abrupt and not anything like I wanted it to be.

4. SOUND! – None of it to be exact. I would have liked to embed a swf with sounds or an mp3, but  there just was not enough room.

5. Enemy mines don’t shoot at player: Again, I didn't even attempt this as there was no code space left, but the original intention was to to have multiple mine types and at least one that shoots back.

6. No more than 1 ship, no power-ups: The design doc for this 4K game was pretty ambitious and included many things that never saw the light of day. Two that would have improved it immensely were multiple player ships (not on the screen at the same time, but in reserve) and power-ups such as shield and mega bombs. As it stands, the game lacks that extra punch associated with power-ups.

I plan to use the core of this engine to make a much more elaborate game (still in under 100K), so maybe it will be worth all of your time when it is complete (and maybe not).

Here is the final submitted version of Mine-X 4K. I also created one with Mochi that adds in high scores and couple extras lines of text (yes and an ad you can skip). The ad is actually automatically applied when you use their encryption service, so that was not any extra work. I am not planning on making any money off that game, but using Mochi lets me see how many plays it has and adds leader board support. I also wanted to see what the final file size would be when those things were added and put though  the Mochi encryption. Also, it ballooned up to 45K with the standard 8bitrocket retro cartridge title screen. Your can Try that version if you want. This helped me choose a file size to constrain the next set of 8bitrocket games we plan to make. They will all be constrained to fit under a certain file size (probably 100K). That size needs to fit Mochi, sounds, and assets, as well game game-play additions.

Pages: 1 2 3 4 5 6

Post Metadata

Date
March 20th, 2009

Author
urbansquall

Category


Leave a Reply