MVC in Games

In the game I’m currently working on, it appears that I’m slowly drifting towards a design that’s a close resemblance of the Model-View-Controller (MVC) pattern, despite originally rejecting the idea because I believed it would require my game world to expose too much of its internal data just so the view could keep track of things.

Because I originally believed to be building a very simple game with very simple logic, I chose a design that would create a nice, non-fractured interface to the world so I would have an easier time building the AI and player controls on top of it:

UML diagram showing an object tree representing the entire game state

In this design, everything could access everything else – a monolithic world component where the public interface was well encapsulated, but that allowed the implementation to take the most direct path possible.

"Everything could access everything else" doesn’t mean my objects directly modified each other’s state, but it meant, for example, that a building had a reference to the island it was placed on and that it could call an internal method in the Island class to inform it when the building was destroyed or moved.

A full design, in contrast, would give the buildings an interface through which they determined properties about the ground (is it too rough? underwater?) and some events so its owner would know when the building was destroyed.

If I had only taken game logic into account, this all would have worked out very well. But there were some things that added a lot of complexity…

Lessons Learned: Complexity

Back when I created above design, XNA had just reached its 1.0 release. One still had to cope with lost devices (that means at any random point, all your graphics resources like VertexBuffers or Texture2Ds would go bang and you had to dispose and recreate them, something that was later hidden from the programmer with XNA 2.0’s virtualized GraphicsDevice), so I did the only sane thing I could do and built a layer for the visuals which would hide that little inconvenience from the game logic (you can see it at the bottom of my UML diagram, the Asset class).

The flaw that made it all come down was that the game logic objects owned the Assets. And because I wanted to be able to unit test my game logic without graphics resources, I designed my Building, Unit, etc. classes to make the Asset optional.

Assets were created through the AssetManager. But how would a Unit or Building obtain a reference to the AssetManager? Simple, I thought: the World owns an AssetManager. As soon as a Unit or Building is added to the World, it would set up its Assets.

Can you smell the problem already? Let’s see what logic each building has to incorporate now, just to function properly within the system I set up:

  1. A building can be constructed and added to an island that is part of a world with an AssetManager.
  2. A building can be constructed and added to an island that is part of a world with no AssetManager
  3. A building can be constructed and added to an island that does not belong to a world. The island can then be added to a world with an AssetManager
  4. A building can be constructed and added to an island that does not belong to a world. The island can then be added to a world without an AssetManager

Now duplicate these 4 cases for when the AssetManager is added to the world after the islands and buildings have been created. And get everything to works right in reverse: the building could be removed from the island again, the island could be removed from the world and the world could loose its AssetManager (in order to avoid imposing a destruction order on the game’s shutdown process)

The result is that each game logic object in the nice tree I built needs to be informed of any ownership changes to its parent, its parent’s parent and so on. And that’s what finally kicked this design out of the door for me.

MVC to the Rescue

To get rid of this complexity, I am currently removing all graphics code from my game logic classes and writing external Renderer classes that contain the graphics code.

The game objects will have to provide additional detail, for example, I’m not sure yet how I handle turrets: they will need to expose their orientation, elevation and either hand over the bullets they’re spewing into the air to another manager or (if I decide to make bullets instantaneous hits/misses) provide at least a list of vectors of the bullets that were fired in the last Update() cycle so the renderer can draw the appropriate streaks.

As it turns out, this more an more resembles the MVC pattern:

UML diagram showing a tree of game objects with separate renderers

I was a bit skeptical as to whether MVC makes any sense as a tool in game programming (for example, see my reply on Doolwind’s blog post "Model View Controller (MVC) Game Engine"), but now I believe that it’s generally a good idea to design the game logic without mixing any graphics code into it. I would select a radically different design for a game with a larger scale, but even then, keeping the graphics code separate from the game logic code seems to be a good idea.

All my problems are nails and MVC is my hammer!

That’s of course not what I’m proclaiming here, but if this turns out well, MVC will probably my preferred architecture for future games :)