Hey everyone, sorry, first time being in this forum so im not sure if im doing it right,
I’ve been following multiple class on godot and familiarised myself with gdscript, so when finished the Build a 2D Action-Adventure Game, i felt comfortable enough to expand it a bit and create a boss enemy.
Buuuuuut, i think i overestimate my skills, because i’ve been stuck for the past few days trying so many things, i feel like im lost in the sauce. So… Help please?
The goal, is to have a big boss that has two attack one on the right, one on the left, when the player enters the attack range, the boss should “charge” the right or left area depending on where the character is, so that the player can try to quickly leave that area before the boss attacks.
However, right now, i have two big problems, if the player enters both the right and left attack range, it attacks twice (which is unfortunate - i also wanted to randomised that with randf() but it didnt seem to work so ive deleted that) and also, it only attacks once the player enters the zone, and not everytime the player is within that zone.
Ive tried so many things, and right now i think the attack don’t even work anymore, so please, what am i doing wrong? (im gonna put the code that doesnt seem to work and exclude what does work so its easier on the eyes)
thanks in advance cause im getting crazy
extends CharacterBody2D
var target: Node2D
@export var speed: int = 30
@export var acceleration: float = 5
@export var hp: int = 30
@onready var damage_sfx: AudioStreamPlayer2D = $DamageSFX
@onready var animated_sprite_2d: AnimatedSprite2D = $AnimatedSprite2D
@onready var left_attack_range_area_2d: Area2D = $LeftAttackRangeArea2D
@onready var right_attack_range_area_2d: Area2D = $RightAttackRangeArea2D
@onready var attack_cool_down: Timer = $AttackCoolDown
@onready var sword_slash: AudioStreamPlayer2D = $sword_slash
var can_attack: bool = true
var is_in_attack_range: bool = false
var is_attacking: bool = false
var is_charging: bool = false
func _physics_process(delta: float) -> void:
if hp <= 0:
return
if not is_in_attack_range:
move_and_slide()
chase_target()
else:
velocity = Vector2.ZERO
if is_attacking == false and is_charging == false:
animate_enemy()
func _on_attack_range_area_2d_body_entered(body: Node2D) -> void:
if body is Player:
is_in_attack_range = true
print("Player entered attack range")
charge_attack(body)
func _on_attack_range_area_2d_body_exited(body: Node2D) -> void:
if body is Player:
is_in_attack_range = false
print("Player left attack range")
func charge_attack(body: Node2D) -> void:
if is_attacking or can_attack == false:
return
print("can't attack")
print("charge")
is_charging = true
var in_left_range = left_attack_range_area_2d.get_overlapping_bodies().has(body)
var in_right_range = right_attack_range_area_2d.get_overlapping_bodies().has(body)
if in_left_range and in_right_range:
print("is in both range")
animated_sprite_2d.play("charge_left")
await animated_sprite_2d.animation_finished
attack_left_player(body)
elif in_left_range:
print("is in left range")
animated_sprite_2d.play("charge_left")
await animated_sprite_2d.animation_finished
attack_left_player(body)
elif in_right_range:
print("is in right range")
animated_sprite_2d.play("charge_right")
await animated_sprite_2d.animation_finished
attack_right_player(body)
is_charging = false
func start_attack(direction: String, body: Node2D) -> void:
if direction == "left":
animated_sprite_2d.play("charge_left")
await animated_sprite_2d.animation_finished
attack_left_player(body)
elif direction == "right":
animated_sprite_2d.play("charge_right")
await animated_sprite_2d.animation_finished
attack_left_player(body)
func attack_right_player(body: Node2D) -> void:
attack_cool_down.start()
is_attacking = true
print("Right Attack!")
can_attack = false
sword_slash.play()
animated_sprite_2d.play("right_attack")
body.take_damage()
await animated_sprite_2d.animation_finished
is_attacking = false
func attack_left_player(body: Node2D) -> void:
attack_cool_down.start()
is_attacking = true
print("Left Attack!")
can_attack = false
animated_sprite_2d.play("left_attack")
sword_slash.play()
body.take_damage()
await animated_sprite_2d.animation_finished
is_attacking = false
func _on_attack_cool_down_timeout() -> void:
print("cooldown is over")
can_attack = true