OpenGL 是一个强大的跨平台图形 API,用于渲染 2D 和 3D 图形。以下是 OpenGL 3D 编程的入门基础。
一. 环境设置
安装必要的库
GLFW: 用于创建窗口和处理输入
GLEW 或 GLAD: 用于加载 OpenGL 函数
GLM: 数学库,用于 3D 变换
// 基本 OpenGL 程序结构示例
#include <GL/glew.h>
#include <GLFW/glfw3.h>
int main() {
// 初始化 GLFW
if (!glfwInit()) return -1;
// 创建窗口
GLFWwindow* window = glfwCreateWindow(800, 600, "OpenGL 3D", NULL, NULL);
if (!window) {
glfwTerminate();
return -1;
}
// 设置当前上下文
glfwMakeContextCurrent(window);
// 初始化 GLEW
if (glewInit() != GLEW_OK) return -1;
// 主循环
while (!glfwWindowShouldClose(window)) {
// 清屏
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
// 渲染代码
// 交换缓冲区
glfwSwapBuffers(window);
// 处理事件
glfwPollEvents();
}
glfwTerminate();
return 0;
}
二. 3D 基础概念
坐标系
OpenGL 使用右手坐标系
X轴向右,Y轴向上,Z轴向外(朝向观察者)
变换矩阵
模型矩阵(Model): 物体从局部空间到世界空间的变换
视图矩阵(View): 世界空间到相机空间的变换
投影矩阵(Projection): 从相机空间到裁剪空间的变换
// 使用 GLM 创建变换矩阵示例
#include <glm/glm.hpp>
#include <glm/gtc/matrix_transform.hpp>
#include <glm/gtc/type_ptr.hpp>
glm::mat4 model = glm::mat4(1.0f); // 单位矩阵
model = glm::rotate(model, glm::radians(45.0f), glm::vec3(0.0f, 1.0f, 0.0f)); // 绕Y轴旋转45度
model = glm::translate(model, glm::vec3(1.0f, 0.0f, 0.0f)); // 沿X轴平移
glm::mat4 view = glm::lookAt(
glm::vec3(0.0f, 0.0f, 3.0f), // 相机位置
glm::vec3(0.0f, 0.0f, 0.0f), // 观察目标
glm::vec3(0.0f, 1.0f, 0.0f) // 上向量
);
glm::mat4 projection = glm::perspective(
glm::radians(45.0f), // 视野角度
800.0f / 600.0f, // 宽高比
0.1f, 100.0f // 近平面和远平面
);
三. 渲染3D物体
顶点数据
// 立方体顶点数据示例
float vertices[] = {
// 位置 // 颜色
-0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f,
0.5f, -0.5f, -0.5f, 0.0f, 1.0f, 0.0f,
// ... 其他顶点
};
顶点缓冲对象(VBO)和顶点数组对象(VAO)
unsigned int VBO, VAO;
glGenVertexArrays(1, &VAO);
glGenBuffers(1, &VBO);
glBindVertexArray(VAO);
glBindBuffer(GL_ARRAY_BUFFER, VBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
// 位置属性
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(float), (void*)0);
glEnableVertexAttribArray(0);
// 颜色属性
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(float), (void*)(3 * sizeof(float)));
glEnableVertexAttribArray(1);
着色器程序
顶点着色器示例:
glsl
#version 330 core
layout (location = 0) in vec3 aPos;
layout (location = 1) in vec3 aColor;
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;
out vec3 ourColor;
void main() {
gl_Position = projection * view * model * vec4(aPos, 1.0);
ourColor = aColor;
}
片段着色器示例:
glsl
#version 330 core
in vec3 ourColor;
out vec4 FragColor;
void main() {
FragColor = vec4(ourColor, 1.0);
}