class_name RootUI extends CanvasLayer @export var startup_scene:PackedScene @export var game_scene:PackedScene @export var autostart_game_scene:bool = true @onready var scene = %Scene @onready var ui_panels:Array = [ %MainMenuUI, %NewGameUI, %GameUI ] @onready var active_ui_panel:Control = null enum ROOT_UI_STATE { UNDEFINED, MENU, GAME } var _root_ui_state:ROOT_UI_STATE = ROOT_UI_STATE.UNDEFINED var current_level_resource:String func _ready(): if autostart_game_scene: load_scene(game_scene) set_root_ui_state(ROOT_UI_STATE.GAME) else: set_root_ui_state(ROOT_UI_STATE.MENU) func activate_ui_panel(ui_panel:Control): for control in ui_panels: if control == ui_panel: control.visible = true else: control.visible = false active_ui_panel = ui_panel func load_scene(scene_resource:PackedScene): for scene_child in scene.get_children(): scene_child.queue_free() scene_child.get_parent().remove_child(scene_child) print("Loading level '" + scene_resource.resource_path + "'") scene.add_child(scene_resource .instantiate()) current_level_resource = scene_resource.resource_path func save_game(): var player:Player = scene.find_child("Player", true, false) if player == null: push_error("Cannot load game: no player found!") return var save_game:SaveGame = SaveGame.new() save_game.level = current_level_resource save_game.level_pickup_items = %GameUI.picked_up_level_items save_game.player_transform = player.global_transform for node:Node in get_tree().get_nodes_inv_group("quest_state"): save_game.quest_states[node.name] = {} for property in node.get_property_list(): if (property.usage & PROPERTY_USAGE_STORAGE != 0) and (property.usage & PROPERTY_USAGE_SCRIPT_VARIABLE) != 0: save_game.quest_states[node.name][property.name] = node.get(property.name) for item_stack in player.inventory.get_item_stacks(): save_game.inventory.append({"item": item_stack.item, "count": item_stack.count}) ResourceSaver.save(save_game, "user://savegame.tres") activate_ui_panel(%GameUI) func load_game(): set_root_ui_state(RootUI.ROOT_UI_STATE.UNDEFINED) %GameUI.picked_up_level_items.clear() var save_game:SaveGame = load("user://savegame.tres") as SaveGame var level_resource:PackedScene = load(save_game.level) load_scene(level_resource) var player:Player = scene.find_child("Player", true, false) if player == null: push_error("Cannot load game: no player found!") return print("main.gd:load_game() Player = " + str(player)) player.global_transform = save_game.player_transform # Quest state for node:Node in get_tree().get_nodes_in_group("quest_state"): for property in node.get_property_list(): if (property.usage & PROPERTY_USAGE_STORAGE != 0) and (property.usage & PROPERTY_USAGE_SCRIPT_VARIABLE) != 0: node.set(property.name, save_game.quest_states[node.name][property.name]) # Inventory player.inventory.clear() var inventory_item_stacks:Array[ItemStack] = player.inventory.get_item_stacks() assert(inventory_item_stacks.size() >= save_game.inventory.size()) for i in range(save_game.inventory.size()): inventory_item_stacks[i].item = save_game.inventory[i]["item"] inventory_item_stacks[i].count = save_game.inventory[i]["count"] # Picked up items for item_path in save_game.level_pickup_items: if get_tree().root.has_node(item_path): var item_node = get_tree().root.get_node(item_path) %GameUI.picked_up_level_items.append(item_path) item_node.queue_free() set_root_ui_state(RootUI.ROOT_UI_STATE.GAME) func set_root_ui_state(state:ROOT_UI_STATE): if _root_ui_state == state: return if state == ROOT_UI_STATE.GAME: %GameUI.activate_game_scene(scene.get_child(0)) activate_ui_panel(%GameUI) elif state == ROOT_UI_STATE.MENU: load_scene(startup_scene) %GameUI.activate_game_scene(null) activate_ui_panel(%MainMenuUI) _root_ui_state = state func _on_start_game_button_pressed(): load_scene(game_scene) set_root_ui_state(ROOT_UI_STATE.GAME) func _on_quit_button_pressed(): get_tree().quit() func _on_new_game_button_pressed(): activate_ui_panel(%NewGameUI) func _to_main_menu_button_pressed(): set_root_ui_state(ROOT_UI_STATE.MENU)