extends SceneTree ## Dev tool: a skin's RAW import beside the same model with the game's character ## treatment, under identical lighting — the reference shot for tuning ## LevelMaterials.apply_character_look() against the model's source render. ## godot --path . --windowed --resolution 1280x720 \ ## -s res://debug/character_look_capture.gd -- [res-path-to-glb] ## Saves look_head.png and look_body.png (left = raw import, right = ours). const DEFAULT_GLB := "res://assets/characters/skins/taila.glb" var _frames := 0 var _out_dir := "." var _glb_path := DEFAULT_GLB var _cam: Camera3D = null func _initialize() -> void: var args := OS.get_cmdline_user_args() if args.size() > 0: _out_dir = args[0] if args.size() > 1: _glb_path = args[1] var scene := Node3D.new() root.add_child(scene) current_scene = scene # Neutral studio light, matched to the game's tonemap so colours compare. var env := WorldEnvironment.new() var e := Environment.new() e.background_mode = Environment.BG_COLOR e.background_color = Color(0.30, 0.32, 0.38) e.ambient_light_source = Environment.AMBIENT_SOURCE_COLOR e.ambient_light_color = Color(0.85, 0.87, 0.95) e.ambient_light_energy = 1.1 e.tonemap_mode = Environment.TONE_MAPPER_FILMIC e.tonemap_white = 2.4 env.environment = e scene.add_child(env) var sun := DirectionalLight3D.new() sun.rotation_degrees = Vector3(-38, 28, 0) sun.light_energy = 2.0 scene.add_child(sun) var raw := GLBLoader.load(_glb_path) if not raw: printerr("character_look_capture: could not load ", _glb_path) quit(1) return raw.position = Vector3(-0.45, 0, 0) scene.add_child(raw) var ours := GLBLoader.load(_glb_path) ours.position = Vector3(0.45, 0, 0) scene.add_child(ours) LevelMaterials.apply_toon_recursive(ours) LevelMaterials.apply_character_look(ours) _cam = Camera3D.new() scene.add_child(_cam) func _process(_delta: float) -> bool: _frames += 1 if _frames < 30: return false if _frames == 30: _look(Vector3(0, 1.42, 1.05), Vector3(0, 1.38, 0)) return false if _frames == 32: _snap("look_head") _look(Vector3(0, 1.15, 2.2), Vector3(0, 0.95, 0)) return false if _frames == 34: _snap("look_body") return true return false func _look(pos: Vector3, at: Vector3) -> void: _cam.global_position = pos _cam.look_at(at, Vector3.UP) func _snap(tag: String) -> void: var img := root.get_viewport().get_texture().get_image() img.save_png(_out_dir + "/" + tag + ".png") print("character_look_capture: saved ", tag)