跳到主要内容

OpenGL速查表

本文档提供OpenGL常用函数和概念的快速参考。

初始化

// GLFW初始化
glfwInit();
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);

// 创建窗口
GLFWwindow* window = glfwCreateWindow(800, 600, "Title", NULL, NULL);
glfwMakeContextCurrent(window);

// GLAD初始化
gladLoadGLLoader((GLADloadproc)glfwGetProcAddress);

// 视口
glViewport(0, 0, 800, 600);

缓冲对象

VBO

GLuint VBO;
glGenBuffers(1, &VBO);
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glBufferData(GL_ARRAY_BUFFER, size, data, GL_STATIC_DRAW);

VAO

GLuint VAO;
glGenVertexArrays(1, &VAO);
glBindVertexArray(VAO);

EBO

GLuint EBO;
glGenBuffers(1, &EBO);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, size, data, GL_STATIC_DRAW);

顶点属性

glVertexAttribPointer(index, size, type, normalized, stride, pointer);
glEnableVertexAttribArray(index);
glDisableVertexAttribArray(index);

绘制

glDrawArrays(GL_TRIANGLES, 0, vertexCount);
glDrawElements(GL_TRIANGLES, indexCount, GL_UNSIGNED_INT, 0);
glDrawArraysInstanced(GL_TRIANGLES, 0, vertexCount, instanceCount);
glDrawElementsInstanced(GL_TRIANGLES, indexCount, GL_UNSIGNED_INT, 0, instanceCount);

着色器

GLuint shader = glCreateShader(type);
glShaderSource(shader, 1, &source, NULL);
glCompileShader(shader);

GLuint program = glCreateProgram();
glAttachShader(program, shader);
glLinkProgram(program);

glUseProgram(program);
glDeleteShader(shader);

Uniform

glUniform1i(location, value);
glUniform1f(location, value);
glUniform3f(location, x, y, z);
glUniform4f(location, x, y, z, w);
glUniformMatrix4fv(location, count, transpose, value_ptr);

纹理

GLuint texture;
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);

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_MIPMAP_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);

glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, data);
glGenerateMipmap(GL_TEXTURE_2D);

glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, texture);

变换矩阵(GLM)

glm::mat4 model = glm::mat4(1.0f);
model = glm::translate(model, glm::vec3(x, y, z));
model = glm::rotate(model, glm::radians(angle), glm::vec3(x, y, z));
model = glm::scale(model, glm::vec3(x, y, z));

glm::mat4 view = glm::lookAt(cameraPos, cameraTarget, cameraUp);

glm::mat4 projection = glm::perspective(glm::radians(fov), aspect, near, far);
glm::mat4 projection = glm::ortho(left, right, bottom, top, near, far);

摄像机

glm::vec3 cameraPos = glm::vec3(0.0f, 0.0f, 3.0f);
glm::vec3 cameraFront = glm::vec3(0.0f, 0.0f, -1.0f);
glm::vec3 cameraUp = glm::vec3(0.0f, 1.0f, 0.0f);

glm::mat4 view = glm::lookAt(cameraPos, cameraPos + cameraFront, cameraUp);

// 移动
cameraPos += speed * cameraFront;
cameraPos -= speed * cameraFront;
cameraPos += glm::normalize(glm::cross(cameraFront, cameraUp)) * speed;
cameraPos -= glm::normalize(glm::cross(cameraFront, cameraUp)) * speed;

光照

// 环境光
vec3 ambient = ambientStrength * lightColor;

// 漫反射
vec3 norm = normalize(Normal);
vec3 lightDir = normalize(lightPos - FragPos);
float diff = max(dot(norm, lightDir), 0.0);
vec3 diffuse = diff * lightColor;

// 镜面反射
vec3 viewDir = normalize(viewPos - FragPos);
vec3 reflectDir = reflect(-lightDir, norm);
float spec = pow(max(dot(viewDir, reflectDir), 0.0), shininess);
vec3 specular = specularStrength * spec * lightColor;

// 最终颜色
vec3 result = (ambient + diffuse + specular) * objectColor;

