extends SceneTree ## Screenshot every UI screen, so the theme can be LOOKED at rather than ## asserted about. ## ## A theme is the one kind of change no headless check can validate: every ## contrast mistake, every panel that turns out to be invisible against the ## thing behind it, and every button whose label sits outside its own chip ## compiles perfectly. So this drives the real screens with rendering on and ## writes a PNG of each. ## ## godot --path . -s res://debug/ui_capture.gd -- ## ## Writes shot_menu.png, shot_pause.png, shot_character.png and ## shot_settings.png. var _frames := 0 var _out_dir := "." func _initialize() -> void: var args := OS.get_cmdline_user_args() if args.size() > 0: _out_dir = args[0] change_scene_to_file("res://ui/main_menu/main_menu.tscn") func _process(_delta: float) -> bool: _frames += 1 match _frames: 50: _shot("menu") # Into a real match. The pause menu deliberately refuses to open over # the main menu, and it is the in-game background — a lit 3D level # rather than a flat colour — that its legibility has to survive. var nm = root.get_node_or_null("NetworkManager") if nm and nm.has_method("start_singleplayer_match"): nm.start_singleplayer_match("Deathmatch") change_scene_to_file("res://scenes/maps/test_level/test_level.tscn") 200: _open("_show_main_menu") 215: _shot("pause") _open("_show_character") 320: # Long enough for the model to load and the springs to settle. _shot("character") _open("_show_settings") 340: _shot("settings") quit() return false func _open(screen: String) -> void: var menu = root.get_node_or_null("PauseMenu") if menu == null: push_warning("ui_capture: no PauseMenu autoload") return menu.visible = true menu.call(screen) func _shot(name: String) -> void: var img := root.get_texture().get_image() var path := "%s/shot_%s.png" % [_out_dir, name] img.save_png(path) print("wrote %s" % path)