Hello!
Answer to question:
Both options are good, but in your case I'd use Area2D. If you're using an arrow, than you'll probably have to update the global_position of it, because otherwise, if you move the parent node, it moves too. You'll need to make your own collisions, but I think, that haveing a RigidBody2D would be unnecessary, because you won't really use physics for it's movement.
My advice:
I think you should use a State Machine, because you can set states, so when you shoot the arrow, it's in a moving state, if it hits something it's in a stopped state.
You can obviously make the script (and the state machine) really simple, but I recon' spending some time with it because you can reuse it, and it makes you code be nicer.
I only know this tutorial, but you can totally apply it to kinda everything:
https://www.youtube.com/watch?v=BNU8xNRk_oU&list=PLdp0y9qO3Xou3PmOkWW1Az9vaIVfL8Pi2&index=5&t=0s
this is a part of the tutorial:
https://www.youtube.com/watch?v=j_pM3CiQwts&list=PLdp0y9qO3Xou3PmOkWW1Az9vaIVfL8Pi2&index=4&t=0s
but if you don't want to have complexity to your arrow, then I made a simple state machine inside this little code section:
extends Area2D
# Varaiables for moveing
var move_direction = Vector2(0,0)
export(int) var speed = 10
var states = ["fly", "stop"]
var current_state
var pos
# Damage
export(int) var dmg = 10
# When I spawn the bullets I give them a direction to go,
# In the parent node. Obviously you can change tha direction around if you want to.
func _physics_process(delta):
if move_direction != Vector2(0,0):
current_state = states.fly
match current_state:
states.fly:
global_position += move_direction * speed
global_rotation = move_direction.angle()
pos = global_position
states.stop:
global_position = pos
func _on_Area2D_area_entered(area):
# if area.is_in_group("PlayerHitbox"):
# area.get_parent().take_damage(dmg)
# destroy_bullet()
if area.is_in_group("wall"):
current_state = states.stop