extends SceneTree const EntryShell = preload("res://entry/entry_shell.gd") const SettingsStore = preload("res://entry/settings_store.gd") const SAVE_PATH := "user://aetherbound_guild_p10_3.json" const SETTINGS_PATH := "user://dev1_title_settings_test.json" const DRAFT_PATH := "user://dev1_title_initial_company_test.json" const COMPANY_PATH := "user://dev1_title_company_test.json" var failures: Array[String] = [] func _initialize() -> void: call_deferred("run_test") func run_test() -> void: _cleanup() await verify_no_save_and_return_paths() await verify_resumable_state() _cleanup() if failures.is_empty(): print("ABG_DEV1_TITLE_OK new_game=initial_company continue_missing=disabled continue_valid=enabled settings_return=true credits_return=true exit_review=true") quit(0) else: for failure in failures: push_error(failure) quit(1) func verify_no_save_and_return_paths() -> void: var shell = await _shell() var continue_button: Button = shell.get_node("TitleSafeArea/TitleLayout/TitleCopy/TitleActions/TitleContinue") var new_game: Button = shell.get_node("TitleSafeArea/TitleLayout/TitleCopy/TitleActions/TitleNewGame") expect(continue_button.disabled, "Continue is disabled when no save exists") expect(new_game.has_focus(), "New Game owns the initial keyboard/controller focus") expect(shell.get_node_or_null("TitleMasterWorldExtension") != null and shell.get_node_or_null("TitleSafeArea/TitleMasterComposite") != null, "Title uses the approved v001 world and coordinate master") expect(shell.get_node_or_null("TitleSafeArea/TitleLayout/TitleHeader/TitleIdentity") != null, "Title uses engine-rendered identity copy") expect(shell.get_node_or_null("TitleSafeArea/TitleLayout/TitleCommandDock") != null, "Title actions align to the physical command prop") expect(new_game.get_node_or_null("ButtonLabel") != null and continue_button.get_node_or_null("ButtonLabel") != null, "Title actions use engine-rendered labels") expect(shell.get_node_or_null("TitleSafeArea/TitleLayout/TitleTools/TitleSettings") != null and shell.get_node_or_null("TitleSafeArea/TitleLayout/TitleTools/TitleCredits") != null, "Title utility controls map to the lower command sign") expect(not continue_button.get_node("TitleContinueReason").text.is_empty(), "disabled Continue has a visible reason") shell.open_new_game_boundary() await process_frame expect(shell.current_screen == "initial_company" and shell.get_node_or_null("InitialCompanyPage/InitialCompanySafeArea") != null, "New Game reaches the real Initial Company page") shell.initial_company_page.request_back() await process_frame expect(shell.current_screen == "title", "Initial Company Back returns to Title without losing the draft") shell.show_settings_placeholder() await process_frame expect(shell.current_screen == "settings", "Settings opens from Title") shell.back_to_title() await process_frame expect(shell.current_screen == "title", "Settings returns exactly to Title") shell.show_credits_placeholder() await process_frame shell.back_to_title() await process_frame expect(shell.current_screen == "title", "Credits returns exactly to Title") shell.request_exit() await process_frame expect(shell.current_screen == "exit_review" and shell.get_node_or_null("ChildSafeArea/ChildLayout/ExitConfirm") != null, "Back boundary uses an exit review") shell.queue_free() await process_frame func verify_resumable_state() -> void: _write(SAVE_PATH, JSON.stringify({"save_kind": "aetherbound_guild_p10_3", "save_version": 9})) var shell = await _shell() var continue_button: Button = shell.get_node("TitleSafeArea/TitleLayout/TitleCopy/TitleActions/TitleContinue") expect(not continue_button.disabled, "Continue enables for a structurally valid local save") shell.open_continue_boundary() await process_frame expect("unchanged" in shell.get_node("TitleSafeArea/TitleLayout/TitleCopy/TitleActions/TitleContinue/TitleNotice").text, "Continue preserves the save and explains the later resume review") shell.queue_free() await process_frame func _shell(): var shell = EntryShell.new() shell.auto_start = false shell.initial_company_service.path = DRAFT_PATH shell.initial_company_service.company_path = COMPANY_PATH root.add_child(shell) await process_frame shell.settings = SettingsStore.new().defaults() shell.settings.setup_completed = true shell.settings.locale = "en" shell.show_title() await process_frame return shell func _write(path: String, text: String) -> void: var file := FileAccess.open(path, FileAccess.WRITE) file.store_string(text) file.close() func _cleanup() -> void: for path in [SAVE_PATH, SETTINGS_PATH]: if FileAccess.file_exists(path): DirAccess.remove_absolute(path) for suffix in ["", ".bak", ".candidate", ".bak.candidate", ".corrupt"]: var draft_path := "%s%s" % [DRAFT_PATH, suffix] if FileAccess.file_exists(draft_path): DirAccess.remove_absolute(draft_path) var company_path := "%s%s" % [COMPANY_PATH, suffix] if FileAccess.file_exists(company_path): DirAccess.remove_absolute(company_path) func expect(condition: bool, message: String) -> void: if not condition: failures.append("DEV-1 Title: %s" % message)