在OpenGL中,深度缓冲区值是根据场景的近剪裁平面和远剪裁平面计算的。 (参考:Getting the true z value from the depth buffer)
这在WebGL中如何运作?我的理解是WebGL不知道我的场景远近剪裁平面。近剪裁平面和远剪裁平面用于计算我的投影矩阵,但我从不告诉WebGL它们是明确的,因此它不能用它们来计算深度缓冲值。
渲染场景时,WebGL如何在深度缓冲区中设置值?
答案 0 :(得分:6)
WebGL(与现代OpenGL和OpenGL ES一样)从您在顶点着色器中提供给gl_Position.z
的值中获取深度值(尽管您也可以使用某些扩展直接写入深度缓冲区,但这不太常见)
WebGL中没有场景,也没有现代的OpenGL。场景的概念是90年代早期遗留下来的遗留OpenGL的一部分,早已被弃用。它在OpenGL ES中不存在(在Android,iOS,ChromeOS,Raspberry PI,WebGL等上运行的OpenGL ......)
现代OpenGL和WebGL只是光栅化API。您编写着色器,这些着色器是在GPU上运行的小功能。您可以通过属性(每个迭代数据),制服(全局变量),纹理(2d / 3d数组),变换(从顶点着色器传递到片段着色器的数据)为这些着色器提供数据。
其余由您和您提供的着色器功能决定。现代OpenGL和WebGL用于所有意图和目的只是具有一定限制的通用计算引擎。让他们做任何事都取决于你提供着色器。
有关详情,请参阅webglfundamentals.org。
在Q& A中你链接到的是程序员提供的着色器决定使用视锥数学决定如何设置gl_Position.z
。平截头体数学由程序员提供。 WebGL / GL并不关心如何计算gl_Position.z
,只是它是-1.0和+1.0之间的值,所以如何从深度缓冲区获取一个值并返回Z完全取决于程序员如何决定首先计算它。
This article涵盖了在使用WebGL / OpenGL渲染3D时设置gl_Position.z
时最常用的数学运算。根据你的问题,虽然我建议阅读在那篇文章开头链接的前面的文章。
关于将实际值写入深度缓冲区的是
ndcZ = gl_Position.z / gl_Position.w;
depthValue = (far - near) / 2 * ndcZ + (near - far) / 2
near
和far
分别默认为0和1,但您可以使用gl.depthRange
设置它们,但假设它们为0和1则
ndcZ = gl_Position.z / gl_Position.w;
depthValue = .5 * ndcZ - .5
那个depthValue将在0到1的范围内,并转换为深度缓冲区的任何位深度。通常有一个24位深度缓冲区,所以
bitValue = depthValue * (2^24 - 1)