15func configure(unlocked_ids:Array, equipped_ids:Array = [], options:Dictionary = {}) -> void:
16 max_slots = max(1, int(options.get(
"max_slots", 3)))
17 min_slots = clamp(int(options.get(
"min_slots", 1)), 0, max_slots)
18 fallback_ids = _unique_ids(options.get(
"fallback_ids", []))
20 for id
in unlocked_ids:
24 for id
in fallback_ids:
27 equipped = _unique_ids(equipped_ids)
32func add_unlocks(unlock_ids:Array, auto_equip := true) -> Array:
33 var newly_equipped := []
39 if auto_equip
and equipped.size() < max_slots
and not equipped.has(key):
41 newly_equipped.append(key)
46func toggle(card_id:String) -> Dictionary:
47 if is_equipped(card_id):
48 return unequip(card_id)
52func equip(card_id:String) -> Dictionary:
53 if not unlocked.has(card_id):
54 return {
"ok": false,
"reason":
"locked",
"message":
"That spell is not unlocked yet."}
55 if equipped.has(card_id):
56 return {
"ok": true,
"action":
"already_equipped",
"equipped": get_equipped_ids()}
57 if equipped.size() >= max_slots:
58 return {
"ok": false,
"reason":
"full",
"message":
"No open spell slots."}
59 equipped.append(card_id)
61 return {
"ok": true,
"action":
"equipped",
"equipped": get_equipped_ids()}
64func unequip(card_id:String) -> Dictionary:
65 if not equipped.has(card_id):
66 return {
"ok": true,
"action":
"already_unequipped",
"equipped": get_equipped_ids()}
67 if equipped.size() <= min_slots:
68 return {
"ok": false,
"reason":
"minimum",
"message":
"Keep at least one spell equipped."}
69 equipped.erase(card_id)
71 return {
"ok": true,
"action":
"unequipped",
"equipped": get_equipped_ids()}
74func is_unlocked(card_id:String) -> bool:
75 return unlocked.has(card_id)
78func is_equipped(card_id:String) -> bool:
79 return equipped.has(card_id)
82func get_unlocked_ids() -> Array:
83 var ids = unlocked.keys()
88func get_equipped_ids() -> Array:
89 return equipped.duplicate()
92func get_state() -> Dictionary:
94 "unlocked": unlocked.duplicate(true),
95 "equipped": equipped.duplicate(),
96 "max_slots": max_slots,
97 "min_slots": min_slots,
98 "fallback_ids": fallback_ids.duplicate()
102func apply_state(state:Dictionary) -> void:
103 unlocked = state.get(
"unlocked", {}).duplicate(true)
104 equipped = state.get(
"equipped", []).duplicate()
105 max_slots = max(1, int(state.get(
"max_slots", 3)))
106 min_slots = clamp(int(state.get(
"min_slots", 1)), 0, max_slots)
107 fallback_ids = _unique_ids(state.get(
"fallback_ids", []))
111func _normalize() -> void:
115 if unlocked.has(key)
and not normalized.has(key):
116 normalized.append(key)
117 for id
in fallback_ids:
118 if normalized.size() >= min_slots:
120 if unlocked.has(id)
and not normalized.has(id):
121 normalized.append(id)
122 for id
in get_unlocked_ids():
123 if normalized.size() >= min_slots:
125 if not normalized.has(id):
126 normalized.append(id)
127 equipped = normalized.slice(0, max_slots)
130func _unique_ids(ids:Array) -> Array:
134 if key !=
"" and not rows.has(key):