I am making a top down shooter game, and I wanted to check if the mouse position converted to angle is equal to some of the following angles: 0, 90, 180 and 360.
Of course, that this won't work because it is very specific (the player would have to point to the angle directly, with a superhuman precision), so I thought about checking if the mouse position to angle is in a range, so that it would have some sort of tolerance.

This is my code:

``````const FLOAT_EPSILON = 0.000001
#45 of tolerance, this means that if the direct angle is 90, the corresponding range is (90 - 45): 45 (minimum value) and (90 + 45): 135 (maximum value)

if is_inside_range(angles, 45, 135): #90 direct angle
print("down")
elif is_inside_range(angles, 136, 225): #180 direct angle
print("left")
elif is_inside_range(angles, 226, 315): #270 direct angle
print("up")
elif is_inside_range(angles, 316, 360): or is_inside_range(0, 45) #360 direct angle
print("right")

func is_inside_range(val : float, min_val : float, max_val : float) -> bool:
return val >= (min_val - FLOAT_EPSILON) and val <= (max_val + FLOAT_EPSILON)
``````

As you can see, this should work well, and it does, except for one little issue. If the angles variable is too close to the beggining/end of a range of values (for example, if it is 90.1), but not the exact value, it will print two states
How could I fix this error? Is there a better way to achieve this?

in Engine

+1 vote

Hi,
since your solution uses a if - elif statement it can only print one or none state at a time.

I would solve it this way:

``````#build a normalized vector from player to mouse
var dir = player_position_vector.direction_to(mouse_position_vector)

if abs(x) > abs(y): #x-axis deviation is higher than y-axis
#its more sideways then up or down
if x > 0:
#mouse is right
pass
else:
#mouse is left
pass
else:
# its more up or down then sideways
if y > 0:
#mouse is lower
pass
else:
#mouse is higher
pass
``````

this is a vector based solution.

by (4,010 points)

This is great, however, how could I detect if it is in another value? For example: Vector(1, 1) or 60° angle (down right the player)

just check if the diviation is in a limit ...
do it for both axis

``````var limit = 0.5 # is about 60 degree

#build a normalized vector from player to mouse
var dir = player_position_vector.direction_to(mouse_position_vector)

if abs(x) > limit: #is in limit
if x > 0:
#mouse is right
pass
else:
#mouse is left
pass

if abs(y) > limit : # is in limit
if y > 0:
#mouse is down
pass
else:
#mouse is up
pass
``````

with the limit you can adjust the overlap of the axis

could I implement an eight direction (maybe even more) system following this with small modifications?