mirror of
https://github.com/MaSzyna-EU07/maszyna.git
synced 2026-07-22 12:49:18 +02:00
vr: compute shadow bounding area for both eyes
This commit is contained in:
@@ -168,6 +168,7 @@ bool opengl33_renderer::Init(GLFWwindow *Window)
|
|||||||
default_viewport.width = Global.gfx_framebuffer_width;
|
default_viewport.width = Global.gfx_framebuffer_width;
|
||||||
default_viewport.height = Global.gfx_framebuffer_height;
|
default_viewport.height = Global.gfx_framebuffer_height;
|
||||||
default_viewport.main = true;
|
default_viewport.main = true;
|
||||||
|
default_viewport.shadow = true;
|
||||||
default_viewport.window = m_window;
|
default_viewport.window = m_window;
|
||||||
default_viewport.draw_range = 1.0f;
|
default_viewport.draw_range = 1.0f;
|
||||||
|
|
||||||
@@ -193,6 +194,7 @@ bool opengl33_renderer::Init(GLFWwindow *Window)
|
|||||||
m_viewports.back()->custom_backbuffer = true;
|
m_viewports.back()->custom_backbuffer = true;
|
||||||
m_viewports.back()->proj_type = viewport_config::vr_right;
|
m_viewports.back()->proj_type = viewport_config::vr_right;
|
||||||
m_viewports.back()->draw_range = 1.0f;
|
m_viewports.back()->draw_range = 1.0f;
|
||||||
|
m_viewports.back()->shadow = true;
|
||||||
|
|
||||||
if (!init_viewport(*m_viewports.back()))
|
if (!init_viewport(*m_viewports.back()))
|
||||||
return false;
|
return false;
|
||||||
@@ -1446,14 +1448,31 @@ void opengl33_renderer::setup_pass(viewport_config &Viewport, renderpass_config
|
|||||||
}
|
}
|
||||||
case rendermode::shadows:
|
case rendermode::shadows:
|
||||||
{
|
{
|
||||||
// calculate lightview boundaries based on relevant area of the world camera frustum:
|
// calculate lightview boundaries based on relevant area of the world camera frustum:
|
||||||
// ...setup chunk of frustum we're interested in...
|
// ...setup chunk of frustum we're interested in...
|
||||||
// auto const zfar = std::min(1.f, Global.shadowtune.range / (Global.BaseDrawRange * Global.fDistanceFactor) * std::max(1.f, Global.ZoomFactor * 0.5f));
|
// auto const zfar = std::min(1.f, Global.shadowtune.range / (Global.BaseDrawRange * Global.fDistanceFactor) * std::max(1.f, Global.ZoomFactor * 0.5f));
|
||||||
// auto const zfar = ( Zfar > 1.f ? Zfar * std::max( 1.f, Global.ZoomFactor * 0.5f ) : Zfar );
|
// auto const zfar = ( Zfar > 1.f ? Zfar * std::max( 1.f, Global.ZoomFactor * 0.5f ) : Zfar );
|
||||||
auto const zfar = ( Zfar > 1.f ? Zfar : Zfar * Global.shadowtune.range * std::max( Zfar, Global.ZoomFactor * 0.5f ) );
|
auto const zfar = ( Zfar > 1.f ? Zfar : Zfar * Global.shadowtune.range * std::max( Zfar, Global.ZoomFactor * 0.5f ) );
|
||||||
renderpass_config worldview;
|
|
||||||
setup_pass(Viewport, worldview, rendermode::color, Znear, zfar, true);
|
size_t bounding_viewports_count = 0;
|
||||||
auto &frustumchunkshapepoints = worldview.pass_camera.frustum_points();
|
std::vector<glm::vec4> frustumchunkshapepoints;
|
||||||
|
glm::dvec3 pass_camera;
|
||||||
|
|
||||||
|
for (std::unique_ptr<viewport_config> &conf : m_viewports) {
|
||||||
|
if (!conf->shadow)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
renderpass_config worldview;
|
||||||
|
setup_pass(*conf, worldview, rendermode::color, Znear, zfar, true);
|
||||||
|
|
||||||
|
auto &points = worldview.pass_camera.frustum_points();
|
||||||
|
frustumchunkshapepoints.insert(frustumchunkshapepoints.end(), points.begin(), points.end());
|
||||||
|
|
||||||
|
pass_camera += worldview.pass_camera.position();
|
||||||
|
bounding_viewports_count++;
|
||||||
|
}
|
||||||
|
pass_camera /= bounding_viewports_count;
|
||||||
|
|
||||||
// ...modelview matrix: determine the centre of frustum chunk in world space...
|
// ...modelview matrix: determine the centre of frustum chunk in world space...
|
||||||
glm::vec3 frustumchunkmin, frustumchunkmax;
|
glm::vec3 frustumchunkmin, frustumchunkmax;
|
||||||
bounding_box(frustumchunkmin, frustumchunkmax, std::begin(frustumchunkshapepoints), std::end(frustumchunkshapepoints));
|
bounding_box(frustumchunkmin, frustumchunkmax, std::begin(frustumchunkshapepoints), std::end(frustumchunkshapepoints));
|
||||||
@@ -1461,7 +1480,7 @@ void opengl33_renderer::setup_pass(viewport_config &Viewport, renderpass_config
|
|||||||
// ...cap the vertical angle to keep shadows from getting too long...
|
// ...cap the vertical angle to keep shadows from getting too long...
|
||||||
auto const lightvector = glm::normalize(glm::vec3{m_sunlight.direction.x, std::min(m_sunlight.direction.y, -0.2f), m_sunlight.direction.z});
|
auto const lightvector = glm::normalize(glm::vec3{m_sunlight.direction.x, std::min(m_sunlight.direction.y, -0.2f), m_sunlight.direction.z});
|
||||||
// ...place the light source at the calculated centre and setup world space light view matrix...
|
// ...place the light source at the calculated centre and setup world space light view matrix...
|
||||||
camera.position() = worldview.pass_camera.position() + glm::dvec3{frustumchunkcentre};
|
camera.position() = pass_camera + glm::dvec3{frustumchunkcentre};
|
||||||
viewmatrix *= glm::lookAt(camera.position(), camera.position() + glm::dvec3{lightvector}, glm::dvec3{0.f, 1.f, 0.f});
|
viewmatrix *= glm::lookAt(camera.position(), camera.position() + glm::dvec3{lightvector}, glm::dvec3{0.f, 1.f, 0.f});
|
||||||
// ...projection matrix: calculate boundaries of the frustum chunk in light space...
|
// ...projection matrix: calculate boundaries of the frustum chunk in light space...
|
||||||
auto const lightviewmatrix = glm::translate(glm::mat4{glm::mat3{viewmatrix}}, -frustumchunkcentre);
|
auto const lightviewmatrix = glm::translate(glm::mat4{glm::mat3{viewmatrix}}, -frustumchunkcentre);
|
||||||
|
|||||||
@@ -200,6 +200,7 @@ class opengl33_renderer : public gfx_renderer {
|
|||||||
GLFWwindow *window = nullptr; // ogl window context
|
GLFWwindow *window = nullptr; // ogl window context
|
||||||
bool real_window = true; // whether we need to blit onto GLFWwindow surface
|
bool real_window = true; // whether we need to blit onto GLFWwindow surface
|
||||||
bool custom_backbuffer = false; // whether we want to render to our offscreen LDR backbuffer (pipeline required)
|
bool custom_backbuffer = false; // whether we want to render to our offscreen LDR backbuffer (pipeline required)
|
||||||
|
bool shadow = false; // include this viewport area in shadowmap
|
||||||
|
|
||||||
enum vp_type {
|
enum vp_type {
|
||||||
normal,
|
normal,
|
||||||
|
|||||||
Reference in New Issue
Block a user