什么时候OpenGL对象名称为零?或者,零是否有语义?

时间:2013-08-12 17:44:57

标签: opengl

我一直想知道:OpenGL对象“名称”,由glGenTextures等生成的整数似乎永远不会为零,所以我使用零来表示未初始化的句柄并检查错误。到目前为止一切都还好。

我还被告知,在完成一个对象之后调用glBind *(0)是一个好习惯,以确保之后不会意外地操纵延迟绑定对象。听起来很明智。

在任何情况下,OpenGL对象ID都为零,使我的测试无效,或者以这种方式使用零会产生令人惊讶的效果,因为它不会引用非对象吗?

P.S。零作为非对象是否有符号名称?

P.P.S。是否会因大量使用绑定/解除绑定模式而遭受性能损失? (由于封装,代码的某些部分主要是冗余的重新绑定。)

5 个答案:

答案 0 :(得分:5)

来自OpenGL 4.4 Core Profile Specification

  

每个对象类型都有一个对应的名称空间。对象的名称由uint类型的无符号整数表示。 GL保留名称零;   对于某些对象类型,零命名该类型的默认对象,而在其他对象类型中为零   永远不会对应该对象类型的实际实例。

您可以依赖名称生成函数(例如GenBuffers)永远不会将零作为生成的名称返回零。您可以使用零来表示“无对象”。

答案 1 :(得分:1)

纹理名称零是一个保留的纹理名称,每当您删除纹理时,它就像绑定到纹理名称零一样。所以在这种情况下,它是一种始终在使用的特殊纹理名称。

glGenTextures()仅检索当前未使用的名称,并且由于零正在使用中,因此您永远不应将其作为有效名称。

但请注意,在零上使用glIsTexture将返回false,因此从技术上讲,它不会被识别为纹理。

答案 2 :(得分:1)

大多数检查GL对象(glIsTextureglIsBuffer等的有效性的函数)在给定值0时返回GL_FALSE。因此,为了回答您的第一个问题,我认为您不认为测试将被打破。

至于#2,是的。冗余绑定/解除绑定可能会导致性能下降,具体取决于驱动程序和绑定/未绑定的对象。通常,出于性能原因 - 最好避免在OpenGL中进行状态更改(冗余或其他)。

希望这有帮助。

答案 3 :(得分:1)

  

在任何情况下,OpenGL对象ID都为零,使我的测试无效,或者以这种方式使用零会产生令人惊讶的效果,因为它没有引用非对象吗?

之后绑定对象零将永远不会使您的代码无效,除非后面的代码仍然期望绑定对象。至于任何令人惊讶的效果,只要你没有实际使用零对象,只要你不对该对象执行任何操作,你就可以了。

话虽如此,这里是所有OpenGL对象的综合列表,其对象零不是非对象:

  • Framebuffer对象。零是默认的帧缓冲区,非特殊地从非默认帧缓冲区处理。您可能需要在某个时刻故意使用此默认对象;)

  • 顶点数组对象,但兼容性OpenGL中仅 。在核心配置文件中,VAO零不是有效对象。

  • 转换来自GL-4.x之前版本功能的反馈对象。

  • 纹理对象。这些对象以非常奇怪和奇怪的方式运行,与常规纹理对象非常不同。从不故意将数据放入其中;仅使用它们解开纹理。这可能是最大的"令人惊讶的效果"你会看到。

  

P.P.S。是否会因大量使用绑定/解除绑定模式而遭受性能损失? (由于封装,代码的某些部分主要是冗余的重新绑定。)

这种使用模式可能会导致性能问题。但是如果您的渲染代码是封装的,那么您可能会遇到很多其他性能问题。例如,基于状态变化进行排序必须非常困难。

答案 4 :(得分:0)

  

在任何情况下,OpenGL对象ID都为零,使我的测试无效,或者以这种方式使用零会产生令人惊讶的效果,因为它不会引用非对象吗?

纹理。绑定纹理0glDisable(GL_TEXTURE_[1|2|3]D)不完全相同。