Godot Version
4.4.1.stable
Question
I have a nav agent on my player, and am clicking to set where the player moves on the nav mesh. The issue is when i click on where a collision box is outside of the nav mesh the player moves back and forth on seemingly the end of the path, never emitting target reached.
Here is a video showing it in action:
In the video i click a few different places, on where the nav mesh is, off the navmesh but not on a collision shape that blocks the nav mesh, and on a collision shape blocking the nav mesh, which is the only one that causes the back and forth movement.
Code: comments added for clarity just incase
# This is a function to get the plavement of where the player clicked.
func GetTargetPositionOnMouseClick() -> void:
var mousePos := get_viewport().get_mouse_position()
var rayLength := 100
var from : Vector3 = camera.project_ray_origin(mousePos)
var to : Vector3 = from + camera.project_ray_normal(mousePos) * rayLength
var space := get_world_3d().direct_space_state
var rayQuery := PhysicsRayQueryParameters3D.new()
rayQuery.from = from
rayQuery.to = to
rayQuery.collide_with_areas = true
var result := space.intersect_ray(rayQuery)
if OS.is_debug_build():
print("debug results: ", result)
# This stops it from crashing if you click off playable area.
if result.size() == 0:
return
else:
navAgent.target_position = result.position
# This moves the player
func moveToPoint(delta : float) -> void:
var targetPos := navAgent.get_next_path_position()
var direction : Vector3 = global_position.direction_to(targetPos)
if direction.length_squared() > 1.0:
direction = direction.normalized()
velocity = velocity.move_toward(direction * speed * runMultiplier, acceleration * delta)#lerp(direction * speed * runMultiplier, acceleration)
# This is input:
func _input(event: InputEvent) -> void:
# TODO: make a double click to run
if currentState != playerState.TALK:
if event.is_action_pressed("LeftMC"):
GetTargetPositionOnMouseClick()
# then in my idle state to start moving the character
if !player.navAgent.is_target_reached():
ChangeState("walk")
# in my walk script to stop moving the player: it never emits target_reached so it never leaves the walk state.
if player.navAgent.is_target_reached():
ChangeState("idle")
Adding to this a couple things i tried:
Upping the path desired distance, result: does nothing to help from my testing, only makes corners harder to pass
adding this to the walk state:
if player.global_position.distance_to(player.navAgent.target_position) <= 3.0:
player.navAgent.target_reached.emit()
result: no change