batrix/scripts/player/player_attack.gd

99 lines
2.6 KiB
GDScript

class_name PlayerAttack
extends Area3D
signal attacked
const COOLDOWN_TIME: float = 0.3
const HIT_WINDOW_TIME: float = 0.25
const SWOOP_EFFECT_TIME: float = 0.25
@export var _collision_debug_material: Material
@export var _attack_max_angle: float = PI / 2
var _debug_collision_shapes := DebugCollisionShapes.new()
var _cooldown_timer: float
var _hit_window_timer: float
var _swoop_effect_timer: float
@onready var _swoop_mesh: MeshInstance3D = $SwoopMesh
func _ready() -> void:
_debug_collision_shapes.init(get_children(), self, _collision_debug_material)
Debugger.add_event("attacked")
attacked.connect(func() -> void: Debugger.event_emitted("attacked", []))
body_entered.connect(_on_body_entered)
position.y = Projectile.HEIGHT
func _unhandled_input(event: InputEvent) -> void:
if event.is_action_pressed("attack"):
_attack()
func _process(delta: float) -> void:
if _cooldown_timer > 0:
_cooldown_timer -= delta
if _hit_window_timer > 0:
_hit_window_timer -= delta
elif _debug_collision_shapes.is_visible:
_debug_collision_shapes.set_visibility(false)
if _swoop_effect_timer > 0:
_swoop_effect_timer -= delta
(_swoop_mesh.material_override as StandardMaterial3D).albedo_color = Color(
1, 1, 1, _swoop_effect_timer / SWOOP_EFFECT_TIME
)
_swoop_mesh.visible = _swoop_effect_timer > 0
Debugger.text("_cooldown_timer", _cooldown_timer, 2)
Debugger.text("_hit_window_timer", _hit_window_timer, 2)
Debugger.text("_swoop_effect_timer", _swoop_effect_timer, 2)
Debugger.vector(
"fghdh",
global_position,
global_position + global_basis.z.rotated(Vector3.UP, _attack_max_angle) * 2
)
Debugger.vector(
"fghdh2",
global_position,
global_position + global_basis.z.rotated(Vector3.UP, -_attack_max_angle) * 2
)
func _physics_process(_delta: float) -> void:
monitoring = Input.is_action_just_pressed("attack")
func _attack() -> void:
if _cooldown_timer > 0:
return
attacked.emit()
_cooldown_timer = COOLDOWN_TIME
_hit_window_timer = HIT_WINDOW_TIME
_swoop_effect_timer = SWOOP_EFFECT_TIME
_debug_collision_shapes.set_visibility(true)
func _hit_projectile(projectile: Projectile) -> void:
var diff := projectile.global_position - global_position
diff.y = 0
var angle := global_basis.z.angle_to(diff)
Debugger.vector("ASDSAD", global_position, global_position + global_basis.z)
Debugger.vector("ASDSAD2", global_position, global_position + diff)
if angle > _attack_max_angle:
return
projectile.queue_free()
func _on_body_entered(node: Node3D) -> void:
if _hit_window_timer <= 0:
return
if node is Projectile:
_hit_projectile(node as Projectile)