7

我需要计算3点之间的角度。为此,我执行以下操作:

  1. 抓住 3 个点(上一个、当前和下一个,它在一个循环中)
  2. 用毕达哥拉斯计算点之间的距离
  3. 使用计算角度Math.acos

这似乎适用于没有超过 180 度角的形状,但是如果形状有这样的角,它会计算短边。这是一个说明我的意思的插图(红色值是错误的):

说明计算出了什么问题的代码

这是进行计算的代码:

// Pythagoras for calculating distance between two points (2D)
pointDistance = function (p1x, p1y, p2x, p2y) {
    return Math.sqrt((p1x - p2x)*(p1x - p2x) + (p1y - p2y)*(p1y - p2y));
};

// Get the distance between the previous, current and next points
// vprev, vcur and vnext are objects that look like this:
//     { x:float, y:float, z:float }
lcn = pointDistance(vcur.x, vcur.z, vnext.x, vnext.z);
lnp = pointDistance(vnext.x, vnext.z, vprev.x, vprev.z);
lpc = pointDistance(vprev.x, vprev.z, vcur.x, vcur.z);

// Calculate and print the angle
Math.acos((lcn*lcn + lpc*lpc - lnp*lnp)/(2*lcn*lpc))*180/Math.PI

代码中是否有问题,是我忘记做某事,还是应该以完全不同的方式完成?

4

3 回答 3

4

你好,你的数学和计算是完美的。您遇到了大多数人在计算器上遇到的相同问题,即方向。我要做的是找出该点是否位于使用此代码的前两个点所形成的向量的左侧或右侧,我从

确定点位于直线的哪一侧

isLeft = function(ax,ay,bx,by,cx,cy){
 return ((bx - ax)*(cy - ay) - (by - ay)*(cx - ax)) > 0;
}

其中 ax 和 ay 构成你的第一个点 bx 你的第二个和 cx cy 你的第三个。

如果它在左边,只需将 180 添加到您的角度

于 2013-08-01T15:55:56.690 回答
1

我有一个工作但不一定简短的例子来说明它是如何工作的:

var point1x = 0, point1y = 0,
    point2x = 10, point2y = 10,
    point3x = 20, point3y = 10,
    point4x = 10, point4y = 20;

var slope1 = Math.atan2(point2y-point1y,point2x-point1x)*180/Math.PI;
var slope2 = Math.atan2(point3y-point2y,point3x-point2x)*180/Math.PI;
var slope3 = Math.atan2(point4y-point3y,point4x-point3x)*180/Math.PI;
alert(slope1);
alert(slope2);
alert(slope3);
var Angle1 = slope1-slope2;
var Angle2 = slope2-slope3;
alert(180-Angle1);
alert(180-Angle2);

(见http://jsfiddle.net/ZUESt/1/

为了解释多个步骤,slopeN变量是各个线段的斜率。AngleN 是每个结点(即点 N+1)处的转动量。正角是右转,负角是左转。

然后,您可以从 180 中减去该角度,以获得您想要的实际内角。

需要注意的是,这段代码当然可以压缩,五行只是输出变量,看看发生了什么。我会让你担心优化它以供你自己使用,这是一个概念证明。

于 2013-08-01T15:24:52.987 回答
0

您需要检查边界条件(显然,如果点是共线的)并应用适当的计算来找到角度。此外,三角形的任何(内)角都不能大于 180 度。三角形的角和是180度。

于 2013-08-01T14:34:52.623 回答