Try to write out the skin.

Something's not working as all I get is a black texture, but the basics
(MDL writing) seem to be ok.
This commit is contained in:
Bill Currie 2011-09-22 00:58:57 +09:00
parent ba4ccaf816
commit a58f9582b0
2 changed files with 113 additions and 2 deletions

View file

@ -43,6 +43,53 @@ def export_mdl(operator, context, filepath):
"Mesh has faces with more than 3 vertices.")
return {'CANCELLED'}
#reset selection to what it was before the check.
for f, s in map(lambda x,y: (x, y), mesh.faces, save_select):
for f, s in map(lambda x, y: (x, y), mesh.faces, save_select):
f.select = s
mdl = MDL()
mdl.name = obj.name
mdl.ident = "IDPO" #only 8 bit for now
mdl.version = 6 #write only version 6 (nothing usable uses 3)
mdl.scale = (1.0, 1.0, 1.0) #FIXME
mdl.scale_origin = (0.0, 0.0, 0.0) #FIXME
mdl.boundingradius = 1.0 #FIXME
mdl.eyeposition = (0.0, 0.0, 0.0) #FIXME
mdl.synctype = 0 #FIXME config (right default?)
mdl.flags = 0 #FIXME config
mdl.size = 0 #FIXME ???
mdl.skins = []
mdl.stverts = []
mdl.tris = []
mdl.frames = []
if (not mesh.uv_textures or not mesh.uv_textures[0].data
or not mesh.uv_textures[0].data[0].image):
mdl.skinwidth = mdl.skinheight = 4
skin = MDL.Skin()
skin.type = 0
skin.pixels = bytes(mdl.skinwidth * mdl.skinheight) # black skin
else:
image = mesh.uv_textures[0].data[0].image
mdl.skinwidth, mdl.skinheight = image.size
skin = MDL.Skin()
skin.type = 0
skin.pixels = bytearray(mdl.skinwidth * mdl.skinheight) # preallocate
for y in range(mdl.skinheight):
for x in range(mdl.skinwidth):
oi = y * mdl.skinwidth + x
# quake textures are top to bottom, but blender images
# are bottom to top
ii = ((mdl.skinheight - 1 - y) * mdl.skinwidth + x) * 4
rgb = image.pixels[ii : ii + 3] # ignore alpha
rgb = map(lambda x: int(x * 255 + 0.5), rgb)
best = (3*256*256, -1)
for i, p in enumerate(palette):
if i > 255: # should never happen
break
r = 0
for x in map (lambda a, b: (a - b) ** 2, rgb, p):
r += x
if r < best[0]:
best = (r, i)
skin.pixels[i] = best[1]
mdl.skins.append(skin)
mdl.write (filepath)
return {'FINISHED'}

View file

@ -19,7 +19,7 @@
# <pep8 compliant>
from struct import unpack
from struct import unpack, pack
from mathutils import Vector
@ -45,6 +45,15 @@ class MDL:
return self
self.read_pixels(mdl)
return self
def write(self, mdl, sub=9):
if not sub:
mdl.write_int(self.type)
if self.type:
mdl.write_float(self.times)
for subskin in self.skins:
subskin.write(mdl, 1)
return
mdl.write_bytes(self.pixels)
def read_pixels(self, mdl):
size = self.width * self.height
@ -147,6 +156,32 @@ class MDL:
s = s + chr(c)
return s
def write_byte(self, data):
if not hasattr(data, "__len__"):
data = (data,)
self.file.write(pack(("<%dB" % len(data)), *data))
def write_int(self, data):
if not hasattr(data, "__len__"):
data = (data,)
self.file.write(pack(("<%di" % len(data)), *data))
def write_float(self, data):
if not hasattr(data, "__len__"):
data = (data,)
self.file.write(pack(("<%df" % len(data)), *data))
def write_bytes(self, data, size=-1):
if size == -1:
size = len(data)
self.file.write(data[:size])
if size > len(data):
self.file.write(bytes(size - len(data)))
def write_string(self, data, size=-1):
data = data.encode()
self.write_bytes(data, size)
def __init__(self):
pass
def read(self, filepath):
@ -185,3 +220,32 @@ class MDL:
for i in range(numframes):
self.frames.append(MDL.Frame().read(self, numverts))
return self
def write (self, filepath):
self.file = open(filepath, "wb")
self.write_string (self.ident, 4)
self.write_int (self.version)
self.write_float (self.scale)
self.write_float (self.scale_origin)
self.write_float (self.boundingradius)
self.write_float (self.eyeposition)
self.write_int (len(self.skins))
self.write_int ((self.skinwidth, self.skinheight))
self.write_int (len(self.stverts))
self.write_int (len(self.tris))
self.write_int (len(self.frames))
self.write_int (self.synctype)
self.write_int (self.flags)
self.write_float (self.size)
# write out the skin data
for skin in self.skins:
skin.write(self)
#write out the st verts (uv map)
for stvert in self.stverts:
stvert.write(self)
#write out the tris
for tri in self.tris:
tri.write(self)
#write out the frames
for frame in self.frames:
frame.write(self)