350 lines
		
	
	
		
			8.8 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
		
		
			
		
	
	
			350 lines
		
	
	
		
			8.8 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
|   | #! /usr/bin/env python | ||
|  | 
 | ||
|  | ####################### | ||
|  | # (c) Jan Walter 2000 # | ||
|  | ####################### | ||
|  | 
 | ||
|  | # CVS | ||
|  | # $Author$ | ||
|  | # $Date$ | ||
|  | # $RCSfile$ | ||
|  | # $Revision$ | ||
|  | 
 | ||
|  | """This is the Python API for Blender""" | ||
|  | 
 | ||
|  | def _findNewName(name, names): | ||
|  |     import string | ||
|  |     words = string.split(name, ".") | ||
|  |     basename = words[0] | ||
|  |     newname  = name | ||
|  |     num = 1 | ||
|  |     while newname in names: | ||
|  |         newname = basename + ".%03d" % num | ||
|  |         num = num + 1 | ||
|  |     return newname | ||
|  | 
 | ||
|  | ################### | ||
|  | # Blender classes # | ||
|  | ################### | ||
|  | 
 | ||
|  | class Camera: | ||
|  |     def __init__(self, name, Lens = 35.0, ClipSta = 0.1, ClipEnd = 100.0): | ||
|  |         self.name = name | ||
|  |         self.ipos = {} | ||
|  |         self.Lens = Lens | ||
|  |         self.ClipSta = ClipSta | ||
|  |         self.ClipEnd = ClipEnd | ||
|  | 
 | ||
|  | class Curve: | ||
|  |     def __init__(self, name): | ||
|  |         # ... | ||
|  |         self.name = name | ||
|  |         self.ipos = {} | ||
|  |         self.materials = [] | ||
|  | 
 | ||
|  | class Ika: | ||
|  |     def __init__(self, name): | ||
|  |         self.name = name | ||
|  | 
 | ||
|  | class Ipo: | ||
|  |     def __init__(self, name): | ||
|  |         self.name = name | ||
|  | 
 | ||
|  | class Lamp: | ||
|  |     def __init__(self, name, Energ = 1.0, R = 1.0, G = 1.0, B = 1.0, | ||
|  |                  SpoSi = 45.0, | ||
|  |                  OfsX = 0.0, OfsY = 0.0, OfsZ = 0.0, | ||
|  |                  SizeX = 1.0, SizeY = 1.0, SizeZ = 1.0): | ||
|  |         self.name = name | ||
|  |         self.ipos = {} | ||
|  |         self.Energ = Energ | ||
|  |         self.R = R | ||
|  |         self.G = G | ||
|  |         self.B = B | ||
|  |         self.SpoSi = SpoSi | ||
|  |         self.OfsX = OfsX | ||
|  |         self.OfsY = OfsY | ||
|  |         self.OfsZ = OfsZ | ||
|  |         self.SizeX = SizeX | ||
|  |         self.SizeY = SizeY | ||
|  |         self.SizeZ = SizeZ | ||
|  | 
 | ||
|  | class Material: | ||
|  |     def __init__(self, name, | ||
|  |                  R = 0.8, G = 0.8, B = 0.8, | ||
|  |                  SpecR = 1.0, SpecG = 1.0, SpecB = 1.0, | ||
|  |                  MirR = 1.0, MirG = 1.0, MirB = 1.0, | ||
|  |                  Ref = 0.8, Alpha = 1.0, Emit = 0.0, Amb = 0.5, | ||
|  |                  Spec = 0.5, Hard = 50): | ||
|  |         self.name = name | ||
|  |         self.ipos = {} | ||
|  |         self.R = R | ||
|  |         self.G = G | ||
|  |         self.B = B | ||
|  |         self.SpecR = SpecR | ||
|  |         self.SpecG = SpecG | ||
|  |         self.SpecB = SpecB | ||
|  |         self.MirR = MirR | ||
|  |         self.MirG = MirG | ||
|  |         self.MirB = MirB | ||
|  |         self.Ref = Ref | ||
|  |         self.Alpha = Alpha | ||
|  |         self.Emit = Emit | ||
|  |         self.Amb = Amb | ||
|  |         self.Spec = Spec | ||
|  |         self.Hard = Hard | ||
|  | 
 | ||
