2020-01-10 18:15:50 +01:00
|
|
|
# Determines any agent that is in the specified list as being neighbors with the owner agent if
|
|
|
|
# they lie within the specified radius.
|
2020-04-03 02:31:59 +02:00
|
|
|
# @category - Proximities
|
2020-02-11 18:33:25 +01:00
|
|
|
extends GSAIProximity
|
|
|
|
class_name GSAIRadiusProximity
|
2020-01-08 18:46:42 +01:00
|
|
|
|
2020-01-29 05:56:10 +01:00
|
|
|
# The radius around the owning agent to find neighbors in
|
2020-01-16 09:44:44 +01:00
|
|
|
var radius := 0.0
|
2020-01-08 18:46:42 +01:00
|
|
|
|
2020-01-16 09:44:44 +01:00
|
|
|
var _last_frame := 0
|
2020-01-09 18:24:55 +01:00
|
|
|
var _scene_tree: SceneTree
|
|
|
|
|
2020-01-08 18:46:42 +01:00
|
|
|
|
2020-02-11 20:36:06 +01:00
|
|
|
func _init(agent: GSAISteeringAgent, agents: Array, _radius: float).(agent, agents) -> void:
|
|
|
|
self.radius = _radius
|
2020-01-09 18:24:55 +01:00
|
|
|
_scene_tree = Engine.get_main_loop()
|
2020-01-08 18:46:42 +01:00
|
|
|
|
|
|
|
|
2020-01-29 05:56:10 +01:00
|
|
|
# Returns a number of neighbors based on a `callback` function.
|
|
|
|
#
|
2020-01-29 22:53:57 +01:00
|
|
|
# `_find_neighbors` calls `callback` for each agent in the `agents` array that lie within
|
2020-01-29 05:56:10 +01:00
|
|
|
# the radius around the owning agent and adds one to the count if its `callback` returns true.
|
2020-04-03 02:31:59 +02:00
|
|
|
# @tags - virtual
|
2020-01-29 22:53:57 +01:00
|
|
|
func _find_neighbors(callback: FuncRef) -> int:
|
2020-01-16 09:44:44 +01:00
|
|
|
var agent_count := agents.size()
|
|
|
|
var neighbor_count := 0
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-16 09:44:44 +01:00
|
|
|
var current_frame := _scene_tree.get_frame() if _scene_tree else -_last_frame
|
2020-01-09 18:24:55 +01:00
|
|
|
if current_frame != _last_frame:
|
|
|
|
_last_frame = current_frame
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-16 09:44:44 +01:00
|
|
|
var owner_position := agent.position
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-09 18:24:55 +01:00
|
|
|
for i in range(agent_count):
|
2020-02-11 18:33:25 +01:00
|
|
|
var current_agent := agents[i] as GSAISteeringAgent
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-09 18:24:55 +01:00
|
|
|
if current_agent != agent:
|
2020-01-16 09:44:44 +01:00
|
|
|
var distance_squared := owner_position.distance_squared_to(current_agent.position)
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-16 09:44:44 +01:00
|
|
|
var range_to := radius + current_agent.bounding_radius
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-09 18:24:55 +01:00
|
|
|
if distance_squared < range_to * range_to:
|
2020-01-10 18:15:50 +01:00
|
|
|
if callback.call_func(current_agent):
|
2020-01-29 22:53:57 +01:00
|
|
|
current_agent.is_tagged = true
|
2020-01-09 18:24:55 +01:00
|
|
|
neighbor_count += 1
|
|
|
|
continue
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-29 22:53:57 +01:00
|
|
|
current_agent.is_tagged = false
|
2020-01-09 18:24:55 +01:00
|
|
|
else:
|
|
|
|
for i in range(agent_count):
|
2020-02-11 18:33:25 +01:00
|
|
|
var current_agent = agents[i] as GSAISteeringAgent
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-29 22:53:57 +01:00
|
|
|
if current_agent != agent and current_agent.is_tagged:
|
2020-01-10 18:15:50 +01:00
|
|
|
if callback.call_func(current_agent):
|
2020-01-08 18:46:42 +01:00
|
|
|
neighbor_count += 1
|
2020-01-29 17:04:04 +01:00
|
|
|
|
2020-01-08 18:46:42 +01:00
|
|
|
return neighbor_count
|