User Tools

Site Tools


monogame_version_17

Table of Contents

Version 1.7

This time I decided to understand how to rotate things around a centre as I wanted to achieve the effect of rotating a map in a game.

Please bear with me as it got a bit messy, but it looks better if you understand how I thought:

  • RotateSomeSkulls() - This is the 'map', some objects rotating around a centre.
  • DrawSomeSkulls() - Not sure about this one, it is similar to RotateSomeSkulls().
  • DrawFlower() - Drawing a single pixel-image in a circle while changing the radius creates a flower!
  • DrawCircleAndAxis() - Drawing the single pixel-image along the x and y-axis and a circle.

Source code

Our code

Let's start with the rotating “map” as it is what I wanted to achieve with the code.

In LoadContent():

  int top = -windowedHeight / 2;
  int bottom = windowedHeight / 2 - Art.Skull.Height;
  int left = -windowedWidth / 2;
  int right = windowedWidth / 2 - Art.Skull.Width;
  for (int i = 0; i < 10; i++)
  {
      things.Add(new PositionScaleRotation()
      {
          position = new Vector2(randomizer.Next(left, right), randomizer.Next(top, bottom)),
          rotation = 0.0f,
          scale = 1.0f
      });
  }

Here we create 10 skulls at random positions. Please note the top and left variables! They are negative. Since we want to rotate them around the centre of the screen, we want them randomized all around this centre, so some should have a negative position.

We are not using the rotation or scale in this code example but you can easily add it.

In Update():

  angle += (float)(fullCircle / (3600.0d * 2) * gameTime.ElapsedGameTime.TotalMilliseconds);

We continuously increase the angle which is the rotation angle of the “map”.

In Draw() we are just calling RotateSomeSkulls(), which has the following code:

  Matrix rotationMatrix = Matrix.CreateRotationZ(angle);
  Matrix positionMatrix = Matrix.CreateTranslation(windowedWidth / 2, windowedHeight / 2, 0.0f);
  
  rotationMatrix *= positionMatrix;

We create two matrixes, the rotationMatrix which rotates around the Z-axis, and the positionMatrix which translates to the centre of the monogame window.

Then we multiply them with each other. Multiplication of matrixes are different from ordinary multiplication; the order matters! Written more clearly, this is what happens:

  rotationMatrix =  rotationMatrix * positionMatrix;

What happens here? Since we are multiplying the rotation matrix with the position matrix we are effectively moving the rotation centre to the given position on the screen.

If you would do the opposite then, multiplying the position matrix with the rotation matrix? Doing that would effectively rotate the position around the 0,0 position. That is what we are doing in the 1.6 version.

The easiest way of learning these things is to just test around!

  spriteBatch.Begin(
      SpriteSortMode.Deferred, 
      BlendState.NonPremultiplied, 
      null, null, null, null,
      rotationMatrix);

Calling spriteBatch.Begin() with our rotationMatrix will do the magic for us; everything we draw now are rotated around the centre of the window.

  foreach (PositionScaleRotation thing in things)
  {
      spriteBatch.Draw(Art.Skull, thing.position, Color.White);
  }

And that is what we do here, we draw every skull in things at its position. The position is then rotated around the centre of the window.

Back to index

monogame_version_17.txt · Last modified: 2023/01/26 13:39 by jl