Ned*_*igg 4 opengl directx 3d geometry mesh
如果将圆柱体细分为8面棱镜,根据它们的位置计算顶点法线("平滑着色"),它看起来非常好.
如果你将一个圆锥体细分为一个8面金字塔,根据它们的位置计算法线,你就会卡在圆锥的顶端(技术上是锥体的顶点,但我们称之为尖端,以避免与网格顶点混淆) .

对于每个三角形面,您希望沿两条边匹配法线.但是因为你只能在三角形的每个顶点指定一个法线,你可以匹配一条边或另一条边,但不能同时匹配两条边.您可以通过选择两条边的平均值的尖端法线来妥协,但现在没有一条边看起来很好.以下是选择每个尖端顶点的平均法线的详细信息.

在一个完美的世界中,GPU可以光栅化真正的四边形,而不仅仅是三角形.然后我们可以用退化四边形指定每个面,允许我们为每个三角形的两个相邻边指定不同的法线.但我们必须使用的是三角形...我们可以将锥体切割成多个"堆叠",这样边缘不连续性只能在锥体的尖端而不是整个物体上看到,但是仍然会有小费!
任何人都有光滑阴影低聚锥的任何技巧?
我在现代OpenGL(即着色器)中使用由三角形组成的锥体挣扎,但后来我找到了一个非常简单的解决方案!我会说它比目前接受的答案中建议的要好得多,也简单得多.
我有一个三角形阵列(显然每个都有3个顶点),形成锥面.我不关心底面(圆形底座),因为这非常简单.在我的所有工作中,我使用以下简单的顶点结构:
position: vec3 (通过添加1.0f作为最后一个元素,在着色器中自动转换为vec4)
normal_vector: vec3 (在着色器中保留为vec3,因为它用于计算点光源产品)
color: vec3 (我没有使用透明度)
在我的顶点着色器中,我只是变换顶点位置(乘以投影和模型视图矩阵)并且还变换法向量(乘以模型 - 视图矩阵的变换逆).然后将变换后的位置,法向量和未变换的颜色传递给片段着色器,在那里我计算了光方向和法向量的点积,并将该数乘以颜色.
让我从我做的开始,发现不满意:
尝试#1:每个锥面(三角形)使用恒定法向量,即一个三角形的所有顶点具有相同的法向量.这很简单但没有实现平滑的光照,每个面都有一个恒定的颜色,因为三角形的所有碎片都具有相同的法向矢量.错误.
尝试#2:我分别计算了每个顶点的法向量.对锥体圆形底座上的顶点来说这很容易,但锥体的顶端应该使用什么?我使用了整个三角形的法向量(即与尝试#中的值相同).这是更好的,因为我在靠近锥体底部的部分有光滑的照明,但在尖端附近不光滑.错误.
但后来我找到了解决方案:
尝试#3:我在尝试#2中做了所有事情,除了我在锥尖顶点中指定了等于零向量vec3(0.0f,0.0f,0.0f)的法向量.这是诀窍的关键!然后将该零法向量传递给片段着色器(即,在顶点和片段着色器之间,它与其他两个顶点的法向矢量一起自动插值).当然,您需要对片段(!)着色器中的向量进行标准化,因为它的常量大小不是1(我需要点积).所以我将它标准化 - 当然这对于法线向量大小为零的锥体的尖端是不可能的.但它适用于所有其他方面.就是这样.
有一件重要的事情需要记住,要么你只能规范片段着色器中的法向量.如果你试图在C++中规范化零大小的矢量,你肯定会得到错误.因此,如果由于某种原因在进入片段着色器之前需要进行标准化,请确保排除大小为零的法向量(即锥体的尖端或者您将得到错误).
这样可以在除锥形尖端的所有点之外的所有点上产生锥形的平滑阴影.但这一点并不重要(谁关心一个像素......)或者你可以用特殊的方式处理它.另一个优点是你甚至可以使用非常简单的着色器.唯一的变化是在片段着色器中而不是在顶点着色器中甚至在之前标准化法向量.
| 归档时间: |
|
| 查看次数: |
2786 次 |
| 最近记录: |