假设我在网格环境中有某个多边形的顶点,我如何遍历它包含的每个单元格(包括边缘上的单元格)?
为了澄清,我有以下顶点(算作左上角是(0, 0)
):
//each point is [x, y]
var verts = [
[1, 1],
[3, 1],
[3, 2],
[4, 2],
[4, 4],
[0, 4],
[0, 3],
[1, 3]
];
这将定义一个多边形,例如:
根据上面的顶点,每个绿点都是我想要迭代的点。顶点沿着多边形边缘的方向没有模式,它可以围绕多边形顺时针或逆时针移动。但是,它们将井然有序;也就是说,如果你放下笔并按顺序移动到每个顶点,而不抬起,它会在不交叉多边形内部的情况下绘制轮廓。
用例是我imageData
通过画布 API 加载了来自 PNG 的文件。这个PNG被分成“区域”,我需要迭代当前“区域”的每个像素。每个“区域”都由一个顶点数组定义,如上。
我尝试了类似以下的方法,它将为数组中的每组 4 个顶点创建一个正方形来迭代。
for(var v = 0, vl = verts.length - 4; v < vl; ++v) {
//grabbing the minimum X, Y and maximum X, Y to define a square to iterate in
var minX = Math.min(verts[v][0], verts[v + 1][0], verts[v + 2][0], verts[v + 3][0]),
minY = Math.min(verts[v][1], verts[v + 1][1], verts[v + 2][1], verts[v + 3][1]),
maxX = Math.max(verts[v][0], verts[v + 1][0], verts[v + 2][0], verts[v + 3][0]),
maxY = Math.min(verts[v][1], verts[v + 1][1], verts[v + 2][1], verts[v + 3][1]);
for(var x = minX; x < maxX; ++x) {
for(var y = minY; y < maxY; ++y) {
//do my checks on this pixel located at X, Y in the PNG
}
}
}
但是有两个大问题:
- 它可以在多边形内重复点,并且
- 它可以抓取多边形外的点
我可以通过跟踪我检查的点来解决第一个问题,所以我不会重复检查。第二个只能通过PointInPoly
对每个点进行检查来解决,这会使这个解决方案比我想要的要重得多。
编辑
迭代整个图像中的每个像素并对每个像素进行PointInPoly
检查也是不可接受的;它甚至比上述算法还要慢。