【发布时间】:2018-05-16 21:28:04
【问题描述】:
我遇到了令我困惑的事情,但我找不到答案。当我这样写着色器时:
layout (location = 0) in vec3 inPosition;
layout (location = 1) in vec3 inNormal;
layout (location = 2) in vec2 inTexCoords;
我知道 vec3 不像许多 vec4 那样是 16 字节对齐的,也不是 SIMD 兼容的数据类型。我知道这一点(我认为),因为我的 C++ 代码中的数据是:
struct Vertex
{
vec3 position;
vec3 normal;
vec2 texCoords;
};
每个向量彼此紧贴,没有填充,大小为 8 * sizeof(float),32 字节。我将它传递给制服,着色器读取它很好,所以我知道它们都是对齐的。
但是当涉及到 GLSL 中的统一块时,例如在 std140 标准中,vec3 必须在添加另一个 vec3 或 vec4 之前额外填充四个字节:
- 如果成员是一个三分量向量,其分量消耗 N 个基本机器单元,则基本对齐为 4N
但是,您也可以在 vec3 和下一个 vec3 之间存储一个四字节 int 或四字节 bool 以压缩大小。那么这是否意味着顶点布局的属性指针值不遵循 std140 布局?此外,如果我在 C++ 代码中使用 SIMD 16 字节对齐向量,这是否意味着我将不再能够将属性指针值设置为 vec3、vec3、vec2,而是拥有所有 vec4?
我还在文档中看到以下警告:
警告:实现有时会导致 std140 布局错误 vec3 组件。建议您手动填充 结构/数组,完全避免使用 vec3。
这里是说完全避免使用 vec3,但我认为在 vec3 之后打包一个四字节 int 或 bool 是一种节省空间的聪明技术。
【问题讨论】:
标签: c++ opengl alignment glsl shader