简体   繁体   English

沿逆时针方向排序3D多边形顶点

[英]Sorting 3D polygon vertices in anticlockwise direction

I have to find the normal of a polygon, but in order to do that I first have to order the vertices (x,y,z) in anticlockwise direction. 我必须找到多边形的法线,但是要做到这一点,我首先必须沿逆时针方向对顶点(x,y,z)进行排序。 Lets say I am given n number of vertices points entered by the user, how do I order the vertices in anticlockwise direction to turn them into a polygon? 可以说,我给了用户输入的n个顶点,我如何在逆时针方向上将顶点变成多边形?

You can't order your points without knowing the normal, and vice-versa. 您不能在不知道法线的情况下订购积分,反之亦然。 If you say "anti-clockwise from the front" then you need to know what side is the front, and thus you need to know the normal. 如果您说“从正面逆时针方向”,那么您需要知道正面在哪一边,因此您需要知道法线。 So your question doesn't have an answer, as it stands, because it is a bit circular: You don't have enough information to determine what you are looking for. 因此,您的问题目前没有答案,因为它有点循环:您没有足够的信息来确定要寻找的内容。

You need a little bit more information. 您需要更多信息。 For example, if this polygon is part of a convex surface, you can compute the geometric center of the surface. 例如,如果此多边形是凸曲面的一部分,则可以计算曲面的几何中心。 Then pick any 3 non-colinear points a, b, c on your polygon, calculate the normal ( norm((a - b) cross (c - b)) ), calculate the vector from the centroid to one of your points (eg b - centroid ), then check if the normal faces the same (or opposite, whatever) direction as that vector (sign of normal dot (b - centroid) ) and flip it if it's the wrong way. 然后在多边形上选取任意3个非共线点a,b,c ,计算法线( norm((a-b)cross(c-b)) ),计算从质心到您的一个点的向量(例如b-质心 ),然后检查法线是否与该矢量( 法线点(b-质心)的符号)方向相同(或相反)。如果方向错误,则将其翻转。 Essentially you just calculate a perpendicular unit vector (there are two, remember), then make sure it's pointing towards the inside / outside of your object. 本质上,您只是计算一个垂直单位矢量(记住两个),然后确保它指向对象的内部/外部。

If your face is part of a concave surface, you can make all the normals point the same general direction by taking the dot product of your normal with an adjacent face's normal and flipping it if it's negative. 如果您的脸是凹面的一部分,则可以通过获取法线与相邻脸部法线的点积并将其翻转为负值来使所有法线指向相同的大致方向。 You'd still need to decide on a way to determine which side of the face was on the inside vs. outside of the surface, but at least all the normals would be pointing towards one or the other. 您仍然需要确定一种方法来确定面部的哪一侧在表面的内部与外部,但是至少所有法线都指向一个或另一个。

If you don't have information about the general direction the normal should be facing, you'll have to get your anti-clockwise info from elsewhere. 如果您没有有关法线应该面对的大致方向的信息,则必须从其他地方获取逆时针信息。 You can sort the points around the center of your polygon to get them in order, but to determine if that order is clockwise vs. anti-clockwise requires additional info (eg ask the user, etc.). 您可以对多边形中心周围的点进行排序,以使它们按顺序排列,但是要确定该顺序是顺时针还是逆时针,则需要其他信息(例如,询问用户等)。

Note that the atan -based 2D solutions implicitly rely on some extra information: The rely on the fact that the normal faces out of the screen / off the paper and towards you, the viewer, and thus you can sort in a known direction around that normal. 请注意,基于atan的2D解决方案隐式依赖于一些额外的信息:依赖于这样的事实,即法线朝向屏幕外/纸张外并朝向您,观察者,因此您可以围绕该方向进行分类正常。 That assumption is generally made without anybody ever actually speaking of it. 该假设通常是在没有人真正谈论过的情况下做出的。 However, in reality, you need to decide which side is the front and the back - not always easy for 3D (if you are rendering to the screen and you have a viewpoint set up, you could use that as the extra info - say the normal faces the camera, then order around that normal). 但是,实际上,您需要确定正面和背面是哪一侧-3D并不总是那么容易(如果要渲染到屏幕上并且设置了视点,则可以将其用作附加信息-例如法线朝向相机,然后围绕该法线排序)。


Another way to phrase the above is, in general, we have 3 unknowns: 通常,我们有3个未知数:

  1. What is the winding order when viewed from the "front"? 从“正面”看时的缠绕顺序是什么?
  2. Which of the two perpendicular unit vectors to the plane do we choose to be on the "front" or "which side is the front"? 我们选择在平面的两个垂直单位向量中的哪一个位于“前” “哪一侧是前”?
  3. What is the sort order of the given points that corresponds to the winding order? 给定点对应于缠绕顺序的排序顺序是什么?

We need to have two of these to determine the third. 我们需要其中两个来确定第三个。

In response to Andon's comments below: For the rasterizer, it defines #1 itself (or takes it from configuration), and #3 is assumed by API requirements, and so #2 can be inferred. 针对以下Andon的评论:对于光栅化器,它定义了#1本身(或从配置中获取),并且API要求假定了#3,因此可以推断出#2。

In the 2D cases that you often see described (which I mentioned above), #1 is specified as a requirement, #2 is assumed to be "the side facing the viewer is the front", and so #3 can be determined with atan and sorting in increasing/decreasing order. 在您经常看到的2D情况下(我在上面提到),将#1指定为要求,假定#2为“面对观察者的一侧为前方”,因此可以使用atan来确定#3并按升序/降序排序。

In your original question, you know #1 (you've defined it), but you don't know #2 (which side is the front?), and therefore you cannot determine #3. 在您最初的问题中,您知道#1(已经定义了它),但是您不知道#2(哪一侧是正面?),因此无法确定#3。 You need some way to determine #2 (eg facing away from centroid, facing towards viewer, whatever). 您需要某种方法来确定#2(例如,远离质心,面向观察者等)。

See atan . 阿坦

To find the angle of a point (X,Y), you just need to do atan(Y/X) . 要找到一个点的角度(X,Y),您只需要执行atan(Y/X) Here are some caveats: 以下是一些警告:

http://upload.wikimedia.org/math/5/7/1/571efb70f630041f9e2b00019025171e.png http://upload.wikimedia.org/math/5/7/1/571efb70f630041f9e2b00019025171e.png Atan网域

Finally, order your results from lowest to highest (add 360 to negative numbers). 最后,从最低到最高对结果进行排序(将360加到负数)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM