# DungeonResultUI —— CPythonEventManager::ShowDungeonResult 的轻量 Godot 载体。 # # 参考端收到 [DUNGEON_RESULT] 后直接调用 interface.ShowDungeonResult,并把 # 九个整数交给独立结算窗口。本组件只负责呈现这九个服务端字段,不修改副本 # 状态,也不凭空发奖励;奖励仍由网络协议驱动。 extends Node const RESULT_KEYS := [ "killstone_count", "killmob_count", "find_hidden", "hidden_total", "use_potion", "is_revived", "killallmob", "total_time", "bonus_exp", ] var _root: Control var _rows: VBoxContainer var _result: Dictionary = {} func setup(parent: Node) -> void: if _root != null: return _root = Control.new() _root.name = "DungeonResult" _root.set_anchors_preset(Control.PRESET_CENTER) _root.position = Vector2(-190, -175) _root.size = Vector2(380, 350) _root.visible = false _root.mouse_filter = Control.MOUSE_FILTER_STOP _root.z_index = 120 parent.add_child(_root) var panel := Panel.new() panel.set_anchors_preset(Control.PRESET_FULL_RECT) var style := StyleBoxFlat.new() style.bg_color = Color(0.055, 0.045, 0.035, 0.98) style.border_color = Color(0.78, 0.62, 0.30, 1.0) style.set_border_width_all(2) style.set_corner_radius_all(6) panel.add_theme_stylebox_override("panel", style) _root.add_child(panel) var title := Label.new() title.text = "副本结算" title.horizontal_alignment = HORIZONTAL_ALIGNMENT_CENTER title.position = Vector2(16, 14) title.size = Vector2(348, 32) title.add_theme_font_size_override("font_size", 20) _root.add_child(title) _rows = VBoxContainer.new() _rows.position = Vector2(34, 58) _rows.size = Vector2(312, 218) _rows.add_theme_constant_override("separation", 5) _root.add_child(_rows) var close_button := Button.new() close_button.text = "关闭" close_button.position = Vector2(130, 300) close_button.size = Vector2(120, 32) close_button.pressed.connect(close) _root.add_child(close_button) func show_result(result: Dictionary) -> void: if _root == null: return _result = result.duplicate(true) for child in _rows.get_children(): child.queue_free() for spec in _display_rows(): var row := Label.new() row.text = str(spec[0]) + ":" + str(spec[1]) row.add_theme_font_size_override("font_size", 14) _rows.add_child(row) _root.visible = true func open(result: Dictionary) -> void: show_result(result) func close() -> void: if _root: _root.visible = false func is_open() -> bool: return _root != null and _root.visible func result() -> Dictionary: return _result.duplicate(true) func _display_rows() -> Array: var elapsed := maxi(0, int(_result.get("total_time", 0))) var mins := elapsed / 60 var secs := elapsed % 60 return [ ["击杀石碑", int(_result.get("killstone_count", 0))], ["击杀怪物", int(_result.get("killmob_count", 0))], ["隐藏目标", "%d / %d" % [int(_result.get("find_hidden", 0)), int(_result.get("hidden_total", 0))]], ["使用药水", int(_result.get("use_potion", 0))], ["复活次数", int(_result.get("is_revived", 0))], ["完成条件", "已完成" if int(_result.get("killallmob", 0)) != 0 else "未完成"], ["用时", "%02d:%02d" % [mins, secs]], ["奖励经验", int(_result.get("bonus_exp", 0))], ] func _unhandled_input(event: InputEvent) -> void: if is_open() and event is InputEventKey and event.pressed \ and not event.echo and event.keycode == KEY_ESCAPE: close() get_viewport().set_input_as_handled()