Release v0.1.3 2026-07-11
This commit is contained in:
@@ -0,0 +1,68 @@
|
||||
"""Print rig and mesh details for the locally-authored inspired creature models."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import json
|
||||
from pathlib import Path
|
||||
import subprocess
|
||||
import tempfile
|
||||
|
||||
import bpy
|
||||
from mathutils import Vector
|
||||
|
||||
|
||||
ROOT = Path(__file__).resolve().parents[2]
|
||||
MODEL_ROOT = ROOT / "game_assets/models/downloaded/yugioh"
|
||||
|
||||
|
||||
def reset_scene() -> None:
|
||||
if bpy.context.object and bpy.context.object.mode != "OBJECT":
|
||||
bpy.ops.object.mode_set(mode="OBJECT")
|
||||
bpy.ops.object.select_all(action="SELECT")
|
||||
bpy.ops.object.delete(use_global=False)
|
||||
|
||||
|
||||
def inspect_model(path: Path) -> dict[str, object]:
|
||||
reset_scene()
|
||||
source_path = path.with_suffix(".smd")
|
||||
with tempfile.TemporaryDirectory(prefix="thor-yugioh-inspect-") as temp_dir:
|
||||
converted_path = Path(temp_dir) / "model.glb"
|
||||
subprocess.run(
|
||||
["assimp", "export", str(source_path), str(converted_path), "-f", "glb2"],
|
||||
check=True,
|
||||
capture_output=True,
|
||||
text=True,
|
||||
)
|
||||
bpy.ops.import_scene.gltf(filepath=str(converted_path))
|
||||
armatures = [obj for obj in bpy.context.scene.objects if obj.type == "ARMATURE"]
|
||||
meshes = [obj for obj in bpy.context.scene.objects if obj.type == "MESH"]
|
||||
bounds = []
|
||||
for mesh in meshes:
|
||||
bounds.extend(mesh.matrix_world @ Vector(corner) for corner in mesh.bound_box)
|
||||
return {
|
||||
"asset": path.parent.name,
|
||||
"source": source_path.name,
|
||||
"armatures": [
|
||||
{
|
||||
"name": rig.name,
|
||||
"bones": [bone.name for bone in rig.data.bones],
|
||||
"actions": [action.name for action in bpy.data.actions],
|
||||
}
|
||||
for rig in armatures
|
||||
],
|
||||
"meshes": [mesh.name for mesh in meshes],
|
||||
"materials": sorted({slot.material.name for mesh in meshes for slot in mesh.material_slots if slot.material}),
|
||||
"bounds": {
|
||||
"min": [round(min(point[index] for point in bounds), 4) for index in range(3)],
|
||||
"max": [round(max(point[index] for point in bounds), 4) for index in range(3)],
|
||||
} if bounds else None,
|
||||
}
|
||||
|
||||
|
||||
def main() -> None:
|
||||
report = [inspect_model(path) for path in sorted(MODEL_ROOT.glob("*/MMD_*.fbx"))]
|
||||
print("YUGIOH_MODEL_REPORT=" + json.dumps(report, indent=2))
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
Reference in New Issue
Block a user