@icon("res://assets/editor/64x64/fc1098.png")
extends Node2D
class_name ModifierManager

signal modifier_added(modifier)
signal modifier_removed(modifier)
signal stats_updated()

var stats_component: StatsComponent

# Stores all active modifiers
var modifiers: Array[Modifier] = []

func _ready() -> void:
	Log.pr("ModifierManager initialized")
	Log.pr("StatsComponent: ", stats_component)

func set_stats(stats: StatsComponent) -> void:
	self.stats_component = stats

func has_modifier(modifier_id: String) -> bool:
	for modifier in modifiers:
		if modifier.id == modifier_id:
			return true
	return false

func add_modifier(modifier: Modifier) -> void:
	modifiers.append(modifier)
	modifier.on_equip(get_parent())
	emit_signal("modifier_added", modifier)
	recalculate_stats()

func remove_modifier(modifier_id: String) -> void:
	for i in range(modifiers.size()):
			if modifiers[i].id == modifier_id:
					var modifier = modifiers[i]
					modifier.on_unequip(get_parent())
					modifiers.remove_at(i)
					emit_signal("modifier_removed", modifier)
					recalculate_stats()
					break

func recalculate_stats() -> void:
	# Reset stats to base values
	stats_component.reset_stats()

	# Sort modifiers by priority
	modifiers.sort_custom(func(a, b): return a.priority > b.priority)

	# First pass: Apply OVERRIDE modifiers (highest priority first)
	for modifier in modifiers:
		if modifier.modifier_type == Modifier.ModifierType.OVERRIDE:
			_apply_modifier_stats(modifier)

	# Second pass: Apply ADDITIVE modifiers
	for modifier in modifiers:
		if modifier.modifier_type == Modifier.ModifierType.ADDITIVE:
			_apply_modifier_stats(modifier)

	# Third pass: Apply MULTIPLICATIVE modifiers
	for modifier in modifiers:
		if modifier.modifier_type == Modifier.ModifierType.MULTIPLICATIVE:
			_apply_modifier_stats(modifier)

	# Last pass: Apply CONDITIONAL modifiers
	for modifier in modifiers:
		if modifier.modifier_type == Modifier.ModifierType.CONDITIONAL:
				_apply_modifier_stats(modifier)
	
	emit_signal("stats_updated")

func check_callable(func_name: String) -> Callable:
	# Create a default callable that does nothing and returns null
	var default_callable = func(): return null

	# Check each modifier in priority order
	for modifier in modifiers:
			if modifier.has_method(func_name):
					# Return the callable from this modifier
					return Callable(modifier, func_name)

	# Return the default callable if no modifier has the function
	return default_callable

# Convenience method to check and call in one step
func check_and_call(func_name: String, args := []):
	var callable = check_callable(func_name)
	if callable.is_valid():
			if args.size() > 0:
					return callable.callv(args)
			else:
					return callable.call()
	return null

func _apply_modifier_stats(modifier: Modifier) -> void:
	if modifier.has_method("apply_stats_modification"):
		modifier.apply_stats_modification(stats_component)
