OSDN Git Service

add pymeshio.
[meshio/meshio.git] / swig / blender / pmd_import.py
index 192e995..5ef212f 100755 (executable)
@@ -7,7 +7,7 @@
  Tooltip: 'Import PMD file for MikuMikuDance.'
 """
 __author__= ["ousttrue"]
-__version__= "1.8"
+__version__= "2.0"
 __url__=()
 __bpydoc__="""
 pmd Importer
@@ -31,10 +31,28 @@ This script imports a pmd into Blender for editing.
 1.6 20100629: sphere map.
 1.7 20100703: implement bone group.
 1.8 20100710: implement toon texture.
+1.9 20100718: keep model name, comment.
+2.0 20100724: update for Blender2.53.
+2.1 20100731: add full python module.
 """
+bl_addon_info = {
+        'category': 'Import/Export',
+        'name': 'Import: MikuMikuDance Model Format (.pmd)',
+        'author': 'ousttrue',
+        'version': '2.0',
+        'blender': (2, 5, 3),
+        'location': 'File > Import',
+        'description': 'Import from the MikuMikuDance Model Format (.pmd)',
+        'warning': '', # used for warning icon and text in addons panel
+        'wiki_url': 'http://sourceforge.jp/projects/meshio/wiki/FrontPage',
+        }
 
 MMD_SHAPE_GROUP_NAME='_MMD_SHAPE'
+MMD_MB_NAME='mb_name'
+MMD_MB_COMMENT='mb_comment'
+MMD_COMMENT='comment'
 BASE_SHAPE_NAME='Basis'
+RIGID_NAME='rigid_name'
 RIGID_SHAPE_TYPE='rigid_shape_type'
 RIGID_PROCESS_TYPE='rigid_process_type'
 RIGID_BONE_NAME='rigid_bone_name'
@@ -55,6 +73,7 @@ CONSTRAINT_ROT_MIN='const_rot_min'
 CONSTRAINT_ROT_MAX='const_rot_max'
 CONSTRAINT_SPRING_POS='const_spring_pos'
 CONSTRAINT_SPRING_ROT='const_spring_rot'
+TOON_TEXTURE_OBJECT='ToonTextures'
 
 
 ###############################################################################
@@ -64,8 +83,14 @@ import os
 import sys
 import math
 
-# C extension
-from meshio import pmd, englishmap
+try:
+    # C extension
+    from meshio import pmd, englishmap
+except ImportError:
+    # full python
+    from pymeshio import englishmap
+    from pymeshio import mmd as pmd
+    pmd.IO=pmd.PMDLoader
 
 def isBlender24():
     return sys.version_info[0]<3
@@ -121,7 +146,6 @@ if isBlender24():
 else:
     # for 2.5
     import bpy
-    from bpy.props import *
     import mathutils
 
     # wrapper
@@ -207,8 +231,8 @@ def get_group_name(g):
 
 
 def __importToonTextures(io, tex_dir):
-    mesh, meshObject=bl.mesh.create('ToonTextures')
-    material=bl.material.create('ToonTextures')
+    mesh, meshObject=bl.mesh.create(TOON_TEXTURE_OBJECT)
+    material=bl.material.create(TOON_TEXTURE_OBJECT)
     bl.mesh.addMaterial(mesh, material)
     for i in range(10):
         t=io.getToonTexture(i)
@@ -326,6 +350,7 @@ def __build(armature, b, p, parent):
     bone=bl.armature.createBone(armature, name)
 
     if parent and (b.tail_index==0 or b.type==6 or b.type==7 or b.type==9):
+        # 先端ボーン
         bone.head = bl.createVector(*convert_coord(b.pos))
         bone.tail=bone.head+bl.createVector(0, 1, 0)
         bone.parent=parent
@@ -445,14 +470,8 @@ def __import16MaerialAndMesh(meshObject, l,
             break
 
         material=createPmdMaterial(m, material_index)
-        toon_index=bl.material.addTexture(
-                material, 
-                bl.material.getTexture(
-                    toon_material, 
-                    0 if m.toon_index==0xFF else m.toon_index
-                    ),
-                False)
 
+        # main texture
         texture_name=m.getTexture()
         if texture_name!='':
             for i, t in enumerate(texture_name.split('*')):
@@ -471,7 +490,17 @@ def __import16MaerialAndMesh(meshObject, l,
                     # sphere map
                     setSphereMap(material, texture_index, 'ADD')
 
+        # toon texture
+        toon_index=bl.material.addTexture(
+                material, 
+                bl.material.getTexture(
+                    toon_material, 
+                    0 if m.toon_index==0xFF else m.toon_index
+                    ),
+                False)
+
         bl.mesh.addMaterial(mesh, material)
+
         index+=1
 
     ############################################################
@@ -680,10 +709,8 @@ def __importConstraints(io):
     print("create constraint")
     container=bl.object.createEmpty('Constraints')
     layer=[
-            True, False, False, False, False, False, False, False,
-            False, False, False, False, False, False, False, False,
-            False, False, False, False, False, False, False, False,
-            False, False, False, False, False, False, False, False,
+        True, False, False, False, False, False, False, False, False, False,
+        False, False, False, False, False, False, False, False, False, False,
             ]
     material=bl.material.create('constraint')
     material.diffuse_color=(1, 0, 0)
@@ -730,14 +757,12 @@ def __importRigidBodies(io):
 
     container=bl.object.createEmpty('RigidBodies')
     layer=[
-            True, False, False, False, False, False, False, False,
-            False, False, False, False, False, False, False, False,
-            False, False, False, False, False, False, False, False,
-            False, False, False, False, False, False, False, False,
+        True, False, False, False, False, False, False, False, False, False,
+        False, False, False, False, False, False, False, False, False, False,
             ]
     material=bl.material.create('rigidBody')
     rigidMeshes=[]
-    for rigid in io.rigidbodies:
+    for i, rigid in enumerate(io.rigidbodies):
         if rigid.boneIndex==0xFFFF:
             # no reference bone
             bone=io.bones[0]
@@ -773,7 +798,8 @@ def __importRigidBodies(io):
         mesh=bl.object.getData(meshObject)
         rigidMeshes.append(meshObject)
         bl.mesh.addMaterial(mesh, material)
-        meshObject.name=rigid.getName()
+        meshObject.name='r_%d' % i
+        meshObject[RIGID_NAME]=rigid.getName()
         #meshObject.draw_transparent=True
         #meshObject.draw_wire=True
         meshObject.max_draw_type='WIRE'
@@ -822,6 +848,9 @@ def _execute(filename):
     if len(model_name)==0:
         model_name=io.getName()
     root=bl.object.createEmpty(model_name)
+    root[MMD_MB_NAME]=io.getName()
+    root[MMD_MB_COMMENT]=io.getComment()
+    root[MMD_COMMENT]=io.getEnglishComment()
 
     # toon textures
     tex_dir=os.path.dirname(filename)
@@ -880,21 +909,13 @@ else:
 
         # List of operator properties, the attributes will be assigned
         # to the class instance from the operator settings before calling.
-
-        path = StringProperty(
-                name="File Path", 
-                description="File path used for importing the PMD file", 
-                maxlen= 1024, default= "")
-        filename = StringProperty(
-                name="File Name", 
-                description="Name of the file.")
-        directory = StringProperty(
-                name="Directory", 
-                description="Directory of the file.")
+        filepath = bpy.props.StringProperty()
+        filename = bpy.props.StringProperty()
+        directory = bpy.props.StringProperty()
 
         def execute(self, context):
             bl.initialize('pmd_import', context.scene)
-            _execute(self.properties.path)
+            _execute(self.properties.filepath)
             bl.finalize()
             return 'FINISHED'
 
@@ -906,7 +927,9 @@ else:
     # register menu
     def menu_func(self, context): 
         self.layout.operator(IMPORT_OT_pmd.bl_idname, 
-                text="MikuMikuDance model (.pmd)")
+                text="MikuMikuDance model (.pmd)",
+                icon='PLUGIN'
+                )
 
     def register():
         bpy.types.register(IMPORT_OT_pmd)