深度测试

glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LESS);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

模板测试

glEnable(GL_STENCIL_TEST);
glStencilFunc(func, ref, mask);
glStencilOp(sfail, dpfail, dppass);
glClear(GL_STENCIL_BUFFER_BIT);

混合

glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glBlendEquation(GL_FUNC_ADD);

帧缓冲

GLuint fbo;
glGenFramebuffers(1, &fbo);
glBindFramebuffer(GL_FRAMEBUFFER, fbo);

// 纹理附件
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture, 0);

// 渲染缓冲附件
GLuint rbo;
glGenRenderbuffers(1, &rbo);
glBindRenderbuffer(GL_RENDERBUFFER, rbo);
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8, width, height);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rbo);

// 检查完整性
if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)

glBindFramebuffer(GL_FRAMEBUFFER, 0);

立方体贴图

GLuint textureID;
glGenTextures(1, &textureID);
glBindTexture(GL_TEXTURE_CUBE_MAP, textureID);

for (int i = 0; i < 6; i++) {
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_RGB,
width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, data);
}

glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);

常用枚举值

图元类型

枚举说明
GL_POINTS
GL_LINES线段
GL_LINE_STRIP连续线段
GL_LINE_LOOP闭合线段
GL_TRIANGLES三角形
GL_TRIANGLE_STRIP三角形带
GL_TRIANGLE_FAN三角形扇

纹理过滤

枚举说明
GL_NEAREST最近邻
GL_LINEAR线性插值
GL_NEAREST_MIPMAP_NEAREST最近mipmap+最近邻
GL_LINEAR_MIPMAP_NEAREST最近mipmap+线性
GL_NEAREST_MIPMAP_LINEAR线性mipmap+最近邻
GL_LINEAR_MIPMAP_LINEAR线性mipmap+线性

纹理环绕

枚举说明
GL_REPEAT重复
GL_MIRRORED_REPEAT镜像重复
GL_CLAMP_TO_EDGE边缘拉伸
GL_CLAMP_TO_BORDER边框颜色

缓冲用途

枚举说明
GL_STATIC_DRAW设置一次,使用多次
GL_DYNAMIC_DRAW多次修改,使用多次
GL_STREAM_DRAW设置一次,使用很少

GLSL内置变量

变量说明
gl_Position顶点着色器输出位置
gl_FragColor片段着色器输出颜色(旧版)
gl_FragCoord片段窗口坐标
gl_FrontFacing是否为正面
gl_PointSize点大小
gl_VertexID顶点索引
gl_InstanceID实例索引

GLSL内置函数

// 数学函数
abs(x), sign(x), floor(x), ceil(x), fract(x)
min(x, y), max(x, y), clamp(x, min, max)
mix(x, y, a), step(edge, x), smoothstep(edge0, edge1, x)

// 三角函数
sin(x), cos(x), tan(x), asin(x), acos(x), atan(y, x)

// 指数函数
pow(x, y), exp(x), log(x), sqrt(x), inversesqrt(x)

// 向量函数
length(x), distance(x, y), dot(x, y), cross(x, y)
normalize(x), reflect(I, N), refract(I, N, eta)

// 矩阵函数
matrixCompMult(x, y), transpose(m), inverse(m)

// 纹理函数
texture(sampler, coord), textureProj(sampler, coord)
texelFetch(sampler, ivec, lod)

错误检查

GLenum err;
while ((err = glGetError()) != GL_NO_ERROR) {
switch (err) {
case GL_INVALID_ENUM: break;
case GL_INVALID_VALUE: break;
case GL_INVALID_OPERATION: break;
case GL_OUT_OF_MEMORY: break;
}
}

清理资源

glDeleteBuffers(1, &VBO);
glDeleteBuffers(1, &EBO);
glDeleteVertexArrays(1, &VAO);
glDeleteTextures(1, &texture);
glDeleteFramebuffers(1, &FBO);
glDeleteRenderbuffers(1, &RBO);
glDeleteProgram(shaderProgram);