2026-08-31 02:18:08 +02:00
|
|
|
extends "res://ui/menus/ModalMenu.gd"
|
|
|
|
|
|
|
|
|
|
signal research_requested(id: String)
|
|
|
|
|
|
|
|
|
|
@onready var tree: Control = $Tree
|
|
|
|
|
@onready var detail: Label = $DetailLabel
|
|
|
|
|
@onready var cost: Control = $CostNumber
|
|
|
|
|
@onready var status: Label = $StatusLabel
|
|
|
|
|
@onready var resource_bar: Control = $Bar
|
|
|
|
|
|
2026-09-02 13:43:56 +02:00
|
|
|
var building_id: int = 0
|
|
|
|
|
|
2026-08-31 02:18:08 +02:00
|
|
|
|
|
|
|
|
func _ready() -> void:
|
|
|
|
|
super._ready()
|
|
|
|
|
tree.node_picked.connect(refresh)
|
|
|
|
|
tree.node_confirmed.connect(func(id: String): research_requested.emit(id))
|
|
|
|
|
|
|
|
|
|
|
2026-09-02 13:43:56 +02:00
|
|
|
func open_for(next_building_id: int) -> void:
|
|
|
|
|
building_id = next_building_id
|
2026-08-31 02:18:08 +02:00
|
|
|
resource_bar.building_id = building_id
|
2026-09-02 13:43:56 +02:00
|
|
|
var building: Dictionary = GameState.find_building(building_id)
|
|
|
|
|
cost.set_payment_position(building.get("position", null))
|
2026-08-31 02:18:08 +02:00
|
|
|
open_menu()
|
|
|
|
|
tree.reset_scroll()
|
|
|
|
|
refresh()
|
|
|
|
|
|
|
|
|
|
|
2026-09-02 13:43:56 +02:00
|
|
|
func close_menu() -> void:
|
|
|
|
|
super.close_menu()
|
|
|
|
|
building_id = 0
|
|
|
|
|
cost.set_payment_position(null)
|
|
|
|
|
|
|
|
|
|
|
2026-08-31 02:18:08 +02:00
|
|
|
func selected_id() -> String:
|
|
|
|
|
return String(tree.selected_id)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
func research_completed(id: String) -> void:
|
|
|
|
|
tree.queue_redraw()
|
|
|
|
|
refresh(id)
|
|
|
|
|
|
|
|
|
|
|
2026-09-02 13:43:56 +02:00
|
|
|
func set_status(message: String) -> void:
|
|
|
|
|
status.text = message
|
|
|
|
|
|
|
|
|
|
|
2026-08-31 02:18:08 +02:00
|
|
|
func refresh(id: String = "") -> void:
|
|
|
|
|
if id == "":
|
|
|
|
|
id = String(tree.selected_id)
|
|
|
|
|
if id == "":
|
|
|
|
|
detail.text = "Select a node to see what it unlocks."
|
|
|
|
|
cost.show_price({})
|
|
|
|
|
status.text = "Fleet capacity %d · Research points %d" \
|
|
|
|
|
% [GameState.max_fleet_size(), GameState.research_points]
|
|
|
|
|
return
|
|
|
|
|
|
|
|
|
|
var node: Dictionary = GameState.skill_node(id)
|
|
|
|
|
if node.is_empty():
|
|
|
|
|
return
|
|
|
|
|
detail.text = "%s\n%s" % [node.name, node.desc]
|
|
|
|
|
cost.show_price(GameState.skill_costs(id), GameState.skill_research_point_cost(id))
|
|
|
|
|
if GameState.is_unlocked(id):
|
|
|
|
|
status.text = "Researched"
|
|
|
|
|
elif not GameState.prerequisite_met(id):
|
|
|
|
|
status.text = "Needs %s first" % GameState.skill_node(node.requires).name
|
|
|
|
|
elif not cost.is_affordable():
|
|
|
|
|
status.text = ""
|
|
|
|
|
else:
|
|
|
|
|
status.text = "Tap again to research"
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
func handle_unhandled_input(event: InputEvent) -> bool:
|
|
|
|
|
if not visible:
|
|
|
|
|
return false
|
|
|
|
|
if event is InputEventScreenTouch:
|
|
|
|
|
tree.handle_touch(event)
|
|
|
|
|
elif event is InputEventScreenDrag:
|
|
|
|
|
tree.handle_drag(event)
|
|
|
|
|
elif event is InputEventMouseButton:
|
|
|
|
|
tree.handle_mouse_button(event)
|
|
|
|
|
elif event is InputEventMouseMotion:
|
|
|
|
|
tree.handle_mouse_motion(event)
|
|
|
|
|
return true
|