110 lines
4.1 KiB
GDScript
110 lines
4.1 KiB
GDScript
extends SceneTree
|
|
## Regression test for world chunk alignment and ground positioning.
|
|
|
|
var _passed: int = 0
|
|
var _failed: int = 0
|
|
|
|
|
|
func _check(label: String, condition: bool) -> void:
|
|
if condition:
|
|
print(" PASS: %s" % label)
|
|
_passed += 1
|
|
else:
|
|
printerr(" FAIL: %s" % label)
|
|
_failed += 1
|
|
|
|
|
|
func _init() -> void:
|
|
call_deferred("_run_tests")
|
|
|
|
|
|
func _run_tests() -> void:
|
|
print("--- World Chunk & Ground Alignment Test ---")
|
|
await process_frame
|
|
|
|
var packed: PackedScene = load("res://scenes/game.tscn")
|
|
var result := change_scene_to_packed(packed)
|
|
if result != OK:
|
|
printerr("SMOKE: failed to change scene, error ", result)
|
|
quit(1)
|
|
return
|
|
|
|
await scene_changed
|
|
var game: Node3D = current_scene as Node3D
|
|
_check("game scene ready", game != null)
|
|
|
|
# Initially, ground is at default test level position (0, -0.5, 0)
|
|
var ground: StaticBody3D = game.get_node_or_null("Level/Ground") as StaticBody3D
|
|
_check("Ground initially exists", ground != null)
|
|
_check("Ground initially at (0, -0.5, 0)", ground.position.is_equal_approx(Vector3(0, -0.5, 0)))
|
|
|
|
# Create a ChunkScene for chunk (0, 0, 0) with corner objects
|
|
var chunk_scene := ChunkScene.new()
|
|
chunk_scene.coord = Vector3i(0, 0, 0)
|
|
chunk_scene.name = "chunk_0_0_0"
|
|
game.add_child(chunk_scene)
|
|
|
|
# Add lamp post at corner (0.5, 0.5) and corner (31.5, 31.5)
|
|
var obj_corner1 := WorldObject.new()
|
|
obj_corner1.id = "lamp1"
|
|
obj_corner1.type = "prop"
|
|
obj_corner1.position = Vector3(0.5, 0.5, 0.0)
|
|
obj_corner1.properties = {"catalog_id": "lamp_post_01"}
|
|
chunk_scene.add_object(obj_corner1)
|
|
|
|
var obj_corner2 := WorldObject.new()
|
|
obj_corner2.id = "lamp2"
|
|
obj_corner2.type = "prop"
|
|
obj_corner2.position = Vector3(31.5, 31.5, 0.0)
|
|
obj_corner2.properties = {"catalog_id": "lamp_post_01"}
|
|
chunk_scene.add_object(obj_corner2)
|
|
|
|
# Trigger _on_chunk_loaded
|
|
game.call("_on_chunk_loaded", Vector3i(0, 0, 0), chunk_scene)
|
|
|
|
# Verify Ground has moved to center of chunk: (16.0, -0.5, 16.0)
|
|
_check("Ground moved to chunk center (16, -0.5, 16)", ground.position.is_equal_approx(Vector3(16.0, -0.5, 16.0)))
|
|
|
|
var shape_node := ground.find_child("CollisionShape3D", true, false) as CollisionShape3D
|
|
_check("Ground CollisionShape3D size >= 40x40", shape_node != null and (shape_node.shape as BoxShape3D).size.x >= 40.0 and (shape_node.shape as BoxShape3D).size.z >= 40.0)
|
|
|
|
var mesh_node := ground.find_child("MeshInstance3D", true, false) as MeshInstance3D
|
|
_check("Ground MeshInstance3D size >= 40x40", mesh_node != null and (mesh_node.mesh as BoxMesh).size.x >= 40.0 and (mesh_node.mesh as BoxMesh).size.z >= 40.0)
|
|
|
|
# Verify corners are inside ground bounds
|
|
var half_x: float = (shape_node.shape as BoxShape3D).size.x * 0.5
|
|
var half_z: float = (shape_node.shape as BoxShape3D).size.z * 0.5
|
|
var min_gx: float = ground.position.x - half_x
|
|
var max_gx: float = ground.position.x + half_x
|
|
var min_gz: float = ground.position.z - half_z
|
|
var max_gz: float = ground.position.z + half_z
|
|
|
|
_check("Corner (0.5, 0.5) is on ground", 0.5 >= min_gx and 0.5 <= max_gx and 0.5 >= min_gz and 0.5 <= max_gz)
|
|
_check("Corner (31.5, 31.5) is on ground", 31.5 >= min_gx and 31.5 <= max_gx and 31.5 >= min_gz and 31.5 <= max_gz)
|
|
|
|
# Verify PlayerSpawn defaulted to chunk center (16, 1.5, 16)
|
|
var spawn_marker := game.get_node_or_null("Level/PlayerSpawn") as Node3D
|
|
_check("PlayerSpawn marker is at (16, 1.5, 16)", spawn_marker != null and spawn_marker.global_position.is_equal_approx(Vector3(16.0, 1.5, 16.0)))
|
|
|
|
# Now test placed spawn_point object
|
|
var chunk_scene2 := ChunkScene.new()
|
|
chunk_scene2.coord = Vector3i(0, 0, 0)
|
|
chunk_scene2.name = "chunk_with_spawn"
|
|
game.add_child(chunk_scene2)
|
|
|
|
var spawn_obj := WorldObject.new()
|
|
spawn_obj.id = "spawn1"
|
|
spawn_obj.type = "spawn_point"
|
|
spawn_obj.position = Vector3(8.5, 12.5, 0.0)
|
|
spawn_obj.properties = {"catalog_id": "spawn_point"}
|
|
chunk_scene2.add_object(spawn_obj)
|
|
|
|
game.call("_on_chunk_loaded", Vector3i(0, 0, 0), chunk_scene2)
|
|
_check("PlayerSpawn moved to placed spawn_point at (8.5, 1.5, 12.5)", spawn_marker != null and spawn_marker.global_position.is_equal_approx(Vector3(8.5, 1.5, 12.5)))
|
|
|
|
print("\n=== SMOKE RESULT: %d/%d passed ===" % [_passed, _passed + _failed])
|
|
if _failed > 0:
|
|
quit(1)
|
|
else:
|
|
quit(0)
|