My platform game engine using MonoGame

I would like to present the hobby project that I’ve been working on for a while now. It’s open source, and the repository is located at https://github.com/bramdemoor/MonoGame-PlatformerPOC.

It’s a proof of concept of a multiplayer platform game, built using MonoGame, the (pretty awesome) open-source XNA port. The main idea here is to play around with the POC until I have a solid foundation for a game. After that, I will start to develop the ‘real’ game (design document is ready, I’m looking forward to implementing it!).

I work this way because I often tried to do a lot of things at the same time in the past. Eventually, all these attempts failed miserably, so that’s why I’m taking the step-by-step approach now. And it’s working out pretty good so far.

When it’s completed, the engine will feature:

  • LAN network play for two to eight players (using the Lidgren network library)
  • Basic AI bots (allows up to 16 players in total)
  • In-game console
  • Full debug mode
  • Tiled level editor
  • Horizontally scrolling levels with parallax backgrounds
  • Multiple characters
  • Multiple game modes
  • Multiple weapons
  • Different tilesets and level backgrounds
  • Unit tests
  • Compiled to run at many platforms (“everything monogame supports”)

Some of these features are already partially implemented at the moment. But I still have a lot of work to do, and because of my limited time, it will take a while before everything is done.

Anyway, it’s in no way meant to be a one-size-fits-all game engine. It’s just a pile of code for my own use, but I hope somebody else can use it too.

In a while, I might post a video of the game in action, and also some follow-up posts about this project. All depends on the interest of course, so make sure to follow the project on GitHub or comment/tweet. That’s the best encouragement for a lazy developer 😉

Finally, here’s a screenshot of what the thing looks like now. Please note that I used some free graphics in combination with my own uber-sucky photoshop skills. The result: It looks like crap 😉

Don’t worry, the final game will feature graphics by a designer.

My first project on GitHub!

In my recent post Showing off code is hard I concluded that I wanted to focus more on sharing, the community and open source code.
A few days ago, I took a first step in the right direction. I created my very first GitHub repo! I forked this repo. It’s a simple demo of a multiplayer game using HTML5 Canvas for rendering, and SignalR for the network communication.
You can find my repo here. It’s called ‘Jetpack demo’, and builds on the foundations laid out by the original project. My goal with this project is to experiment with scalability, performance and manageability of games built on this simple stack. It’s not a real game, rather a proof of concept. At the moment, it only allows players to connect and fly around in the canvas. That’s about it 🙂
I really like the GitHub workflow so far. I’m using both GitHub for Windows and TortoiseGit. Putting small projects like this one online has a lot of advantages:
  • Instant backup
  • Can instantly show my creation to the guys at work 🙂
  • Maybe it helps/inspires someone
  • …and also…
…it puts some structure in my workflow!
Contrary to my projects at work, my personal projects tend to turn into a mess quite often. I start over a hundred times, throw code away only to realize I want it back, and I try to implement too much features at once. Working with Git (or any other version control system) makes me work more structured, even for mini-projects like this one. I do small, incremental updates with clear commit messages instead of dumping big-bang boatloads of code. This is a nice experience, so I’m going to put a lot of projects on GitHub in the future!
Specifically for this project, I have no real clue where it’s going. Worst case: it just sits on GitHub and gets abandoned. No harm there. It’s better than sitting on my harddrive.

But I might put some cool stuff in. Next things I might implement:

  1. Integrate a lightweight javascript game framework. Current #1 option for me is http://gamejs.org/, but I’m considering other options as well (let me know if you have a good one!). This abstracts away some of the canvas-related stuff and allows me to have an efficient and clear game loop.
  2. Experiment with simple physics, using server-side simulation and client-side motion prediction

Footnote: I often have the ‘my code is not good enough to release to the public’ syndrome. But more recently, I stopped giving a damn. If everyone thought that way, we’d still be in the stone ages of information technology 🙂

Strongly typed XtraReports

At work, we have an application that needs to generate PDF documents related to invoicing. While I usually dislike working with WYSIWYG editors of any kind, the process of creating PDFs to mail and print is so fixed unit-based that it actually makes some sense here. We ended up using XtraReports from DevExpress.
The problem with most reporting frameworks is that they are, well, reporting solutions instead of pure document generation frameworks. So all their concepts are tightly coupled to directly querying a database and aggregating data. Things I don’t need here: I just want strongly typed bindings on in-memory objects! Out of the box, I don’t see any simple way to achieve this. This means: let’s get to work! 🙂
 
Here’s what I want to end up with:
  • Layout created by the report designer, following all conventions of the reporting tool itself
  • A clean viewmodel, so we can prepare the data we want, using LINQ etc instead of some obscure reporting binding language.
  • All databinding strongly typed (e.g. in the’ code behind’ of the report document)
I was very happy when I found the blogpost ‘Strongly-typed Telerik reports
by Jimmy Bogard. I quote: “Magic strings are maintainability grenades, and I like to squash them wherever they show up.” This post really set me on the right track. But Jimmy’s solution is for Telerik, and since we used DevExpress, I had to move some things around. The solution presetend here also uses the ‘UINameHelper‘ class (just google “UINameHelper”). Our custom class where the magic will happen is DevExpressBindingExtensions:
using System;
using System.Linq.Expressions;
using DevExpress.XtraReports.UI;

namespace Reporting
{
    public enum SimpleFormats
    {
        None,
        Date,
        Currency
    }

    public static class DevExpressBindingExtensions
    {
        public static void BindTo<TModel>(this XRLabel label, Expression<Func<TModel, object>> expression, SimpleFormats format = SimpleFormats.None)
        {
            label.DataBindings.Add(new XRBinding("Text", null, UINameHelper.BuildNameFrom(expression), GetFormatString(format)));
        }

        public static void BindVisibilityTo<TModel>(this XRControl control, Expression<Func<TModel, object>> expression)
        {
            control.DataBindings.Add(new XRBinding("Visible", null, UINameHelper.BuildNameFrom(expression)));
        }

        private static string GetFormatString(SimpleFormats format)
        {
            if (format == SimpleFormats.None) return "";
            if (format == SimpleFormats.Date) return "{0:dd/MM/yyyy}";
            if (format == SimpleFormats.Currency) return "{0:€ 0.00}";
            return "";
        }
    }
}
 Then, in a document, we can bind a label like this:
lblCompanyName.BindTo<InvoiceDocumentModel>(m => m.Invoice.Company.DisplayName);
Or we can use a simple format:
lblAmountTotal.BindTo<InvoiceDocumentModel>(m => m.Invoice.AmountTotal, SimpleFormats.Currency);

Finally, we need to address one more issue. As far as I could tell, XtraReports only allows us to bind to collections, and we have a single model instead. Let’s put the fix for that in a single place, the line where we render the actual report:

        internal byte[] RenderTemplate(XtraReport template, TModel model)
        {
            using (var memoryStream = new MemoryStream())
            {
                template.DataSource = new[] { model };        // WHY: XtraReports can only bind to collections
                template.CreateDocument();
                template.ExportToPdf(memoryStream);

                return memoryStream.ToArray();
            }
        }
This feels a lot more natural to me than the standard databinding features. What do you think? Useful or not? Any feedback is welcome!