Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/opengl/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Opengl GTX 980上深度预通过后的Z战斗_Opengl_Rendering_Depth Testing - Fatal编程技术网

Opengl GTX 980上深度预通过后的Z战斗

Opengl GTX 980上深度预通过后的Z战斗,opengl,rendering,depth-testing,Opengl,Rendering,Depth Testing,我正在OpenGL中实现深度预处理。在Intel HD Graphics 5500上,此代码可以正常工作,但在Nvidia GeForce GTX 980上则不行(下图显示了由此产生的z-fighting)。我使用下面的代码生成图像。(所有与问题无关的内容都省略了。) glDepthFunc似乎没有更改为GL\u LEQUAL。但是,当我在RenderDoc中单步执行GL调用时,glDepthFunc被正确设置 这听起来像是一个驱动程序错误还是你有什么建议我可能做错了?当这是一个驱动程序错误时,

我正在OpenGL中实现深度预处理。在Intel HD Graphics 5500上,此代码可以正常工作,但在Nvidia GeForce GTX 980上则不行(下图显示了由此产生的z-fighting)。我使用下面的代码生成图像。(所有与问题无关的内容都省略了。)

glDepthFunc似乎没有更改为
GL\u LEQUAL
。但是,当我在RenderDoc中单步执行GL调用时,
glDepthFunc
被正确设置

这听起来像是一个驱动程序错误还是你有什么建议我可能做错了?当这是一个驱动程序错误时,我如何实现深度预处理


有些版本的Sponza是巨大的。我记得我用以下两种解决方案之一修复了该问题:

  • 24位深度缓冲器


第二种方法在平铺体系结构上较差,后者利用了。在移动平台上,性能下降可能非常明显。

当对深度预过程使用不同的着色器程序时,必须明确确保该程序生成与主过程程序相同的深度值(尽管在相同的几何体上调用)。这是通过使用
gl\u位置
上的
不变量
限定符来完成的

GLSL规范4.4解释的差异:

在本节中,方差是指从同一表达式中获得不同值的可能性 不同的节目。例如,假设在不同的程序中有两个顶点着色器,每个着色器都使用 两个着色器中的表达式相同,并且当两个着色器同时存在时,该表达式中的输入值相同 着色器运行。由于两个着色器的独立编译,指定给 运行两个着色器时,gl_位置不完全相同。在本例中,这可能会导致问题 在多通道算法中对齐几何体

在这种情况下,限定符的用法如下:

invariant gl_Position;
这一行保证
gl_Position
由着色器中给出的精确表达式计算,而无需任何优化,因为这将改变操作,因此很可能以某种较小的方式改变结果

在我的具体案例中,任务是问题的根源。主过程程序的顶点着色器包含以下行:

fWorldPosition = ModelMatrix*vPosition; // World position to the fragment shader
gl_Position = ProjectionMatrix*ViewMatrix*fWorldPosition;
在一个表达式中计算的预过程程序的顶点着色器
gl\u位置

gl_Position = ProjectionMatrix*ViewMatrix*ModelMatrix*vPosition;
将此更改为:

vec4 worldPosition = ModelMatrix*vPosition;
gl_Position = ProjectionMatrix*ViewMatrix*worldPosition;

我解决了这个问题。

为什么要用
glDepthMask(GL\u FALSE)
禁用深度写入?您为深度缓冲区分配了多少位?问题中的代码远远不够,有太多可能出错。例如,您是否在所有与两个过程相关的着色器中将
gl_位置
输出正确地限定为
不变量
?@rabbi76我想到了
glPolygonOffset
,但由于代码在英特尔上运行,因此我假设肯定存在其他问题,并希望首先探讨这个问题。但是,我实现了您的解决方案(变通方法),它完成了任务。@Ripi2如果您问为什么:我禁用深度写入,因为主渲染过程不需要渲染深度,因为它已经由预处理过程完成。如果你问为什么要使用
glDepthMask(GL\u FASLE)
:我想这是通常的方式。正如在对原始问题的评论中提到的:我使用的是24位深度缓冲区,将其更改为32位没有帮助。对数深度缓冲区很有趣,但太多了。这个场景被截头台紧紧地包裹着,因此(我想)这些位被很好地利用了。原来的场景实际上是巨大的,但也缩小了。
vec4 worldPosition = ModelMatrix*vPosition;
gl_Position = ProjectionMatrix*ViewMatrix*worldPosition;