Reputation: 176
So I want to set my _target_node
to null when an enemy dies.
Here how I target an enemy:
in my player.gd
I have:
var _target_node: Node = null
func handle_target_lock():
if Input.is_action_just_pressed("target_lock"):
if _target_node:
_target_node = null
else:
var enemies: Array = get_tree().get_nodes_in_group("Enemy")
if enemies.size() > 0:
_target_node = enemies[0]
if _target_node:
look_at(_target_node.global_transform.origin, Vector3.UP)
Problem is, when an enemy dies, _target_node
is now referencing a deleted instance.
My enemy node emits a signal died
when its hp is 0, but I don't know how to use this information to notify my player.
How do I notify the player that the targeted enemy is dead and _target_node
should be set to null?
Godot version 3.5.1
Upvotes: 1
Views: 376
Reputation: 40295
Problem is, when an enemy dies, _target_node is now referencing a deleted instance.
You can check for that:
if is_instance_valid(_target_node):
On the other hand, this form:
if _target_node:
Is checking if the variable is not zeroed. For an Object
type (such as Node
) it is checking if the variable is not set to null
. However you can free Node
s while there are still references to them. As you might now, Node
is not reference counted (it does not extend Reference
), instead you free them manually with free
or queue_free
. When a Node
is freed, Godot does not automatically turn the references that point to it into null
, instead they become invalid references. We use is_instance_valid
to check for that.
Upvotes: 1
Reputation: 1729
So you are saying there is a died signal so you could connect to it's die signal, when it is targeted:
if Input.is_action_just_pressed("target_lock"):
if _target_node:
#"died" should be renamed to your signal name!
_target_node.disconnect("died",self, "on_target_died") # disconnect if you switch the target
_target_node = null
else:
var enemies: Array = get_tree().get_nodes_in_group("Enemy")
if enemies.size() > 0:
_target_node = enemies[0]
#"died" should be renamed to your signal name!
_target_node.connect("died",self, "on_target_died")
func on_target_died():
_target_node = null
Edit: It could help to pass the enemy as a parameter in the died signal so you can check, if the event was really fired from the enemy that is currently targeted. Otherwise there could be the chance, the player is still connected to the wrong enemy while switching targets
Upvotes: 2