From b53e05a145458b59891a0fcdd09e1502424e2620 Mon Sep 17 00:00:00 2001 From: "Hermes (scopedvr-dev)" Date: Tue, 20 Oct 2026 08:07:15 +0000 Subject: [PATCH] T1 t_1cdc1a72: F5-Smoke-Test an neuen Lauf-Modus angepasst (PlaytestMode statt Client-Fehler) + Render-Probe-Script --- tests/probe_playtest_render.gd | 122 +++++++++++++++++++++++++++++ tests/probe_playtest_render.gd.uid | 1 + tests/test_gui_smoke.gd | 18 +++-- 3 files changed, 135 insertions(+), 6 deletions(-) create mode 100644 tests/probe_playtest_render.gd create mode 100644 tests/probe_playtest_render.gd.uid diff --git a/tests/probe_playtest_render.gd b/tests/probe_playtest_render.gd new file mode 100644 index 0000000..98190bb --- /dev/null +++ b/tests/probe_playtest_render.gd @@ -0,0 +1,122 @@ +extends SceneTree +## WEGWERF-Renderprobe (Karte t_1cdc1a72, Lauf-Modus im Map Builder selbst) — +## (a) Spieleraugen-Startansicht am Team-0-Spawnpunkt (Kisten voraus, HUD an) +## (b) Nach 8 m Gehen (60 × step 1/30 s) — Spieler bewegt, bleibt auf Terrain +## (c) Nach ESC: Editor-Panels wieder da, Spiel-Kamera weg, Status meldet +## Ausführen: +## xvfb-run -a godot4 --path . --rendering-driver opengl3 -s res://tests/probe_playtest_render.gd +## Wegwerf-Probe (nicht im Repo-Commit — Datei-Grenzen der Karte), Beweise nach +## /opt/data/scopedvr/work/t1cdc_beweise/. + +var main: Control +var subvp: SubViewport + +func _initialize() -> void: + _run.call_deferred() + +func _png(name: String) -> String: + return "/opt/data/scopedvr/work/t1cdc_beweise/" + name + +func _shot(name: String) -> void: + await process_frame + await process_frame + var img := subvp.get_texture().get_image() + img.save_png(_png(name)) + print("PROBE_PNG=%s (%dx%d)" % [_png(name), img.get_width(), img.get_height()]) + +func _find_subvp(node: Node) -> SubViewport: + if node is SubViewport: + return node as SubViewport + for c in node.get_children(): + var f := _find_subvp(c) + if f != null: + return f + return null + +func _press_key(code: Key) -> InputEventKey: + var key := InputEventKey.new() + key.keycode = code + key.physical_keycode = code + key.pressed = true + return key + +func _run() -> void: + DirAccess.make_dir_recursive_absolute("/opt/data/scopedvr/work/t1cdc_beweise") + var scene: PackedScene = load("res://scenes/main.tscn") + main = scene.instantiate() + root.add_child(main) + await process_frame + await process_frame + subvp = _find_subvp(main) + var container: SubViewportContainer = subvp.get_parent() + container.stretch = false + subvp.size = Vector2i(1600, 900) + await process_frame + + # Test-Szene: 1024er Map, 3 Kisten vor dem Spieler (Richtung -Z), + # Team-0-Spawn am Ursprung — der Spieler spawnt dort mit Blick auf die Kisten. + var doc: Dictionary = SvmapDocument.create_new("T1-Probe", 1024.0, "mittag") + doc["objects"] = [ + {"id": "crate_wood", "pos": [0.0, 0.0, -150.0], "scale": 1.0, "rot_y_deg": 0.0}, + {"id": "crate_wood", "pos": [-120.0, 0.0, -280.0], "scale": 1.0, "rot_y_deg": 0.0}, + {"id": "crate_wood", "pos": [150.0, 0.0, -320.0], "scale": 1.0, "rot_y_deg": 0.0}, + ] + doc["spawn_zones"] = {"0": {"points": [{"id": "spawn0", "pos": [0.0, 0.0, 0.0]}]}} + main.set("doc", doc) + main.call("_refresh_all") + await process_frame + await process_frame + + # --- (a) Lauf-Modus starten (F5-Route: _on_test_run) ---------------------- + main.call("_on_test_run") + await process_frame + await process_frame + var pt: Node = main.get("playtest") + print("ZAHLEN (a) playtest aktiv: ", pt != null, " | mode.active=", pt.get("active")) + var body: Node3D = pt.get("body") + print("ZAHLEN (a) Spawn: body.position=", body.position, + " | Terrainhöhe dort=", body.terrain_height(0.0, 0.0)) + print("ZAHLEN (a) yaw=", body.get("yaw_deg"), " pitch=", body.get("pitch_deg"), + " eye_height=", body.get("eye_height"), " radius=", body.get("radius")) + var look_cam: Camera3D = body.get("look_cam") + var editor_cam: Camera3D = main.get("camera") + print("ZAHLEN (a) Spiel-Kamera current=", look_cam.current, + " | Editor-Kamera current=", editor_cam.current) + print("ZAHLEN (a) Kiste (0,0.6,-150) im Frustum=", + look_cam.is_position_in_frustum(Vector3(0.0, 0.6, -150.0)), + " | Kiste (−120,0.6,−280) im Frustum=", + look_cam.is_position_in_frustum(Vector3(-120.0, 0.6, -280.0))) + var hp: Label = pt.get("hud_pos") + print("ZAHLEN (a) HUD: hud=", pt.get("hud") != null, " pos-text='", hp.text, "'") + print("ZAHLEN (a) Top-Bar sichtbar=", main.get("ui_top_bar").visible, + " links=", main.get("ui_left_panel").visible, + " rechts=", main.get("ui_right_panel").visible) + await _shot("t1_a_spieler_startansicht.png") + + # --- (b) 2 s Gehen (60 × step 1/30 s, fwd) — Bewegung + Terrainanpassung -- + var pos_vor: Vector3 = body.position + for i in 60: + body.call("step", 1.0 / 30.0, {"fwd": true, "back": false, "left": false, + "right": false, "run": false, "jump": false}) + var pos_nach: Vector3 = body.position + print("ZAHLEN (b) Position vor/nach 60 steps: ", pos_vor, " → ", pos_nach, + " (Δ=", pos_vor.distance_to(pos_nach), " m)") + print("ZAHLEN (b) on_floor=", body.get("on_floor"), + " y-nach=", pos_nach.y, + " Terrainhöhe dort=", body.terrain_height(pos_nach.x, pos_nach.z)) + await _shot("t1_b_spieler_gelaufen.png") + + # --- (c) ESC: zurück in den Editor ----------------------------------------- + main._unhandled_key_input(_press_key(KEY_ESCAPE)) + await process_frame + await process_frame + print("ZAHLEN (c) playtest nach ESC null=", main.get("playtest") == null) + print("ZAHLEN (c) Top-Bar sichtbar=", main.get("ui_top_bar").visible, + " links=", main.get("ui_left_panel").visible, + " rechts=", main.get("ui_right_panel").visible, + " Statusleiste=", main.get("ui_status_bar").visible) + print("ZAHLEN (c) Editor-Kamera current=", editor_cam.current) + print("ZAHLEN (c) Status: ", main.status_label.text) + await _shot("t1_c_editor_zurueck.png") + print("PROBE_FERTIG") + quit(0) diff --git a/tests/probe_playtest_render.gd.uid b/tests/probe_playtest_render.gd.uid new file mode 100644 index 0000000..8bcc49c --- /dev/null +++ b/tests/probe_playtest_render.gd.uid @@ -0,0 +1 @@ +uid://barv4phjmebje diff --git a/tests/test_gui_smoke.gd b/tests/test_gui_smoke.gd index 054b092..80df5cc 100644 --- a/tests/test_gui_smoke.gd +++ b/tests/test_gui_smoke.gd @@ -262,13 +262,19 @@ func _test_shortcuts_karte3() -> void: main._unhandled_key_input(_press_key(KEY_H, false)) _check(not main.help_overlay.visible, "H zweimal: Overlay wieder zu (Toggle)") - # --- F5: Karte testen (echter Flow existiert — hier läuft er in den - # „Client nicht gefunden“-Zweig, Hauptsache die Route ist verdrahtet) ----- + # --- F5: Karte testen (Karte t_1cdc1a72): startet den Lauf-Modus im + # Builder selbst — kein Client, kein Fehler-Dialog. ESC verlässt ihn + # sauber (Panels wieder sichtbar), danach geht der Test weiter. --------- main._unhandled_key_input(_press_key(KEY_F5, false)) - _check(str(main.status_label.text).contains("Karte testen"), - "F5: Karte-testen-Flow angesprungen (Statuszeile meldet)") - _check(main.error_dialog.visible, "F5: Fehler-Dialog im nicht-gefunden-Zweig geöffnet") - main.error_dialog.hide() + _check(str(main.status_label.text).contains("Testlauf läuft"), + "F5: Lauf-Modus gestartet (Statuszeile meldet)") + _check(not main.error_dialog.visible, + "F5: kein Fehler-Dialog (Lauf-Modus braucht keinen Client)") + _check(main.get("playtest") != null, "F5: PlaytestMode ist aktiv") + main._unhandled_key_input(_press_key(KEY_ESCAPE, false)) + _check(main.get("playtest") == null, "F5+ESC: Lauf-Modus sauber beendet") + _check(main.error_dialog == null or not main.error_dialog.visible, + "F5+ESC: kein Fehler-Dialog offen") # --- Dirty-Schutz: Strg+N bei ungespeicherten Änderungen FRAGT ZUERST ---- main.dirty = true