From f8438601ef385447750eb61fa82153fa2c461f68 Mon Sep 17 00:00:00 2001 From: lawnjelly Date: Sat, 16 Mar 2024 16:02:22 +0000 Subject: [PATCH] Physics Interpolation 2D - fix light and light occluder resetting It turns out `NOTIFICATION_TRANSFORM_CHANGED` is deferred for these nodes, which can mean the transform is not set in the `VisualServer` until after the reset has been sent, even if the transform is set before the reset in script. This prevented the reset from acting correctly. Here we explicitly set the transform prior to each reset, to ensure the `VisualServer` is up to date. --- scene/2d/light_2d.cpp | 7 ++++++- scene/2d/light_occluder_2d.cpp | 7 ++++++- 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/scene/2d/light_2d.cpp b/scene/2d/light_2d.cpp index 799ea828fbc9..8a556e90321e 100644 --- a/scene/2d/light_2d.cpp +++ b/scene/2d/light_2d.cpp @@ -319,7 +319,12 @@ void Light2D::_notification(int p_what) { } break; case NOTIFICATION_RESET_PHYSICS_INTERPOLATION: { if (is_visible_in_tree() && is_physics_interpolated()) { - VisualServer::get_singleton()->canvas_light_reset_physics_interpolation(canvas_light); + // Explicitly make sure the transform is up to date in VisualServer before + // resetting. This is necessary because NOTIFICATION_TRANSFORM_CHANGED + // is normally deferred, and a client change to transform will not always be sent + // before the reset, so we need to guarantee this. + VS::get_singleton()->canvas_light_set_transform(canvas_light, get_global_transform()); + VS::get_singleton()->canvas_light_reset_physics_interpolation(canvas_light); } } break; } diff --git a/scene/2d/light_occluder_2d.cpp b/scene/2d/light_occluder_2d.cpp index d200a031d999..a715eb66575d 100644 --- a/scene/2d/light_occluder_2d.cpp +++ b/scene/2d/light_occluder_2d.cpp @@ -202,7 +202,12 @@ void LightOccluder2D::_notification(int p_what) { } break; case NOTIFICATION_RESET_PHYSICS_INTERPOLATION: { if (is_visible_in_tree() && is_physics_interpolated()) { - VisualServer::get_singleton()->canvas_light_occluder_reset_physics_interpolation(occluder); + // Explicitly make sure the transform is up to date in VisualServer before + // resetting. This is necessary because NOTIFICATION_TRANSFORM_CHANGED + // is normally deferred, and a client change to transform will not always be sent + // before the reset, so we need to guarantee this. + VS::get_singleton()->canvas_light_occluder_set_transform(occluder, get_global_transform()); + VS::get_singleton()->canvas_light_occluder_reset_physics_interpolation(occluder); } } break; }