tested export scripts with a large scene and resolved errors that came up as well...
authorCampbell Barton <ideasman42@gmail.com>
Thu, 11 Jan 2007 09:39:16 +0000 (09:39 +0000)
committerCampbell Barton <ideasman42@gmail.com>
Thu, 11 Jan 2007 09:39:16 +0000 (09:39 +0000)
release/scripts/3ds_export.py
release/scripts/bpymodules/BPyMesh.py
release/scripts/lightwave_export.py
release/scripts/nendo_export.py
release/scripts/object_cookie_cutter.py
release/scripts/xsi_export.py

index fb59ef0401e5fdf0ed235001ae25cbc9233eda49..28acaa567283ad53b17f2021a6b91467f1edaa8d 100644 (file)
@@ -887,16 +887,18 @@ def save_3ds(filename):
                        if data:
                                data.transform(mat)
                                mesh_objects.append((ob_derived, data))
-                               
+                               mat_ls = data.materials
+                               mat_ls_len = len(mat_ls)
                                # get material/image tuples.
                                if data.faceUV:
-                                       mat_ls = data.materials
-                                       
                                        if not mat_ls:
                                                mat = mat_name = None
                                        
                                        for f in data.faces:
                                                if mat_ls:
+                                                       mat_index = f.mat
+                                                       if mat_index >= mat_ls_len:
+                                                               mat_index = f.mat = 0
                                                        mat = mat_ls[f.mat]
                                                        if mat: mat_name = mat.name
                                                        else:   mat_name = None
@@ -914,12 +916,17 @@ def save_3ds(filename):
                                                        materialDict[mat_name, img_name]= mat, img
                                        
                                else:
-                                       for mat in data.materials:
+                                       for mat in mat_ls:
                                                if mat: # material may be None so check its not.
                                                        try:
                                                                materialDict[mat.name, None]
                                                        except:
                                                                materialDict[mat.name, None]= mat, None
+                                       
+                                       # Why 0 Why!
+                                       for f in data.faces:
+                                               if f.mat >= mat_ls_len:
+                                                       f.mat = 0 
        
        # Make material chunks for all materials used in the meshes:
        for mat_and_image in materialDict.itervalues():
index 763bdf9086a3d3115affa48831147a0c4f04be90..7eee04ecb350c918a69fdebe30302a820f7f727f 100644 (file)
@@ -300,7 +300,6 @@ def mesh2linkedFaces(me):
        return [fg for fg in face_groups if fg]
 
 
