From 80432f85fb88d023d75274133e889e662b10a675 Mon Sep 17 00:00:00 2001 From: Sara Date: Thu, 30 Apr 2026 22:27:17 +0200 Subject: [PATCH] feat: camera follows movement --- modules/viscosity/player_camera.cpp | 32 +++++++++++++++++++++++------ modules/viscosity/player_camera.h | 1 + 2 files changed, 27 insertions(+), 6 deletions(-) diff --git a/modules/viscosity/player_camera.cpp b/modules/viscosity/player_camera.cpp index 5d97cf52..9393efda 100644 --- a/modules/viscosity/player_camera.cpp +++ b/modules/viscosity/player_camera.cpp @@ -2,10 +2,12 @@ #include "core/config/engine.h" #include "core/input/input.h" #include "core/math/math_defs.h" +#include "core/math/math_funcs.h" #include "core/object/class_db.h" #include "core/object/object.h" #include "core/typedefs.h" #include "scene/main/viewport.h" +#include "viscosity/player_body.h" void PlayerCamera::_bind_methods() { BIND_PROPERTY(Variant::FLOAT, target_distance); @@ -13,19 +15,35 @@ void PlayerCamera::_bind_methods() { } void PlayerCamera::update_rotation() { + double const delta{ get_process_delta_time() }; + Vector3 velocity{ get_parent_node_3d()->get_global_position() - this->previous_origin }; + if (velocity.length() > 0.1 && this->mouse_look_input.is_zero_approx() && this->joystick_input.is_zero_approx()) { + Vector3 forward{ -get_global_basis().get_column(2) }; + forward.y = 0; + float x_difference{ forward.normalized().signed_angle_to({ velocity.x, 0, velocity.z }, Vector3::UP) }; + if (Math::abs(x_difference) > 0.1f) { + this->rotate(Vector3::UP, CLAMP(x_difference * delta, -1.f * delta, 1.f * delta)); + } + forward = -get_global_basis().get_column(2) + Vector3(0, .2, 0); + float y_difference{ forward.signed_angle_to(velocity, get_global_basis().get_column(0)) }; + + if (Math::abs(y_difference) > 0.1) { + this->rotate_object_local(Vector3::RIGHT, CLAMP(y_difference, -0.002, 0.002)); + } + } this->mouse_look_input *= 0.0001f; - this->rotate(Vector3::DOWN, this->mouse_look_input.x * this->mouse_sensitivity - this->joystick_input.x * get_process_delta_time() * this->joystick_sensitivity); - this->rotate_object_local(Vector3::LEFT, this->mouse_look_input.y * this->mouse_sensitivity + this->joystick_input.y * get_process_delta_time() * this->joystick_sensitivity); + this->rotate(Vector3::DOWN, this->mouse_look_input.x * this->mouse_sensitivity - this->joystick_input.x * delta * this->joystick_sensitivity); + this->rotate_object_local(Vector3::LEFT, this->mouse_look_input.y * this->mouse_sensitivity + this->joystick_input.y * delta * this->joystick_sensitivity); static float const lim{ Math::PI / 2.f - 0.1f }; - Vector3 rotation{ this->get_rotation() }; - rotation.y = CLAMP(rotation.y, -lim, lim); + Vector3 rotation{ get_rotation() }; + rotation.x = CLAMP(rotation.x, -lim, lim); this->set_rotation(rotation); this->mouse_look_input = { 0.f, 0.f }; } void PlayerCamera::update_position() { - Vector3 direction{ get_global_basis().get_column(2) }; Vector3 origin{ get_parent_node_3d()->get_global_position() }; + Vector3 direction{ get_global_basis().get_column(2) }; float distance{ this->target_distance }; Vector3 target{ origin + direction * distance }; this->ray.from = origin; @@ -37,6 +55,7 @@ void PlayerCamera::update_position() { distance -= 1.f; } look_at_from_position(origin + direction * MAX(distance, 1.f), origin); + this->previous_origin = origin; } void PlayerCamera::_notification(int what) { @@ -49,8 +68,9 @@ void PlayerCamera::_notification(int what) { case NOTIFICATION_READY: set_process(true); set_process_unhandled_input(true); - set_rotation_order(EulerOrder::XYZ); + set_rotation_order(EulerOrder::YZX); Input::get_singleton()->set_mouse_mode(Input::MouseMode::MOUSE_MODE_CAPTURED); + this->previous_origin = get_parent_node_3d()->get_global_position(); return; case NOTIFICATION_PROCESS: update_rotation(); diff --git a/modules/viscosity/player_camera.h b/modules/viscosity/player_camera.h index f8d3d642..441df60a 100644 --- a/modules/viscosity/player_camera.h +++ b/modules/viscosity/player_camera.h @@ -21,6 +21,7 @@ private: Vector2 mouse_look_input{}; Vector2 joystick_input{}; + Vector3 previous_origin{}; PhysicsDirectSpaceState3D::RayParameters ray{ .from = Vector3(), .to = Vector3(),