@icon("uid://dek4dvcv5fyh5")
extends RigidBody3D
class_name BoatBody3D

@export var float_force := 20.0
@export var water_drag := 0.05
@export var water_angular_drag := 0.05

@onready var gravity:float = ProjectSettings.get_setting("physics/3d/default_gravity")

@onready var probes = $ProbeContainer.get_children()

var submerged := false

var is_docked: bool = false

@export var ocean : Ocean #= get_tree().get_nodes_in_group("ocean")[0]

@export var max_thrust_force: float = 2048
@export var max_steering: float = 128

var steering: float = 0 # steering rudder angle in radians
var thrust_force: float = 0 # forward thrust force in Newtons


func _process(_delta):
	if Input.get_action_strength("move_forward") > 0.0:
		thrust()
	if Input.get_action_strength("turn_right") > 0.0:
		steer_right()
	if Input.get_action_strength("turn_left") > 0.0:
		steer_left()

# Called when the node enters the scene tree for the first time.
func _ready():
	add_to_group("boats",true)



func _physics_process(delta):
	submerged = false
	if probes.size() != 0.0 && ocean != null:
		for p in probes:
			if p.visible == true:
				var depth = ocean.get_water_level(p.global_position) - p.global_position.y
				if depth > 0:
					submerged = true
					apply_force(Vector3.UP * float_force * gravity * depth, p.global_position - global_position)
					#print("Applying force: "+str(Vector3.UP * float_force * gravity * depth)+" at "+ str(p.position) +"("+str(p)+")")
			
	## Code for user-input movement
	apply_central_force(self.global_transform.basis.x.normalized() * Vector3(1, 0, 1) * thrust_force * delta) 
	#apply_torque(Vector3.UP * steering * delta)
	
	apply_torque(global_transform.basis.y.normalized() * steering * 0.05) # for sideways motion
	
	
	reset_forces()

func _integrate_forces(state: PhysicsDirectBodyState3D):
	if submerged:
		state.linear_velocity *=  1 - water_drag
		state.angular_velocity *= 1 - water_angular_drag 



func thrust():
	if not is_docked:
		thrust_force = max_thrust_force

func steer_right():
	if not is_docked:
		steering = -PI * max_steering

func steer_left():
	if not is_docked:
		steering = PI * max_steering


func reset_forces():
	thrust_force = 0
	steering = 0