-
 def getFaceLoopEdges(faces, seams=[]):
        '''
        Takes me.faces or a list of faces and returns the edge loops
@@ -321,8 +320,7 @@ def getFaceLoopEdges(faces, seams=[]):
                if len(f) == 4:
                        edge_keys = f.edge_keys
                        for i, edkey in enumerate(f.edge_keys):
-                               try:    edges[edkey].append(edge_keys[OTHER_INDEX[i]])
-                               except: edges[edkey] =  [ edge_keys[OTHER_INDEX[i]] ]
+                               edges.setdefault(edkey, []).append(edge_keys[OTHER_INDEX[i]])
        
        for edkey in seams:
                edges[edkey] = []
@@ -1058,8 +1056,7 @@ def meshCalcNormals(me, vertNormals=None):
        for f in me.faces:
                f_v = f.v
                for edkey in f.edge_keys:
-                       try:    edges[edkey].append(f.no)
-                       except: edges[edkey]= [f.no]
+                       edges.setdefault(edkey, []).append(f.no)
        
        # Weight the edge normals by total angle difference
        for fnos in edges.itervalues():
index d3d7099594fc09c07190991bc32fb78527f14e66..f6760dafb11d5878ae0e75de6a7b2774ddce3f90 100644 (file)
@@ -98,15 +98,14 @@ def write(filename):
        meshdata = cStringIO.StringIO()
        layer_index = 0
        for object in objects:
+               if object.type != 'Mesh': continue
                objname = object.name
-               meshname = object.data.name
-               mesh = Blender.NMesh.GetRaw(meshname)
-               #mesh = Blender.NMesh.GetRawFromObject(meshname)        # for SubSurf
+               mesh = object.data
                obj = Blender.Object.Get(objname)
-               if not mesh: continue
-
+               
+               mesh.transform(obj.matrixWorld)
                layr = generate_layr(objname, layer_index)
-               pnts = generate_pnts(mesh, obj.matrix)
+               pnts = generate_pnts(mesh)
                bbox = generate_bbox(mesh)
                pols = generate_pols(mesh)
                ptag = generate_ptag(mesh, material_names)
@@ -180,44 +179,42 @@ def generate_nstring(string):
 def get_used_material_names(objects):
        matnames = {}
        for object in objects:
-               objname = object.name
-               meshname = object.data.name
-               mesh = Blender.NMesh.GetRaw(meshname)
-               if not mesh: continue
-               if (not mesh.materials) and (meshtools.has_vertex_colors(mesh)):
-                       # vcols only
-                       if meshtools.average_vcols:
-                               matnames["\251 Per-Vert Vertex Colors"] = None
+               if object.type == 'Mesh':
+                       mesh = object.getData(mesh=1)
+                       if (not mesh.materials) and (meshtools.has_vertex_colors(mesh)):
+                               # vcols only
+                               if meshtools.average_vcols:
+                                       matnames["\251 Per-Vert Vertex Colors"] = None
+                               else:
+                                       matnames["\251 Per-Face Vertex Colors"] = None
+                       elif (mesh.materials) and (not meshtools.has_vertex_colors(mesh)):
+                               # materials only
+                               for material in mesh.materials:
+                                       matnames[material.name] = None
+                       elif (not mesh.materials) and (not meshtools.has_vertex_colors(mesh)):
+                               # neither
+                               matnames["\251 Blender Default"] = None
                        else:
-                               matnames["\251 Per-Face Vertex Colors"] = None
-               elif (mesh.materials) and (not meshtools.has_vertex_colors(mesh)):
-                       # materials only
-                       for material in mesh.materials:
-                               matnames[material.name] = None
-               elif (not mesh.materials) and (not meshtools.has_vertex_colors(mesh)):
-                       # neither
-                       matnames["\251 Blender Default"] = None
-               else:
-                       # both
-                       for material in mesh.materials:
-                               matnames[material.name] = None
-       return matnames
+                               # both
+                               for material in mesh.materials:
+                                       matnames[material.name] = None
+       return matnames.keys()
 
 # =========================================
 # === Generate Tag Strings (TAGS Chunk) ===
 # =========================================
 def generate_tags(material_names):
-       material_names = map(generate_nstring, material_names.keys())
+       material_names = map(generate_nstring, material_names)
        tags_data = reduce(operator.add, material_names)
        return tags_data
 
 # ========================
 # === Generate Surface ===
 # ========================
-def generate_surface(name, mesh):
-       if name.find("\251 Per-") == 0:
-               return generate_vcol_surf(mesh)
-       elif name == "\251 Blender Default":
+def generate_surface(name):
+       #if name.find("\251 Per-") == 0:
+       #       return generate_vcol_surf(mesh)
+       if name == "\251 Blender Default":
                return generate_default_surf()
        else:
                return generate_surf(name)
@@ -226,10 +223,7 @@ def generate_surface(name, mesh):
 # === Generate Surfs ===
 # ======================
 def generate_surfs(material_names):
-       keys = material_names.keys()
-       values = material_names.values()
-       surfaces = map(generate_surface, keys, values)
-       return surfaces
+       return map(generate_surface, material_names)
 
 # ===================================
 # === Generate Layer (LAYR Chunk) ===
@@ -245,12 +239,12 @@ def generate_layr(name, idx):
 # ===================================
 # === Generate Verts (PNTS Chunk) ===
 # ===================================
-def generate_pnts(mesh, matrix):
+def generate_pnts(mesh):
        data = cStringIO.StringIO()
-       for i in range(len(mesh.verts)):
+       for i, v in enumerate(mesh.verts):
                if not i%100 and meshtools.show_progress:
                        Blender.Window.DrawProgressBar(float(i)/len(mesh.verts), "Writing Verts")
-               x, y, z = meshtools.apply_transform(mesh.verts[i].co, matrix)
+               x, y, z = v.co
                data.write(struct.pack(">fff", x, z, y))
        return data.getvalue()
 
@@ -260,10 +254,14 @@ def generate_pnts(mesh, matrix):
 def generate_bbox(mesh):
        data = cStringIO.StringIO()
        # need to transform verts here
-       nv = map(getattr, mesh.verts, ["co"]*len(mesh.verts))
-       xx = map(operator.getitem, nv, [0]*len(nv))
-       yy = map(operator.getitem, nv, [1]*len(nv))
-       zz = map(operator.getitem, nv, [2]*len(nv))
+       if mesh.verts:
+               nv = [v.co for v in mesh.verts]
+               xx = map(operator.getitem, nv, [0]*len(nv))
+               yy = map(operator.getitem, nv, [1]*len(nv))
+               zz = map(operator.getitem, nv, [2]*len(nv))
+       else:
+               xx = yy = zz = [0.0,]
+       
        data.write(struct.pack(">6f", min(xx), min(zz), min(yy), max(xx), max(zz), max(yy)))
        return data.getvalue()
 
@@ -274,22 +272,25 @@ def average_vertexcolors(mesh):
        vertexcolors = {}
        vcolor_add = lambda u, v: [u[0]+v[0], u[1]+v[1], u[2]+v[2], u[3]+v[3]]
        vcolor_div = lambda u, s: [u[0]/s, u[1]/s, u[2]/s, u[3]/s]
-       for i in range(len(mesh.faces)):        # get all vcolors that share this vertex
+       for i, f in enumerate(mesh.faces):      # get all vcolors that share this vertex
                if not i%100 and meshtools.show_progress:
                        Blender.Window.DrawProgressBar(float(i)/len(mesh.verts), "Finding Shared VColors")
-               for j in range(len(mesh.faces[i].v)):
-                       index = mesh.faces[i].v[j].index
-                       color = mesh.faces[i].col[j]
-                       r,g,b,a = color.r, color.g, color.b, color.a
-                       vertexcolors.setdefault(index, []).append([r,g,b,a])
-       for i in range(len(vertexcolors)):      # average them
+               col = f.col
+               for j in xrange(len(f)):
+                       index = f[j].index
+                       color = col[j]
+                       r,g,b = color.r, color.g, color.b
+                       vertexcolors.setdefault(index, []).append([r,g,b,255])
+       i = 0
+       for index, value in vertexcolors.iteritems():   # average them
                if not i%100 and meshtools.show_progress:
                        Blender.Window.DrawProgressBar(float(i)/len(mesh.verts), "Averaging Vertex Colors")
                vcolor = [0,0,0,0]      # rgba
-               for j in range(len(vertexcolors[i])):
-                       vcolor = vcolor_add(vcolor, vertexcolors[i][j])
-               shared = len(vertexcolors[i])
-               vertexcolors[i] = vcolor_div(vcolor, shared)
+               for v in value:
+                       vcolor = vcolor_add(vcolor, v)
+               shared = len(value)
+               value[:] = vcolor_div(vcolor, shared)
+               i+=1
        return vertexcolors
 
 # ====================================================
@@ -301,8 +302,9 @@ def generate_vmap_vc(mesh):
        data.write(struct.pack(">H", 3))                        # dimension
        data.write(generate_nstring("Blender's Vertex Colors")) # name
        vertexcolors = average_vertexcolors(mesh)
-       for i in range(len(vertexcolors)):
-               r, g, b, a = vertexcolors[i]
+       for i in xrange(len(vertexcolors)):
+               try:    r, g, b, a = vertexcolors[i] # has a face user
+               except: r, g, b, a = 255,255,255,255
                data.write(struct.pack(">H", i)) # vertex index
                data.write(struct.pack(">fff", r/255.0, g/255.0, b/255.0))
        return data.getvalue()
@@ -315,15 +317,15 @@ def generate_vmad_vc(mesh):
        data.write("RGB ")                                      # type
        data.write(struct.pack(">H", 3))                        # dimension
        data.write(generate_nstring("Blender's Vertex Colors")) # name
-       for i in range(len(mesh.faces)):
+       for i, f in enumerate(mesh.faces):
                if not i%100 and meshtools.show_progress:
                        Blender.Window.DrawProgressBar(float(i)/len(mesh.faces), "Writing Vertex Colors")
-               numfaceverts = len(mesh.faces[i].v)
-               for j in range(numfaceverts-1, -1, -1):                         # Reverse order
-                       r = mesh.faces[i].col[j].r
-                       g = mesh.faces[i].col[j].g
-                       b = mesh.faces[i].col[j].b
-                       v = mesh.faces[i].v[j].index
+               col = f.col
+               for j in xrange(len(f)-1, -1, -1):                      # Reverse order
+                       r = col.r
+                       g = col.g
+                       b = col.b
+                       v = f[j].index
                        data.write(struct.pack(">H", v)) # vertex index
                        data.write(struct.pack(">H", i)) # face index
                        data.write(struct.pack(">fff", r/255.0, g/255.0, b/255.0))
@@ -337,13 +339,15 @@ def generate_vmad_uv(mesh):
        data.write("TXUV")                                       # type
        data.write(struct.pack(">H", 2))                         # dimension
        data.write(generate_nstring("Blender's UV Coordinates")) # name
-       for i in range(len(mesh.faces)):
+       
+       for i, f in enumerate(mesh.faces):
                if not i%100 and meshtools.show_progress:
                        Blender.Window.DrawProgressBar(float(i)/len(mesh.faces), "Writing UV Coordinates")
-               numfaceverts = len(mesh.faces[i].v)
-               for j in range(numfaceverts-1, -1, -1):                         # Reverse order
-                       U,V = mesh.faces[i].uv[j]
-                       v = mesh.faces[i].v[j].index
+               
+               uv = f.uv
+               for j in xrange(len(f)-1, -1, -1):                      # Reverse order
+                       U,V = uv[j]
+                       v = f[j].index
                        data.write(struct.pack(">H", v)) # vertex index
                        data.write(struct.pack(">H", i)) # face index
                        data.write(struct.pack(">ff", U, V))
@@ -365,14 +369,13 @@ def generate_vx(index):
 def generate_pols(mesh):
        data = cStringIO.StringIO()
        data.write("FACE")  # polygon type
-       for i in range(len(mesh.faces)):
+       for i,f in enumerate(mesh.faces):
                if not i%100 and meshtools.show_progress:
                        Blender.Window.DrawProgressBar(float(i)/len(mesh.faces), "Writing Faces")
-               data.write(struct.pack(">H", len(mesh.faces[i].v))) # numfaceverts
-               numfaceverts = len(mesh.faces[i].v)
-               for j in range(numfaceverts-1, -1, -1):                         # Reverse order
-                       index = mesh.faces[i].v[j].index
-                       data.write(generate_vx(index))
+               data.write(struct.pack(">H", len(f))) # numfaceverts
+               numfaceverts = len(f)
+               for j in xrange(numfaceverts-1, -1, -1):                        # Reverse order
+                       data.write(generate_vx(f[j].index))
        return data.getvalue()
 
 # =================================================
@@ -381,25 +384,27 @@ def generate_pols(mesh):
 def generate_ptag(mesh, material_names):
        data = cStringIO.StringIO()
        data.write("SURF")  # polygon tag type
-       for i in range(len(mesh.faces)): # numfaces
+       mesh_materials = mesh.materials
+       for i, f in enumerate(mesh.faces): # numfaces
                if not i%100 and meshtools.show_progress:
                        Blender.Window.DrawProgressBar(float(i)/len(mesh.faces), "Writing Surface Indices")
                data.write(generate_vx(i))
-               if (not mesh.materials) and (meshtools.has_vertex_colors(mesh)):                # vcols only
+               if (not mesh_materials) and (meshtools.has_vertex_colors(mesh)):                # vcols only
                        if meshtools.average_vcols:
                                name = "\251 Per-Vert Vertex Colors"
                        else:
                                name = "\251 Per-Face Vertex Colors"
-               elif (mesh.materials) and (not meshtools.has_vertex_colors(mesh)):              # materials only
-                       idx = mesh.faces[i].mat #erialIndex
-                       name = mesh.materials[idx].name
-               elif (not mesh.materials) and (not meshtools.has_vertex_colors(mesh)):  # neither
+               elif (mesh_materials) and (not meshtools.has_vertex_colors(mesh)):              # materials only
+                       idx = f.mat     #erialIndex
+                       name = mesh_materials[idx].name
+               elif (not mesh_materials) and (not meshtools.has_vertex_colors(mesh)):  # neither
                        name = "\251 Blender Default"
                else:                                                                                                                                           # both
-                       idx = mesh.faces[i].mat
-                       name = mesh.materials[idx].name
-               names = material_names.keys()
-               surfidx = names.index(name)
+                       idx = f.mat
+                       if idx >= len(mesh_materials): idx = 0
+                       name = mesh_materials[idx].name
+               
+               surfidx = material_names.index(name)
                data.write(struct.pack(">H", surfidx)) # surface index
        return data.getvalue()
 
@@ -552,8 +557,8 @@ def generate_default_surf():
        data.write("CMNT")  # material comment
        comment = material_name + ": Exported from Blender\256 " + meshtools.blender_version_str
 
-       # vals = map(chr, range(164,255,1))
-       # keys = range(164,255,1)
+       # vals = map(chr, xrange(164,255,1))
+       # keys = xrange(164,255,1)
        # keys = map(lambda x: `x`, keys)
        # comment = map(None, keys, vals)
        # comment = reduce(operator.add, comment)
@@ -602,7 +607,7 @@ def generate_icon():
 def generate_clip(mesh, material_names):
        data = cStringIO.StringIO()
        clipid = 1
-       for i in range(len(mesh.materials)):                                                                    # Run through list of materials used by mesh
+       for i in xrange(len(mesh.materials)):                                                                   # Run through list of materials used by mesh
                material = Blender.Material.Get(mesh.materials[i].name)
                mtextures = material.getTextures()                                                                      # Get a list of textures linked to the material
                for mtex in mtextures:
@@ -637,7 +642,7 @@ def write_header(file, chunks):
        file.write("LWO2")
 
 def fs_callback(filename):
-       if filename.find('.lwo', -4) <= 0: filename += '.lwo'
+       if not filename.lower().endswith('.lwo'): filename += '.lwo'
        write(filename)
 
-Blender.Window.FileSelector(fs_callback, "Export LWO")
+Blender.Window.FileSelector(fs_callback, "Export LWO", Blender.sys.makename(ext='.lwo'))
index 139d61027ab8918ffe927e6bf0c7354ad23023a9..722b4edadac288ac21776e22c40dcd880d4b7d0f 100644 (file)
@@ -87,6 +87,11 @@ def write(filename):
        objname = objects[0].name
        meshname = objects[0].getData(name_only=1)
        mesh = Blender.NMesh.GetRaw(meshname)
+       
+       if not mesh:
+               Blender.Draw.PupMenu("Nendo Export Error%t|no active mesh")
+               return
+       
        obj = objects[0]
 
        numedges = len(mesh.verts)+len(mesh.faces)-2
index 51e4a343442f684ef1f2f0522e1894cdbbc2f22b..561975b5d266ac4f6c42aa724369ad19e4d3250c 100755 (executable)
@@ -188,8 +188,7 @@ def mesh_edge_dict(me):
        for f in me.faces:
                if not f.hide:
                        for edkey in f.edge_keys:
-                               try:    ed_dict[edkey].append(f)
-                               except: ed_dict[edkey]= [f]
+                               ed_dict.setdefault(edkey, []).append(f)
        
        return ed_dict
 
@@ -328,11 +327,8 @@ def terrain_cut_2d(t, c, PREF_Z_LOC):
                        faces= []
                
                for f in faces:
-                       try:
-                               faces_intersecting[f.index].append(ed_isect)
-                       except:
-                               faces_intersecting[f.index]= [ed_isect]
-                               
+                       faces_intersecting.setdefault(f.index, []).append(ed_isect)
+       
        # this list is used to store edges that are totaly inside a face ( no intersections with terrain)
        # we can remove these as we
        face_containing_edges= [[] for i in xrange(len(me_t.faces))]
@@ -542,9 +538,6 @@ def terrain_cut_2d(t, c, PREF_Z_LOC):
                                uv= f_uv[ii]
                                uv.x= new_uv.x
                                uv.y= new_uv.y
-                       
-                       for col in f.col:
-                               col.r= col.g= col.b= 255
        
        me_t.faces.delete(1, faces_intersecting.keys())
        me_t.sel= 1
index 64d372aa3ddfc55e876d0d0e781d5d21144c0068..b18938a6b59a78281c85255aa076c2755fb547e8 100644 (file)
@@ -109,7 +109,7 @@ FD  = []                # file handle
 NORMALS = []                   # normal list
 mats = []
 EXPORT_DIR = ''
-WORLD = Blender.World.Get() 
+WORLD = Blender.World.GetCurrent() 
 
 # ---------------------------------------------------------------------------
 # get_path returns the path portion o/wf the supplied filename.
@@ -167,27 +167,12 @@ def get_materials(obj):
 
   # now drop down to the mesh level
   #mesh = Blender.NMesh.GetRaw(obj.data.name)
-  mesh = obj.data
 
-  if mesh.materials:
-    for mat in mesh.materials:
-      mats.append(mat)
+  mats.extend(obj.getData(mesh=1).materials)
 
   # return the materials list
   return mats
 
-
-
-# ---------------------------------------------------------------------------
-# apply_transform converts a vertex to co-ords
-# ---------------------------------------------------------------------------
-def apply_transform(vert, matrix):
-  vc = Mathutils.CopyVec(vert)
-  vc.resize4D()
-  return Mathutils.VecMultMat(vc, matrix)
-
-
-
 # ---------------------------------------------------------------------------
 # do_header writes out the header data
 # ---------------------------------------------------------------------------
@@ -230,7 +215,8 @@ def do_header():
   FD.write("}\n\n")
 
   # static ambience block 
-  ambient = WORLD[0].getAmb()
+  if WORLD:    ambient = WORLD.getAmb()
+  else:                ambient = 0,0,0
 
   FD.write("SI_Ambience  {\n")
   FD.write("   %f,\n" % ambient[0])
@@ -413,11 +399,11 @@ def do_texture(mtex):
   # mapping type  ? uv  map wrapped is 4, how to detect?
   # start with a simple xy mapping ie 0
   FD.write("                   4,\n")
-
-  print img.getSize ()
+  
+  if img.has_data:     ix, iy = img.getSize()
+  else:                        ix, iy = 512,512
 
   # image width, and height
-  ix, iy = img.getSize()
   FD.write("                   %d,\n" % ix)
   FD.write("                   %d,\n" % iy)
   # u crop min/max, v crop min/max
@@ -432,9 +418,12 @@ def do_texture(mtex):
     uvs = 1
   FD.write("                   %d,\n" % uvs )
   # u/v repeat
-  iru = img.getXRep()
+  if img.has_data:     iru = img.getXRep()
+  else:                        iru = 1
   FD.write("                   %d,\n" % iru )
-  irv = img.getYRep()
+  if img.has_data:     irv = img.getYRep()
+  else:                        irv = 1
+
   FD.write("                   %d,\n" % irv )
   # u/v alt - 0, 0
   FD.write("                   0,\n" ) 
@@ -564,15 +553,6 @@ def do_model_material(obj):
     FD.write("         }\n\n" )
 
 
-
-def meshHasUV ( mesh ):
-  if mesh.hasFaceUV():
-    return TRUE
-#  materials = mesh.materials
-#    if len(materials) > 0:
-         
-  return FALSE
-
 # ---------------------------------------------------------------------------
 # do_collect_uv, makes an easy to use list out of the uv data
 # todo, remove duplicates and compress the list size, xsi supports this.
@@ -598,9 +578,9 @@ def do_collect_uv(mesh):
   # run through all the faces
   j = 0
   for f in mesh.faces:
-    for i in range(len(f)):
+    for uv in f.uv:
       UVI.append(j)
-      UVC.append(f.uv[i])
+      UVC.append(uv)
       j+=1
     UVI.append(-1)
 
@@ -625,9 +605,9 @@ def do_collect_colour(mesh):
   # run through all the faces
   j = 0
   for f in mesh.faces:
-    for i in range(len(f)):
+    for c in f.col:
       VCI.append(j)
-      VCC.append(f.col[i])
+      VCC.append(c)
       j+=1
     VCI.append(-1)
 
@@ -1168,9 +1148,8 @@ def do_camera(obj):
 # ---------------------------------------------------------------------------
 
 def do_light_ambient():
-  ambient = WORLD[0].getAmb()
-  if ambient == [0.0,0.0,0.0]:
-    ambient = [0.5,0.5,0.5]
+  if WORLD:    ambient = WORLD.getAmb()
+  else:                ambient = 0,0,0
 
   FD.write("   SI_Light ambient_sw3d {\n")