我有一个工作代码,我在纹理缓冲区中从着色器中读取vec4值。
在客户端,我创建了一个位移矢量缓冲区:
vec4 vector1 : vec4(x1, y1, z1, w1);
vec4 vector2 : vec4(x2, y2, z2, w2);
vec4 vector3 : vec4(x3, y3, z3, w3);
..
然后我创建一个包含vector1,vector2,vector3 ....的顶点缓冲区。
接下来,我创建一个纹理并使用以下方法将上面的缓冲区绑定到它:
glTexBuffer(GL_TEXTURE_BUFFER, GL_RGBA32F, bufferID);
我选择了GL_RGBA32F,因为x1,y1,z1,w1等都是浮点数。
在着色器中我可以使用以下方法获取各个向量:
vec4 vector1 = texelFetch(samplerObj, 0);
vec4 vector2 = texelFetch(samplerObj, 1);
.
.
但是,现在假设我的位移矢量不是vec4,而是一个整数。 即
int vector1 = x1; //(int is 32 bit unsigned)
int vector2 = x2; //(int is 32 bit unsigned)
有人可以告诉相应的internalFormat会是什么?
是吗
glTexBuffer(GL_TEXTURE_BUFFER, GL_R32UI, bufferID);
我还将如何在着色器中使用texelFetch获取值? 是吗
int vector1 = texelFetch(samplerObj, 0);
或
int vector1 = texelFetch(samplerObj, 0).r ?
我很困惑因为texelFetch应该返回一个有4个组件的纹素,所以我必须使用结果的红色组件吗?
答案 0 :(得分:7)
您已经提到了无符号整数的正确大小的内部格式:R32UI
。允许的格式在表8.15 中列举,可在OpenGL 4.4核心配置文件规范的第8.9节中找到。请注意,在具有上述内部格式的缓冲区纹理上使用texelFetch
时,缓冲区存储的内容不会被标准化!这意味着,在进行查找时,您不会获得[0,1]范围内的值,但是在[0,2 ^(n-1)]范围内。
而不是samplerBuffer
,您还需要usamplerBuffer
。
如果texelFetch
的{{1}}内部格式为samplerBuffer
,如上述表格所示,将返回一个uvec4,返回的组件将包含以下值:R32UI
。
uvec4(R, 0, 0, 1)
这将导致编译时错误,因为没有从int vector1 = texelFetch(samplerObj, 0);
到uvec4
的隐式转换。
int
此swizzle-mask将返回int vector1 = texelFetch(samplerObj, 0).r;
返回的uvec4的R分量,并执行从texelFetch
到uint
的隐式转换。从语义上讲,将标量值命名为 vector 也没有意义。 ;)
你真正想要的是像
int
其中uint displacement = texelFetch(samplerObj, 0).r;
是samplerObj
。
编辑:为了澄清,usamplerBuffer
将始终返回gvec4 - 其中 g 将只是空(固定和浮点格式), i 或 u 。填充向量的方式取决于缓冲区纹理的内部格式。如果你选择R32F,你会得到一个非标准化的vec4(R,0,0,1),对于RGBA16你会得到一个标准化的vec4(R,G,B,A)。
为避免进一步混淆:使用单分量格式时,不为4分量向量分配内存!他们只是在查找时扩展到了gvec4!