2V2-e.5b: feed native map height and light into game render

This commit is contained in:
shenlei
2026-09-23 22:10:29 +09:00
parent 702fef7b47
commit 5a1df57e69
13 changed files with 678 additions and 76 deletions
+47 -11
View File
@@ -109,9 +109,17 @@ func run() -> void:
report["unlit_stand_in_count"] = world.unlit_stand_in_count
report["terrain"] = world.terrain_report
report["atlas_entries"] = world._atlas.size()
_check(world._atlas.size() > 0, "40250 AtlasInfo chooses the current map")
_check(not Metin2PythonHost.current_map_name().is_empty(), "native AtlasInfo chooses the current map")
if world.terrain:
report["terrain_base_cm"] = str(world.terrain.call("get_map_base_cm"))
report["native_map_name"] = Metin2PythonHost.current_map_name()
_check(world.map_path == Metin2PythonHost.current_map_name(), "terrain uses native Warp map")
var first_draws: Array = Metin2PythonHost.render3d_draws()
if not first_draws.is_empty():
var camera_world: Vector3 = world.d3d_transform(first_draws[0]["view"]).affine_inverse().origin
report["camera_world_cm"] = str(camera_world)
report["terrain_height_at_camera_cm"] = float(world.terrain.call("sample_height",
camera_world.x / 100.0, -camera_world.y / 100.0)) * 100.0
var tile_bounds := []
for tile in world.terrain.find_children("Terrain*", "MeshInstance3D", true, false):
if tile_bounds.size() >= 4:
@@ -130,6 +138,33 @@ func run() -> void:
report["camera_far"] = world.camera.far
var textures := []
var draws: Array = Metin2PythonHost.render3d_draws()
var native_lit_draws := 0
var view_finite := true
var actor_foot_cm := INF
var foot_xy := Vector2.ZERO
for draw in draws:
if draw["light0"]:
native_lit_draws += 1
for value in draw["view"]:
if not is_finite(value):
view_finite = false
var world_xform: Transform3D = world.d3d_transform(draw["world"])
for vertex in draw["positions"]:
var p: Vector3 = world_xform * vertex
if p.z < actor_foot_cm:
actor_foot_cm = p.z
foot_xy = Vector2(p.x, -p.y)
report["native_lit_draws"] = native_lit_draws
report["view_finite"] = view_finite
_check(view_finite, "native camera view stays finite")
if world.terrain and not is_inf(actor_foot_cm):
var ground_cm := float(world.terrain.call("sample_height", foot_xy.x / 100.0, foot_xy.y / 100.0)) * 100.0
report["actor_foot_cm"] = actor_foot_cm
report["ground_at_foot_cm"] = ground_cm
_check(absf(actor_foot_cm - ground_cm) < 120.0,
"native actor feet meet map height (delta %.1f cm)" % absf(actor_foot_cm - ground_cm))
_check(not drawn or native_lit_draws == draws.size(),
"native RenderGame light0 comes from map .msenv (%d/%d)" % [native_lit_draws, draws.size()])
if not draws.is_empty():
report["proj"] = Array(draws[0]["proj"])
report["view"] = Array(draws[0]["view"])
@@ -193,18 +228,19 @@ func run() -> void:
lit += 1
report["centre_lit_samples"] = lit
_check(lit > 50, "character pixels in the middle of the screen (%d samples)" % lit)
var ground_low := 1.0
var ground_high := 0.0
for y in range(image.get_height() * 3 / 4, image.get_height() - 20, 17):
for x in range(30, image.get_width() - 30, 23):
var luminance := image.get_pixel(x, y).get_luminance()
ground_low = minf(ground_low, luminance)
ground_high = maxf(ground_high, luminance)
report["ground_luminance_range"] = ground_high - ground_low
_check(ground_high - ground_low > 0.08, "textured ground visible in screenshot")
# The 3D pass alone, for looking at the character without the UI.
ui.visible = false
await RenderingServer.frame_post_draw
root.get_texture().get_image().save_png(output.path_join("game_3d.png"))
var game_image := root.get_texture().get_image()
game_image.save_png(output.path_join("game_3d.png"))
var textured_pairs := 0
for y in range(game_image.get_height() * 3 / 4, game_image.get_height() - 20, 13):
for x in range(30, game_image.get_width() - 35, 17):
var left := game_image.get_pixel(x, y).get_luminance()
var right := game_image.get_pixel(x + 5, y).get_luminance()
if absf(left - right) > 0.04:
textured_pairs += 1
report["ground_texture_pairs"] = textured_pairs
_check(textured_pairs > 20, "textured ground visible in screenshot (%d local contrasts)" % textured_pairs)
ui.visible = true
await _finish(output, report)