class_name CPPool extends RefCounted ## CPPool - Tracks Crystal Points generated during a turn # CP stored by element var _cp: Dictionary = {} func _init() -> void: clear() ## Clear all CP (called at end of each action) func clear() -> void: for element in Enums.Element.values(): _cp[element] = 0 ## Add CP of a specific element func add_cp(element: Enums.Element, amount: int) -> void: _cp[element] = _cp.get(element, 0) + amount ## Get CP of a specific element func get_cp(element: Enums.Element) -> int: return _cp.get(element, 0) ## Get total CP available func get_total_cp() -> int: var total = 0 for element in _cp: total += _cp[element] return total ## Check if we can afford a card cost func can_afford_card(card_data: CardDatabase.CardData) -> bool: if not card_data: return false var cost = card_data.cost var elements = card_data.elements # For Light/Dark cards, just need total CP var is_light_dark = false for element in elements: if Enums.is_light_or_dark(element): is_light_dark = true break if is_light_dark: return get_total_cp() >= cost # For multi-element cards, need at least 1 CP of each element if elements.size() > 1: for element in elements: if get_cp(element) < 1: return false # Total must be at least the cost return get_total_cp() >= cost # For single element cards, need at least 1 CP of that element var primary_element = elements[0] if elements.size() > 0 else Enums.Element.FIRE if get_cp(primary_element) < 1: return false return get_total_cp() >= cost ## Spend CP to pay a card cost ## Returns true if successful, false if cannot afford func spend_for_card(card_data: CardDatabase.CardData) -> bool: if not can_afford_card(card_data): return false var cost = card_data.cost var elements = card_data.elements var remaining = cost # For multi-element, spend 1 of each required element first if elements.size() > 1: for element in elements: _cp[element] -= 1 remaining -= 1 # For single element (non-Light/Dark), spend at least 1 of that element elif elements.size() == 1: var element = elements[0] if not Enums.is_light_or_dark(element): _cp[element] -= 1 remaining -= 1 # Spend remaining from any element while remaining > 0: var spent = false for element in _cp: if _cp[element] > 0: _cp[element] -= 1 remaining -= 1 spent = true break if not spent: push_error("Failed to spend remaining CP") return false return true ## Check if we can afford an ability cost func can_afford_ability(cost: CardDatabase.CostData) -> bool: if not cost: return true # No cost means free # Check element-specific requirements if cost.fire > 0 and get_cp(Enums.Element.FIRE) < cost.fire: return false if cost.ice > 0 and get_cp(Enums.Element.ICE) < cost.ice: return false if cost.wind > 0 and get_cp(Enums.Element.WIND) < cost.wind: return false if cost.lightning > 0 and get_cp(Enums.Element.LIGHTNING) < cost.lightning: return false if cost.water > 0 and get_cp(Enums.Element.WATER) < cost.water: return false if cost.earth > 0 and get_cp(Enums.Element.EARTH) < cost.earth: return false if cost.light > 0 and get_cp(Enums.Element.LIGHT) < cost.light: return false if cost.dark > 0 and get_cp(Enums.Element.DARK) < cost.dark: return false # Check total return get_total_cp() >= cost.get_total_cp() ## Spend CP to pay an ability cost func spend_for_ability(cost: CardDatabase.CostData) -> bool: if not can_afford_ability(cost): return false # Spend element-specific CP if cost.fire > 0: _cp[Enums.Element.FIRE] -= cost.fire if cost.ice > 0: _cp[Enums.Element.ICE] -= cost.ice if cost.wind > 0: _cp[Enums.Element.WIND] -= cost.wind if cost.lightning > 0: _cp[Enums.Element.LIGHTNING] -= cost.lightning if cost.water > 0: _cp[Enums.Element.WATER] -= cost.water if cost.earth > 0: _cp[Enums.Element.EARTH] -= cost.earth if cost.light > 0: _cp[Enums.Element.LIGHT] -= cost.light if cost.dark > 0: _cp[Enums.Element.DARK] -= cost.dark # Spend generic from any element var generic_remaining = cost.generic while generic_remaining > 0: for element in _cp: if _cp[element] > 0: _cp[element] -= 1 generic_remaining -= 1 break return true ## Get a display-friendly dictionary of current CP func get_display_data() -> Dictionary: var data = {} for element in _cp: if _cp[element] > 0: data[Enums.element_to_string(element)] = _cp[element] return data func _to_string() -> String: var parts = [] for element in _cp: if _cp[element] > 0: parts.append("%s: %d" % [Enums.element_to_string(element), _cp[element]]) if parts.size() == 0: return "[CPPool: empty]" return "[CPPool: " + ", ".join(parts) + "]"