X-Git-Url: http://git.tdb.fi/?a=blobdiff_plain;f=mesh_export.py;h=75db9d12dd1d1ab70faf9347c2b247f822155604;hb=982005bfbccb429767d0676bd840caf1118c9e21;hp=cdab35f3486b4dcb00ec1b0014d617235908030a;hpb=7ef0e6407e21acdcd9865651a12b40d6a3cb3c0e;p=libs%2Fgl.git diff --git a/mesh_export.py b/mesh_export.py index cdab35f3..75db9d12 100644 --- a/mesh_export.py +++ b/mesh_export.py @@ -9,13 +9,18 @@ Group: 'Export' import sys import math +import bpy import Blender class Edge: def __init__(self, me): - self._medge=me + if me.__class__==Edge: + self._medge=me._medge + self.smooth=me.smooth + else: + self._medge=me + self.smooth=False self.faces=[] - self.smooth=False def __getattr__(self, attr): return getattr(self._medge, attr) @@ -42,8 +47,11 @@ class Vertex: def __init__(self, mv): if mv.__class__==Vertex: self._mvert=mv._mvert + self.uv=mv.uv else: self._mvert=mv + self.uv=None + self.orig_index=self._mvert.index def __getattr__(self, attr): return getattr(self._mvert, attr) @@ -60,19 +68,13 @@ class Face: def __getattr__(self, attr): return getattr(self._mface, attr) - def get_following_vertex(self, *vt): - seen=False - indices=[v.index for v in vt] - for v in self.verts: - if v.index in indices: - seen=True - elif seen: - return v - - if seen: - return self.verts[0] - - return None + def get_vertices_from(self, *vt): + indices=[u.index for u in vt] + flags=[(v.index in indices) for v in self.verts] + l=len(self.verts) + for i in range(l): + if flags[i] and not flags[(i+l-1)%l]: + return self.verts[i:]+self.verts[:i] class SmoothGroup: @@ -88,13 +90,65 @@ class SmoothGroup: v=f.verts[i] if v.index not in vert_map: vt=Vertex(v) - if not f.smooth: - vt.no=f.no + vt.index=len(self.verts) self.verts.append(vt) + vert_map[v.index]=vt + vt.no=Blender.Mathutils.Vector(f.no) + else: + vt=vert_map[v.index] + vt.no+=f.no + f.verts[i]=vt + + for v in self.verts: + v.no.normalize() + + def separate_uv(self): + copies={} + for f in self.faces: + for i in range(len(f.verts)): + v=f.verts[i] + if not v.uv: + v.uv=f.uv[i] + elif f.uv[i]!=v.uv: + if v.index not in copies: + copies[v.index]=[] + + vt=None + for w in copies[v.index]: + if w.uv==f.uv[i]: + vt=w + break + + if not vt: + vt=Vertex(v) + vt.index=len(self.verts) + vt.uv=f.uv[i] + self.verts.append(vt) + copies[v.index].append(vt) + f.verts[i]=vt + + def create_edges(self): + edge_map={} + for f in self.faces: + vert_map=dict([(v.orig_index, v) for v in f.verts]) + for i in range(len(f.edges)): + v1=vert_map[f.edges[i].v1.index] + v2=vert_map[f.edges[i].v2.index] + key=tuple(sorted((v1.index, v2.index))) + + if key in edge_map: + e=edge_map[key] else: - f.verts[i]=vert_map[v.index] + e=Edge(f.edges[i]) + edge_map[key]=e + e.v1=v1 + e.v2=v2 + e.key=key + + f.edges[i]=e + e.faces.append(f) class Exporter: @@ -106,6 +160,7 @@ class Exporter: self.out_file=file(fn, "w") self.use_strips=True self.use_degen_tris=True + self.debug=False def find_smooth_group(self, face, sg): face.smooth_group=sg @@ -132,18 +187,24 @@ class Exporter: if not edge: return None - v1=face.get_following_vertex(edge.v1, edge.v2) - v2=face.get_following_vertex(v1) - if len(face.verts)==4: - result=[v2, v1] - else: - result=[v1, v2] + if self.debug: + print "Starting strip from %s"%[v.index for v in face.verts] + + verts=face.get_vertices_from(edge.v1, edge.v2) + result=[verts[-2], verts[-1]] while 1: + verts=face.get_vertices_from(*result[-2:]) + k=len(result)%2 + if self.debug: + print " %d %s"%(len(result), [v.index for v in verts]) + face.flag=True - for i in range(2, len(face.verts)): - v=face.get_following_vertex(result[-2], result[-1]) - result.append(v) + if len(verts)==4 and not k: + result.append(verts[3]) + result.append(verts[2]) + if len(verts)==4 and k: + result.append(verts[3]) i1=result[-2].index i2=result[-1].index @@ -154,16 +215,19 @@ class Exporter: break next=edge.other_face(face) - if next.smooth_group.index!=face.smooth_group.index or next.flag: + if not next or next.smooth_group.index!=face.smooth_group.index or next.flag: break face=next + if self.debug: + print " %s"%[v.index for v in result] + return result def export(self): - scene=Blender.Scene.GetCurrent() + scene=bpy.data.scenes.active - obj=scene.getActiveObject() + obj=scene.objects.active if obj.getType()!="Mesh": raise Exception, "Can only export Mesh data" @@ -181,6 +245,9 @@ class Exporter: for e in edges.itervalues(): e.check_smooth(smooth_limit) + if self.debug: + print "%d faces, %d edges"%(len(faces), len(edges)) + smooth_groups=[] for f in faces: if not f.smooth_group: @@ -190,6 +257,21 @@ class Exporter: for sg in smooth_groups: sg.find_vertices() + if mesh.faceUV: + sg.separate_uv() + sg.create_edges() + + verts=[] + for sg in smooth_groups: + for v in sg.verts: + v.index=len(verts) + verts.append(v) + + if self.debug: + print "%d smooth groups:"%(len(smooth_groups)) + for i in range(len(smooth_groups)): + sg=smooth_groups[i] + print " %d: %d faces, %d vertices"%(i, len(sg.faces), len(sg.verts)) strips=[] if self.use_strips: @@ -218,15 +300,19 @@ class Exporter: strips=[big_strip] - verts=[] - for sg in smooth_groups: - for v in sg.verts: - v.index=len(verts) - verts.append(v) - - self.out_file.write("vertices NORMAL3_VERTEX3\n{\n") + self.out_file.write("vertices NORMAL3") + if mesh.faceUV: + self.out_file.write("_TEXCOORD2") + self.out_file.write("_VERTEX3\n{\n") + norm=None + uv=None for v in verts: - self.out_file.write("\tnormal3 %f %f %f;\n"%tuple(v.no)) + if v.no!=norm: + self.out_file.write("\tnormal3 %f %f %f;\n"%tuple(v.no)) + norm=v.no + if v.uv!=uv: + self.out_file.write("\ttexcoord2 %f %f;\n"%tuple(v.uv)) + uv=v.uv self.out_file.write("\tvertex3 %f %f %f;\n"%tuple(v.co)) self.out_file.write("};\n") for s in strips: @@ -258,6 +344,8 @@ class FrontEnd: def export(self, fn): exp=Exporter(fn) + #exp.use_degen_tris=False + #exp.debug=True exp.export()