1GAM: February is Different

Well, February’s 1GAM is not really what I expected. A few things happened in January/Feb:

One, it’s official that MS is killing XNA. We’ve all known this, but it’s really really true now. Announced true.

Two, MonoGame is the new hotness for XNA developers. I’m waiting a release or two for the DirectX templates to be made current, but I think this is the way to go. Keep everything the same (it’s event namespace equivalent!) while using an OSS framework that can run on Win, Mac, and mobile devices. XNA dying and developers moving to MonoGame may actually be a win for the community, though losing MS’s brains and backing is not a small matter.

Three, I realized I had been letting a lot of weaknesses in the IceCream engine slide for awhile that I shouldn’t. They became more obvious when I tried to make even a tiny game from start to finish for January. Little things, like sprite-sheet management, positioning being wrong in an annoyingly subtle way, and the code-base being quite large and bloated with large unused portions hanging around. So I scraped it to go custom. I hate writing engines because I think it’s a waste of time, but this way I can do things right and know where to go when I need to dig in. Besides, it won’t be nearly as big as IceCream.

Four, I found the Gearset library for XNA games. This is amazing. I don’t understand why this tool set isn’t mentioned in every XNA article ever written. It’s $35 for Pro and worth every penny. It’s like having better-than-debugger functionality in real-time. Bolded to make sure you read it. It’s a steal and I hope they recompile for MonoGame. It replaces hundreds of man-hours of coding real-time editing and debugging tools. What a find.

Five (wow really?), I installed analytics on my blog and discovered that my article on using the lidgren network framework to build a P2P app is by-far my most read piece (nearly 50% of all my traffic). How and why are still a mystery. It makes me think I should revisit the article, update the app, and post about it again.

Ok, I’m giving up on the list thing. Instead I will accept that this is simply a stream of consciousness and deal with it.

My February game was going to be a top-down zombie killer. I started using tIDE to build levels because it’s a great tool with a great XNA library (though it needs a way to bulk-edit tile properties). Then I put a little player sprite, a zombie spawner and zombies with horrible AI, wired up twin-stick-shooter controls, gave him a pistol, and wanted to kill myself when I tried the result. I stopped all game dev for 4 days afterward. It was terrible. I’m considering trying to salvage it into a Link to the Past like thing (think single environment, not entire world-map) but am having a hard time even opening the code base after seeing the abomination my own hands created. On the up side, I really like the progress I made on the engine. It works, is super-simple, and integrates with TexturePacker well. Next up: PhysicsEditor, then Spriter.

Additionally, failing is good for me. I should get used to it. Better to fail after a week of development in my spare time than after months of betting the farm on it. So really, this is a win.

But seriously, Gearset. I wholeheartedly endorse this library, and get nothing in return if you click any of the links or buy it. I’ve tried a lot of tools in my time, big and small, Windows/Mac/Linux, and this is a cut above. It’s simply a great tool, and you can try before you buy to ensure it’s compat with your kit.

1GAM: Tactical Space Release

Woohoo! First game is done! Download it here:

Tactical Space Release, 5.8 MB 7z

Yes, I shrunk the size from last time by deleting a bunch of textures I wasn’t using. Here are a few screenshots from this latest version to entice you to download it:

Title Screen
Press F1 and F2 for debug info.
Level 3 (the last)


I’m mostly happy with how it turned out. I still like the concept, but the mechanics need a lot of tuning to be more fun. Mostly it consists of: shoot randomly and… watch the puzzle solve itself. It’s interesting from a programming and conceptual point of view, but I think much less fun for the gamer. It’s also not nearly as tactical as I was hoping. When the planets don’t move, it’s incredibly easy. When they do move, they move so fast that getting hits through is random and it becomes extremely difficult aside from spraying the field. If ammo were limited, this would be incredibly frustrating. With unlimited ammo, being tactical is pointless when you can just spray and pray.

I once read that when making games, there are three types of fun:

  1. Fun for the gamer.
  2. Fun for the programmer.
  3. Fun for the computer.

I feel like Tactical Space falls too much into buckets 2 and 3, and not enough of bucket 1. Lesson learned for next time!

Additional lessons learned:

  1. I need a tool to start handling my sprite sheets. The Milkshake editor doesn’t cut it when sprite sheets are changing with assets. Assets I don’t end up using that I want to remove are a bit of a pain. I was able to do it easily manually this time, but only because this is a very small project. I’m going to try to integrate TexturePacker into my process.
  2. IrfanView is a cool concept but handles PNG transparency like the ’90’s. Disappointed.
  3. With many bullets on the screen, performance comes to a crawl. I think because Farseer Physics is way overkill for this game (radius distance collision would have been perfect) and because I think I’m supposed to scale the world to non-real-size (0.1 maybe) and I’m not currently doing that. I may even switch over to polygon collision soon.
  4. I need a re-useable library of my common stuff. I’ve now made so many quick hack games that I’m starting to see what’s reusable across games.

