rev |
line source |
nuclear@39
|
1 # Goat3D Blender >2.63 exporter
|
nuclear@40
|
2 import bpy
|
nuclear@36
|
3 import ctypes
|
nuclear@36
|
4 from ctypes import *
|
nuclear@36
|
5 from ctypes.util import find_library
|
nuclear@33
|
6
|
nuclear@40
|
7 GOAT3D_MAT_ATTR_DIFFUSE = "diffuse".encode('utf-8')
|
nuclear@40
|
8 GOAT3D_MAT_ATTR_SPECULAR = "specular".encode('utf-8')
|
nuclear@40
|
9 GOAT3D_MAT_ATTR_SHININESS = "shininess".encode('utf-8')
|
nuclear@40
|
10 GOAT3D_MAT_ATTR_NORMAL = "normal".encode('utf-8')
|
nuclear@40
|
11 GOAT3D_MAT_ATTR_BUMP = "bump".encode('utf-8')
|
nuclear@40
|
12 GOAT3D_MAT_ATTR_REFLECTION = "reflection".encode('utf-8')
|
nuclear@40
|
13 GOAT3D_MAT_ATTR_TRANSMISSION = "transmission".encode('utf-8')
|
nuclear@40
|
14 GOAT3D_MAT_ATTR_IOR = "ior".encode('utf-8')
|
nuclear@40
|
15 GOAT3D_MAT_ATTR_ALPHA = "alpha".encode('utf-8')
|
nuclear@40
|
16
|
nuclear@40
|
17 # these must match the goat3d_vertex_attr enumeration values in goat3d.h
|
nuclear@40
|
18 GOAT3D_MESH_ATTR_VERTEX = 0
|
nuclear@40
|
19 GOAT3D_MESH_ATTR_NORMAL = 1
|
nuclear@40
|
20 GOAT3D_MESH_ATTR_TANGENT = 2
|
nuclear@40
|
21 GOAT3D_MESH_ATTR_TEXCOORD = 3
|
nuclear@40
|
22 GOAT3D_MESH_ATTR_SKIN_WEIGHT = 4
|
nuclear@40
|
23 GOAT3D_MESH_ATTR_SKIN_MATRIX = 5
|
nuclear@40
|
24 GOAT3D_MESH_ATTR_COLOR = 6
|
nuclear@40
|
25
|
nuclear@33
|
26
|
nuclear@38
|
27 def export(oper, ctx, fname):
|
nuclear@38
|
28 print("Exporting goat3d file: " + fname)
|
nuclear@33
|
29
|
nuclear@39
|
30 lib = init_libgoat()
|
nuclear@39
|
31 if not lib:
|
nuclear@39
|
32 return False
|
nuclear@39
|
33
|
nuclear@39
|
34 # initiaize a goat3d object and start filling it up with data
|
nuclear@39
|
35 goat = lib.goat3d_create()
|
nuclear@39
|
36 if not goat:
|
nuclear@39
|
37 oper.report({'ERROR'}, "Failed to create goat3d object")
|
nuclear@39
|
38 return False
|
nuclear@39
|
39
|
nuclear@39
|
40 lib.goat3d_set_name(goat, fname.encode('utf-8'))
|
nuclear@39
|
41
|
nuclear@39
|
42 export_env(ctx, goat, lib)
|
nuclear@39
|
43 export_meshes(ctx, goat, lib)
|
nuclear@39
|
44 export_nodes(ctx, goat, lib)
|
nuclear@39
|
45
|
nuclear@39
|
46 lib.goat3d_save(goat, fname.encode('utf-8'))
|
nuclear@39
|
47 lib.goat3d_free(goat)
|
nuclear@39
|
48 return True
|
nuclear@39
|
49
|
nuclear@39
|
50 def export_env(ctx, goat, lib):
|
nuclear@39
|
51 return False
|
nuclear@39
|
52
|
nuclear@40
|
53 def export_material(bmtl, goat, lib):
|
nuclear@40
|
54 name = bmtl.name.encode("utf-8")
|
nuclear@40
|
55
|
nuclear@40
|
56 mtl = lib.goat3d_create_mtl()
|
nuclear@40
|
57 lib.goat3d_set_mtl_name(mtl, name)
|
nuclear@40
|
58
|
nuclear@40
|
59 s = bmtl.diffuse_intensity
|
nuclear@40
|
60 col = bmtl.diffuse_color
|
nuclear@40
|
61 lib.goat3d_set_mtl_attrib4f(mtl, GOAT3D_MAT_ATTR_DIFFUSE, c_float(col[0] * s), c_float(col[1] * s), c_float(col[2] * s), 1.0)
|
nuclear@40
|
62
|
nuclear@40
|
63 s = bmtl.specular_intensity
|
nuclear@40
|
64 col = bmtl.specular_color
|
nuclear@40
|
65 lib.goat3d_set_mtl_attrib4f(mtl, GOAT3D_MAT_ATTR_SPECULAR, c_float(col[0] * s), c_float(col[1] * s), c_float(col[2] * s), 1.0)
|
nuclear@40
|
66 lib.goat3d_set_mtl_attrib1f(mtl, GOAT3D_MAT_ATTR_SHININESS, c_float(bmtl.specular_hardness))
|
nuclear@40
|
67 lib.goat3d_set_mtl_attrib1f(mtl, GOAT3D_MAT_ATTR_ALPHA, c_float(bmtl.alpha))
|
nuclear@40
|
68
|
nuclear@40
|
69 if bmtl.raytrace_mirror.use:
|
nuclear@40
|
70 lib.goat3d_set_mtl_attrib1f(mtl, GOAT3D_MAT_ATTR_REFLECTION, c_float(bmtl.raytrace_mirror.reflect_factor))
|
nuclear@40
|
71 if bmtl.use_transparency and bmtl.transparency_method == 'RAYTRACE':
|
nuclear@40
|
72 lib.goat3d_set_mtl_attrib1f(mtl, GOAT3D_MAT_ATTR_IOR, c_float(bmtl.raytrace_transparency.ior))
|
nuclear@40
|
73 lib.goat3d_set_mtl_attrib1f(mtl, GOAT3D_MAT_ATTR_TRANSMISSION, 1.0)
|
nuclear@40
|
74
|
nuclear@40
|
75 # grab all the textures and apply them to the correct attributes
|
nuclear@40
|
76 for texslot in bmtl.texture_slots:
|
nuclear@40
|
77 if not texslot:
|
nuclear@40
|
78 continue
|
nuclear@40
|
79
|
nuclear@40
|
80 tex = texslot.texture
|
nuclear@40
|
81 if tex.type != 'IMAGE':
|
nuclear@40
|
82 print("ignoring texture " + tex.name + ": not an image!")
|
nuclear@40
|
83 continue
|
nuclear@40
|
84
|
nuclear@40
|
85 fname = tex.image.filepath.encode('ascii')
|
nuclear@40
|
86
|
nuclear@40
|
87 attr = ""
|
nuclear@40
|
88 if texslot.use_map_color_diffuse or texslot.use_map_diffuse:
|
nuclear@40
|
89 attr = GOAT3D_MAT_ATTR_DIFFUSE
|
nuclear@40
|
90 elif texslot.use_map_color_spec or texslot.use_map_specular:
|
nuclear@40
|
91 attr = GOAT3D_MAT_ATTR_SPECULAR
|
nuclear@40
|
92 elif texslot.use_map_color_reflection or texslot.use_map_reflect:
|
nuclear@40
|
93 attr = GOAT3D_MAT_ATTR_REFLECTION
|
nuclear@40
|
94 elif texslot.use_map_hardness:
|
nuclear@40
|
95 attr = GOAT3D_MAT_ATTR_SHININESS
|
nuclear@40
|
96 elif texslot.use_map_alpha:
|
nuclear@40
|
97 attr = GOAT3D_MAT_ATTR_ALPHA
|
nuclear@40
|
98 elif texslot.use_map_normal:
|
nuclear@40
|
99 attr = GOAT3D_MAT_ATTR_NORMAL
|
nuclear@40
|
100
|
nuclear@40
|
101 if attr != "":
|
nuclear@40
|
102 lib.goat3d_set_mtl_attrib_map(mtl, attr, fname)
|
nuclear@40
|
103
|
nuclear@40
|
104 lib.goat3d_add_mtl(goat, mtl)
|
nuclear@40
|
105 return mtl
|
nuclear@40
|
106
|
nuclear@39
|
107
|
nuclear@39
|
108 def export_meshes(ctx, goat, lib):
|
nuclear@39
|
109 print("exporting " + str(len(ctx.scene.objects)) + " objects")
|
nuclear@39
|
110 for obj in ctx.scene.objects:
|
nuclear@39
|
111 if obj.type != 'MESH':
|
nuclear@39
|
112 continue
|
nuclear@39
|
113
|
nuclear@40
|
114 bmesh = obj.data
|
nuclear@39
|
115 # make sure we get a tesselated mesh
|
nuclear@40
|
116 bmesh.update(calc_tessface = True)
|
nuclear@39
|
117
|
nuclear@40
|
118 # create goat3d mesh and set the data
|
nuclear@40
|
119 mesh = lib.goat3d_create_mesh()
|
nuclear@40
|
120 lib.goat3d_set_mesh_name(mesh, bmesh.name.encode("utf-8"))
|
nuclear@40
|
121
|
nuclear@40
|
122 # get the material, add it to the scene and apply it to this mesh
|
nuclear@40
|
123 for bmtl in bmesh.materials:
|
nuclear@40
|
124 mtl = export_material(bmtl, goat, lib)
|
nuclear@40
|
125 lib.goat3d_set_mesh_mtl(mesh, mtl)
|
nuclear@40
|
126 break # we only care about one material
|
nuclear@40
|
127
|
nuclear@40
|
128 for vert in bmesh.vertices:
|
nuclear@40
|
129 v = vert.co
|
nuclear@40
|
130 n = vert.normal
|
nuclear@40
|
131 lib.goat3d_add_mesh_attrib3f(mesh, GOAT3D_MESH_ATTR_VERTEX, v[0], v[1], v[2])
|
nuclear@40
|
132 lib.goat3d_add_mesh_attrib3f(mesh, GOAT3D_MESH_ATTR_NORMAL, n[0], n[1], n[2])
|
nuclear@40
|
133
|
nuclear@40
|
134 for face in bmesh.tessfaces:
|
nuclear@39
|
135 fverts = face.vertices
|
nuclear@40
|
136 lib.goat3d_add_mesh_face(mesh, fverts[0], fverts[1], fverts[2])
|
nuclear@39
|
137
|
nuclear@40
|
138 lib.goat3d_add_mesh(goat, mesh)
|
nuclear@39
|
139 return False
|
nuclear@39
|
140
|
nuclear@39
|
141
|
nuclear@39
|
142 def export_nodes(ctx, goat, lib):
|
nuclear@39
|
143 return False
|
nuclear@39
|
144
|
nuclear@39
|
145 def init_libgoat():
|
nuclear@38
|
146 # load all relevant functions from libgoat3d
|
nuclear@38
|
147 libname = find_library("goat3d")
|
nuclear@38
|
148 if not libname:
|
nuclear@38
|
149 oper.report({'ERROR'}, "Could not find the goat3d library! make sure it's installed.")
|
nuclear@39
|
150 return None
|
nuclear@33
|
151
|
nuclear@39
|
152 lib = CDLL(libname)
|
nuclear@39
|
153 if not lib:
|
nuclear@38
|
154 oper.report({'ERROR'}, "Could not open goat3d library!")
|
nuclear@39
|
155 return None
|
nuclear@37
|
156
|
nuclear@39
|
157 lib.goat3d_create.argtypes = None
|
nuclear@39
|
158 lib.goat3d_create.restype = c_void_p
|
nuclear@36
|
159
|
nuclear@39
|
160 lib.goat3d_free.argtypes = [c_void_p]
|
nuclear@39
|
161 lib.goat3d_free.restype = None
|
nuclear@36
|
162
|
nuclear@39
|
163 lib.goat3d_set_name.argtypes = [c_void_p, c_char_p]
|
nuclear@36
|
164
|
nuclear@39
|
165 lib.goat3d_set_ambient3f.argtypes = [c_void_p, c_float, c_float, c_float]
|
nuclear@39
|
166 lib.goat3d_set_ambient3f.restype = None
|
nuclear@36
|
167
|
nuclear@39
|
168 lib.goat3d_add_mtl.argtypes = [c_void_p, c_void_p]
|
nuclear@39
|
169 lib.goat3d_add_mtl.restype = None
|
nuclear@36
|
170
|
nuclear@39
|
171 lib.goat3d_create_mtl.argtypes = None
|
nuclear@39
|
172 lib.goat3d_create_mtl.restype = c_void_p
|
nuclear@36
|
173
|
nuclear@39
|
174 lib.goat3d_set_mtl_name.argtypes = [c_void_p, c_char_p]
|
nuclear@39
|
175 lib.goat3d_set_mtl_name.restype = None
|
nuclear@33
|
176
|
nuclear@40
|
177 lib.goat3d_set_mtl_attrib1f.argtypes = [c_void_p, c_char_p, c_float]
|
nuclear@40
|
178 lib.goat3d_set_mtl_attrib1f.restype = None
|
nuclear@40
|
179
|
nuclear@39
|
180 lib.goat3d_set_mtl_attrib4f.argtypes = [c_void_p, c_char_p, c_float, c_float, c_float, c_float]
|
nuclear@39
|
181 lib.goat3d_set_mtl_attrib4f.restype = None
|
nuclear@33
|
182
|
nuclear@39
|
183 lib.goat3d_set_mtl_attrib_map.argtypes = [c_void_p, c_char_p, c_char_p]
|
nuclear@39
|
184 lib.goat3d_set_mtl_attrib_map.restype = None
|
nuclear@33
|
185
|
nuclear@39
|
186 lib.goat3d_add_mesh.argtypes = [c_void_p, c_void_p]
|
nuclear@39
|
187 lib.goat3d_add_mesh.restype = None
|
nuclear@33
|
188
|
nuclear@39
|
189 lib.goat3d_create_mesh.argtypes = None
|
nuclear@39
|
190 lib.goat3d_create_mesh.restype = c_void_p
|
nuclear@38
|
191
|
nuclear@39
|
192 lib.goat3d_set_mesh_name.argtypes = [c_void_p, c_char_p]
|
nuclear@39
|
193 lib.goat3d_set_mesh_name.restype = None
|
nuclear@38
|
194
|
nuclear@39
|
195 lib.goat3d_set_mesh_mtl.argtypes = [c_void_p, c_void_p]
|
nuclear@39
|
196 lib.goat3d_set_mesh_mtl.restype = None
|
nuclear@38
|
197
|
nuclear@40
|
198 lib.goat3d_add_mesh_attrib3f.argtypes = [c_void_p, c_int, c_float, c_float, c_float]
|
nuclear@40
|
199 lib.goat3d_add_mesh_attrib3f.restype = None
|
nuclear@38
|
200
|
nuclear@40
|
201 lib.goat3d_add_mesh_attrib4f.argtypes = [c_void_p, c_int, c_float, c_float, c_float, c_float]
|
nuclear@40
|
202 lib.goat3d_add_mesh_attrib4f.restype = None
|
nuclear@40
|
203
|
nuclear@40
|
204 lib.goat3d_add_mesh_face.argtypes = [c_void_p, c_int, c_int, c_int]
|
nuclear@40
|
205 lib.goat3d_add_mesh_face.restype = None
|
nuclear@38
|
206
|
nuclear@39
|
207 lib.goat3d_add_node.argtypes = [c_void_p, c_void_p]
|
nuclear@39
|
208 lib.goat3d_add_node.restype = None
|
nuclear@38
|
209
|
nuclear@39
|
210 lib.goat3d_create_node.argtypes = None
|
nuclear@39
|
211 lib.goat3d_create_node.restype = c_void_p
|
nuclear@38
|
212
|
nuclear@39
|
213 lib.goat3d_set_node_name.argtypes = [c_void_p, c_char_p]
|
nuclear@39
|
214 lib.goat3d_set_node_name.restype = None
|
nuclear@38
|
215
|
nuclear@39
|
216 lib.goat3d_set_node_object.argtypes = [c_void_p, c_int, c_void_p]
|
nuclear@39
|
217 lib.goat3d_set_node_object.restype = None
|
nuclear@38
|
218
|
nuclear@39
|
219 lib.goat3d_add_node_child.argtypes = [c_void_p, c_void_p]
|
nuclear@39
|
220 lib.goat3d_add_node_child.restype = None
|
nuclear@38
|
221
|
nuclear@39
|
222 lib.goat3d_set_node_position.argtypes = [c_void_p, c_float, c_float, c_float, c_long]
|
nuclear@39
|
223 lib.goat3d_set_node_position.restype = None
|
nuclear@38
|
224
|
nuclear@39
|
225 lib.goat3d_set_node_rotation.argtypes = [c_void_p, c_float, c_float, c_float, c_float, c_long]
|
nuclear@39
|
226 lib.goat3d_set_node_rotation.restype = None
|
nuclear@38
|
227
|
nuclear@39
|
228 lib.goat3d_set_node_scaling.argtypes = [c_void_p, c_float, c_float, c_float, c_long]
|
nuclear@39
|
229 lib.goat3d_set_node_scaling.restype = None
|
nuclear@38
|
230
|
nuclear@39
|
231 lib.goat3d_set_node_pivot.argtypes = [c_void_p, c_float, c_float, c_float]
|
nuclear@39
|
232 lib.goat3d_set_node_pivot.restype = None
|
nuclear@38
|
233
|
nuclear@39
|
234 lib.goat3d_save.argtypes = [c_void_p, c_char_p]
|
nuclear@39
|
235 return lib
|