diff --git a/modules/jolt_physics/objects/jolt_area_3d.cpp b/modules/jolt_physics/objects/jolt_area_3d.cpp index b8131afa18a..1299b0437eb 100644 --- a/modules/jolt_physics/objects/jolt_area_3d.cpp +++ b/modules/jolt_physics/objects/jolt_area_3d.cpp @@ -83,7 +83,7 @@ void JoltArea3D::_add_to_space() { jolt_settings->SetShape(jolt_shape); - JPH::Body *new_jolt_body = space->add_rigid_body(*this, *jolt_settings); + JPH::Body *new_jolt_body = space->add_rigid_body(*this, *jolt_settings, _should_sleep()); if (new_jolt_body == nullptr) { return; } @@ -275,6 +275,18 @@ void JoltArea3D::_force_areas_exited(bool p_remove) { } } +void JoltArea3D::_update_sleeping() { + if (space == nullptr) { + return; + } + + if (_should_sleep()) { + space->get_body_iface().DeactivateBody(jolt_body->GetID()); + } else { + space->get_body_iface().ActivateBody(jolt_body->GetID()); + } +} + void JoltArea3D::_update_group_filter() { if (!in_space()) { return; @@ -316,19 +328,23 @@ void JoltArea3D::_events_changed() { } void JoltArea3D::_body_monitoring_changed() { - if (has_body_monitor_callback()) { + if (is_monitoring_bodies()) { _force_bodies_entered(); } else { _force_bodies_exited(false); } + + _update_sleeping(); } void JoltArea3D::_area_monitoring_changed() { - if (has_area_monitor_callback()) { + if (is_monitoring_areas()) { _force_areas_entered(); } else { _force_areas_exited(false); } + + _update_sleeping(); } void JoltArea3D::_monitorable_changed() { @@ -513,7 +529,7 @@ void JoltArea3D::set_monitorable(bool p_monitorable) { } bool JoltArea3D::can_monitor(const JoltBody3D &p_other) const { - return (collision_mask & p_other.get_collision_layer()) != 0; + return is_monitoring_bodies() && (collision_mask & p_other.get_collision_layer()) != 0; } bool JoltArea3D::can_monitor(const JoltSoftBody3D &p_other) const { @@ -521,7 +537,7 @@ bool JoltArea3D::can_monitor(const JoltSoftBody3D &p_other) const { } bool JoltArea3D::can_monitor(const JoltArea3D &p_other) const { - return p_other.is_monitorable() && (collision_mask & p_other.get_collision_layer()) != 0; + return is_monitoring_areas() && p_other.is_monitorable() && (collision_mask & p_other.get_collision_layer()) != 0; } bool JoltArea3D::can_interact_with(const JoltBody3D &p_other) const { diff --git a/modules/jolt_physics/objects/jolt_area_3d.h b/modules/jolt_physics/objects/jolt_area_3d.h index 6a076c90d0b..1cc9a4cfea5 100644 --- a/modules/jolt_physics/objects/jolt_area_3d.h +++ b/modules/jolt_physics/objects/jolt_area_3d.h @@ -116,6 +116,8 @@ private: virtual JPH::EMotionType _get_motion_type() const override { return JPH::EMotionType::Kinematic; } + bool _should_sleep() const { return !is_monitoring(); } + virtual void _add_to_space() override; void _enqueue_call_queries(); @@ -137,6 +139,7 @@ private: void _force_areas_entered(); void _force_areas_exited(bool p_remove); + void _update_sleeping(); void _update_group_filter(); void _update_default_gravity(); @@ -165,6 +168,10 @@ public: bool has_area_monitor_callback() const { return area_monitor_callback.is_valid(); } void set_area_monitor_callback(const Callable &p_callback); + bool is_monitoring_bodies() const { return has_body_monitor_callback(); } + bool is_monitoring_areas() const { return has_area_monitor_callback(); } + bool is_monitoring() const { return is_monitoring_bodies() || is_monitoring_areas(); } + bool is_monitorable() const { return monitorable; } void set_monitorable(bool p_monitorable);