我应该如何将glNormal()用于三角形和四边形之间共享的顶点?

时间:2014-04-26 14:56:50

标签: opengl

让顶点成为三角形和四边形的一部分。
据我所知,该顶点的法线是四边形法线的平均值和三角形的法线。

在四边形之前绘制三角形。什么时候应该调用glNormal和什么向量?

  • 我应该调用glNormal 2次,每次使用相同的向量(平均法向量)吗?
  • 我应该在最后一次绘制顶点时调用glNormal,平均法向量是多少?

2 个答案:

答案 0 :(得分:3)

  

据我所知,该顶点的法线是平均值   四边形的法线和三角形的法线。

理想情况下,法线矢量应与您渲染的曲面在任何点上正交。但是,GL仅支持将曲面渲染为多边形模型(至少直接)。所以主要有两种可能性:

  1. 多边形表示确实代表您想要显示的对象。一个简单的例子就是一个立方体。

  2. 多边形represantation只是您想要显示的表面的(picewise线性)近似。想想光滑的表面。

  3. 在情况1中,每个三角形需要一个标称(因为正常情况下,由三角形定义的平面是正常的)。但是,这意味着对于共享边缘或角落的相邻三角形,法线必须不同。从GL的角度来看,每个trianlges使用不同的顶点,即使这些顶点共享空间中的位置。顶点是所有属性的集合,而不仅仅是位置。对于立方体,这意味着您不仅需要8个不同的顶点,而且需要24个,因此每个角落都有3个。

    在案例2中,您确实希望尽可能好地掩盖模型的多边形结构。其中一个方面是使用平滑着色技术。对每个顶点处的相邻traingles的normales进行平均是这样做的一个启发式。在这种情况下,相邻图元实际上可以共享顶点,因为对于连接到它的任何三角形,法线和某个角点的位置是相同的。

    这种启发式方法有一些缺点,特别是如果你的表面确实包含光滑的部分和你想要保留的“锐边”。有一些改进的启发式方法试图检测尖锐边缘和分裂顶点,以允许连接三角形的不同法线不会使这些边缘平滑。但是在某些情况下,所有这些启发式方法都可能失败 - 理想情况下,首先创建模型时会提供法线。

      

    在四边形之前绘制三角形。什么时候应该调用glNormal和   用什么载体?

    OpenGL是一个状态机,这意味着你设置kepp的方式,直到你再次调用它们 - 并且设置法线也不例外。需要注意的第二件事是法线是顶点属性。因此对于每个顶点,每个arrtibute 总是有一些值(但取决于GL状态的其余部分,渲染时不会使用所有这些属性)。

    由于你使用固定函数GL,法线是内置的顶点属性 - 所以你以某种方式发出的每个顶点都有一些值作为它的正常属性 - 在立即模式渲染glBegin()/End()时,它将是一个您使用最近的glNormal()调用进行了设置(如果您从未调用glNormal(),则会设置初始默认值。)

    所以回答你的问题: 你必须在第一次发出对该特定顶点的glVertex()调用之前设置该法线,并且必须重新发出该正常命令,以便第二次使用“this”顶点绘制(技术上是反正不同的顶点)如果你在指定其他顶点时确实改变了它。

答案 1 :(得分:2)

  

据我所知,该顶点的法线是四边形法线的平均值和三角形的法线。

没有。平面的法线是以90度角指向“平面外”的矢量。在OpenGL中,这用于着色计算,并且为了支持各种效果,OpenGL允许您指定所需的任何法线,而不是从基元计算它。对于平面照明,法线应设置为每个图元的法线的数学定义,而对于平滑照明,法线应设置为共享顶点的所有图元的平均法线。

glNormal设置OpenGL中的值,只要您调用glVertex,就会读取该值,并且在您再次调用glNormal之前保持不变。所以这段代码

glNormal3d(0,0,1)
glVertex3d(1,0,0)
glVertex3d(1,1,0)
glVertex3d(0,1,0)
glVertex3d(0,0,0)

指定4个顶点,每个顶点的法线为(0,0,1)。