在OpenGL ES中,将值传入Shader的方式主要有以下几种:
1. Uniform变量
- 用途:用于传递在绘制过程中不变的常量数据,如变换矩阵、颜色等。
 - 步骤: 
- 在Shader中声明Uniform变量:
uniform mat4 uMVPMatrix; // 例如一个模型视图投影矩阵 uniform vec4 uColor; // 例如一个颜色值 - 在C/C++代码中获取Uniform变量的位置:
GLint uMVPMatrixLocation = glGetUniformLocation(program, "uMVPMatrix"); GLint uColorLocation = glGetUniformLocation(program, "uColor"); - 使用
glUniform*系列函数将数据传入Shader:glUniformMatrix4fv(uMVPMatrixLocation, 1, GL_FALSE, mvpMatrix); glUniform4f(uColorLocation, r, g, b, a); 
 - 在Shader中声明Uniform变量:
 
2. Attribute变量
- 用途:用于传递每个顶点不同的数据,如顶点位置、法线、纹理坐标等。
 - 步骤: 
- 在Shader中声明Attribute变量:
attribute vec4 aPosition; // 顶点位置 attribute vec2 aTexCoord; // 纹理坐标 - 在C/C++代码中获取Attribute变量的位置:
GLint aPositionLocation = glGetAttribLocation(program, "aPosition"); GLint aTexCoordLocation = glGetAttribLocation(program, "aTexCoord"); - 使用
glVertexAttribPointer指定数据格式和位置:glVertexAttribPointer(aPositionLocation, 3, GL_FLOAT, GL_FALSE, stride, vertexData); glVertexAttribPointer(aTexCoordLocation, 2, GL_FLOAT, GL_FALSE, stride, texCoordData); - 启用Attribute变量:
glEnableVertexAttribArray(aPositionLocation); glEnableVertexAttribArray(aTexCoordLocation); 
 - 在Shader中声明Attribute变量:
 
3. Texture(纹理)
- 用途:用于传递纹理数据,通常用于贴图。
 - 步骤: 
- 在Shader中声明Sampler变量:
uniform sampler2D uTexture; // 2D纹理 - 在C/C++代码中绑定纹理并传入Shader:
glActiveTexture(GL_TEXTURE0); // 激活纹理单元0 glBindTexture(GL_TEXTURE_2D, textureId); // 绑定纹理 GLint uTextureLocation = glGetUniformLocation(program, "uTexture"); glUniform1i(uTextureLocation, 0); // 将纹理单元0传入Shader 
 - 在Shader中声明Sampler变量:
 
4. Varying变量
- 用途:用于在Vertex Shader和Fragment Shader之间传递插值数据,如颜色、纹理坐标等。
 - 步骤: 
- 在Vertex Shader中声明Varying变量并赋值:
varying vec2 vTexCoord; void main() {vTexCoord = aTexCoord; // 从Attribute变量传入gl_Position = uMVPMatrix * aPosition; } - 在Fragment Shader中声明相同的Varying变量并使用:
varying vec2 vTexCoord; void main() {gl_FragColor = texture2D(uTexture, vTexCoord); // 使用插值后的纹理坐标 } 
 - 在Vertex Shader中声明Varying变量并赋值:
 
5. Shader Storage Buffer Object (SSBO)
- 用途:用于传递大量数据,通常用于计算Shader或复杂的数据结构。
 - 步骤: 
- 在Shader中声明SSBO:
layout(std430, binding = 0) buffer MyBuffer {vec4 data[]; }; - 在C/C++代码中创建并绑定SSBO:
GLuint ssbo; glGenBuffers(1, &ssbo); glBindBuffer(GL_SHADER_STORAGE_BUFFER, ssbo); glBufferData(GL_SHADER_STORAGE_BUFFER, size, data, GL_DYNAMIC_DRAW); glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 0, ssbo); 
 - 在Shader中声明SSBO:
 
6. Uniform Buffer Object (UBO)
- 用途:用于在多个Shader之间共享Uniform数据。
 - 步骤: 
- 在Shader中声明UBO:
layout(std140) uniform MyUBO {mat4 uMVPMatrix;vec4 uColor; }; - 在C/C++代码中创建并绑定UBO:
GLuint ubo; glGenBuffers(1, &ubo); glBindBuffer(GL_UNIFORM_BUFFER, ubo); glBufferData(GL_UNIFORM_BUFFER, size, data, GL_STATIC_DRAW); glBindBufferBase(GL_UNIFORM_BUFFER, 0, ubo); 
 - 在Shader中声明UBO:
 
总结
- Uniform:用于传递常量数据。
 - Attribute:用于传递顶点数据。
 - Texture:用于传递纹理数据。
 - Varying:用于在Vertex和Fragment Shader之间传递插值数据。
 - SSBO:用于传递大量数据。
 - UBO:用于在多个Shader之间共享Uniform数据。
 
根据具体需求选择合适的方式将数据传入Shader。
