【发布时间】:2014-05-15 02:25:50
【问题描述】:
我想出了一个想法,需要将数千个缓冲区(原子计数器和着色器存储缓冲区)绑定到一个 GLSL 程序。我首先检查了这是否对 openGL 的限制有意义,这似乎有两个原因:
- 在我的笔记本电脑上,GL_MAX_ATOMIC_COUNTER_BUFFER_BINDINGS 和 GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS 都在 32k 左右。因此,openGL 倾向于让我一次绑定数千个缓冲区。
-
openGL 4.4 提出:
void BindBuffersBase(enum target, uint first, sizei count, const uint *buffers);
在 C 代码上看起来很简单,但我不知道如何制作我的着色器。绑定索引缓冲区时,我们应该使用:
layout (std430, binding = 0) buffer Objects
{
Object objects[];
};
绑定几个缓冲区时就可以了。但就我而言:
- 我事先不知道会绑定多少个缓冲区
- 即使我知道,我是否应该为每个缓冲区编写几行代码并在布局绑定中定义 0、1、2、...、n?
那么问题是: 有没有办法让着色器不知道将绑定到它的缓冲区的数量?假设它们都包含相同类型的数据。
答案:
感谢Andon M. Coleman 提供快速清晰的答案。
首先,我错误地认为我的硬件支持数千个绑定。菜鸟错误,我取的是定义的值而不是运行时的值。
在我的机器上:
- GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS = 96
- GL_MAX_ATOMIC_COUNTER_BUFFER_BINDINGS = 8
- GL_MAX_UNIFORM_BUFFER_BINDINGS = 84
这与我提出问题的依据相去甚远。
但是,在着色器中定义多个缓冲区是一种方法:
A
{
B b[];
}
layout (std430, binding = 0) buffer A a[32];
必须事先知道最大绑定的数量,但这些缓冲区将占用从 0 到 31 的绑定。
【问题讨论】:
-
您确实在运行时查询了这些值,而不是使用常量的值,对吧?大多数较新的扩展在该范围内都有常数。此外,您的数组下标位置错误,它需要位于块的末尾之后。
-
绝对不是,你猜对了。我刚刚看到一个帖子,有人说他的限制是 96,所以我在运行时检查以确定。 8 个用于原子,96 个用于存储。现在就在这里杀死这笔交易。
-
如果我仍然把数组下标放在块的末尾,它会覆盖绑定 0 到 n 吗?
-
它可以,如果你分配一个像
} foo [32];这样的名字...这个由32个块组成的数组将按顺序分配绑定:0 - 31 -
谢谢先生。我现在就写答案。
标签: opengl binding buffer glsl indexed