|  | class Matrix: | ||
|  |     def __init__(self): | ||
|  |         self.elements = [[1, 0, 0, 0], | ||
|  |                          [0, 1, 0, 0], | ||
|  |                          [0, 0, 1, 0], | ||
|  |                          [0, 0, 0, 1]] | ||
|  | 
 | ||
|  |     def __repr__(self): | ||
|  |         str = "%s" % self.elements | ||
|  |         return str | ||
|  | 
 | ||
|  | class Mesh: | ||
|  |     """Creates an (empty) instance of a Blender mesh.\n\
 | ||
|  |     E.g.: "m = Blender.Mesh('Plane')"\n\ | ||
|  |     To create faces first add vertices with \n\ | ||
|  |     "i1 = m.addVertex(x, y, z, nx, ny, nz, r = -1.0, r = 0.0, b = 0.0)"\n\ | ||
|  |     then create faces with "index = m.addFace(i1, i2, i3, i4, isSmooth)"."""
 | ||
|  | 
 | ||
|  |     _meshes = {} | ||
|  | 
 | ||
|  |     def __init__(self, name): | ||
|  |         self.name = name | ||
|  |         self.ipos = {} | ||
|  |         self.materials = [] | ||
|  |         self.vertices = [] | ||
|  |         self.normals = [] | ||
|  |         self.colors = [] | ||
|  |         self.faces = [] | ||
|  |         if name in Mesh._meshes.keys(): | ||
|  |             print 'Mesh "%s" already exists ...' % name | ||
|  |             self.name = _findNewName(name, Mesh._meshes.keys()) | ||
|  |             print '... so it will be called "%s"' % self.name | ||
|  |         Mesh._meshes[self.name] = self | ||
|  | 
 | ||
|  |     def __repr__(self): | ||
|  |         str = 'Mesh(name = "%s",\n' % self.name | ||
|  |         str = str + '     vertices = %s,\n' % len(self.vertices) | ||
|  |         str = str + '     faces = %s)' % len(self.faces) | ||
|  |         return str | ||
|  | 
 | ||
|  |     def addFace(self, i1, i2, i3, i4, isSmooth): | ||
|  |         """addFace(self, i1, i2, i3, i4)""" | ||
|  |         self.faces.append([i1, i2, i3, i4, isSmooth]) | ||
|  |         return (len(self.faces) - 1) | ||
|  | 
 | ||
|  |     def addVertex(self, x, y, z, nx, ny, nz, r = -1.0, g = 0.0, b = 0.0): | ||
|  |         """addVertex(self, x, y, z, nx, ny, nz, r = -1.0, g = 0.0, b = 0.0)""" | ||
|  |         self.vertices.append([x, y, z]) | ||
|  |         self.normals.append([nx, ny, nz]) | ||
|  |         if r != -1.0: | ||
|  |             self.colors.append([r, g, b]) | ||
|  |         return (len(self.vertices) - 1) | ||
|  | 
 | ||
|  | class MetaBall: | ||
|  |     def __init__(self, name): | ||
|  |         self.name = name | ||
|  | 
 | ||
|  | class Object: | ||
|  |     """Creates an instance of a Blender object""" | ||
|  | 
 | ||
|  |     _objects = {} | ||
|  | 
 | ||
