As Michael just posted, today we released XNA Game Studio Express Beta 2 for Windows. The biggest addition in this release is that the Content Pipeline is now included, making it super easy to load and use content in your games. We’ve also fixed a lot of bugs and addressed a lot of your feedback from the first beta. I wanted to take a few posts to discuss some of the larger changes in the XNA Framework. Today I’ll be going over the Application Model and the things that have changed.
The first thing you’ll notice when you create a new game is that there is no support for designable game and game components. For beta we only had design time for Windows. Since beta we’ve been working on getting designers to work on Xbox. When we got them running, it was clear that the cross-platform story for developing your game was really difficult when trying to do it via designers. And what if you wanted to create a cross-platform game component for others to use? It was even more difficult. Seeing that this was not ideal, we decided to remove design time support for the application model for v1. Adding a rich design time experience is something we’re investigating for a future version. The reason we introduced design time support initially was because we got it for nearly “free” on Windows. Once we tried to make it work on Xbox, we realized “free” wasn’t, and decided to remove them.
This does not mean we’ve removed game components. They are still there (and improved – more on that later) and behave much like they did previously. We’ve just moved to a code only model. The code that the designers generated inside InitializeComponent is the code you’ll need to write yourself. It’s still very clean and more explicit, which is a good thing.
Game is for the most part the same. We renamed some things and moved some things around based on feedback including improving device management and made resource loading and unloading easier. Here’s a list of the changes:
- Starting event and OnStarting method were removed.
- Initialize was added and replaces what Starting was used for. You should hook up your dependencies and load your non-graphics content here.
- Added LoadGraphicsContent and UnloadGraphicsContent. You no longer have to hook up the various device events (either from GraphicsDevice or IGraphicsDeviceService). We now do all of that for you and call these two methods at the appropriate times.
- Added BeginRun and EndRun. These are protected virtual that you can override if you need to perform some one time scene setup before running, or saving high scores after running.
- Update and Draw now take a GameTime parameter. GameTime provides a snapshot of time passed into these methods.
- Time related properties have been removed from Game. As mentioned, GameTime provides timing data, so we don’t need them on Game anymore.
- Added BeginDraw and EndDraw. These are used by Game to provide a bit more device management. BeginDraw will verify that the device is in a valid state to be used. If it is not, then Draw will not be called. This removes the need for EnsureDevice, which we had in the beta. EndDraw calls Present for you. You can override either of these to have more control, but you usually will not need to.
- UpdateComponents and DrawComponents have been removed. You now call base.Update and base.Draw, which is as it should be.
As mentioned above, we have not removed support for game components. We only removed the ability to design them visually, which was marginally useful at best. But what we did do is take all of the feedback we’ve gotten from the beta and the forums and addressed a lot of it. This makes our game components provide a little more policy, which is good, while also allowing some flexibility in how users can incorporate existing code bases into our component model. The following is a list of changes and additions:
- Added the IGameComponent interface. This is the minimum implementation required to be inserted into Game.Components. It provides initialization hooks.
- Added the IUpdateable interface. This allows for “logic only” components that don’t need or want to draw.
- Added Enabled via the IUpdateable interface. This provides programmatically turning on or off “updates” for a component. This was asked for by several customers.
- Added UpdateOrder via the IUpdateable interface. This provides controlling the order components get updated without having to control the order they are added to the Game.Components collection. This was asked for by several customers.
- Added the IDrawable interface. This allows for components to draw independent of if they can update.
- Added Visible via the IDrawable interface. This provides programmatically turning on or off “draws” for a component. This was asked for by several customers.
- Added DrawOrder via the IDrawable interface. This provides controlling the order components get drawn without having to control the order they are added to the Game.Components collection. This was asked for by several customers.
- GameComponent provides a default implementation of IGameComponent and IUpdateable. It no longer “draws” anything.
- Added DrawableGameComponent that derives from GameComponent and adds IDrawable support. We also removed the need for the component to query for the IGraphicsDeviceService service. Now we provide a GraphicsDevice property and, just like Game, we provide LoadGraphicsContent and UnloadGraphicsContent.
So the big changes here are that we introduced a layering of components by providing logical and logical + visual implementations. Most of you will just derive from GameComponent or DrawableGameComponent. We introduced the interfaces as a way to be a bit more flexible. Now if you have, for instance, a large scene graph code base that you’d like to incorporate into your XNA Game, you can just implement the appropriate interfaces and you’re good to go. You won’t have to flip your hierarchy around and derive everything from GameComponent just to “play” in the Application Model.
In beta, we had a GameComponent called GraphicsComponent that provided GraphicsDevice creation and management. Many people found it odd to have such a “system” level object at the same level as their components. This type is now called GraphicsDeviceManager and is no longer a component. All of the properties are still there to set up the back buffer size, enable multisampling, etc. Additionally, it still publishes the services it provides like it did before.
So I hope that helps explain what the application model looks like now, what the changes were, and what the motivation behind them are. I think the end result will be an API that is easier to use, more explicit and addresses many of the suggestions and problems customers had with the beta application model.
program manager | xna framework