Files
stickman/tests/test_content_paths.gd

121 lines
5.3 KiB
GDScript

extends SceneTree
const CONTENT_PATHS := preload("res://scripts/shared/content_paths.gd")
const CLI_LAUNCHER := preload("res://scripts/tools/cli_scene_launcher.gd")
const STAGE_SCENE_IO := preload("res://scripts/stage/stage_scene_io.gd")
const STAGE_SCENE := preload("res://scenes/stage/sandbox_stage.tscn")
const LEGACY_STAGE_PATH: String = "res://tests/.phase14_legacy_paths.scene"
const RESAVED_STAGE_PATH: String = "res://tests/.phase14_resaved_paths_resaved.scene"
var _checks: int = 0
var _failures: int = 0
func _initialize() -> void:
call_deferred("_run")
func _run() -> void:
_test_path_mapping()
_test_moved_stage_file_paths()
await _test_legacy_stage_round_trip()
_cleanup()
print("RESULT: %d checks, %d failures" % [_checks, _failures])
quit(1 if _failures > 0 else 0)
func _expect(condition: bool, message: String) -> void:
_checks += 1
if condition:
print("PASS: " + message)
else:
_failures += 1
push_error("Content path test failed: " + message)
func _test_path_mapping() -> void:
_expect(CONTENT_PATHS.canonicalize("res://stickmen/basic.stk") == "res://content/stickmen/basic.stk", "legacy stickman resource paths map into content")
_expect(CONTENT_PATHS.canonicalize("res://props/briefcase.prop") == "res://content/props/briefcase.prop", "legacy prop resource paths map into content")
_expect(CONTENT_PATHS.canonicalize("res://game_scenes/bend.scene") == "res://content/stages/bend.scene", "legacy stage resource paths map into content")
_expect(CONTENT_PATHS.canonicalize("res://unmanaged/asset.stk") == "res://unmanaged/asset.stk", "unknown resource paths pass through")
_expect(CONTENT_PATHS.canonicalize("user://stickmen/basic.stk") == "user://stickmen/basic.stk", "user-selected paths pass through")
_expect(CONTENT_PATHS.canonicalize("/tmp/external/stickmen/basic.stk") == "/tmp/external/stickmen/basic.stk", "external absolute paths pass through")
var project_root: String = ProjectSettings.globalize_path("res://").trim_suffix("/")
var old_absolute: String = project_root.path_join("stickmen/basic.stk")
var new_absolute: String = project_root.path_join("content/stickmen/basic.stk")
_expect(CONTENT_PATHS.canonicalize(old_absolute) == new_absolute, "legacy absolute paths inside the project migrate in place")
var cli_result: Dictionary = CLI_LAUNCHER.parse(["--scene", "res://game_scenes/bend.scene"])
_expect(String(cli_result.get("scene_path", "")) == "res://content/stages/bend.scene", "CLI stage paths migrate before playback")
func _test_moved_stage_file_paths() -> void:
var result: Dictionary = STAGE_SCENE_IO.read_file("res://game_scenes/bend.scene")
_expect(bool(result.get("ok", false)), "stage IO opens a stage through its previous project path")
func _test_legacy_stage_round_trip() -> void:
_cleanup()
var legacy_data: Dictionary = {
"version": STAGE_SCENE_IO.FILE_VERSION,
"scene_name": "Legacy Asset Paths",
"camera": {"position": {"x": 0.0, "y": -400.0}, "zoom": 0.5},
"objects": [
{
"file_id": "stickman_1",
"type": "stickman",
"position": {"x": 0.0, "y": 0.0},
"rotation": 0.0,
"stk_path": "res://stickmen/test.stk",
"action_queue": [],
},
{
"file_id": "prop_1",
"stage_object_id": "prop_1",
"type": "prop",
"position": {"x": 180.0, "y": 0.0},
"rotation": 0.0,
"asset_id": "res://props/briefcase.prop",
"scale": {"x": 1.0, "y": 1.0},
"material_preset": 1,
},
],
"event_rules": [],
"metadata": {},
}
_expect(bool(STAGE_SCENE_IO.write_file_safe(LEGACY_STAGE_PATH, legacy_data).get("ok", false)), "legacy stage fixture writes")
var stage: Node2D = STAGE_SCENE.instantiate() as Node2D
root.add_child(stage)
await process_frame
var loaded: bool = bool(stage.call("_load_scene_from_path", LEGACY_STAGE_PATH))
_expect(loaded, "legacy stage with moved stickman and prop assets loads")
var world: Node = stage.get("_world") as Node
_expect(world != null and world.get_child_count() == 2, "both moved assets are present after load")
var scene_data: Dictionary = stage.call("_collect_scene_data", false) as Dictionary
var objects: Array = scene_data.get("objects", [])
var saved_stickman_path: String = ""
var saved_prop_path: String = ""
for value: Variant in objects:
if not value is Dictionary:
continue
var entry: Dictionary = value as Dictionary
if String(entry.get("type", "")) == "stickman":
saved_stickman_path = String(entry.get("stk_path", ""))
elif String(entry.get("type", "")) == "prop":
saved_prop_path = String(entry.get("asset_id", ""))
_expect(saved_stickman_path == "res://content/stickmen/test.stk", "resaved stickman reference uses the canonical path")
_expect(saved_prop_path == "res://content/props/briefcase.prop", "resaved prop reference uses the canonical path")
_expect(bool(STAGE_SCENE_IO.write_file_safe(RESAVED_STAGE_PATH, scene_data).get("ok", false)), "canonical stage document resaves")
var reread: Dictionary = STAGE_SCENE_IO.read_file(RESAVED_STAGE_PATH)
_expect(bool(reread.get("ok", false)), "resaved stage document reads successfully")
var current_path: String = String(stage.get("_current_scene_path"))
_expect(current_path == LEGACY_STAGE_PATH, "unmanaged stage document path remains unchanged")
stage.queue_free()
await process_frame
func _cleanup() -> void:
for path: String in [LEGACY_STAGE_PATH, RESAVED_STAGE_PATH]:
if FileAccess.file_exists(path):
DirAccess.remove_absolute(ProjectSettings.globalize_path(path))