2010-04-22 101 views
1

我在一个屏幕坐标空间中工作,它不同于经典的X/Y坐标空间,其中我的Y方向在正向下降,而不是向上。C#矢量数学问题

我也试图弄清楚如何让我的屏幕上的圆始终背离屏幕的中心点。

如果我的屏幕的中心点在x(200)y(300)并且我的圆心的点在x(150)和y(380),那么我想计算圆的角度应该面对。

目前,我有这样的:

 Point centerPoint = new Point(200, 300); 
     Point middleBottom = new Point(200, 400); 

     Vector middleVector = new Vector(centerPoint.X - middleBottom.X, centerPoint.Y - middleBottom.Y); 

     Vector vectorOfCircle = new Vector(centerPoint.X - 150, centerPoint.Y - 400); 

     middleVector.Normalize(); 
     vectorOfCircle.Normalize(); 

     var angle = Math.Acos(Vector.CrossProduct(vectorOfCircle, middleVector)); 

     Console.WriteLine("Angle: {0}", angle * (180/Math.PI)); 

我不是得到什么我期望的那样。

我会说,当我在我的圈子的x(150)和y(300)中输入时,我期望看到90度的旋转,但我没有得到那个...我得到180!

在这里的任何帮助将不胜感激。

干杯, 马克

+0

圆圈如何面向方向?它具有∞倍的径向对称性。此外,你不断改变圆的中心。是(150,380),(150,400)还是(150,300)? – outis 2010-04-22 07:15:37

回答

1

它的好,我想我现在弄明白了:

我读这篇文章:

http://www.euclideanspace.com/maths/algebra/vectors/angleBetween/index.htm

这确定了我需要使用ATAN2,而不是ACOS

 Point centerPoint = new Point(200, 300); 
     Point middleBottom = new Point(200, 400); 

     Vector middleVector = new Vector(centerPoint.X - middleBottom.X, centerPoint.Y - middleBottom.Y); 
     Vector vectorOfCircle = new Vector(centerPoint.X - 250, centerPoint.Y - 300); 

     middleVector.Normalize(); 
     vectorOfCircle.Normalize(); 

     var angle = Math.Atan2(vectorOfCircle.Y, vectorOfCircle.X) - Math.Atan2(middleVector.Y, middleVector.X); 

     Console.WriteLine("Angle: {0}", angle * (180/Math.PI)); 
+0

+1对! Atan2是一个非常有用的功能,几乎没有人知道它。 – 2010-04-22 14:07:35

+0

我更喜欢'var angle = Math.Acos(dotProduct)'。在数学背景少的情况下,理解起来更容易,效率也更高(如果你挑剔的话)。减法不可交换,这意味着当使用Math.Atan2(通常需要检查)时,会得到负值和/或非标准化> 2pi的角度。如果这不是您想要的,即您总是希望两个矢量之间的最小角度,请使用点积。 – 2012-09-10 09:51:14

+0

正如我现在看到的,实际上在你的例子中使用点积是没有意义的,因为对于像面对类似的东西我会依赖负面的角度。所以'var angle = Math.Asin(crossProduct)'会比Math.Atan2解决方案更好地为您提供带符号的角度,因为您不必检查> 2pi的角度。 – 2012-09-10 09:53:18

0

不,这是正确的。零角度从原点(中心点)向右。由于圆是在origo的左边,所以角度是180度。

1

一条评论:

cos-sinus函数用于点乘积中。 Cross产品使用窦。

+0

这会有什么影响? – Mark 2010-04-22 23:09:19

+1

您在代码中使用Acos代替Asin或错误类型的矢量产品。仔细看看这一行:var angle = Math.Acos(Vector.CrossProduct(vectorOfCircle,middleVector)); – 2010-04-23 01:30:51