javascript - 八顶点立方体的法向量
我今天在玩 WEBGL 时遇到了我的立方体顶点法线的问题。
我用从网上获取的立方体网格检查了我的代码,它运行得很棒。
问题是,网上的立方体有24个顶点(每个面4个 * 6个面),我认为对于一个立方体来说太多了。
摆弄我的立方体 | 摆弄互联网立方体(我的代码从第200行开始)
我发现一个立方体最多只需要8个顶点和12个索引。但是当我渲染我的立方体时,屏幕上出现了一个奇怪的形状(是因为法线吗?)
这是立方体形式的互联网,几乎处于和我的立方体相同的旋转位置:
这是我的立方体:
var cube = {
"vertices" : [
-0.5 , 0.5 , 0.5, // 0
0.5 , 0.5 , 0.5, // 1
-0.5 ,-0.5 , 0.5, // 2
0.5 ,-0.5 , 0.5, // 3
-0.5 , 0.5 , -0.5, // 4
0.5 , 0.5 , -0.5, // 5
-0.5 ,-0.5 , -0.5, // 6
0.5 ,-0.5 , -0.5 // 7
],
"normals" : [
0.57 , 0.57 , -0.57 ,
0.57 , -0.57 , -0.57 ,
-0.57 , -0.57 , -0.57 ,
-0.57 , 0.57 , -0.57 ,
0.57 , 0.57 , 0.57 ,
0.57 , -0.57 , 0.57 ,
-0.57 , -0.57 , 0.57 ,
-0.57 , 0.57 , 0.57
],
"indices" : [
0 , 2 , 3 ,
0 , 3 , 1 ,
0 , 4 , 5 ,
0 , 5 , 1 ,
0 , 4 , 6 ,
0 , 6 , 2 ,
2 , 6 , 7 ,
2 , 7 , 3 ,
1 , 5 , 7 ,
1 , 7 , 3 ,
4 , 6 , 7 ,
4 , 7 , 5
]
}
我的问题是:
有可能为一个8顶点的立方体创建正确的法线吗?如果不行,有什么替代方案?
答案#1
你需要理解,vertex 不仅仅是空间中的一个点,它更是由多个不同属性组成的一个对象。这些属性包括位置,但也可能有法线、颜色、纹理坐标等。
在3D图形中,你经常需要两个或更多顶点放置在同一个位置,但具有不同的法线、颜色或纹理坐标。你的立方体就是这种情况——立方体通常只有8个角,但每个角连接3个面,每个面都有不同的法线,这就是为什么你看到的所有示例立方体都有24个顶点的原因。
实际上,你的立方体非常类似于球体,几何形状非常简单,以至于球体上的每个顶点只有一个法线,并且顶点周围的光照是平滑的。在立方体中,你需要将每一面都渲染为平面,所以构成立方体某一面的所有顶点都需要相同的法线。
如果你把立方体看作6个不同的四边形,并用独立的顶点创建所有这些四边形,可能会更容易理解。
答案#2
你可以使用一个通过几何着色器来绕过这个问题。
几何着色器接收一个形状并输出另一个形状(可以是相同类型的)。在你的情况下,它应该只输出它作为输入接收的同一个三角形。它还应该计算法线并将其传送到片段着色器。
在这里找到 VS、GS 和 FS 的代码:https://community.khronos.org/t/calculate-normals-in-vertex-shader/71573/4
有关几何着色器的更多信息,请查看此处的“可视化法线向量”:https://learnopengl.com/Advanced-OpenGL/Geometry-Shader

