@tool @icon("res://addons/reedscene/prop/icon/prop_states_manager.svg") class_name ReedPropStateManager extends Node @export var auto_refresh: bool = true func _ready() -> void: if not Engine.is_editor_hint(): return child_entered_tree.connect(_on_child_entered_tree) child_exiting_tree.connect(_on_child_exiting_tree) _refresh_states() func _notification(what: int) -> void: if not Engine.is_editor_hint(): return if what == NOTIFICATION_CHILD_ORDER_CHANGED: if auto_refresh: call_deferred("_refresh_states") func _on_child_entered_tree(node: Node) -> void: if not Engine.is_editor_hint(): return if node is ReedPropState and auto_refresh: call_deferred("_refresh_states") func _on_child_exiting_tree(node: Node) -> void: if not Engine.is_editor_hint(): return if node is ReedPropState and auto_refresh: call_deferred("_refresh_states") func _refresh_states() -> void: var index := 0 for child in get_children(): if not child is ReedPropState: continue _assign_state_id(child, index) _rename_state_node(child, index) index += 1 func _assign_state_id(state: ReedPropState, id: int) -> void: if state.state_id == id: return state.set("state_id", id) func _rename_state_node(state: ReedPropState, id: int) -> void: var base_name := _strip_id_prefix(state.name) var expected := "[ID_%d] %s" % [id, base_name] if state.name == expected: return state.name = expected func _strip_id_prefix(name: String) -> String: var result := name # 连续剥离所有 [ID_x] 前缀,防止叠加 while result.begins_with("[ID_"): var end := result.find("]") if end == -1: break # 跳过 "] " 或 "]" var cut := end + 1 if cut < result.length() and result[cut] == " ": cut += 1 result = result.substr(cut) return result.strip_edges() func _extract_raw_name(name: String) -> String: if name.begins_with("[ID:"): var end := name.find("]") if end != -1 and end + 2 < name.length(): return name.substr(end + 2) return name