diff --git a/car.gd b/car.gd index 83dfb17..c14ab46 100644 --- a/car.gd +++ b/car.gd @@ -6,3 +6,7 @@ extends RigidBody3D func _physics_process(_delta: float) -> void: for wheel: Wheel in wheels: wheel.apply_forces(self) + +##Point argument is in local space +func get_velocity_at_point(point: Vector3) -> Vector3: + return linear_velocity + angular_velocity.cross(point - center_of_mass) diff --git a/wheel.gd b/wheel.gd index d296dd5..9420a92 100644 --- a/wheel.gd +++ b/wheel.gd @@ -4,6 +4,7 @@ extends RayCast3D @export var wheel_radius: float = 0.316 @export var suspension_rest_length: float = 0.1 @export var suspension_stiffness: float = 250_000 +@export var suspension_damping: float = 2000 func _ready() -> void: target_position *= suspension_rest_length + wheel_radius @@ -11,10 +12,10 @@ func _ready() -> void: func apply_forces(car: Car) -> void: force_raycast_update() - var force: Vector3 = get_suspension_force() + var force: Vector3 = get_suspension_force(car) car.apply_force(force, car.to_local(get_collision_point())) -func get_suspension_force() -> Vector3: +func get_suspension_force(car: Car) -> Vector3: var up: Vector3 = global_basis.y if not is_colliding(): $"RX-Wheel".position = -up * suspension_rest_length @@ -26,7 +27,13 @@ func get_suspension_force() -> Vector3: var suspension_length: float = -up.dot(wheel_center) var suspension_displacement: float = suspension_rest_length - suspension_length #https://en.wikipedia.org/wiki/Hookes_law - var y_force_scalar: float = suspension_stiffness * suspension_displacement + var hookes_force_scalar: float = suspension_stiffness * suspension_displacement + + var wheel_velocity: Vector3 = car.get_velocity_at_point(car.to_local(to_global(wheel_center))) + var wheel_up_velocity: float = up.dot(wheel_velocity) + var damping_force_scalar: float = suspension_damping * wheel_up_velocity + + var y_force_scalar: float = hookes_force_scalar - damping_force_scalar var force: Vector3 = Vector3.UP * y_force_scalar return force