Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Rotation of an object around a central vector2 point

Tags:

c#

math

xna

xna-4.0

I should preface this with I am not anywhere near a math person. The code I've found in another question seems to be working somewhat... except that it causes the object I place to rotate in a large circle mostly off screen.

Here's the code:

public void Update(GameTime gameTime)
{
    Location = RotateAboutOrigin(Center, Origin, 0.01f);
}

public Vector2 RotateAboutOrigin(Vector2 point, Vector2 origin, float rotation)
{
    var u = point - origin; //point relative to origin  

    if (u == Vector2.Zero)
         return point;

    var a = (float)Math.Atan2(u.Y, u.X); //angle relative to origin  
    a += rotation; //rotate  

    //u is now the new point relative to origin  
    u = u.Length() * new Vector2((float)Math.Cos(a), (float)Math.Sin(a));
    return u + origin;
} 

Location is set by a mouse click in an arbitrary position around the central vector.

Center is the (you guessed it) center of the object I 'place' when I click. It's determined by simply dividing the height and width of the texture.

Origin is the vector2 I am attempting to rotate around. It's statically set at 384,384.


As best I can tell, it's getting the distance between the two vectors and then using atan2 to determine the angle. The rest afterward is a mystery to me. I'm aware that I should learn what everything does, and I do intend to when I go to college(only a decade late) starting in the spring. I've tried reading up on them, but I'm lost. Any help would be appreciated.

Also, if you have a good trig for dummies site you can recommend, I would be delighted to read through it.

like image 916
Justin Popa Avatar asked Nov 16 '11 08:11

Justin Popa


2 Answers

Here is an alternative:

public Vector2 RotateAboutOrigin(Vector2 point, Vector2 origin, float rotation)
{
    return Vector2.Transform(point - origin, Matrix.CreateRotationZ(rotation)) + origin;
} 

It does the "translate to the world origin, rotate, then translate back" bit.

This rotates 'point' around 'origin' by 'rotation' radians regardless of where origin is relative to the world origin. The trig happens in the 'CreateRotationZ()' built in function. To see how it applies the trig, reflect that method in the framework.

Edit: fixing variable name

like image 127
Steve H Avatar answered Oct 18 '22 18:10

Steve H


This is easier done using matricies, although the underlying theory is possibly a bit harder to understand, you don't really need to know it all to use it (standing on the shoulders of giants and all that).

To rotate a vector about the origin:

Vector2.Transform(PosComponent.Direction, Matrix.CreateRotationZ(-0.1f))

Where PosComponent.Direction is my vector and -0.1f is the amount it want to rotate by (in radians, not degrees).

Since you want to rotate a vector around something other than the origin you'll need to move the vector first, then rotate, then move it back. That's basically what you're code above is doing, except to get the angle and do the rotation it's using trig.

Do do a rotation:

  1. You get the point relative to the origin (as in your code),
  2. then rotate either
    • using trig to get the angle, manipulate it then recalculate the vector (as in your code),
    • or using matricies (as in my code).
  3. Finally move the vector back (as in your code).

This question and my answer, might be of some use in understanding trig: Get position of point on circumference of circle, given an angle?

like image 2
George Duckett Avatar answered Oct 18 '22 20:10

George Duckett