Vertex attributes:
所有 OpenGL ES 3.0 的实现必须至少支持16个vertex attribute,实际支持的个数可以通过GL_MAX_VERTEX_ATTRIBS查询
GLint maxVertexAttribs; // n will be >= 16
glGetIntegerv(GL_MAX_VERTEX_ATTRIBS, &maxVertexAttribs);
Constant Vertex Attribute
void glVertexAttriblf(GLuint index, GLfloat x);
void glVertexAttrib2f(GLuint index, GLfloat x, GLfloat y);
void glVertexAttrib3f( GLuint index, GLfloat x, GLfloat y, GLfloat z);
void glVertexAttrib4f( GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w);
void glVertexAttriblfv(GLuint index, const GLfloat *values);
void glVertexAttrib2fv(GLuint index, const GLfloat *values);
void glVertexAttrib3fv(GLuint index, const GLfloat *values);
void glVertexAttrib4fv(GLuint index, const GLfloat *values);
The glVertexAttrib*commands are used to load the generic vertex attribute specified by index.
其中
(1)glVertexAttriblf 和 glVertexAttriblfv 加载 (x, 0.0, 0.0, 1.0)
(2)glVertexAttrib2f 和 glVertexAttrib2fv 加载 (x, y, 0.0, 1.0)
(3)glVertexAttrib3f 和 glVertexAttrib3fv 加载 (x, y, z, 1.0)
(4)glVertexAttrib4f 和 glVertexAttribl4fv 加载 (x, y, z, w)
一般来说使用Constant Vertex Attribute类似于使用a scalar/vector uniform
index应该指明的是什么属性
Vertex arrays
使用glVertexAttribPointer 或者 glVertexAttribIPointer
Two methods are commonly used for allocating and storing vertex attribute data: (array of structures & a structure of arrays)
• Store vertex attributes together in a single buffer—a method called an
array of structures.The structure represents all attributes of a vertex,
and we have an array of these attributes per vertex.
• Store each vertex attribute in a separate buffer—a method called a
structure of arrays.
Performance Hints
(1)How to Store Different Attributes of a Vertex
一般使用array of structures, The reason is that the attribute data for each vertex can be
read in sequential fashion, which will most likely result in an efficient
memory access pattern。
array of structures 的缺点是如果某一个属性的值需要更新,比如position,则the entire vertex attribute buffer 需要重新加载。
而a structure of arrays,不同的属性值在不同的buffer对象中,没有上述缺点。
(2)Which Data Format to Use for Vertex Attributes
建议使用GL_HALF_FLOAT
(3)How the Normalized Flag in gIVertexAttribPointer Works
如果 Normalized = false,效果类似直接把非float型转换成float型。
如果 Normalized = true,则非float型会被映射到[-1.0,1.0] (有符号型)或 [0.0, 1.0](无符号型)
如果是只想使用整型,则使用接口glVertexAttribIPointerfunction
(4)Selecting Between a Constant Vertex Attribute or a Vertex Array
Declaring Vertex Attribute Variables in a Vertex Shader
(1)in 修饰的变量就是vertex attribute。一般还会使用layout修饰,标明index。例如:
layout(location = 0) in vec4 a_position;
layout(location = 1) in vec2 a_texcoord;
layout(location = 2) in vec3 a_normal;
(2)in修饰 支持的类型:float, vec2,
vec3, vec4, int, ivec2, ivec3, ivec4, uint, uvec2, uvec3,
uvec4, mat2, mat2x2, mat2x3, mat2x4, mat3, mat3x3, mat3x4,
mat4, mat4x2,and mat4x3
(3)vertex attribute支持数量有限,最少16,最多通过GL_MAX_VERTEX_ATTRIBS查询.
如果一个vetex attribute被定义了,但没有使用,则不算是active的,不参与计数
(4)read only。in 变量是只读的,不能被赋值
(5)当一个program链接成功之后,有两种方式去 access an active vertex attributes
方式一就是在定义的时候使用layout修饰符,推荐。
方式二使用glGetProgramiv(program, GL_ACTIVE_ATTRIBUTES, &numActiveAttribs)获取活跃的属性的数目,然后使用glGetActiveAttrib。
Binding Vertex Attributes to Attribute Variables in a Vertex Shader
In OpenGL ES 3.0, three approaches may be used to map a generic vertex
attribute index to an attribute variable name in the vertex shader. These
approaches can be categorized as follows:
• The index can be specified in the vertex shader source code using the
layout(location = N)qualifier (recommended).
• OpenGL ES 3.0 will bind the generic vertex attribute index to the
attribute name.
• The application can bind the vertex attribute index to an attribute
name.
In the linking phase, the OpenGL ES 3.0 implementation performs the following operation for each attribute variable:
For each attribute variable, check whether a binding has been specified via
glBindAttribLocation. If a binding is specified, the appropriate attribute
index specified is used. If not, the implementation will assign a generic vertex
attribute index.
Vertex Buffer Objects (VBO)
两类:
(1)array buffer objects : GL_ARRAY_BUFFER
(2) element array buffer objects : GL_ELEMENT_ARRAY_BUFFER
The state associated with a buffer object can be categorized as follows:
• GL_BUFFER_SIZE. This refers to the size of the buffer object data that
is specified by glBufferData. The initial value when the buffer object
is first bound using glBindBufferis 0.
• GL_BUFFER_USAGE. This is a hint as to how the application will use the
data stored in the buffer object. It is described in detail in Table 6-2.
The initial value is GL_STATIC_DRAW.
As mentioned earlier, GL_BUFFER_USAGE is a hint to OpenGL ES—not a guarantee.
GL_BUFFER_USAGE仅仅是一个提示,并不保证实际的效果。比如: an application could allocate a buffer object data
store with usage set to GL_STATIC_DRAWand frequently modify it。
The vertex array data or element array data storage is created and initialized using the glBufferData command.
The contents of the buffer object data store can be initialized or updated using the glBufferSubData command.
Mapping Buffer Objects
So far, we have shown how to load data into buffer objects using glBufferDataor glBufferSubData. It is also possible for applications to map and unmap a buffer object’s data storage into the application’s address space. There are several reasons why an application might prefer to map a buffer rather than load its data using glBufferDataor glBufferSubData:
• Mapping the buffer can reduce the memory utilization of the application because potentially only a single copy of the data needs to be stored.
• On architectures with shared memory, mapping the buffer returns a direct pointer into the address space where the buffer will be stored for the GPU. By mapping the buffer, the application can avoid the copy step, thereby realizing better performance on updates.
glMapBufferRange:
glUnmapBuffer :
glFlushMappedBufferRange :
Copying Buffer Objects
glCopyBufferSubData :