3tree3
February 16, 2026, 6:22pm
1
Godot Version
Godot 4.6
Question
I’m making a bullet. Why doesn’t it delete when these conditions are met?
extends CharacterBody3D
@export var SPEED = 1
@export var target_position = null
@export var attack = 10
@export var attack_type = []
func _physics_process(delta):
if target_position != null:
var dtt= target_position - position
dtt= direction_to_target.normalized()
if dtt.length() > 0:
velocity.x = dtt.x * SPEED
velocity.z = dtt.z * SPEED
if position.distance_to(target_position) <= 0.2:
queue_free()
move_and_slide()
func _on_area_3d_body_shape_entered(body_rid: RID, body: Node3D, body_shape_index: int, local_shape_index: int) -> void:
if body is CharacterBody3D:
if body.name == "Mob":
body.HP -= attack
queue_free()
Upd. I'm making a bullet. Why doesn't it delete when these conditions are met? - #5 by 3tree3
Which condition? You have two in your code.
Are both of them broken?
Is “target_position” always set? It might be null, so none of your code in _physics_process get executed.
Are you sure the body’s name is "Mob" and not "mob" or any similar variation?
Are your collision checks set up correctly? (Mask for example)
1 Like
That might be the biggest issue the target itself how do you set it ?
Try printing out the distances to the target position. If the speed of the bullet is so high that it does not hit the distance range (that is -0.2…0.2 ) within at least one physics frame, then it might just be too fast.
Now that I’m looking again, with a speed of 1 this is proobably not the case here.
For the other function, I see multiple potential issues.
First of all, check that the collision masks / layers of the objects that should collide match with each other.
Also, the check for the name “Mob” might not catch everything. If possible, check if the class matches your expected class, e.g.
if body is Mob:
#...
edit: sorry if I’m repeating other people here, I just took too long to answer
3tree3
February 16, 2026, 6:43pm
5
Thanks to everyone who responded. Here’s what I forgot to add. Bullet is called from outside.
func long_attack(spell_speed):
var bullet = preload("res://MECHANICS/bull.tscn").instantiate()
bullet.attack = core.attack
bullet.attack_type = core.attack_type
bullet.SPEED = spell_speed
bullet.target_position = tp
bullet.position = $RayCast3D/MeshInstance3D.global_position
get_parent().add_child(bullet)
Video:
3tree3:
func _on_area_3d_body_shape_entered(body_rid: RID, body: Node3D, body_shape_index: int, local_shape_index: int) -> void:
if body is CharacterBody3D:
if body.name == "Mob":
body.HP -= attack
queue_free()
try
on_area_body instead passing just body..
and put the enemy in a group “enemy”
if body.is_in_group(“enemy”)
body.queue_free #### or whatever
baba
February 16, 2026, 7:38pm
7
Check the name. Is the nsme of mob-node “mob” or is it (as i assume) the scene thst is called “mob”?
Use a better condition for hit detection
3tree3
February 16, 2026, 10:41pm
8
tibaverus:
Which condition? You have two in your code.
Are both of them broken?
Is “target_position” always set? It might be null, so none of your code in _physics_process get executed.
Are you sure the body’s name is "Mob" and not "mob" or any similar variation?
Are your collision checks set up correctly? (Mask for example)
The bullet reaches the desired position, and everything is set outside of this code. The question is why the bullet is not removed.
var is set outside of the code, called in another script
func long_attack(spell_speed):
var bullet = preload("res://MECHANICS/bull.tscn").instantiate()
bullet.attack = core.attack
bullet.attack_type = core.attack_type
bullet.SPEED = spell_speed
bullet.target_position = tp
bullet.position = $RayCast3D/MeshInstance3D.global_position
get_parent().add_child(bullet)
3tree3
February 16, 2026, 10:43pm
9
target_position is set outside of the code, called in another script
func long_attack(spell_speed):
var bullet = preload("res://MECHANICS/bull.tscn").instantiate()
bullet.attack = core.attack
bullet.attack_type = core.attack_type
bullet.SPEED = spell_speed
bullet.target_position = tp
bullet.position = $RayCast3D/MeshInstance3D.global_position
get_parent().add_child(bullet)
3tree3
February 16, 2026, 10:46pm
10
substain:
Try printing out the distances to the target position. If the speed of the bullet is so high that it does not hit the distance range (that is -0.2…0.2 ) within at least one physics frame, then it might just be too fast.
Now that I’m looking again, with a speed of 1 this is proobably not the case here.
For the other function, I see multiple potential issues.
First of all, check that the collision masks / layers of the objects that should collide match with each other.
Also, the check for the name “Mob” might not catch everything. If possible, check if the class matches your expected class, e.g.
if body is Mob:
#...
edit: sorry if I’m repeating other people here, I just took too long to answer
The bullet reaches its target and kills the enemy, but for some reason, it doesn’t disappear.
3tree3
February 16, 2026, 10:48pm
11
I could implement it later, but it’s unlikely.
3tree3
February 16, 2026, 10:48pm
12
The name matches, and the enemy dies, but the bullet remains.
Maybe your target_position is below the ground and the bullet collides with the ground, so it can’t reach it?
If you inspect those bullets in the remote scene tree, what’s their position and target_position?
1 Like
baba
February 17, 2026, 3:09am
14
And you are 100% sure that the check is successful and that the other lines of the queue free part of the bullet code runs? No way for the mobs to take damage on their own?
Add a print statement in the function. Anything, just to see that it runs.
If it runs but the queue free doesnt happen i would check if call_deferred(“queue_free”) instead of queue_free() works.
3tree3
February 17, 2026, 11:35am
15
Thank you! You’re the most attentive person I’ve ever met.
Print, which is now commented out, produced this "{(11.30185, 0.0, -4.790857)}{(15.51386, 0.996497, 3.510818)}
"
Here is the corrected function:
func _physics_process(delta):
if target_position != null:
target_position.y = position.y
#print("{" + str(target_position) + "}" + "{" + str(position) + "}")
var direction_to_target = target_position - position
direction_to_target = direction_to_target.normalized()
if direction_to_target.length() > 0:
velocity.x = direction_to_target.x * SPEED
velocity.z = direction_to_target.z * SPEED
if position.distance_to(target_position) <= 0.2:
queue_free()
move_and_slide()
3tree3
February 17, 2026, 11:37am
16
I’ve already followed your advice, and most of it has worked. Thank.