2017-02-16 2 views
1

Je ne suis pas très versé dans les mathématiques matricielles, donc toute aide serait appréciée. J'ai donc un simple sprite de vaisseau qui tourne et se déplace. Pour calculer le rectangle de délimitation I essayé d'utiliser une matrice de rotation et le code que je suis sorti de ces tutoriels:Matrice de rotation provoquant la modification de la position du sprite

http://xbox.create.msdn.com/en-US/education/catalog/tutorial/collision_2d_perpixel

Mais chaque fois que le sprite tourne sa position X et Y du changement rectangle englobant de manière drastique, par comme 100s de pixels. La méthode de calcul du nouveau rectangle de délimitation est comme suit:

public static Rectangle CalculateBoundingRectangle(Rectangle rectangle, Matrix transform) 
    { 
     // Get all four corners in local space 
     Vector2 leftTop = new Vector2(rectangle.Left, rectangle.Top); 
     Vector2 rightTop = new Vector2(rectangle.Right, rectangle.Top); 
     Vector2 leftBottom = new Vector2(rectangle.Left, rectangle.Bottom); 
     Vector2 rightBottom = new Vector2(rectangle.Right, rectangle.Bottom); 

     // Transform all four corners into work space 
     Vector2.Transform(ref leftTop, ref transform, out leftTop); 
     Vector2.Transform(ref rightTop, ref transform, out rightTop); 
     Vector2.Transform(ref leftBottom, ref transform, out leftBottom); 
     Vector2.Transform(ref rightBottom, ref transform, out rightBottom); 

     // Find the minimum and maximum extents of the rectangle in world space 
     Vector2 min = Vector2.Min(Vector2.Min(leftTop, rightTop), 
            Vector2.Min(leftBottom, rightBottom)); 
     Vector2 max = Vector2.Max(Vector2.Max(leftTop, rightTop), 
            Vector2.Max(leftBottom, rightBottom)); 

     // Return as a rectangle 
     return new Rectangle((int)min.X, (int)min.Y, 
          (int)(max.X - min.X), (int)(max.Y - min.Y)); 
    } 

Je suppose que cela fonctionne car il provient du site Microsoft et tous. Donc je pense que le problème est avec mes matrices. Je pensais que si je n'utilisais qu'une matrice de rotation, cela ne ferait que tourner la chose; ne change pas ses coordonnées X et Y de manière drastique. en ce moment c'est ce que j'ai:

// calculate transformation 
      Matrix transformation = Matrix.CreateRotationZ((float)rotation) * Matrix.CreateRotationZ((float)rotation);; 

      //update bounding rectangle 
      rectangle = new Rectangle((int)(position.X - origin.X), (int)(position.Y - origin.Y), texture.Width, texture.Height); 
      rectangle = BoundingAndCollision.CalculateBoundingRectangle(rectangle, transformation); 

J'ai essayé une variété d'autres choses, y compris sans la matrice d'origine et des ordres différents d'entre eux. J'ai essayé aussi ce tutoriel dit était d'ordre général qui travaillerait pour rien, mais qui a produit les résultats fondamentalement les mêmes:

Matrix transformation = Matrix.CreateTranslation(new Vector3(origin, 0.0f)) * 
       Matrix.CreateRotationZ((float)rotation) * 
       Matrix.CreateScale(scale) * 
       Matrix.CreateTranslation(position.X, position.Y, 0); 

Si cela ne suffit pas clair, je peux poster des captures d'écran, juste me laisser know.Thank vous d'avance pour l'aide!

Répondre

1

Une matrice de rotation tourne autour de 0,0 et votre rectangle est déjà placé dans le monde. Pour résoudre d'abord, soustrayez le centre du rectangle de chaque sommet (traduisez le rectangle à centrer à 0,0), puis ajoutez-le à nouveau après la rotation (placez à nouveau sur l'emplacement d'origine). Dans le code im supposant Y va de haut en bas:

public static Rectangle CalculateBoundingRectangle(Rectangle rectangle, Matrix transform) 
{ 

    Vector2 center = new Vector2(rectangle.Left + (rectangle.Width/2), rectangle.Top + (rectangle.Height/2); 

    // Get all four corners in local space 
    Vector2 leftTop = new Vector2(rectangle.Left, rectangle.Top) - center; 
    Vector2 rightTop = new Vector2(rectangle.Right, rectangle.Top) - center; 
    Vector2 leftBottom = new Vector2(rectangle.Left, rectangle.Bottom) - center; 
    Vector2 rightBottom = new Vector2(rectangle.Right, rectangle.Bottom) - center; 

    // Transform all four corners into work space 
    Vector2.Transform(ref leftTop, ref transform, out leftTop); 
    Vector2.Transform(ref rightTop, ref transform, out rightTop); 
    Vector2.Transform(ref leftBottom, ref transform, out leftBottom); 
    Vector2.Transform(ref rightBottom, ref transform, out rightBottom); 

    leftTop += center; 
    rightTop += center; 
    leftBottom += center; 
    rightBottom += center; 

    // Find the minimum and maximum extents of the rectangle in world space 
    Vector2 min = Vector2.Min(Vector2.Min(leftTop, rightTop), 
           Vector2.Min(leftBottom, rightBottom)); 
    Vector2 max = Vector2.Max(Vector2.Max(leftTop, rightTop), 
           Vector2.Max(leftBottom, rightBottom)); 

    // Return as a rectangle 
    return new Rectangle((int)min.X, (int)min.Y, 
         (int)(max.X - min.X), (int)(max.Y - min.Y)); 
} 
+0

A travaillé parfaitement! Merci beaucoup! –