Godotã®ã€ã³ããŒãã¹ã¯ãªããã§ã³ãªãžã§ã³ãèªåèšå®ããããã«ãBlenderåŽã§ãæ±ããããããããã®Blenderã¹ã¯ãªããã
Pythonimport bpy
from bpy.app.handlers import persistent
# ð¡ïž ãã³ãã©é¢æ°ã®å®çŸ©
@persistent
def auto_setup_collision_viz(scene):
"""
ã·ãŒã³ã®æŽæ°ãç£èŠããŠã-colé
äžã®ã¡ãã·ã¥ãèªåã§ã¯ã€ã€ãŒè¡šç€ºã«ãã ðµïž
"""
# ã·ãŒã³å
ã®å
šãªããžã§ã¯ããã«ãŒãããŠæ¡ä»¶ãã§ãã¯
for obj in bpy.data.objects:
# 芪ãEmptyã§ããããã€ååã« "-col" ãå«ãŸããŠãããç¢ºèª ðŠ
if obj.parent and obj.parent.type == 'EMPTY' and obj.parent.name.endswith("-col"):
# ã¡ãã·ã¥ãªããžã§ã¯ãã®ã¿å¯Ÿè±¡ ð
if obj.type == 'MESH':
# æ¢ã«èšå®æžã¿ãªãã¹ãããããŠè² è·ãè»œæž â¡
if obj.display_type != 'WIRE' or not obj.show_in_front:
obj.display_type = 'WIRE'
obj.show_in_front = True
print(f"âš [Auto] {obj.name} ãã³ãªãžã§ã³è¡šç€ºã«åãæ¿ããŸãã ð§")
# ð ãã³ãã©ã®ç»é²è§£é€ïŒäºéç»é²ãé²ãïŒ
def register():
if auto_setup_collision_viz not in bpy.app.handlers.depsgraph_update_post:
bpy.app.handlers.depsgraph_update_post.append(auto_setup_collision_viz)
print("ð ã³ãªãžã§ã³ç£èŠãã³ãã©ãç»é²ããŸããïŒ")
def unregister():
if auto_setup_collision_viz in bpy.app.handlers.depsgraph_update_post:
bpy.app.handlers.depsgraph_update_post.remove(auto_setup_collision_viz)
print("ð ã³ãªãžã§ã³ç£èŠãã³ãã©ãè§£é€ããŸããã")
# ð å®è¡
if __name__ == "__main__":
register()
åºæ¬çã«ã¯Blenderã§ã¯æç»ãå€ããã ãã§ç¹ã«äœãããããã§ããªãã
ããã§ç·šéäžã«äœãã³ãªãžã§ã³ã§äœãæç»ãããã®ãèŠãç®ã§å€æã§ããã®ã§å¶äœã®éªéã«ãªããªãã
äœ¿ãæ¹ãšæ³šæç¹
- ç»é²æ¹æ³: Blenderã®ãText Editorãã«ãã®ã³ãŒãã貌ãä»ãããRun Scriptããäžåã ãæŒãã
- åäœ:
- ã¡ãã·ã¥ã
-col ãšããååã®Emptyã®åã«ããç¬éã«ã¯ã€ã€ãŒè¡šç€ºã«ãªãã
- éã«ãæ®éã®Emptyã®ååãåŸãã
-col ã«å€æŽããŠããå³åº§ã«äžèº«ãã¯ã€ã€ãŒåãããã
- ä¿å: ãã®ã¹ã¯ãªãããå«ãŸãã
.blend ãã¡ã€ã«ãä¿åããæ¬¡åéããæã«ãèªåã§æå¹ã«ãããå Žåãããã¹ããšãã£ã¿ã®ã¡ãã¥ãŒãã Text > RegisterïŒç»é²ïŒ ã«ãã§ãã¯ãå
¥ããã
次ã«Godotã®ã€ã³ããŒãã¹ã¯ãªããã
GDScript# ð ïž ã«ã¹ã¿ã ã»ãã¬ã³ããŒã»ã€ã³ããŒã¿ãŒ
# 衚瀺ãªããžã§ã¯ããç¶æãã€ã€ãã³ãªãžã§ã³ãèªåæ§æããŸã
@tool
extends EditorScenePostImport
func _post_import(scene: Node) -> Object:
_iterate_nodes(scene, scene)
return scene
func _iterate_nodes(node: Node, root: Node):
if node == null:
return
# ð ååã "-col" ã§çµããããŒããæ€çŽ¢
if node is Node3D and node.name.ends_with("-col"):
_process_custom_collision(node, root)
# 倿åŸã¯ãã®æã®èµ°æ»ãçµããïŒå
éšã§åæ§ç¯ãããããïŒ
return
for child in node.get_children():
_iterate_nodes(child, root)
func _process_custom_collision(source_node: Node3D, root: Node):
var parent = source_node.get_parent()
if not parent:
return
# ðŠ 1. æ°ãã StaticBody3D ãäœæïŒããã衚瀺ãšç©çã®èŠªã«ãªãïŒ
var static_body = StaticBody3D.new()
static_body.name = source_node.name.replace("-col", "")
static_body.transform = source_node.transform
parent.add_child(static_body)
static_body.owner = root
print("âš [CustomImport] ç©çã»è¡šç€ºçµ±åããŒããçæ: ", static_body.name)
# ð 2. åããŒãïŒã¡ãã·ã¥çïŒã®åŠç
for child in source_node.get_children():
# ç©çåœ¢ç¶ (CollisionShape3D) ã®çæ
if child is MeshInstance3D:
var mesh = child.get_mesh()
if mesh:
# ã³ãªãžã§ã³åœ¢ç¶ã®äœæ
var col_shape = CollisionShape3D.new()
col_shape.shape = mesh.create_convex_shape()
col_shape.transform = child.transform
col_shape.name = "Collision_" + child.name
static_body.add_child(col_shape)
col_shape.owner = root
child.get_parent().remove_child(child)
print(" â
ç©çãšè¡šç€ºãã»ããããŸãã: ", child.name)
# ðïž 3. 圹å²ãçµããå
ã® Empty ã®ã¿ãåé€
source_node.queue_free()
Godotã«ã¯Emptyãèªåçã«ã³ãªãžã§ã³åœ¢ç¶ãšããŠæ±ãæ©èœãããã¯ããªãã ãã©ãã ãã¶åããå®å
šã«æ»ãã§ãã£ãœãã®ã§ãç¹å®ã®Emptyã®åããã¹ãŠã³ãªãžã§ã³åœ¢ç¶ãšããŠæ±ãã¹ã¯ãªãããšããã
泚æ
- ã³ãªãžã§ã³åœ¢ç¶ãã¡ãã·ã¥ãã®ãŸãŸã䜿ãã®ã§ãè€éãªåœ¢ç¶ã¯éããªãã
- StaticBody3Dããæ±ããªãããã«ããŠãã®ã§ãRigidBody3DãArea3Dãªã©ã®ä»ã®åã¯å¥é工倫ããå¿
èŠãããã
å人çã«ã¯ã»ãŒå°åœ¢ã«ãã䜿ããªãã€ãããªã®ã§ãäžæŠããã§é²ããã