|  |     def __init__(self, name): | ||
|  |         self.name = name | ||
|  |         self.ipos = {} | ||
|  |         self.materials = [] | ||
|  |         self.matrix = Matrix() | ||
|  |         self.data = None | ||
|  |         self.type = None | ||
|  |         if name in Object._objects.keys(): | ||
|  |             print 'Object "%s" already exists ...' % name | ||
|  |             self.name = _findNewName(name, Object._objects.keys()) | ||
|  |             print '... so it will be called "%s"' % self.name | ||
|  |         Object._objects[self.name] = self | ||
|  | 
 | ||
|  |     def __repr__(self): | ||
|  |         str = 'Object(name = "%s",\n' % self.name | ||
|  |         str = str + '       matrix = %s,\n' % self.matrix | ||
|  |         if self.type: | ||
|  |             str = str + '       data = %s("%s"))' % (self.type, self.data) | ||
|  |         else: | ||
|  |             str = str + '       data = None)' | ||
|  |         return str | ||
|  | 
 | ||
|  | class Scene: | ||
|  |     """Creates an instance of a Blender scene""" | ||
|  | 
 | ||
|  |     _scenes = {} | ||
|  | 
 | ||
|  |     def __init__(self, name): | ||
|  |         self.name = name | ||
|  |         self.objects = [] | ||
|  | ##         self.camera = None | ||
|  | ##         self.world = None | ||
|  |         Scene._scenes[self.name] = self | ||
|  | 
 | ||
|  |     def __repr__(self): | ||
|  |         str = 'Scene(name = "%s", \n' % self.name | ||
|  |         str = str + '      objects = %s)' % len(self.objects) | ||
|  |         return str | ||
|  | 
 | ||
|  |     def addObject(self, object): | ||
|  |         """addObject(self, object)""" | ||
|  |         self.objects.append(object.name) | ||
|  |         return (len(self.objects) - 1) | ||
|  | 
 | ||
|  | class Surface: | ||
|  |     def __init__(self, name): | ||
|  |         self.name = name | ||
|  |         self.ipos = {} | ||
|  |         self.materials = [] | ||
|  |         # ... | ||
|  | 
 | ||
|  | class Text(Surface): | ||
|  |     def __init__(self, name): | ||
|  |         Surface.__init__(name) | ||
|  | 
 | ||
|  | ############## | ||
|  | # primitives # | ||
|  | ############## | ||
|  | 
 | ||
|  | def addMesh(type, sceneName): | ||
|  |     """Blender.addMesh(type, sceneName)\n\
 | ||
|  |     where type is one of ["Plane"]"""
 | ||
|  | 
 | ||
|  |     if type == "Plane": | ||
|  |         object = Object(type) | ||
|  |         mesh = Mesh(type) | ||
|  |         i1 = mesh.addVertex(+1.0, +1.0, 0.0, 0.0, 0.0, 1.0) | ||
|  |         i2 = mesh.addVertex(+1.0, -1.0, 0.0, 0.0, 0.0, 1.0) | ||
|  |         i3 = mesh.addVertex(-1.0, -1.0, 0.0, 0.0, 0.0, 1.0) | ||
|  |         i4 = mesh.addVertex(-1.0, +1.0, 0.0, 0.0, 0.0, 1.0) | ||
|  |         mesh.addFace(i1, i4, i3, i2, 0) | ||
|  |         connect("OB" + object.name, "ME" + mesh.name) | ||
|  |         connect("SC" + sceneName,  "OB" + object.name) | ||
|  |         return object.name, mesh.name | ||
|  |     elif type == "Cube": | ||
|  |         pass | ||
|  |     elif type == "Circle": | ||
|  |         pass | ||
|  |     elif type == "UVsphere": | ||
|  |         pass | ||
|  |     elif type == "Icosphere": | ||
|  |         pass | ||
|  |     elif type == "Cylinder": | ||
|  |         pass | ||
|  |     elif type == "Tube": | ||
|  |         pass | ||
|  |     elif type == "Cone": | ||
|  |         pass | ||
|  |     elif type == "Grid": | ||
|  |         pass | ||
|  |     else: | ||
|  |         raise TypeError | ||
|  | 
 | ||
