我使用了很少的算法进行顺时针顶点排序,但仍然无法排序,因为它应该排序。
poly总是正方形,切割相同大小的小方块(让我们将它们命名为块)。所以说我有6x6方块,大块是1x1。更具体地说:square具有顶点:[0,0],[5,0],[5,5],[0,5]。 如果我将在位置[0,0]处切掉块(就像从[0,0]到[1,1]的顶点上的较小正方形所做的那样),正方形看起来像这样:
他的顶点现在是:[0,1],[1,1],[1,0],[5,0],[5,5],[0,5]
没关系。但是,让我们做更多的交叉点。我不会在位置[1,0]显示第二个块的交叉点因为一切都很好。现在,如果我要进行第三次交叉,比如位置[0,1],它看起来像这样:
当然,它应该是这样的:
正如您所看到的,它只是排序失败,它在[0,2]
之前对顶点[1,2]进行排序我想知道当我添加诸如检查质心距离之类的东西时它是否会很好。嗯..这是这个排序的代码:
function (a, b) {
var distance1 = Math.sqrt(Math.pow(a.x - centroid.x, 2) + Math.pow(a.y - centroid.y, 2));
var distance2 = Math.sqrt(Math.pow(b.x - centroid.x, 2) + Math.pow(b.y - centroid.y, 2));
var a1 = Math.acos((a.x - centroid.x) / distance1);
var a2 = Math.acos((b.x - centroid.x) / distance2);
if (a.y > centroid.y)
a1 = Math.PI + Math.PI - a1;
if (b.y > centroid.y)
a2 = Math.PI + Math.PI - a2;
return a1 - a2;
}
和质心:
function (vertices) {
var
x = 0,
y = 0,
pointCount = vertices.length;
for (var i = 0; i < pointCount; i++){
x += vertices[i].x;
y += vertices[i].y;
}
x = x/pointCount;
y = y/pointCount;
return new vec2(x, y);
}
答案 0 :(得分:1)
我没有真正检查你的比较函数中是否有任何错误,但它过于复杂。你可以使用Math.atan2
来获得两点之间的角度。你的功能应该是
function(a, b) {
return Math.atan2(a.y - centroid.y, a.x - centroid.x)
- Math.atan2(b.y - centroid.y, b.x - centroid.x);
}
答案 1 :(得分:0)
好的,我在clockWise排序后实现了新功能,即角度优化。整个算法的工作原理如下:
如果有任何吸烟,请随意
这是角度优化的代码:
for (var i = 1; i < vertices.length; i++) {
var a = vertices[i - 1];
var b = vertices[i];
var j = i;
do {
var distanceAngle = Math.abs(Math.atan2(a.y - b.y, a.x - b.x));
if (
distanceAngle == Math.PI / 2 ||
distanceAngle == Math.PI ||
distanceAngle == 3 * Math.PI / 2 ||
distanceAngle == 2 * Math.PI ||
distanceAngle == 0
)
{
var tmp = vertices[i];
vertices[i] = vertices[j];
vertices[j] = tmp;
break;
}
j++;
b = vertices[j];
} while (j < vertices.length);
}