extends Control ## Boot screen that handles update checking before launching the game ## Shows changelog with pagination, checking patch, and resource loading @onready var status_label := %StatusLabel as Label @onready var progress_bar := %ProgressBar as ProgressBar @onready var progress_label := %ProgressLabel as Label @onready var button_container := %ButtonContainer as HBoxContainer @onready var update_button := %UpdateButton as BaseButton @onready var update_button_label := %UpdateButton.get_node("Label") as Label @onready var skip_button := %SkipButton as BaseButton @onready var skip_button_label := %SkipButton.get_node("Label") as Label @onready var changelog_panel := %ChangelogPanel @onready var changelog_richtext := %ChangelogRichText as RichTextLabel @onready var prev_button := %PrevButton as BaseButton @onready var next_button := %NextButton as BaseButton @onready var page_label := %PageLabel as Label var update_manager: Node var update_info: Dictionary = {} var main_scene_path := "res://scenes/ui/login_screen.tscn" # Changelog Pagination var changelog_data: Array = [] var current_page: int = 0 var is_loading_game: bool = false func _ready() -> void: update_manager = _get_update_manager() update_manager.update_check_completed.connect(_on_update_check_completed) update_manager.update_check_failed.connect(_on_update_check_failed) update_manager.download_started.connect(_on_download_started) update_manager.download_progress.connect(_on_download_progress) update_manager.download_completed.connect(_on_download_completed) update_manager.download_failed.connect(_on_download_failed) update_button.pressed.connect(_on_update_pressed) skip_button.pressed.connect(_begin_resource_load) prev_button.pressed.connect(_on_prev_pressed) next_button.pressed.connect(_on_next_pressed) changelog_panel.visible = false button_container.visible = false progress_bar.visible = false progress_label.visible = false status_label.text = "Checking versions..." # Let the GameUpdateManager handle Editor mode (it will use the local version.json) update_manager.check_for_updates() func _get_update_manager() -> Node: if has_node("/root/GameUpdateManager"): return get_node("/root/GameUpdateManager") var manager_script := load("res://scripts/managers/game_update_manager.gd") var manager: Node = manager_script.new() manager.name = "GameUpdateManager" get_tree().root.add_child(manager) return manager func _on_update_check_completed(has_update: bool, info: Dictionary) -> void: update_info = info # Load changelog array specifically changelog_data = update_manager.manifest_data.get("releases", []) if changelog_data.size() > 0: changelog_panel.visible = true current_page = 0 _update_pagination_ui() if has_update and info.can_patch: status_label.text = "Update Available: v" + info.latest_version button_container.visible = true update_button.visible = true skip_button.visible = true skip_button_label.text = "Force Play" else: status_label.text = "Game up to date." button_container.visible = true update_button.visible = false skip_button.visible = true skip_button_label.text = "Play" func _on_update_check_failed(_error: String) -> void: status_label.text = "Could not check for updates" button_container.visible = true update_button.visible = false skip_button.visible = true skip_button_label.text = "Play" func _on_update_pressed() -> void: button_container.visible = false status_label.text = "Downloading update..." update_manager.download_update() func _on_download_started(total_size: int) -> void: progress_bar.visible = true progress_label.visible = true progress_bar.value = 0 progress_label.text = "0%" func _on_download_progress(_downloaded: int, _total: int, percentage: float) -> void: progress_bar.value = percentage progress_label.text = "%.0f%%" % percentage func _on_download_completed() -> void: status_label.text = "Update installed successfully!" progress_bar.visible = false progress_label.visible = false _begin_resource_load() func _on_download_failed(error: String) -> void: status_label.text = "Update failed: " + error progress_bar.visible = false progress_label.visible = false button_container.visible = true update_button_label.text = "Retry" func _begin_resource_load() -> void: button_container.visible = false status_label.text = "Loading resources..." progress_bar.visible = true progress_label.visible = true progress_bar.value = 0 progress_label.text = "0%" is_loading_game = true ResourceLoader.load_threaded_request(main_scene_path) func _process(_delta: float) -> void: if is_loading_game: var progress := [] var status := ResourceLoader.load_threaded_get_status(main_scene_path, progress) if status == ResourceLoader.THREAD_LOAD_IN_PROGRESS: var perc = progress[0] * 100.0 progress_bar.value = perc progress_label.text = "%.0f%%" % perc elif status == ResourceLoader.THREAD_LOAD_LOADED: is_loading_game = false get_tree().change_scene_to_packed(ResourceLoader.load_threaded_get(main_scene_path)) elif status == ResourceLoader.THREAD_LOAD_FAILED: is_loading_game = false status_label.text = "Error Loading Game" # --- Pagination UI Functions --- func _update_pagination_ui(): if changelog_data.size() == 0: changelog_richtext.text = "No changelog data available." prev_button.disabled = true next_button.disabled = true page_label.text = "0/0" return var entry: Dictionary = changelog_data[current_page] var txt: String = "[font_size=20][b]Version " + str(entry.get("version", "Unknown")) + "[/b][/font_size]\n[color=gray]" + str(entry.get("date", "")) + "[/color]\n\n" var changes: Array = entry.get("changelog", []) txt += "[table=2]" for change in changes: txt += "[cell]• [/cell][cell]" + change + "[/cell]" txt += "[/table]" changelog_richtext.text = txt page_label.text = str(current_page + 1) + " / " + str(changelog_data.size()) prev_button.disabled = (current_page == 0) next_button.disabled = (current_page >= changelog_data.size() - 1) func _on_prev_pressed(): if current_page > 0: current_page -= 1 _update_pagination_ui() func _on_next_pressed(): if current_page < changelog_data.size() - 1: current_page += 1 _update_pagination_ui()