aboutsummaryrefslogtreecommitdiff
path: root/src/client/shadows
diff options
context:
space:
mode:
authorElias Fleckenstein <eliasfleckenstein@web.de>2022-06-02 20:54:02 +0200
committerElias Fleckenstein <eliasfleckenstein@web.de>2022-06-02 20:54:02 +0200
commit827b9f8d7054158b058679999d77c1345162a293 (patch)
treeb03741002579b03d3657c1e496e73993e4070fa9 /src/client/shadows
parent3ff3103e98b350712543f926c429ab339700e252 (diff)
parent9fc018ded10225589d2559d24a5db739e891fb31 (diff)
downloaddragonfireclient-827b9f8d7054158b058679999d77c1345162a293.tar.xz
Merge branch 'master' of https://github.com/minetest/minetest
Diffstat (limited to 'src/client/shadows')
-rw-r--r--src/client/shadows/dynamicshadows.cpp20
-rw-r--r--src/client/shadows/dynamicshadowsrender.cpp14
-rw-r--r--src/client/shadows/dynamicshadowsrender.h2
3 files changed, 30 insertions, 6 deletions
diff --git a/src/client/shadows/dynamicshadows.cpp b/src/client/shadows/dynamicshadows.cpp
index ca2d3ce37..9f26ba94a 100644
--- a/src/client/shadows/dynamicshadows.cpp
+++ b/src/client/shadows/dynamicshadows.cpp
@@ -27,10 +27,24 @@ with this program; if not, write to the Free Software Foundation, Inc.,
using m4f = core::matrix4;
+static v3f quantizeDirection(v3f direction, float step)
+{
+
+ float yaw = std::atan2(direction.Z, direction.X);
+ float pitch = std::asin(direction.Y); // assume look is normalized
+
+ yaw = std::floor(yaw / step) * step;
+ pitch = std::floor(pitch / step) * step;
+
+ return v3f(std::cos(yaw)*std::cos(pitch), std::sin(pitch), std::sin(yaw)*std::cos(pitch));
+}
+
void DirectionalLight::createSplitMatrices(const Camera *cam)
{
+ const float DISTANCE_STEP = BS * 2.0; // 2 meters
v3f newCenter;
v3f look = cam->getDirection();
+ look = quantizeDirection(look, M_PI / 12.0); // 15 degrees
// camera view tangents
float tanFovY = tanf(cam->getFovY() * 0.5f);
@@ -42,6 +56,10 @@ void DirectionalLight::createSplitMatrices(const Camera *cam)
// adjusted camera positions
v3f cam_pos_world = cam->getPosition();
+ cam_pos_world = v3f(
+ floor(cam_pos_world.X / DISTANCE_STEP) * DISTANCE_STEP,
+ floor(cam_pos_world.Y / DISTANCE_STEP) * DISTANCE_STEP,
+ floor(cam_pos_world.Z / DISTANCE_STEP) * DISTANCE_STEP);
v3f cam_pos_scene = v3f(cam_pos_world.X - cam->getOffset().X * BS,
cam_pos_world.Y - cam->getOffset().Y * BS,
cam_pos_world.Z - cam->getOffset().Z * BS);
@@ -61,7 +79,7 @@ void DirectionalLight::createSplitMatrices(const Camera *cam)
v3f boundVec = (cam_pos_scene + farCorner * sfFar) - center_scene;
float radius = boundVec.getLength();
float length = radius * 3.0f;
- v3f eye_displacement = direction * length;
+ v3f eye_displacement = quantizeDirection(direction, M_PI / 2880 /*15 seconds*/) * length;
// we must compute the viewmat with the position - the camera offset
// but the future_frustum position must be the actual world position
diff --git a/src/client/shadows/dynamicshadowsrender.cpp b/src/client/shadows/dynamicshadowsrender.cpp
index c13cfe252..b8ceeb623 100644
--- a/src/client/shadows/dynamicshadowsrender.cpp
+++ b/src/client/shadows/dynamicshadowsrender.cpp
@@ -242,7 +242,7 @@ void ShadowRenderer::updateSMTextures()
// detect if SM should be regenerated
for (DirectionalLight &light : m_light_list) {
- if (light.should_update_map_shadow) {
+ if (light.should_update_map_shadow || m_force_update_shadow_map) {
light.should_update_map_shadow = false;
m_current_frame = 0;
reset_sm_texture = true;
@@ -271,14 +271,14 @@ void ShadowRenderer::updateSMTextures()
// should put some gl* fn here
- if (m_current_frame < m_map_shadow_update_frames) {
+ if (m_current_frame < m_map_shadow_update_frames || m_force_update_shadow_map) {
m_driver->setRenderTarget(shadowMapTargetTexture, reset_sm_texture, true,
video::SColor(255, 255, 255, 255));
renderShadowMap(shadowMapTargetTexture, light);
// Render transparent part in one pass.
// This is also handled in ClientMap.
- if (m_current_frame == m_map_shadow_update_frames - 1) {
+ if (m_current_frame == m_map_shadow_update_frames - 1 || m_force_update_shadow_map) {
if (m_shadow_map_colored) {
m_driver->setRenderTarget(0, false, false);
m_driver->setRenderTarget(shadowMapTextureColors,
@@ -298,7 +298,7 @@ void ShadowRenderer::updateSMTextures()
++m_current_frame;
// pass finished, swap textures and commit light changes
- if (m_current_frame == m_map_shadow_update_frames) {
+ if (m_current_frame == m_map_shadow_update_frames || m_force_update_shadow_map) {
if (shadowMapClientMapFuture != nullptr)
std::swap(shadowMapClientMapFuture, shadowMapClientMap);
@@ -306,6 +306,7 @@ void ShadowRenderer::updateSMTextures()
for (DirectionalLight &light : m_light_list)
light.commitFrustum();
}
+ m_force_update_shadow_map = false;
}
}
@@ -432,7 +433,10 @@ void ShadowRenderer::renderShadowMap(video::ITexture *target,
m_driver->setTransform(video::ETS_WORLD,
map_node->getAbsoluteTransformation());
- map_node->renderMapShadows(m_driver, material, pass, m_current_frame, m_map_shadow_update_frames);
+ int frame = m_force_update_shadow_map ? 0 : m_current_frame;
+ int total_frames = m_force_update_shadow_map ? 1 : m_map_shadow_update_frames;
+
+ map_node->renderMapShadows(m_driver, material, pass, frame, total_frames);
break;
}
}
diff --git a/src/client/shadows/dynamicshadowsrender.h b/src/client/shadows/dynamicshadowsrender.h
index 0e4ef6b70..2e3b58f6f 100644
--- a/src/client/shadows/dynamicshadowsrender.h
+++ b/src/client/shadows/dynamicshadowsrender.h
@@ -74,6 +74,7 @@ public:
void removeNodeFromShadowList(scene::ISceneNode *node);
void update(video::ITexture *outputTarget = nullptr);
+ void setForceUpdateShadowMap() { m_force_update_shadow_map = true; }
void drawDebug();
video::ITexture *get_texture()
@@ -131,6 +132,7 @@ private:
bool m_shadows_enabled;
bool m_shadows_supported;
bool m_shadow_map_colored;
+ bool m_force_update_shadow_map;
u8 m_map_shadow_update_frames; /* Use this number of frames to update map shaodw */
u8 m_current_frame{0}; /* Current frame */
f32 m_perspective_bias_xy;