|  | def addCurve(type): | ||
|  |     if type == "Bezier Curve": | ||
|  |         pass | ||
|  |     elif type == "Bezier Circle": | ||
|  |         pass | ||
|  |     elif type == "Nurbs Curve": | ||
|  |         pass | ||
|  |     elif type == "Nurbs Circle": | ||
|  |         pass | ||
|  |     elif type == "Path": | ||
|  |         pass | ||
|  |     else: | ||
|  |         raise TypeError | ||
|  | 
 | ||
|  | def addSurface(type): | ||
|  |     if type == "Curve": | ||
|  |         pass | ||
|  |     elif type == "Circle": | ||
|  |         pass | ||
|  |     elif type == "Surface": | ||
|  |         pass | ||
|  |     elif type == "Tube": | ||
|  |         pass | ||
|  |     elif type == "Sphere": | ||
|  |         pass | ||
|  |     elif type == "Donut": | ||
|  |         pass | ||
|  |     else: | ||
|  |         raise TypeError | ||
|  | 
 | ||
|  | def connect(objName1, objName2): | ||
|  |     """connect(objName1, objName2)""" | ||
|  | 
 | ||
|  |     if objName1[:2] == "OB" and objName2[:2] == "ME": | ||
|  |         obj1 = getObject(objName1[2:]) | ||
|  |         obj1.data = objName2[2:] | ||
|  |         obj1.type = "Mesh" | ||
|  |     elif objName1[:2] == "SC" and objName2[:2] == "OB": | ||
|  |         obj1 = getScene(objName1[2:]) | ||
|  |         obj2 = getObject(objName2[2:]) | ||
|  |         obj1.addObject(obj2) | ||
|  |     else: | ||
|  |         print "ERROR: connect(%s, %s)" % (objName1, objName2) | ||
|  | 
 | ||
|  | def getCurrentScene(): | ||
|  |     """getCurrentScene()""" | ||
|  | 
 | ||
|  |     return Scene._scenes[0] | ||
|  | 
 | ||
|  | def getMesh(name): | ||
|  |     """getMesh(name)""" | ||
|  | 
 | ||
|  |     if name in Mesh._meshes.keys(): | ||
|  |         return Mesh._meshes[name] | ||
|  |     else: | ||
|  |         return None | ||
|  | 
 | ||
|  | def getObject(name): | ||
|  |     """getObject(name)""" | ||
|  | 
 | ||
|  |     if name in Object._objects.keys(): | ||
|  |         return Object._objects[name] | ||
|  |     else: | ||
|  |         return None | ||
|  | 
 | ||
|  | def getScene(name): | ||
|  |     """getScene(name)""" | ||
|  | 
 | ||
|  |     if name in Scene._scenes.keys(): | ||
|  |         return Scene._scenes[name] | ||
|  |     else: | ||
|  |         return None | ||
|  | 
 | ||
|  | def testBlender(): | ||
|  |     scene = Scene("1") | ||
|  |     print scene | ||
|  |     objName, meshName = addMesh("Plane", "1") | ||
|  |     print scene | ||
|  |     obj = Object("Plane") | ||
|  |     connect("OB" + obj.name, "ME" + meshName) | ||
|  |     connect("SC" + scene.name, "OB" + obj.name) | ||
|  |     print scene | ||
|  |     for name in scene.objects: | ||
|  |         obj = getObject(name) | ||
|  |         print obj | ||
|  |         if obj.type == "Mesh": | ||
|  |             mesh = getMesh(obj.data) | ||
|  |             print mesh | ||
|  |             print mesh.vertices | ||
|  |             print mesh.faces | ||
|  |     Mesh("Plane") | ||
|  |     # print global data | ||
|  |     print Scene._scenes | ||
|  |     print Object._objects | ||
|  |     print Mesh._meshes | ||
|  | 
 | ||
|  | if __name__ == "__main__": | ||
|  |     testBlender() |