0

此处glGetActiveUniformBlockName()记录了OpenGL 函数。简短的描述如下:

[它] 在程序中的 uniformBlockIndex 处检索活动统一块的名称。`

如何使统一块处于活动状态

4

2 回答 2

2

统一块的活动方式与统一块的活动方式相同:您在一些产生输出的表达式中使用它。如果您希望统一块处于活动状态,则需要对其成员之一实际执行一些操作,从而对着色器的输出产生实质性影响。

于 2012-05-04T23:52:13.437 回答
0

根据 OpenGL 文档,“活动”统一块的定义取决于实现,因此取决于驱动程序。但是,如果您只需要使一个块“活动”,那么只需在您的 GLSL 代码中使用它。只要您在块中使用了制服,就可以保证该块处于活动状态。

但是,如果您不使用它,则该块可能处于活动状态或处于非活动状态,具体取决于您的硬件。即使您将块标记为使用std140布局,编译器仍然可以优化它。棘手的部分是,您的驱动程序甚至可能以不同的方式对待统一块和统一块数组。这是一个例子:

#version 460

layout(std140, binding = 0) uniform Camera {
    vec3 position;
    vec3 direction;
} camera;

layout(std140, binding = 1) uniform Foo {
    float foo;
    vec3 vec_foo;
} myFoo[2];

layout(std140, binding = 3) uniform Bar {
    float bar;
    vec3 vec_bar;
} myBar[4];

layout(std140, binding = 7) uniform Baz {
    float baz1;
    float baz2;
};

void main() {
    vec3 use_camera = camera.position;  // use the Camera block
    vec3 use_foo = myFoo[0].vec_foo;    // use the Foo block
    color = vec4(1.0);
}

在这个片段着色器中,我们有 8std140个统一块,正在使用Camera和块,因此它们必须处于活动状态。Foo另一方面,BarBaz​​没有被使用,所以你可能认为它们是非活动的,但在我的机器上,虽然Bar是非活动的,但Baz仍然被认为是活动的。我不确定是否可以在其他机器上复制结果,但您可以使用OpenGL 文档中的示例代码对其进行测试。

由于它依赖于实现,因此使用统一块的最安全方法是始终在您的硬件上进行试验。如果您想在所有机器上获得稳定的结果,唯一的方法就是全部使用它们,否则可能很难。正如其他人建议的那样,您可以尝试关闭编译器优化,如下所示,但不幸的是,这仍然不会阻止未使用的块被优化,因为删除不活动的制服不是优化,它只是编译器的工作方式。

#pragma optimize(off)
...
于 2021-08-24T04:41:27.187 回答