82 lines
2.3 KiB
GDScript
82 lines
2.3 KiB
GDScript
class_name DeployedUnit extends Node2D
|
|
|
|
enum UnitState { ALIVE, DEAD }
|
|
|
|
@export var unit: Unit
|
|
|
|
var current_stats: DeployedUnitStats
|
|
var tactics: Array[CombatTactic] = []
|
|
var state: UnitState = UnitState.ALIVE
|
|
|
|
var _sprite: AnimatedSprite2D
|
|
var _previous_position: Vector2
|
|
|
|
signal unit_selected_changed(deployed: DeployedUnit, selected: bool)
|
|
signal unit_allegiance_changed(deployed: DeployedUnit, allegiance: UnitAllegiance)
|
|
signal unit_died(deployed: DeployedUnit)
|
|
|
|
func _ready() -> void:
|
|
current_stats = DeployedUnitStats.from_unit_stats(unit.stats)
|
|
tactics = unit.tactics.duplicate()
|
|
_append_builtin_tactics()
|
|
unit_allegiance_changed.emit(self, unit.allegiance)
|
|
_previous_position = position
|
|
_setup_appearance()
|
|
|
|
func _setup_appearance() -> void:
|
|
_sprite = get_node_or_null("AnimatedSprite2D") as AnimatedSprite2D
|
|
if not _sprite:
|
|
return
|
|
var sprite_frames: SpriteFrames = unit.appearance.deployed_sprite_sheet if unit.appearance else null
|
|
if not sprite_frames:
|
|
return
|
|
_sprite.sprite_frames = sprite_frames
|
|
_sprite.play("idle")
|
|
|
|
func _physics_process(_delta: float) -> void:
|
|
if not _sprite or not _sprite.sprite_frames:
|
|
return
|
|
var delta_pos := position - _previous_position
|
|
_previous_position = position
|
|
if delta_pos.length_squared() < 0.01:
|
|
if _sprite.animation != &"idle":
|
|
_sprite.play("idle")
|
|
return
|
|
var anim: StringName
|
|
if absf(delta_pos.x) >= absf(delta_pos.y):
|
|
anim = &"right" if delta_pos.x > 0 else &"left"
|
|
else:
|
|
anim = &"down" if delta_pos.y > 0 else &"up"
|
|
if _sprite.animation != anim:
|
|
_sprite.play(anim)
|
|
|
|
func _append_builtin_tactics() -> void:
|
|
var attack := AttackCombatTactic.new()
|
|
attack.tactic_name = "Attack"
|
|
attack.tactic_range = UnitMatchingCombatTacticRange.new()
|
|
tactics.append(attack)
|
|
|
|
var defend := DefendCombatTactic.new()
|
|
defend.tactic_name = "Defend"
|
|
defend.tactic_range = AnyCombatTacticRange.new()
|
|
tactics.append(defend)
|
|
|
|
func set_selected(selected: bool) -> void:
|
|
unit_selected_changed.emit(self, selected)
|
|
|
|
func is_alive() -> bool:
|
|
return state == UnitState.ALIVE
|
|
|
|
func take_damage(amount: int) -> void:
|
|
if state != UnitState.ALIVE:
|
|
return
|
|
current_stats.current_hp -= amount
|
|
if current_stats.current_hp <= 0:
|
|
current_stats.current_hp = 0
|
|
_die()
|
|
|
|
func _die() -> void:
|
|
state = UnitState.DEAD
|
|
unit_died.emit(self)
|
|
queue_free()
|