diff options
author | Dan Goodliffe <dan@randomdan.homeip.net> | 2022-12-03 03:41:32 +0000 |
---|---|---|
committer | Dan Goodliffe <dan@randomdan.homeip.net> | 2022-12-03 03:41:32 +0000 |
commit | aa75b018f3b97c72b57de68867417cbda51439c3 (patch) | |
tree | 446efaad2727ae6bff6433e8bfbf590e99d5e310 /gfx/gl/shadowMapper.cpp | |
parent | Add GL_DEBUG_OUTPUT with boost test error handling to test-render context (diff) | |
download | ilt-aa75b018f3b97c72b57de68867417cbda51439c3.tar.bz2 ilt-aa75b018f3b97c72b57de68867417cbda51439c3.tar.xz ilt-aa75b018f3b97c72b57de68867417cbda51439c3.zip |
Initial commit of the shadow map generator and shadows render interface
Lots of hard coding, buggy in places, far from great, but the basics
work.
Diffstat (limited to 'gfx/gl/shadowMapper.cpp')
-rw-r--r-- | gfx/gl/shadowMapper.cpp | 92 |
1 files changed, 92 insertions, 0 deletions
diff --git a/gfx/gl/shadowMapper.cpp b/gfx/gl/shadowMapper.cpp new file mode 100644 index 0000000..4cc2e24 --- /dev/null +++ b/gfx/gl/shadowMapper.cpp @@ -0,0 +1,92 @@ +#include "shadowMapper.h" +#include "gfx/gl/shaders/fs-shadowCast.h" +#include "gfx/gl/shaders/vs-shadowDynamicPoint.h" +#include "gfx/gl/shaders/vs-shadowFixedPoint.h" +#include "gfx/models/texture.h" +#include "location.hpp" +#include "maths.h" +#include "sceneProvider.h" +#include "sceneShader.h" +#include <glm/gtc/type_ptr.hpp> +#include <glm/gtx/transform.hpp> +#include <glm/matrix.hpp> + +ShadowMapper::ShadowMapper(const glm::ivec2 & s) : size {s} +{ + glBindTexture(GL_TEXTURE_2D, depthMap); + glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, size.x, size.y, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER); + static constexpr glm::vec3 border {std::numeric_limits<float>::infinity()}; + // static constexpr glm::vec3 border {1}; + glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, glm::value_ptr(border)); + + glBindFramebuffer(GL_FRAMEBUFFER, depthMapFBO); + glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, depthMap, 0); + glDrawBuffer(GL_NONE); + glReadBuffer(GL_NONE); + if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) { + throw std::runtime_error("Framebuffer not complete!"); + } + glBindFramebuffer(GL_FRAMEBUFFER, 0); +} + +glm::mat4x4 +ShadowMapper::update(const SceneProvider & scene, const glm::vec3 & dir) const +{ + const glm::vec3 centre {1200.F, 1200.F, 0.F}; + const glm::vec3 range = glm::normalize(dir) * 1800.F; + const auto lightProjection = glm::ortho(-1200.F, 1200.F, -1200.F, 1200.F, 0.F, 3600.F); + const auto lightView = glm::lookAt(centre - range, centre, north); + const auto lightViewProjection = lightProjection * lightView; + fixedPoint.setViewProjection(lightViewProjection); + dynamicPoint.setViewProjection(lightViewProjection); + + glBindFramebuffer(GL_FRAMEBUFFER, depthMapFBO); + glViewport(0, 0, size.x, size.y); + glClear(GL_DEPTH_BUFFER_BIT); + glEnable(GL_DEPTH_TEST); + glCullFace(GL_FRONT); + scene.shadows(*this); + glCullFace(GL_BACK); + + // Texture::saveDepth(depthMap, size, "/tmp/depth.tga"); + return lightViewProjection; +} + +ShadowMapper::FixedPoint::FixedPoint() : + Program {shadowFixedPoint_vs, shadowCast_fs}, viewProjectionLoc {*this, "viewProjection"} +{ +} +void +ShadowMapper::FixedPoint::setViewProjection(const glm::mat4 & viewProjection) const +{ + use(); + glUniformMatrix4fv(viewProjectionLoc, 1, GL_FALSE, glm::value_ptr(viewProjection)); +} +void +ShadowMapper::FixedPoint::use() const +{ + glUseProgram(*this); +} + +ShadowMapper::DynamicPoint::DynamicPoint() : + Program {shadowDynamicPoint_vs, shadowCast_fs}, viewProjectionLoc {*this, "viewProjection"}, modelLoc { + *this, "model"} +{ +} +void +ShadowMapper::DynamicPoint::setViewProjection(const glm::mat4 & viewProjection) const +{ + glUseProgram(*this); + glUniformMatrix4fv(viewProjectionLoc, 1, GL_FALSE, glm::value_ptr(viewProjection)); +} +void +ShadowMapper::DynamicPoint::use(const Location & location) const +{ + glUseProgram(*this); + const auto model = glm::translate(location.pos) * rotate_ypr(location.rot); + glUniformMatrix4fv(modelLoc, 1, GL_FALSE, glm::value_ptr(model)); +} |