我有以下统一缓冲区:
layout(std140) uniform Light
{
vec4 AmbientLight;
vec4 LightIntensity;
vec3 LightPosition;
float LightAttenuation;
};
我在缓冲数据和填充时需要添加一些问题。我已经阅读了http://ptgmedia.pearsoncmg.com/images/9780321552624/downloads/0321552628_AppL.pdf,它说我必须在vec3的末尾添加额外的4个字节用于填充 - 所以我将为'Light'上传总共13个字节。然而,当我这样做时,'LightAttenuation'得到我在'LightPosition'上填充的值,而不是前面的一个字节,所以当我不填充时,我在着色器中得到正确的值。这是为什么?
答案 0 :(得分:9)
有关详细信息,请参阅OpenGL规范的7.6.2.2节,但基本上,std140
布局表示每个变量将在前一个变量之后立即布局,并为变量类型所需的对齐添加了足够的填充。 vec3
和vec4
都需要16字节对齐,分别为12和16字节。 float
需要4字节对齐,大小为4字节。因此,使用std140
布局,LightPosition
将获得16字节对齐,因此将始终以12 mod 16的地址结束。由于这是4字节对齐,因此在{{1}之前不会插入额外的填充}}
答案 1 :(得分:0)
通常是的,openGL会将vec3视为vec4。但是在这种情况下AFAIK它将浮动LightAttenuation附加到vec3 LightPosition - 形成一个整体vec4(它的某种优化,由glsl编译器完成)。 整个结构的尺寸为3x vec4。
尝试使用vec3或vec4进行LightAttenuation。