最简单的图片绘制程序
float vertices[] = {
//-- 位置 ---- -- 纹理坐标--
400, 400, 0.0f, 1.0f, 1.0f, // 右上
400, 0, 0.0f, 1.0f, 0.0f, // 右下
0, 0, 0.0f, 0.0f, 0.0f, // 左下
0 , 400, 0.0f, 0.0f, 1.0f // 左上
};
unsigned int indices[] = { // 注意索引从0开始!
0, 1, 3, // 第一个三角形
1, 2 ,3, // 第二个三角形
};
GLuint vbo, ebo, texture;
glGenBuffers(1, &vbo);
glGenBuffers(1, &ebo);
glBindBuffer(GL_ARRAY_BUFFER, vbo);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ebo);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);
glEnableVertexAttribArray(_attribPosition);
glVertexAttribPointer(_attribPosition, 3, GL_FLOAT, GL_FALSE, sizeof(float) * 5, (GLvoid*)0);
glEnableVertexAttribArray(_aTexCoord);
glVertexAttribPointer(_aTexCoord, 2, GL_FLOAT, GL_FALSE, sizeof(float) * 5, (GLvoid*)(sizeof(float) * 3));
Image img;
img.initWithImageFile("./vx.png");
int width = img.getWidth();
int height = img.getHeight();
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);
glEnable(GL_TEXTURE_2D);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
// png使用GL_RGBA, jpg使用GL_RGB
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, img.getData());
glGenerateMipmap(GL_TEXTURE_2D);
glActiveTexture(GL_TEXTURE0);
glUniform1i(_ourTexture, 0);
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, 0);
CHECK_GL_ERROR_DEBUG();
动态合图原理分析
如果多个图片一个drawCall完成绘制,其原理就是将要绘制的图片,统一绘制到一张大纹理(RenderTexture),实现细节为通过glTexSubImage2D可以修改纹理的部分区域。
需要将不同格式(RGB888、RGBA8888等)的纹理数据转换为RenderTexture的纹理格式。
在提交顶点数据时,注意映射好每张图片的纹理坐标,即可。
生成material的规则:
void TrianglesCommand::generateMaterialID()
{
// glProgramState is hashed because it contains:
// * uniforms/values
// * glProgram
//
// we safely can when the same glProgramState is being used then they share those states
// if they don't have the same glProgramState, they might still have the same
// uniforms/values and glProgram, but it would be too expensive to check the uniforms.
struct {
GLuint textureId;
GLenum blendSrc;
GLenum blendDst;
void* glProgramState;
} hashMe;
hashMe.textureId = _textureID;
hashMe.blendSrc = _blendType.src;
hashMe.blendDst = _blendType.dst;
hashMe.glProgramState = _glProgramState;
_materialID = XXH32((const void*)&hashMe, sizeof(hashMe), 0);
}
TriangleCommand只使用了quadIndices前6位:
网友评论