farming-simulator/scripts/util/inspect_models.gd

84 lines
2.7 KiB
GDScript3
Raw Normal View History

fix: реальные расчёты scale через AABB-инспекцию Написал scripts/util/inspect_models.gd — runtime-инструмент. Запустил через --headless --script, получил РЕАЛЬНЫЕ размеры: ХАРАКТЕРЫ (mini-characters): - Все male: 0.77×0.67-0.79×0.34 м (Ш×В×Г), T-pose шириной 0.77м - Pivot near center (offset 0.0005м) - 32 анимации, ВКЛЮЧАЯ «idle», «walk», «sit», «static» ФУРНИТУРА (выборка): - bedSingle: 1.62×0.51×1.89м (реалистичный single bed) - desk: 0.73×0.38×0.56м (мелко, нужно scale ~2.0) - chairDesk: 0.48×0.42×0.44м (мелко, нужно ~2.0-2.5) - kitchenFridgeLarge: 0.79×1.32×0.39м (нормально) РАСЧЁТЫ ОТЦА: - Цель: рост ~1.7м (взрослый отец) - Базовая высота 0.722м → scale = 1.7/0.722 = 2.35 - В T-pose ширина 1.8м (огромный) — НО idle-поза узкая, ~0.7м - Поэтому КРИТИЧНО запустить idle, не T-pose ФИКСЫ: 1. Father scale 2.35 (рост 1.7м, нормальный взрослый) 2. _start_father_idle через call_deferred — glb children могут быть не готовы в _ready, deferred ждёт следующий кадр 3. Animation list = 32 шт. Алгоритм: - Ищет первую анимацию содержащую «idle» (нижний регистр) - Если нет — играет первую в списке (fallback) - Print имя анимации для debug 4. Position x=1.6 (чуть дальше от двери при scale 2.35) ОСТАЁТСЯ ПРОВЕРИТЬ: - Реально ли запустилась idle (увидим по позе — руки опущены или раскинуты T-pose) - Возможно scale 2.35 слишком много с idle — иногда мини-чары выглядят пухло - Furniture scales — TODO следующим коммитом если попросишь Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-24 20:34:06 +03:00
extends SceneTree
func _init() -> void:
var paths_to_check: Array[String] = [
# Mini characters (для отца + других NPC)
"res://assets/models/characters/character-male-a.glb",
"res://assets/models/characters/character-male-b.glb",
"res://assets/models/characters/character-male-c.glb",
"res://assets/models/characters/character-male-d.glb",
"res://assets/models/characters/character-male-e.glb",
"res://assets/models/characters/character-male-f.glb",
"res://assets/models/characters/character-female-a.glb",
# Furniture
"res://assets/models/furniture/bedSingle.glb",
"res://assets/models/furniture/desk.glb",
"res://assets/models/furniture/chairDesk.glb",
"res://assets/models/furniture/chair.glb",
"res://assets/models/furniture/computerScreen.glb",
"res://assets/models/furniture/computerKeyboard.glb",
"res://assets/models/furniture/bookcaseClosedDoors.glb",
"res://assets/models/furniture/cardboardBoxClosed.glb",
"res://assets/models/furniture/kitchenFridgeLarge.glb",
"res://assets/models/furniture/kitchenStove.glb",
"res://assets/models/furniture/kitchenSink.glb",
"res://assets/models/furniture/table.glb",
]
print("=== MODEL INSPECTION ===")
for path in paths_to_check:
var scene: PackedScene = load(path)
if scene == null:
print("FAIL load: %s" % path)
continue
var instance: Node = scene.instantiate()
if instance == null:
print("FAIL instantiate: %s" % path)
continue
var aabb: AABB = _get_total_aabb(instance)
print("--- %s ---" % path.get_file())
print(" size: x=%.3f y=%.3f z=%.3f" % [aabb.size.x, aabb.size.y, aabb.size.z])
print(" pos: x=%.3f y=%.3f z=%.3f" % [aabb.position.x, aabb.position.y, aabb.position.z])
var ap: AnimationPlayer = _find_anim_player(instance)
if ap != null:
var anims: PackedStringArray = ap.get_animation_list()
print(" animations (%d total):" % anims.size())
for name in anims:
print(" - %s" % name)
instance.queue_free()
print("=== END ===")
quit()
func _find_anim_player(node: Node) -> AnimationPlayer:
if node is AnimationPlayer:
return node as AnimationPlayer
for child in node.get_children():
var found: AnimationPlayer = _find_anim_player(child)
if found != null:
return found
return null
func _get_total_aabb(node: Node) -> AABB:
var bounds: AABB = AABB()
var first: bool = true
for mesh_node in _find_all_meshes(node):
var aabb: AABB = mesh_node.get_aabb()
if first:
bounds = aabb
first = false
else:
bounds = bounds.merge(aabb)
return bounds
func _find_all_meshes(node: Node) -> Array:
var result: Array = []
if node is MeshInstance3D:
result.append(node)
for child in node.get_children():
result.append_array(_find_all_meshes(child))
return result