I don’t currently have the source uploaded anywhere but am willing to get it posted (or emailed) if people want it.

Until next time!

(Tech notes: written in .NET 4, XNA, Visual Studio 2012, IceCream engine, Indie Graphics Builder sprites.)

OneGameAMonth: January: Tactical Space

Welcome back!

I’ve started the OneGameAMonth (#1GAM) challenge for 2013! I just wasn’t making much progress on my “big idea”, so I thought it would be best to take smaller but more complete bites. With #1GAM, the idea is to build a very small but complete game each month, and I think that’s exactly what I need to get better.

For January I’ve started a game named, terribly, “Tactical Space”. It came to me while playing the demo of Angry Birds Space. The idea is that you, the player, have a planet on one side of a 2d map and the “enemy” has one on the other side. The goal is to destroy the enemy planet with various weapons, ranging from regular shelling to missiles. Between the two planets are a number of other planets and space debris that block and exert gravitational forces on your projectiles as they fly through space. A screenshot might help:

Click to enlarge (twice, even!)

Let’s pick-apart this hideous excuse for entertainment:

  1. The player is the planet on the left, while the “enemy” is on the far right.
  2. The planets are obvious, but what isn’t obvious is the very lightly faded moon-looking outline on all of them. The texture is poor, but the idea is that it’s showing the field of influence of each of the planets. For example, the two bottom planets have very large fields of effect, and it’s easy to see because of the giant halo around them.
  3. The glowing dots are the projectiles that the player is currently shooting. There are many in this shot.
  4. The salmon-colored lines are for debugging and are drawn between planets and projectiles they’re affecting. On the right you can see a few that are under the influence of two planetary forces.

That’s about it for now, but I’m pretty excited. My next goal is to swap out some of the graphics with images from Indie Graphics Builder (I was part of the Kickstarter), which will help me establish a few more game-dev tools in my toolbox (Irfanview and Texture Packer). Though I think I’m going to go overboard and bloat the game several megabytes just so I can have a few cooler looking sprites. Then I want to add a few weapon options, maybe change the way the enemy planet is destructed, and a few more things I’m sure I won’t have time for in January.

The main tech behind the game is IceCream (modified by me), with Farseer Physics Engine handling hit detection when a sprite hits a planet. I’m not using realistic gravity simulation from Farseer, though I should be! Let me know if you have a great algorithm for handling gravity already written in C#. I just made mine up.

Download the game so far (9.1 MB 7z)

Component Design Systems

On my IceCream 1945 Code Project article, I recently received the following question:

I’m still trying to wrap my head around the component design system. Can you suggest any more required reading on the topic?

I wrote a quick off-the-cuff response, but I’d like to dive a little deeper into the question here. I made a mistake saying it’s like object-oriented programming because I think that’s inaccurate once you get past the basics. Instead, I would say the component model is very much like service oriented programming. Each component is written to provide a specific service to any entity in your game. To demonstrate the difference, here’s an example of a short loop on a game’s enemies using procedural programming:

foreach (Enemy e in enemyList) {
    // etc

Here is a similar loop using object-oriented programming:

foreach (Enemy e in enemyList) {
    // etc

Now, here’s that same loop using the component model:

foreach (SceneItem si in scene.AllSceneItems) {
    foreach (IceComponent component in si.Components) { // list of services attached to this item
        component.Update(); // tell the service to update

Notice this time we don’t care what kind of SceneItem we’re referencing. And, we don’t even need to tell it to execute specific behaviors, which would start to become littered with conditionals in an advanced game. Instead, we’re just telling it to execute whatever service components are bound to it.

This way, we don’t have to worry about the looping, or worry about whether we should call an AI routine on something without AI, or velocity on a static object, etc. If the scene item should have velocity, it gets a VelocityComponent service. If it should have AI, it gets an AIComponent service. With IceCream, those components are automatically run each Update() without us having to write the loop or ensure the proper routines are called on all the right objects. Each of these Components provides a basic service to the SceneItem it is bound to, without any care as to what that SceneItem represents or is “doing” in the game.

For further reading, check out this Wikipedia entry for Component-based software engineering.

How-To: Create a New XNA IceCream Based Project

This seems like a lot of steps, but it’s really quite a simple process. Please let me know in the comments if you need help or I made an error. Have fun!
  1. In Visual Studio, create your XNA 4 Game project.
  2. Add a reference to the IceCream DLL, or optionally include it and MilkShake in your project as source so you can have much better debug information if things break or don’t behave as expected. Be sure to include IceCream, Milkshake, and MilkshakeLibrary if you go the source route. Also, you will a compiled EXE of  Milkshake if you won’t be building it in your project.
    I suggest you include all 3 projects as source in your solution, but it’s not required.
  3. Create a new text file called “Game.icproj” in your game project in Visual Studio (not in the Content project!).
  4. Ensure the Build Action is None and Copy to Output Directory is “Copy if newer”.
  5. Open Game.icproj for editing and modify it to look something like this (change “ProjectName” to your project name)
    <?xml version="1.0"?>
    <IceCreamProject xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
      <ContentFolderRelativePath />
      <LastOpenedScene />
  6. Create another new file, this time in your Content project, called global.ice. Set the Build Action to None and Copy to Output Directory to “Copy if newer”.
  7. Copy-paste in the following contents:
        <Components />
        <SceneItems />
        <Templates />
  8. Open Milkshake.exe and open your newly created Game.icproj file with the Open Project button.
  9. It should load without an errors and you’ll still be staring at a gray screen. However, the toolbar will have updated and you can now create a new scene. Click the New Scene button.
  10. When you’re ready, clicking the Save All button will prompt you to give your new scene a name and location. Save it in your game’s Content project directory. Be sure to include this file in your project and set Build Action to None and Copy to Output Directory to “Copy if newer”.
  11. Anytime you add new assets with the IceCream UI (like a spritesheet), you’ll need to include them in your Visual Studio Content project and ensure they make it in the compiled Content directory.
  12. Navigate to your Game1.cs file (or whatever you’ve renamed it to) and modify it to the following contents (modify the namespace for your game):
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using Microsoft.Xna.Framework;
    using Microsoft.Xna.Framework.Audio;
    using Microsoft.Xna.Framework.Content;
    using Microsoft.Xna.Framework.GamerServices;
    using Microsoft.Xna.Framework.Graphics;
    using Microsoft.Xna.Framework.Input;
    using Microsoft.Xna.Framework.Media;
    namespace ProjectName
        /// <summary>
        /// This is the main type for your game
        /// </summary>
        public class Game1 : IceCream.Game
            public Game1() {
                ContentDirectoryName = "ProjectNameContent";
  13. Set your Content directory to be called <project name>Content instead of just Content. Ensure you’ve added a reference to IceCream in your game project. Build and run!

That’s it! Your base IceCream project is all setup!

Learning XNA 2d Engine IceCream With 1945 Demo Project

Cross-posted to CodeProject.

1945_Code_Package – 1.5 MB
1945_Demo_Package – 542 KB

3-22-2012 Update: The code package had an error in the content project. This has now been fixed.

IceCream1945 is a demonstration of XNA and the IceCream 2d library in a 2d top-down scrolling shooter similar to 1942 for the NES.


XNA is a wonderful game development SDK from Microsoft. It handles so many core game-engine features and allows you as the developer to jump right into the fun stuff. But because it’s open-ended to fit everyone, 2d and 3d games, it can be a bit much to work with once you’ve narrowed down the scope and type of game you want to make. If you’re making a 2d game, you start with a very powerful one-size-fits-all library that takes a lot of refinement. It makes sense to use another layer on top of XNA to get you even closer to your game type without yet having to write any code.

IceCream is a framework written in XNA to handle 2d sprite-based games. If that’s the sort of game you want to make, this article and framework are for you. If you want 3d, your time will be better spent reading something else.

Before diving into the meat of the article, I would encourage you to download the source code and sample demo application and give it a playthrough. It’s very short but demonstrates many of the things this article discusses: loading scenes, sprite movement, player input (WASD), enemies, bullets and collisions, animation, a scrolling background, etc. The controls are:

  • Movement: W, A, S, and D
  • Fire bullet: Space
  • Drop bomb: Left Shift
  • Quit: Escape

Now that you’ve seen the engine in action, let’s talk a little more about the framework.

What is IceCream and its history?

The IceCream library is the fruits of labor by Episcode (Loïc Dansart) and conkerjo. It hadn’t seen a repository commit since 2009 until I found it and asked if there was an update available for XNA 4.0 compatibility. I was in luck, as Loïc had already done all the work but just hadn’t committed it. A few hours later and the latest XNA 4.0 compatible code was committed and ready for action. The official code license as given by Loïc via email is to do whatever you want with it, as long as it’s not for a public derivative editor/engine.

What’s Special About IceCream/Why Should I Use It?

Why write yet another 2d engine for XNA when this one has tons of built-in functionality and a GUI editor? More specifically, IceCream has built-in support for spritesheets, static and animated sprites, layering, tile grids, particle effects, post-processing effects, and composite entities (think: 2d humanoid with arms and legs that are animated like a skeleton rather than a single whole sprite for each position). It even has a GUI editor for putting all those items into your levels (“scenes” as IceCream calls them).

IceCream is built on a component design model. Each SceneItem can have 0 or many Components, which are code pieces you write that do or control anything you want. The most basic type is a velocity component, which gives the sprite its movement. A velocity component might have a Vector2 to describe X and Y velocities, and every Update(), move the sprite by those amounts. But IceCream doesn’t have any built-in components or make assumptions about how you want to write your game. It just enables you to attach reusable code to every scene item, via components, that is given an Update() call every loop.

There is no override-able Draw() method because IceCream handles all drawing. That’s the only constraint of this engine. Since it does all the drawing, you don’t have the opportunity to do your own drawing if that’s your thing. But that’s also the point: all the drawing code has been written for you. (The exception to this is that your main game class, that inherits from IceCream.Game, does get a Draw() override, but components do not.)

If you feel it’s really lacking a drawing ability you want, however, it’s open-source, and you can easily jump in and modify it to your hearts desire. After working in the codebase for the past few months, I can say that it’s pretty easy to understand once you learn where things are. The drawing portion is a bit complicated because it’s extremely capable, but it’s not magic.

I’m going to skip over the details of the GUI because I’m assuming that you have some development experience and knowledge. Thus, the MilkShake UI should come pretty naturally in 10 to 15 minutes of self-exploration when opening the included project file (point MilkShake to IceCream1945/Game.icproj).

Component Properties

As I mentioned, IceCream is component based, and the primary location for your code is within these components. Each component can override the following methods:

  • CopyValuesTo(object target) – Called regularly by the IceCream engine to perform deep-copies. Anytime you add properties to your component, you’ll need to add them to the copy operation that happens in this method. It’s up to you to decide what parts of the object’s state are relevant to a deep copy, and which should be skipped.
  • OnRegister() – Called whenever the parent SceneItem is registered with the scene, which happens when the scene is loaded into memory, or the next Update() after a SceneItem is new-ed and added to the scene (footnote: it’s also possible to tell a scene to register an item immediately rather than next Update()).
  • OnUnRegister() – Called whenever a SceneItem is marked for deletion and removed from the scene.
  • Update(float elapsedTime) – Called every loop for your component to advance state, whatever that might mean. This is where the real meat happens. A component to check for player input would do the input checking in this method. Likewise, our aforementioned VelocityComponent example would use this method to modify the X and Y position of it’s parent SceneItem.

Sometimes it makes sense for these properties to display in the MilkShake GUI settings area when building the scene. To do this, we decorate those properties with [IceComponentProperty(“text”)]. This attribute is used to tell the MilkShake UI that this property should be editable in the property list UI, and what text description to use. Properties without this attribute are not exposed in MilkShake. The easy way to think of this is, if it has an IceComponentProperty decorator, it’s a configuration value in the editor. If not, it’s probably an internally managed state property.

Example of IceComponentProperty

[IceComponentProperty("Velocity Vector")]
public Vector2 Velocity { get; set; }

Various Examples of IceCream Component Properties in the UI

Example: Full VelocityComponent

namespace IceCream1945.Components
    public class VelocityComponent : IceComponent
        [IceComponentProperty("Velocity Vector")]
        public Vector2 Velocity { get; set; }
        public VelocityComponent() {
            Enabled = false;//we manually Enable the component in other locations of code. By default, all components are enabled.
        public override void OnRegister() { }
        public override void CopyValuesTo(object target) {
            if (target is VelocityComponent) {
                VelocityComponent targetCom = target as VelocityComponent;
                targetCom.Velocity = this.Velocity;
        public override void Update(float elapsedTime) {
            if (Enabled) {
                this.Owner.PositionX += Velocity.X * elapsedTime;
                this.Owner.PositionY += Velocity.Y * elapsedTime;

Getting Into the Code

Moving past components and getting into intial game startup for IceCream1945 (not part of the core IceCream library), we have our MainGame class, which inherits from IceCream.Game. We can optionally override the common XNA methods like Update() and Draw(). I use this class for basic initialization, holding the current scene, and navigating among scenes (e.g., title screen to level 1, level 1 to game over, etc). In my sample, I wanted this class to be very lightweight and relatively dumb.

Again, this class is custom code, and not part of the standard IceCream codebase.

public class MainGame : IceCream.Game
	public static GameScene CurrentScene;
	public static readonly string SplashIntroSceneName = "Splash";
	public static readonly string Level1SceneName = "Level1";
	public static readonly string EndingSceneName = "Ending";
	public MainGame() {
		GlobalGameData.ContentDirectoryName = ContentDirectoryName = "IceCream1945Content";
		GlobalGameData.ContentManager = Content;
	protected override void LoadContent() {
		this.IsFixedTimeStep = false;
		CurrentScene = new MenuScene(SplashIntroSceneName);
	protected override void Update(GameTime gameTime) {
		if (GlobalGameData.ShouldQuit) {
			if (CurrentScene != null)
		if (CurrentScene.MoveToNextScene) {
			if (CurrentScene.SceneName == SplashIntroSceneName || CurrentScene.SceneName == EndingSceneName) {
				CurrentScene = new PlayScene(Level1SceneName);
			else if (CurrentScene.SceneName == Level1SceneName) {
				CurrentScene = new MenuScene(EndingSceneName);
	protected override void Draw(GameTime gameTime) {
	protected override void UnloadContent() {

The scene that I’m referring to here is different than the IceCream.Scene. I’ve created an abstract GameScene class that is the base class of PlayScene and MenuScene. This allows me to reuse common methods in GameScene but have specialized circumstance handling for a “menu”-like scene vs a “gameplay” scene (and potentially others). In a GameScene, I’m expecting for the player to be actively controlling a game object, for the AI to be thinking, and for the camera to be moving. But a MenuScene is all about presenting information and waiting for user input. Hence, I felt it would be more clear to split the two cases into separate objects rather than litter a single object with conditionals.

MenuScene Class Update() method

public override void Update(GameTime gameTime) {
	float elapsed = (float)gameTime.ElapsedGameTime.TotalSeconds;
	IceCream.Debug.OnScreenStats.AddStat(string.Format("FPS: {0:0.00}", DrawCount / gameTime.TotalGameTime.TotalSeconds));
	if (ReadInput || WaitBeforeInput.Stopwatch(100)) {
		ReadInput = true;
		if (InputCore.IsAnyKeyDown()) {
			MoveToNextScene = true;

Preloading, Caching, and GlobalGameData

GlobalGameData Class and Startup Caching

public static class GlobalGameData
	public static ContentManager ContentManager = null;
	public static bool ShouldQuit = false;
	public static string ContentDirectoryName = string.Empty;
	public static int ResolutionHeight = 720, ResolutionWidth = 1280;
	public static int PlayerHealth;
	public static int MaxPlayerHealth = 18;
	public static bool SoundOn = true;
	public static bool MusicOn = true;
	public static float SoundEffectVolume = 0.3f;
	public static float MusicVolume = 0.3f;
	public static List InactiveSceneItems = new List&lt;SceneItem&gt;();
	public static List ActiveSceneItems = new List&lt;SceneItem&gt;();
	public static SceneItem PlayerAnimatedSprite = null;
	public static PostProcessAnimation ScreenDamageEffect = null;
	public static PointTracking PlayerOnePointTracking = new PointTracking();
GlobalGameData.PlayerAnimatedSprite = scene.GetSceneItem&lt;AnimatedSprite&gt;("PlayerPlane_1");
HealthBarItem = scene.GetSceneItem&lt;Sprite&gt;("HealthBar");
GlobalGameData.PlayerHealth = GlobalGameData.MaxPlayerHealth;
GlobalGameData.ScreenDamageEffect = scene.CreateCopy&lt;PostProcessAnimation&gt;("PlayerDamageScreenEffect");
foreach (SceneItem si in scene.SceneItems)
//sort the inactive list so we only have to look at the very first one to know if there is anything to activate.
GlobalGameData.InactiveSceneItems.Sort(delegate(SceneItem a, SceneItem b) { return b.PositionY.CompareTo(a.PositionY); });

GlobalGameData is a singleton class (my custom code, not part of base IceCream) that holds references to game settings and commonly used objects. During things like collision detection, it’s necessary to run through all scene items for detection. Something like that is extremely slow and can catch up to you after your game is past a simple proof of concept. So I’ve created Active and InactiveSceneItems lists for just this purpose. When running through items looking for collisions, I only look through what’s active, which I consider to be sprites that are shown on screen or have moved beyond it (though those should be eliminated automatically by a bounds detection component). This way I’m not checking scene items at the end of the level when the player just starts, and I can control the enabling of scene items as the player moves throughout the level rather than having all sprites immediately start traversing the level.

There are faster methods, such as dividing the screen into quadrants or other sectioning, but for now, an active list of only on-screen SceneItems is more than fast enough.

Additionally, things like the health box and score are moved every frame to be at the top of the screen while the camera moves “upward”. This requires the code to always touch the PositionY property, and it’s very wasteful to find these objects every frame. So we find them once and keep a reference at our fingertips.

Essentially, GlobalGameData is where “global” variables are held. In a more robust game, these references would probably be split into more concise objects, such as a static Settings object and a SceneItemCache object, or corrosponding management-type objects. But in all cases, we only need and want one copy of this data, and we want it accessible from nearly everywhere in our game. We don’t want to have to pass around some sort of context object to all our methods when a globally-accessible context object will work just the same (because we’ll never need to have two context’s co-exist in a single running instance). There is a fine line between “global variables are bad” and bloating all your method signatures to pass a reference to an object throughout your code.

Game Loop: Scene Movement and Background Scrolling

The scene is moved along with actual movement of the camera. Some scrollers work by moving the scene into the view of a static camera or other indirect ways, but I decided it was most efficient and mentally straight-forward to move just the camera and have it scan across the level. Some of the reasons include:

  1. If I had to move the scene into the view of the camera, I would need to modify the position of every single scene item every single frame to move them into the view of the camera. By moving the camera, only the scene items actually moving via AI have to move.
  2. Keeping the camera static but spawning objects just outside the view of the camera via a script adds significant code and GUI complexity.
  3. The GUI editor is already setup for camera movement over a laid-out scene. The point of using IceCream is to leverage the tools someone else has written.

Code of Camera Movement

float ScrollPerUnit = 60.0f;
float elapsed = (float)gameTime.ElapsedGameTime.TotalSeconds;
float distance = elapsed * ScrollPerUnit;
scene.ActiveCameras[0].PositionY -= distance;

The background movement is only partially real. It’s just a single sprite the width of the screen and 32 pixels tall, duplicated to the height of the screen plus two. Each time the bottom strip disappears from the view of the camera, it is shuffled to the top. So the background images are perpetually being moved bottom to top as the camera moves along the scene, and we don’t have to waste memory copying the strip to the entire vertical length of the scene. We only need enough memory to cover the users view.

Code of Construction of Background Sprites

/* Load Background Water sprites */
Sprite water = scene.CreateCopy&lt;Sprite&gt;("Water1280");
WaterHeight = water.BoundingRectSize.Y;
double totalWaters = Math.Ceiling(GlobalGameData.ResolutionHeight / WaterHeight) + 1;
for (int i = -1; i &lt; totalWaters; ++i) {
	Sprite w = scene.CreateCopy&lt;Sprite&gt;("Water1280");
	w.Layer = 10;
	w.PositionX = 0;
	w.PositionY = i * WaterHeight;

Code of Background Sprite Movement and Swapping

/* Background Water Movement (totally fake)
 * Since our camera is moving up the Y axis, all we have to do is shift the background upwards
 * everytime the camera moves the equivalent of a tile height. */
BackgroundOffset += distance;
if (BackgroundOffset &gt; WaterHeight) {
	foreach (Sprite water in BackgroundWaters) {
		water.PositionY -= WaterHeight;
	BackgroundOffset -= WaterHeight;

For sprite and camera movement, I decided to move things in the game based upon the time that has passed between update calls. XNA likes to run at 60 fps regardless of whether you enable IsFixedTimeStep, and in a low complexity game as it is right now it doesn’t make much difference. But if our framerate ever starts to drop due to scene complexity, this design decision will keep the game more playable and consistent.

Example of Time-Based Sprite Movement

public override void Update(float elapsedTime) {
	if (Enabled) {
		this.Owner.PositionX += Velocity.X * elapsedTime;
		this.Owner.PositionY += Velocity.Y * elapsedTime;

The other way to write this method is to move each sprite a flat X number of pixels each call to update, regardless of how much time has passed. Very old games written in the 80’s and early 90’s that used this method are out of control on today’s PCs. Back then, developers didn’t think their games would still be played today, so they were written to go all-out with no limiter of any kind in place. I think it’s important to realize your code has much more life in it than you think.

To prevent that scenario from happening in the inevitable future, the XNA framework is supposed to be intelligent enough to cap the framerate at 60 frames per second even if the hardware can play your game much faster.

Player Movement and Firing: PlayerControllableComponent

The PlayerControllableComponent is applied to the sprite that the player controls. It watches for input via IceInput and moves the sprite accordingly. It’s setup for multiple players, but I have not implemented it. The rest of the code could easily be modified for co-op, but I decided it was out of scope for my first exercise.

PlayerControllableComponent Class Update()

public override void Update(float elapsedTime) {
	// when the owner uses PlayerIndex.One
	if (Playerindex == PlayerIndex.One) {
		// if W button is pressed
		if (InputCore.IsKeyDown(Keys.W)) {
			// we go upwards
			Owner.PositionY -= Velocity.Y;
		// if S key is pressed
		if (InputCore.IsKeyDown(Keys.S)) {
			// we go downwards
			Owner.PositionY += Velocity.Y;
		// if A button is pressed
		if (InputCore.IsKeyDown(Keys.A)) {
			// we go to the left
			Owner.PositionX -= Velocity.X;
		// if D button is pressed
		if (InputCore.IsKeyDown(Keys.D)) {
			// we go to the right
			Owner.PositionX += Velocity.X;
		if (BulletTimer.Stopwatch(100) &amp;&amp; InputCore.IsKeyDown(Keys.Space)) {
			//fire projectile
			AnimatedSprite newBullet = Owner.SceneParent.CreateCopy&lt;AnimatedSprite&gt;("FlamingBullet");
			newBullet.Visible = true;
			newBullet.Position = Owner.Position;
			newBullet.PositionX += Owner.BoundingRectSize.X / 2;
			VelocityComponent velocityCom = newBullet.GetComponent&lt;VelocityComponent&gt;();
			velocityCom.Enabled = true;
		if (BombTimer.Stopwatch(100) &amp;&amp; InputCore.IsKeyDown(Keys.LeftShift)) {
			//drop bomb
			Sprite newBullet = Owner.SceneParent.CreateCopy&lt;Sprite&gt;("Bomb");
			newBullet.Visible = true;
			newBullet.Position = Owner.Position;
			newBullet.PositionX += Owner.BoundingRectSize.X / 2;
	//[...] Unused code relating to PlayerTwo
	if (InputCore.IsKeyDown(Keys.Escape)) {
		GlobalGameData.ShouldQuit = true;

This component watches for all player input, including the fire and drop-bomb buttons, so it also handles spawning those scene items when necessary. IceCream allows us to handle this very easily. With MilkShake, I created a FlamingBullet animated sprite with the following components already attached and configured:

  • VelocityComponent: Give this bullet X and Y velocity.
  • LifeComponent: If this bullet lives for longer than 2 seconds, destroy it. This prevents bullets from slipping through other checks and living forever. This is more useful for testing by throwing an exception if 2 seconds is ever reached. Currently, no player bullets should live that long, so anything that does is an error. It’s possible and even prudent to write some components as small tests to ensure other components are doing their job.
  • BoundsComponent: If this bullet moves completely out of view of the camera, destroy it. We don’t want the player destroying objects all the way down the level.
  • BulletComponent: This component handles checking for collisions and dealing damage.

When the player fires a flaming bullet, I ask IceCream to make a copy of this template, tweak the speed on the VelocityComponent, and register the scene item with IceCream. The IceCream engine and my components then take over the rest, and the PlayerControllableComponent can completely forget about it.

Collision Detection

Collision detection in this demo application is only relevant for “bullets”, aka projectiles. The player fires bullets, and enemies fire bullets. Each bullet is an animated sprite with a BulletComponent, which has 2 flags for whether it can damage the player and whether it can damage enemies (it could be both).

When this component executes Update(), it looks through all scene items in the ActiveSceneItems list and compares its bounding rectangle to the bullets. If they intersect, it’s a collision. A better way of it doing it that I didn’t implement here is, after it’s determined the rectangles cross, drop into a more granular test of either pixel-by-pixel, or polygon detection. However, I again decided this was out of scope for this initial exercise. IceCream has some initial support for polygon collision detection, but it’s not yet fully implemented.

If there is a collision, an explosion animation is spawned and damage is applied appropriately. For enemies, right now they simply die. The player, however, has a life bar that decreases per hit. Additionally, if the player is hit, a post-processing effect is briefly played that causes the screen to blur and flash very briefly. This gives the player visual feedback that they were struck that is far more noticeable than looking to see if bullets hit or life decreased. It catches their attention regardless of what part of the screen they’re looking at.

public override void Update(float elapsedTime) {
	//We get all scene items ( not recommended in bigger games, at least not every frame)
	for (int i=0; i &lt; GlobalGameData.ActiveSceneItems.Count; ++i) {
		SceneItem si = GlobalGameData.ActiveSceneItems[i];
		if (si != Owner &amp;&amp; (si.GetType() == typeof(Sprite) || si.GetType() == typeof(AnimatedSprite)) &amp;&amp; !Owner.MarkForDelete) {
			if (CanDamageEnemy) {
				if (si.CheckType(2) &amp;&amp; Owner.BoundingRect.Intersects(si.BoundingRect)) {
					si.MarkForDelete = true;
					Owner.MarkForDelete = true;
					AnimatedSprite explosion = Owner.SceneParent.CreateCopy&lt;AnimatedSprite&gt;("BigExplosion");
					explosion.Visible = true;
					explosion.Position = si.Position;
					explosion.PositionX += si.BoundingRectSize.X / 2;
					explosion.PositionY += si.BoundingRectSize.Y / 2;
					explosion.CurrentAnimation.LoopMax = 1;
					explosion.CurrentAnimation.HideWhenStopped = true;
			if (CanDamagePlayer) {
				if (Owner.BoundingRect.Intersects(GlobalGameData.PlayerAnimatedSprite.BoundingRect)) {
					Owner.MarkForDelete = true;
					GlobalGameData.ScreenDamageEffect.Reset();//if the player is getting bombarded, we want many flashes

Post Processing Effect on Player-Bullet Collision

As I mentioned earlier, IceCream supports various post-prcessing effects out of the box. Many classic scrolling shooters have some sort of screen-flashing effect when the player is hit and loses a health point. A post-processing effect is the natural way to pull off this trick. I load and cache the effect when the scene is first loaded, and just instruct IceCream to play it a single time whenever a collision occurs.

I set up the effect through this UI in Milkshake:

And then call it in the BulletComponent. I call Reset() before I call play, so if the player is hit repeatedly the effect will start over instantly rather than only finishing playing once. I think this sort of immediate feedback to the player is key to a game that feels “tight”.

if (CanDamagePlayer) {
	if (Owner.BoundingRect.Intersects(GlobalGameData.PlayerAnimatedSprite.BoundingRect)) {
		Owner.MarkForDelete = true;
		GlobalGameData.ScreenDamageEffect.Reset();//if the player is getting bombarded, we want many flashes

Enemy Movement and AI, and Tags Feature

One of the wonderful things about IceCream being open-source is that you’re free to modify it if you don’t think it serves all your needs. One of the neat changes I made was to add a “tags” property, which is a simple list of strings that I use for grouping and other attributes. Because it would be slow to parse this tag data during game-play, I parse and cache in one pass when the scene is loaded.

Group (Tag) Caching

protected Dictionary&lt;string, List&lt;SceneItem&gt;&gt; Cache_TagItems;
public GameScene(string sceneName) {
	Cache_TagItems = new Dictionary&lt;string, List&lt;SceneItem&gt;&gt;();
public virtual void LoadContent() {
public string GetGroupTagFor(SceneItem si) {
	foreach (string tag in si.Tags) {
		if (tag.StartsWith("group"))
			return tag;
	return string.Empty;
protected void CacheTagItems() {
	if (scene == null)
		throw new Exception("Can't cache tags before loading a scene (scene == null)");
	foreach (SceneItem si in scene.SceneItems) {
		foreach (string tag in si.Tags) {
			if (!string.IsNullOrEmpty(tag)) {
				if (!Cache_TagItems.ContainsKey(tag)) {
					Cache_TagItems[tag] = new List&lt;SceneItem&gt;();
public List GetItemsWithTag(string tag) {
	if (Cache_TagItems.ContainsKey(tag))
		return Cache_TagItems[tag];
		return new List();

In IceCream1945, the primary use of tags is for grouping enemies. As the level is scrolled, each Update() call checks to see if a sprite has crossed a threshold near the camera’s view and should come to life in the scene. Because this is a top-down shooter, sprites tend to come to life in waves. That is, 4 or more sprites will move across the scene as one. To facilitate this, each sprite is assigned a group through the tag mechanism. When one sprite is activated, the group tag is read, and all other scene items with a matching group are activated. This activates the entire “wave” and keeps them moving as one without extra code or level design complexity.

SceneItem Activation and Group Activation Snippet

int activationBufferUnits = 20;
for (int i=0; i &lt; GlobalGameData.InactiveSceneItems.Count; ++i) {
	SceneItem si = GlobalGameData.InactiveSceneItems[i];
	if (si.BoundingRect.Bottom + activationBufferUnits &gt; scene.ActiveCameras[0].BoundingRect.Top) {
		//grab all other scene items in the same group and turn them on as well
		string groupTag = GetGroupTagFor(si);
		if (groupTag == string.Empty)
		List groupItems = GetItemsWithGroupTag(groupTag);
		foreach (SceneItem gsi in groupItems) {
	else //if we didn't find anything to activate, we can just abort the loop. Our inactive list is sorted
		break; //so that the "earliest" items are first. Thus, continuing the loop is pointless.

Scoring and Achievements

Finally, for scoring and achievement tracking, I have a PointTracking singleton that can be created per-player (or configured for multi-player storage) if you wanted to add multi-player support. Right now it’s only used for scoring, but it’s intended to be in scope for the entire application for other things like number of shots fired, number of kills, etc that can be fun stats to view at the end of a level, or even track for the life of a player and grant achievements.

PointTracking code snippet

/// &lt;summary&gt;
/// General class for tracking score, number of kills, shots fired, and other metrics for achivements and similar
/// &lt;/summary&gt;
public class PointTracking
	public int PlayerScore { get; private set; }
	public void AddScore(int additionalPoints) {
		PlayerScore += additionalPoints;

That concludes this intro to the 2d XNA IceCream library through the sample game IceCream1945. I hope you enjoyed the article and will download the sample application and source code. IceCream is a phenominal library that deserves more attention and contributions.


Moving the Camera in IceCream

I know this sounds silly, so it’s mostly just a note to myself. The proper way to move the camera in IceCream is:

scene.ActiveCameras[0].Position = new Vector2(300300);

I know this may seem obvious, but looking at the various properties, this was not the first thing I tried.

Also, if you’re relying on the camera BoundingRect for anything (like bounds-checking), IceCream by default does not recompute the BoundingRect when the camera is moved. I had to patch that one in, too. I’m really starting to get a feel for the IceCream code base, and I like what I see when I’m digging around.