/***
* Task11 阴影 (如VS版本不同,则右击项目->属性->常规->平台工具集,选中自己的VS版本即可)
* 步骤:
* 1-初始化: GLFW窗口,GLAD。
* 2-帧缓冲: 生成深度贴图,进行光空间变换。
* 3-数据处理: 给定顶点数据,生成并绑定VAO&VBO(准备在GPU中进行处理),设置顶点属性指针(本质上就是告诉OpenGL如何处理数据)。
* 4-载入纹理: 通过stb_image图像库加载图像。
* 5-光源: 设置了平行光。
* 6-着色器: 给出立方体和阴影贴图的着色器,然后在Shader类中分别链接为着色器程序,渲染时使用着色器程序。
* 7-摄像机: 计算出每帧的间隔时间,以及摄像机的摆放位置。
* 8-渲染: 计算间隔时间,输入控制,渲染阴影深度贴图,清空缓冲,开启光源,绑定纹理,绘制立方体,交换缓冲区检查触发事件后释放资源。
*/
#include <iostream>
#define STB_IMAGE_IMPLEMENTATION
#include <stb/stb_image.h>
#include <glad/glad.h>
#include <GLFW/glfw3.h>
#include "Shader.h"
#include "Model.h"
#include "Camera.h"
#include "Texture.h"
//鼠标键盘响应函数
void framebuffer_size_callback(GLFWwindow* window, int width, int height);
void mouse_callback(GLFWwindow* window, double xpos, double ypos);
void scroll_callback(GLFWwindow* window, double xoffset, double yoffset);
void processInput(GLFWwindow *window);
float screen_width = 1280.0f; //窗口宽度
float screen_height = 720.0f; //窗口高度
//摄像机相关参数
Camera camera(glm::vec3(-2.0f, 3.5f, 4.0f), glm::vec3(0, 1, 0), -60, -45);
float lastX = screen_width / 2.0f;
float lastY = screen_height / 2.0f;
bool firstMouse = true;
GLfloat near_plane = 1.0f, far_plane = 7.5f; // 视锥的远近平面
const GLuint SHADOW_WIDTH = 1024, SHADOW_HEIGHT = 1024; // 深度贴图的分辨率
float deltaTime = 0.0f;
float lastFrame = 0.0f;
glm::vec3 lightPos(-3.0f, 4.0f, -1.0f);
unsigned int cube_vbo, cube_vao;
unsigned int plane_vbo, plane_vao;
void DrawScene(Shader shader, float current_frame, unsigned int textureID1, unsigned int textureID2);//绘制整个场景
void renderQuad();//绘制铺满整个屏幕的四边形,用于检测
int main() {
// 初始化GLFW
glfwInit(); // 初始化GLFW
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); // OpenGL版本为3.3,主次版本号均设为3
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); // 使用核心模式(无需向后兼容性)
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); // 如果使用的是Mac OS X系统,需加上这行
glfwWindowHint(GLFW_RESIZABLE, FALSE); // 不可改变窗口大小
// 创建窗口(宽、高、窗口名称)
auto window = glfwCreateWindow(screen_width, screen_height, "shadow", nullptr, nullptr);
if (window == nullptr) {
std::cout << "Failed to Create OpenGL Context" << std::endl;
glfwTerminate();
return -1;
}
glfwMakeContextCurrent(window);
glfwSetFramebufferSizeCallback(window, framebuffer_size_callback);
glfwSetCursorPosCallback(window, mouse_callback);
glfwSetScrollCallback(window, scroll_callback);
glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
// 初始化GLAD,加载OpenGL函数指针地址的函数
if (!gladLoadGLLoader((GLADloadproc)glfwGetProcAddress))
{
std::cout << "Failed to initialize GLAD" << std::endl;
return -1;
}
// 设置离屏渲染帧缓冲(生成深度贴图)
GLuint depthMapFBO;
glGenFramebuffers(1, &depthMapFBO);
GLuint depthMap;
glGenTextures(1, &depthMap);
glBindTexture(GL_TEXTURE_2D, depthMap);
glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, SHADOW_WIDTH, SHADOW_HEIGHT, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL);
//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_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
//解决采样越界
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER);
float borderColor[] = { 1.0, 1.0, 1.0, 1.0 };
glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, borderColor);
glBindFramebuffer(GL_FRAMEBUFFER, depthMapFBO);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, depthMap, 0);
glDrawBuffer(GL_NONE);
glReadBuffer(GL_NONE);
glBindFramebuffer(GL_FRAMEBUFFER, 0);
// 指定当前视口尺寸(前两个参数为左下角位置,后两个参数是渲染窗口宽、高)
glViewport(0, 0, screen_width, screen_height);
// 着色器(立方体和阴影贴图)
Shader cube_shader = Shader("res/shader/DrawScene.vs", "res/shader/DrawScene.fs");
Shader shadowMap_shader = Shader("res/shader/ShadowMap.vs", "res/shader/ShadowMap.fs");
Shader debugQuad = Shader("res/shader/debugDepthQuad.vs", "res/shader/debugDepthQuad.fs");
// 正方体&&地板数据s
float cubeVertices[] = {
// ---- 位置 ---- ---- 法线 ---- - 纹理坐标 -
-1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f,
1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.5f,
1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.5f,
-1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f,
-1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.5f,
-1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f,
1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.5f, 0.0f,
1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.5f, 0.5f,
1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.5f, 0.5f,
-1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.5f,
-1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f,
-1.0f, 1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 0.5f, 0.0f,
-1.0f, 1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 0.5f, 0.5f,
-1.0f, -1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.5f,
-1.0f, -1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.5f,
-1.0f, -1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f,
-1.0f, 1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 0.5f, 0.0f,
1.0f, 1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.5f, 0.0f,
1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.5f,
1.0f, 1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.5f, 0.5f,
1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.5f,
1.0f, 1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.5f, 0.0f,
1.0f, -1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f,
-1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.5f,
1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.5f, 0.5f,
1.0f, -1.0f, 1.0f, 0.0f, -1.0f, 0.0f, 0.5f, 0.0f,
1.0f, -1.0f, 1.0f, 0.0f, -1.0f, 0.0f, 0.5f, 0.0f,
-1.0f, -1.0f, 1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f,
-1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.5f,
-1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.5f,
1.0f, 1.0f , 1.0f, 0.0f, 1.0f, 0.0f, 0.5f, 0.0f,
1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 0.5f, 0.5f,
1.0f, 1.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.5f, 0.0f,
-1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.5f,
-1.0f, 1.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f
};
float planeVertices[] = {
5.0f, -0.5f, 5.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f,
-5.0f, -0.5f, 5.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f,
-5.0f, -0.5f, -5.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f,
5.0f, -0.5f, 5.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f,
-5.0f, -0.5f, -5.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f,
5.0f, -0.5f, -5.0f, 0.0f, 1.0f, 0.0f, 1.0f, 1.0f
};
// ---------------------绑定顶点数组对象----------------------
glGenVertexArrays(1, &cube_vao);
glGenBuffers(1, &cube_vbo);
glBindBuffer(GL_ARRAY_BUFFER, cube_vbo);
glBufferData(GL_ARRAY_BUFFER, sizeof(cubeVertices), cubeVertices, GL_STATIC_DRAW);
glBindVertexArray(cube_vao);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)0);
glEnableVertexAttribArray(0);
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)(3 * sizeof(float)));
glEnableVertexAttribArray(1);
glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)(6 * sizeof(float)));
glEnableVertexAttribArray(2);
glGenVertexArrays(1, &plane_vao);
glGenBuffers(1, &plane_vbo);
glBindBuffer(GL_ARRAY_BUFFER, plane_vbo);
glBufferData(GL_ARRAY_BUFFER, sizeof(planeVertices), planeVertices, GL_STATIC_DRAW);
glBindVertexArray
没有合适的资源?快使用搜索试试~ 我知道了~
OpenGL-Shadow.zip
共55个文件
jpg:10个
obj:6个
tlog:6个
需积分: 5 1 下载量 170 浏览量
2023-05-22
14:05:54
上传
评论
收藏 22.95MB ZIP 举报
温馨提示
在Visual Studio 2015上基于OpenGL实现阴影计算。 当把一个纹理附加到帧缓冲的时候,所有的渲染指令将会写入到这个纹理中,就想它是一个普通的颜色/深度或模板缓冲一样。使用纹理的优点是,所有渲染操作的结果将会被储存在一个纹理图像中,我们之后可以在着色器中很方便地使用它。 渲染缓冲对象(Renderbuffer Object)是在纹理之后引入到OpenGL中,作为一个可用的帧缓冲附件类型的,所以在过去纹理是唯一可用的附件。和纹理图像一样,渲染缓冲对象是一个真正的缓冲,即一系列的字节、整数、像素等。渲染缓冲对象 在了解帧缓冲原理后,我们将会将场景渲染到一个附加到帧缓冲对象上的颜色纹理中,之后将在一个横跨整个屏幕的四边形上绘制这个纹理。 阴影映射(Shadow Mapping)背后的思路非常简单:具体过程是我们从光源视角出发(以光源所在位置作为摄像机位置),绘制一条射线到达场景上各个片元,得到射线第一次击中的那个物体,然后用这个最近点和射线上其他点进行对比。然后我们将测试一下看看射线上的其他点是否比最近点更远,如果是的话,这个点就在阴影中。我们使用深度缓冲来实现阴影。
资源推荐
资源详情
资源评论
收起资源包目录
OpenGL_Shadow.zip (55个子文件)
.vs
OpenGL_Shadow
v14
.suo 57KB
OpenGL_Shadow.sdf 45.13MB
OpenGL_Shadow
Model.h 6KB
Texture.cpp 1KB
Camera.h 1KB
Texture.h 262B
res
texture
floor1.jpg 902KB
container2.jpg 934KB
floor2.jpg 337KB
container.jpg 226KB
floor4.jpg 627KB
floor.jpg 1.12MB
shader
debugDepthQuad.vs 198B
DrawScene.vs 550B
debugDepthQuad.fs 211B
ShadowMap.fs 55B
DrawScene.fs 2KB
ShadowMap.vs 163B
model
skin.jpg 195KB
font_blue.png 2KB
character.obj 552KB
belt.jpg 189KB
hat.jpg 164KB
character.mtl 1KB
font_grey.png 2KB
eye.jpg 92KB
main.cpp 14KB
Mesh.h 3KB
Shader.h 2KB
Camera.cpp 2KB
OpenGL_Shadow.vcxproj.filters 2KB
Shader.cpp 5KB
Debug
OpenGL_Shadow.log 8KB
Texture.obj 44KB
Camera.obj 52KB
glad.obj 175KB
Shader.obj 383KB
OpenGL_Shadow.Build.CppClean.log 2KB
OpenGL_Shadow.tlog
CL.write.1.tlog 4KB
CL.command.1.tlog 4KB
link.command.1.tlog 2KB
link.read.1.tlog 5KB
link.write.1.tlog 1KB
OpenGL_Shadow.lastbuildstate 200B
CL.read.1.tlog 167KB
vc140.idb 1.24MB
vc140.pdb 700KB
main.obj 660KB
OpenGL_Shadow.vcxproj 6KB
Debug
assimp-vc140-mt.lib 236KB
assimp-vc140-mt.dll 14.8MB
OpenGL_Shadow.ilk 1.32MB
OpenGL_Shadow.exe 634KB
OpenGL_Shadow.pdb 1.64MB
OpenGL_Shadow.sln 1KB
共 55 条
- 1
资源评论
UestcXiye
- 粉丝: 5280
- 资源: 86
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功