class_name BossAttackManager
extends Node2D

var boss_behavior : BossBehavior
var boss_remnant_manager : BossRemnantManager

var _attacks : Array[BossAttack]
var current_attack : BossAttack

signal attack_prepared
signal attack_performed
signal attack_cooldown_over
var _cooldown = 0.0

var anchor_state : Dictionary = {}
var attack_history : Dictionary[int, int] = {}
var saved_attack_id : int = 0
var save_history : bool = false
var replayed_attack_id : int = -1

func _ready() -> void:
	if get_parent() and get_parent() is BossBehavior:
		boss_behavior = get_parent() as BossBehavior
	
	SignalBus.anchor_ran_out.connect(clean_up_state)
	for child in get_children():
		if child is BossAttack:
			child.boss_behavior = boss_behavior
			_attacks.append(child)

func randomize_attack():
	var attack_id
	if attack_history.has(replayed_attack_id):
		attack_id = attack_history[replayed_attack_id]
		replayed_attack_id += 1
	else:
		attack_id = randi_range(0, _attacks.size()-1)
		
	if save_history:
		attack_history[saved_attack_id] = attack_id
		saved_attack_id += 1
	select_attack(attack_id)

func select_attack(attack_id):
	current_attack = _attacks[attack_id]
	
	if boss_remnant_manager:
		boss_remnant_manager.attack(attack_id)
		
	connect_to_current_attack()

func start_prepare():
	if boss_remnant_manager:
		boss_remnant_manager.prepare_attack()
	current_attack.start_prepare()

func prepare(delta : float):
	current_attack.prepare(delta)

func end_prepare():
	current_attack.end_prepare()

func start_perform():
	if boss_remnant_manager:
		boss_remnant_manager.perform_attack()
	current_attack.start_perform()
	AudioManager.create_audio(SoundEffect.SOUND_EFFECT_TYPE.BOSS_ATTACK)

func perform(delta : float):
	current_attack.perform(delta)

func end_perform():
	current_attack.end_perform()

func start_cooldown():
	if boss_remnant_manager:
		boss_remnant_manager.attack_cooldown()
	_cooldown = current_attack.attack_cooldown

func cooldown(delta : float):
	if _cooldown > 0:
		_cooldown -= delta
		if _cooldown <= 0:
			attack_cooldown_over.emit()

func connect_to_current_attack():
	current_attack.attack_prepared.connect(func () : attack_prepared.emit())
	current_attack.attack_performed.connect(func () : attack_performed.emit())

#region Anchored Remnant
func save_state():
	anchor_state = {
		"current_attack" = current_attack,
		"_cooldown" = _cooldown,
	}
	save_history = true
	saved_attack_id = 0

func reload_state():
	current_attack = anchor_state.get("current_attack", current_attack)
	connect_to_current_attack()
	_cooldown = anchor_state.get("_cooldown", _cooldown)
	replayed_attack_id = 0
	print(current_attack.attack_name)

func clean_up_state():
	save_history = false
	replayed_attack_id = -1
	saved_attack_id = 0
	attack_history.clear()
#endregion
