Part 2 – Basic structure of a MonoGame Program (The game loop)
In Part 1 of this tutorial, we installed Visual Studio and MonoGame, and created the first version of our Bricks game. In this part, we’ll look at our project, and examine what’s already been created for us. In the Visual Studio Solution Explorer (upper right of the window), you will see a summary of the project that has been created. I’ve highlighted the three files we’ll be looking at in this section:
The first file, “Program.cs”, we’ll just take a very quick look at, because we won’t need to modify it. I just want to mention it in passing, since it plays an important role. This file has the main entry point that Windows uses to launch our game. That’s all it does. It gets loaded when our program runs, and calls our game Run method:
static void Main()
using (var game = new Game1())
We’ll Look at the “Content.mgcb” file in the next section. It’s used to manage our Content Pipeline. We’ll go over that later, but for now, just remember that you will use the content pipeline to make images, sounds and other assets available to your game.
The “Game1.cs” file contains the Game1 class, which contains the main game loop for your program. Let’s look at the methods in this class to see what they do. Everything we add to the project will be called from the methods in this class.
Here’s the Game1 constructor:
graphics = new GraphicsDeviceManager(this);
Content.RootDirectory = "Content";
This short method provides two critical things needed by our game. First, it creates a GraphicsDeviceManager instance that we’ll use to interact with DirectX.
Second, it tells our program where to look for content (images, sounds, etc.) that we’ll be using in our game. By default, this will be a folder called “Content” under the root folder of our project.
Next, there is an Initialize method that is called once at startup, that we can use to perform any initialization needed. This isn’t used for loading graphics and sounds, and we won’t need it for this game:
protected override void Initialize()
// TODO: Add your initialization logic here
We’ll look at LoadContent method in the next section, when we discuss the content pipeline. But in general, we’ll use LoadContent to cache all our image and sounds assets into memory, so that they can be used quickly while the game is running.
There is also an UnloadContent method. You can use this method to unload assets that you didn’t load using the ContentManager. Since we will be using ContentManager to load our assets, we won’t need to use UnloadContent in our program.
We’ll use the remaining two methods the most: Draw and Update. MonoGame will continuously loop and call these two methods for us. We use the Draw method whenever we want to draw something on the screen.
protected override void Draw(GameTime gameTime)
// TODO: Add your drawing code here
The gameTime property provides the elapsed time since the last update, and also allows us to determine if the game is running at too slow a frame rate, so we can take action. We won’t need that for this game, but it is available for when you develop more complex games. The GraphicsDevice.Clear statement is what caused the game to display the “CornflowerBlue” colored background in the game window.
The Update method will allow us to get inputs from the mouse and keyboard (and a controller, if your game supports one)
protected override void Update(GameTime gameTime)
if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed || Keyboard.GetState().IsKeyDown(Keys.Escape))
// TODO: Add your update logic here
You can see that all that the update method does is check if the Back button on a game controller, or the “Escape” key was pressed on the keyboard. If it was, the program exits. That’s why the program terminated when we pressed escape earlier when we ran the program.
In summary, our game will simply have to load any images and sound the program will need, and then handle Draw and Update events provided by MonoGame. Anything we want to display on the screen we must include in the Draw method. And we’ll get inputs and take actions whenever the Update method is called.
Now that we have the basic framework under our belts, let’s look at how MonoGame handles sound and graphics assets in Part 3