def __init__(self, sources, material, index, xmlnode=None): """A TriangleSet should not be created manually. Instead, call the :meth:`collada.geometry.Geometry.createTriangleSet` method after creating a geometry instance. """ if len(sources) == 0: raise DaeIncompleteError("A triangle set needs at least one input for vertex positions") if not "VERTEX" in sources: raise DaeIncompleteError("Triangle set requires vertex input") max_offset = max( [ max([input[0] for input in input_type_array]) for input_type_array in sources.values() if len(input_type_array) > 0 ] ) self.material = material self.index = index self.indices = self.index self.nindices = max_offset + 1 self.index.shape = (-1, 3, self.nindices) self.ntriangles = len(self.index) self.sources = sources if len(self.index) > 0: self._vertex = sources["VERTEX"][0][4].data self._vertex_index = self.index[:, :, sources["VERTEX"][0][0]] self.maxvertexindex = numpy.max(self._vertex_index) checkSource(sources["VERTEX"][0][4], ("X", "Y", "Z"), self.maxvertexindex) else: self._vertex = None self._vertex_index = None self.maxvertexindex = -1 if "NORMAL" in sources and len(sources["NORMAL"]) > 0 and len(self.index) > 0: self._normal = sources["NORMAL"][0][4].data self._normal_index = self.index[:, :, sources["NORMAL"][0][0]] self.maxnormalindex = numpy.max(self._normal_index) checkSource(sources["NORMAL"][0][4], ("X", "Y", "Z"), self.maxnormalindex) else: self._normal = None self._normal_index = None self.maxnormalindex = -1 if "TEXCOORD" in sources and len(sources["TEXCOORD"]) > 0 and len(self.index) > 0: self._texcoordset = tuple([texinput[4].data for texinput in sources["TEXCOORD"]]) self._texcoord_indexset = tuple( [self.index[:, :, sources["TEXCOORD"][i][0]] for i in xrange(len(sources["TEXCOORD"]))] ) self.maxtexcoordsetindex = [numpy.max(tex_index) for tex_index in self._texcoord_indexset] for i, texinput in enumerate(sources["TEXCOORD"]): checkSource(texinput[4], ("S", "T"), self.maxtexcoordsetindex[i]) else: self._texcoordset = tuple() self._texcoord_indexset = tuple() self.maxtexcoordsetindex = -1 if "TEXTANGENT" in sources and len(sources["TEXTANGENT"]) > 0 and len(self.index) > 0: self._textangentset = tuple([texinput[4].data for texinput in sources["TEXTANGENT"]]) self._textangent_indexset = tuple( [self.index[:, :, sources["TEXTANGENT"][i][0]] for i in xrange(len(sources["TEXTANGENT"]))] ) self.maxtextangentsetindex = [numpy.max(tex_index) for tex_index in self._textangent_indexset] for i, texinput in enumerate(sources["TEXTANGENT"]): checkSource(texinput[4], ("X", "Y", "Z"), self.maxtextangentsetindex[i]) else: self._textangentset = tuple() self._textangent_indexset = tuple() self.maxtextangentsetindex = -1 if "TEXBINORMAL" in sources and len(sources["TEXBINORMAL"]) > 0 and len(self.index) > 0: self._texbinormalset = tuple([texinput[4].data for texinput in sources["TEXBINORMAL"]]) self._texbinormal_indexset = tuple( [self.index[:, :, sources["TEXBINORMAL"][i][0]] for i in xrange(len(sources["TEXBINORMAL"]))] ) self.maxtexbinormalsetindex = [numpy.max(tex_index) for tex_index in self._texbinormal_indexset] for i, texinput in enumerate(sources["TEXBINORMAL"]): checkSource(texinput[4], ("X", "Y", "Z"), self.maxtexbinormalsetindex[i]) else: self._texbinormalset = tuple() self._texbinormal_indexset = tuple() self.maxtexbinormalsetindex = -1 if xmlnode is not None: self.xmlnode = xmlnode else: self._recreateXmlNode()
def __init__(self, sources, material, index, xmlnode=None): """A TriangleSet should not be created manually. Instead, call the :meth:`collada.geometry.Geometry.createTriangleSet` method after creating a geometry instance. """ if len(sources) == 0: raise DaeIncompleteError( 'A triangle set needs at least one input for vertex positions') if not 'VERTEX' in sources: raise DaeIncompleteError('Triangle set requires vertex input') max_offset = max([ max([input[0] for input in input_type_array]) for input_type_array in sources.values() if len(input_type_array) > 0 ]) self.material = material self.index = index self.indices = self.index self.nindices = max_offset + 1 self.index.shape = (-1, 3, self.nindices) self.ntriangles = len(self.index) self.sources = sources if len(self.index) > 0: self._vertex = sources['VERTEX'][0][4].data self._vertex_index = self.index[:, :, sources['VERTEX'][0][0]] self.maxvertexindex = numpy.max(self._vertex_index) checkSource(sources['VERTEX'][0][4], ('X', 'Y', 'Z'), self.maxvertexindex) else: self._vertex = None self._vertex_index = None self.maxvertexindex = -1 if 'NORMAL' in sources and len(sources['NORMAL']) > 0 and len( self.index) > 0: self._normal = sources['NORMAL'][0][4].data self._normal_index = self.index[:, :, sources['NORMAL'][0][0]] self.maxnormalindex = numpy.max(self._normal_index) checkSource(sources['NORMAL'][0][4], ('X', 'Y', 'Z'), self.maxnormalindex) else: self._normal = None self._normal_index = None self.maxnormalindex = -1 if 'TEXCOORD' in sources and len(sources['TEXCOORD']) > 0 and len( self.index) > 0: self._texcoordset = tuple( [texinput[4].data for texinput in sources['TEXCOORD']]) self._texcoord_indexset = tuple([ self.index[:, :, sources['TEXCOORD'][i][0]] for i in xrange(len(sources['TEXCOORD'])) ]) self.maxtexcoordsetindex = [ numpy.max(tex_index) for tex_index in self._texcoord_indexset ] for i, texinput in enumerate(sources['TEXCOORD']): checkSource(texinput[4], ('S', 'T'), self.maxtexcoordsetindex[i]) else: self._texcoordset = tuple() self._texcoord_indexset = tuple() self.maxtexcoordsetindex = -1 if 'TEXTANGENT' in sources and len(sources['TEXTANGENT']) > 0 and len( self.index) > 0: self._textangentset = tuple( [texinput[4].data for texinput in sources['TEXTANGENT']]) self._textangent_indexset = tuple([ self.index[:, :, sources['TEXTANGENT'][i][0]] for i in xrange(len(sources['TEXTANGENT'])) ]) self.maxtextangentsetindex = [ numpy.max(tex_index) for tex_index in self._textangent_indexset ] for i, texinput in enumerate(sources['TEXTANGENT']): checkSource(texinput[4], ('X', 'Y', 'Z'), self.maxtextangentsetindex[i]) else: self._textangentset = tuple() self._textangent_indexset = tuple() self.maxtextangentsetindex = -1 if 'TEXBINORMAL' in sources and len( sources['TEXBINORMAL']) > 0 and len(self.index) > 0: self._texbinormalset = tuple( [texinput[4].data for texinput in sources['TEXBINORMAL']]) self._texbinormal_indexset = tuple([ self.index[:, :, sources['TEXBINORMAL'][i][0]] for i in xrange(len(sources['TEXBINORMAL'])) ]) self.maxtexbinormalsetindex = [ numpy.max(tex_index) for tex_index in self._texbinormal_indexset ] for i, texinput in enumerate(sources['TEXBINORMAL']): checkSource(texinput[4], ('X', 'Y', 'Z'), self.maxtexbinormalsetindex[i]) else: self._texbinormalset = tuple() self._texbinormal_indexset = tuple() self.maxtexbinormalsetindex = -1 if xmlnode is not None: self.xmlnode = xmlnode else: self._recreateXmlNode()
def __init__(self, sourcebyid, bind_shape_matrix, joint_source, joint_matrix_source, weight_source, weight_joint_source, vcounts, vertex_weight_index, offsets, geometry, controller_node=None, skin_node=None): """Create a skin. :Parameters: sourceById A dict mapping id's to a collada source bind_shape_matrix A numpy array of floats (pre-shape) joint_source The string id for the joint source joint_matrix_source The string id for the joint matrix source weight_source The string id for the weight source weight_joint_source The string id for the joint source of weights vcounts A list with the number of influences on each vertex vertex_weight_index An array with the indexes as they come from <v> array offsets A list with the offsets in the weight index array for each source in (joint, weight) geometry The source geometry this should be applied to (geometry.Geometry) controller_node XML node of the <controller> tag which is the parent of this skin_node XML node of the <skin> tag if this is from there """ self.sourcebyid = sourcebyid self.bind_shape_matrix = bind_shape_matrix self.joint_source = joint_source self.joint_matrix_source = joint_matrix_source self.weight_source = weight_source self.weight_joint_source = weight_joint_source self.vcounts = vcounts self.vertex_weight_index = vertex_weight_index self.offsets = offsets self.geometry = geometry self.controller_node = controller_node self.skin_node = skin_node self.xmlnode = controller_node if not type(self.geometry) is Geometry: raise DaeMalformedError('Invalid reference geometry in skin') self.id = controller_node.get('id') if self.id is None: raise DaeMalformedError('Controller node requires an ID') self.nindices = max(self.offsets) + 1 if len(bind_shape_matrix) != 16: raise DaeMalformedError('Corrupted bind shape matrix in skin') self.bind_shape_matrix.shape = (4, 4) if not (joint_source in sourcebyid and joint_matrix_source in sourcebyid): raise DaeBrokenRefError("Input in joints not found") if not (type(sourcebyid[joint_source]) is source.NameSource or type(sourcebyid[joint_source]) is source.IDRefSource): raise DaeIncompleteError( "Could not find joint name input for skin") if not type(sourcebyid[joint_matrix_source]) is source.FloatSource: raise DaeIncompleteError( "Could not find joint matrix source for skin") joint_names = [j for j in sourcebyid[joint_source]] joint_matrices = sourcebyid[joint_matrix_source].data joint_matrices.shape = (-1, 4, 4) if len(joint_names) != len(joint_matrices): raise DaeMalformedError( "Skin joint and matrix inputs must be same length") self.joint_matrices = {} for n, m in zip(joint_names, joint_matrices): self.joint_matrices[n] = m if not (weight_source in sourcebyid and weight_joint_source in sourcebyid): raise DaeBrokenRefError("Weights input in joints not found") if not type(sourcebyid[weight_source]) is source.FloatSource: raise DaeIncompleteError("Could not find weight inputs for skin") if not (type(sourcebyid[weight_joint_source]) is source.NameSource or type(sourcebyid[weight_joint_source]) is source.IDRefSource): raise DaeIncompleteError( "Could not find weight joint source input for skin") self.weights = sourcebyid[weight_source] self.weight_joints = sourcebyid[weight_joint_source] try: newshape = [] at = 0 for ct in self.vcounts: this_set = self.vertex_weight_index[self.nindices * at:self.nindices * (at + ct)] this_set.shape = (ct, self.nindices) newshape.append(numpy.array(this_set)) at += ct self.index = newshape except: raise DaeMalformedError( 'Corrupted vcounts or index in skin weights') try: self.joint_index = [ influence[:, self.offsets[0]] for influence in self.index ] self.weight_index = [ influence[:, self.offsets[1]] for influence in self.index ] except: raise DaeMalformedError('Corrupted joint or weight index in skin') self.max_joint_index = numpy.max([ numpy.max(joint) if len(joint) > 0 else 0 for joint in self.joint_index ]) self.max_weight_index = numpy.max([ numpy.max(weight) if len(weight) > 0 else 0 for weight in self.weight_index ]) checkSource(self.weight_joints, ('JOINT', ), self.max_joint_index) checkSource(self.weights, ('WEIGHT', ), self.max_weight_index)
def __init__(self, sources, material, index, xmlnode=None): """A LineSet should not be created manually. Instead, call the :meth:`collada.geometry.Geometry.createLineSet` method after creating a geometry instance. """ if len(sources) == 0: raise DaeIncompleteError( 'A line set needs at least one input for vertex positions') if not 'VERTEX' in sources: raise DaeIncompleteError('Line set requires vertex input') #find max offset max_offset = max([ max([input[0] for input in input_type_array]) for input_type_array in sources.values() if len(input_type_array) > 0 ]) self.sources = sources self.material = material self.index = index self.indices = self.index self.nindices = max_offset + 1 self.index.shape = (-1, 2, self.nindices) self.nlines = len(self.index) if len(self.index) > 0: self._vertex = sources['VERTEX'][0][4].data self._vertex_index = self.index[:, :, sources['VERTEX'][0][0]] self.maxvertexindex = numpy.max(self._vertex_index) checkSource(sources['VERTEX'][0][4], ('X', 'Y', 'Z'), self.maxvertexindex) else: self._vertex = None self._vertex_index = None self.maxvertexindex = -1 if 'NORMAL' in sources and len(sources['NORMAL']) > 0 \ and len(self.index) > 0: self._normal = sources['NORMAL'][0][4].data self._normal_index = self.index[:, :, sources['NORMAL'][0][0]] self.maxnormalindex = numpy.max(self._normal_index) checkSource(sources['NORMAL'][0][4], ('X', 'Y', 'Z'), self.maxnormalindex) else: self._normal = None self._normal_index = None self.maxnormalindex = -1 if 'TEXCOORD' in sources and len(sources['TEXCOORD']) > 0 \ and len(self.index) > 0: self._texcoordset = tuple( [texinput[4].data for texinput in sources['TEXCOORD']]) self._texcoord_indexset = tuple([ self.index[:, :, sources['TEXCOORD'][i][0]] for i in xrange(len(sources['TEXCOORD'])) ]) self.maxtexcoordsetindex = [ numpy.max(tex_index) for tex_index in self._texcoord_indexset ] for i, texinput in enumerate(sources['TEXCOORD']): checkSource(texinput[4], ('S', 'T'), self.maxtexcoordsetindex[i]) else: self._texcoordset = tuple() self._texcoord_indexset = tuple() self.maxtexcoordsetindex = -1 if xmlnode is not None: self.xmlnode = xmlnode """ElementTree representation of the line set.""" else: self.index.shape = (-1) acclen = len(self.index) txtindices = ' '.join(map(str, self.index.tolist())) self.index.shape = (-1, 2, self.nindices) self.xmlnode = E.lines(count=str(self.nlines), material=self.material) all_inputs = [] for semantic_list in self.sources.values(): all_inputs.extend(semantic_list) for offset, semantic, sourceid, set, src in all_inputs: inpnode = E.input(offset=str(offset), semantic=semantic, source=sourceid) if set is not None: inpnode.set('set', str(set)) self.xmlnode.append(inpnode) self.xmlnode.append(E.p(txtindices))
def __init__(self, sources, material, index, vcounts, xmlnode=None): """A Polylist should not be created manually. Instead, call the :meth:`collada.geometry.Geometry.createPolylist` method after creating a geometry instance. """ if len(sources) == 0: raise DaeIncompleteError('A polylist set needs at least one input for vertex positions') if not 'VERTEX' in sources: raise DaeIncompleteError('Polylist requires vertex input') #find max offset max_offset = max([ max([input[0] for input in input_type_array]) for input_type_array in sources.values() if len(input_type_array) > 0]) self.material = material self.index = index self.indices = self.index self.nindices = max_offset + 1 self.vcounts = vcounts self.sources = sources self.index.shape = (-1, self.nindices) self.npolygons = len(self.vcounts) self.nvertices = numpy.sum(self.vcounts) if len(self.index) > 0 else 0 self.polyends = numpy.cumsum(self.vcounts) self.polystarts = self.polyends - self.vcounts self.polyindex = numpy.dstack((self.polystarts, self.polyends))[0] if len(self.index) > 0: self._vertex = sources['VERTEX'][0][4].data self._vertex_index = self.index[:,sources['VERTEX'][0][0]] self.maxvertexindex = numpy.max( self._vertex_index ) checkSource(sources['VERTEX'][0][4], ('X', 'Y', 'Z'), self.maxvertexindex) else: self._vertex = None self._vertex_index = None self.maxvertexindex = -1 if 'NORMAL' in sources and len(sources['NORMAL']) > 0 and len(self.index) > 0: self._normal = sources['NORMAL'][0][4].data self._normal_index = self.index[:,sources['NORMAL'][0][0]] self.maxnormalindex = numpy.max( self._normal_index ) checkSource(sources['NORMAL'][0][4], ('X', 'Y', 'Z'), self.maxnormalindex) else: self._normal = None self._normal_index = None self.maxnormalindex = -1 if 'TEXCOORD' in sources and len(sources['TEXCOORD']) > 0 \ and len(self.index) > 0: self._texcoordset = tuple([texinput[4].data for texinput in sources['TEXCOORD']]) self._texcoord_indexset = tuple([ self.index[:,sources['TEXCOORD'][i][0]] for i in xrange(len(sources['TEXCOORD'])) ]) self.maxtexcoordsetindex = [numpy.max(each) for each in self._texcoord_indexset] for i, texinput in enumerate(sources['TEXCOORD']): checkSource(texinput[4], ('S', 'T'), self.maxtexcoordsetindex[i]) else: self._texcoordset = tuple() self._texcoord_indexset = tuple() self.maxtexcoordsetindex = -1 if xmlnode is not None: self.xmlnode = xmlnode """ElementTree representation of the line set.""" else: txtindices = ' '.join(map(str, self.indices.flatten().tolist())) acclen = len(self.indices) self.xmlnode = E.polylist(count=str(self.npolygons), material=self.material) all_inputs = [] for semantic_list in self.sources.values(): all_inputs.extend(semantic_list) for offset, semantic, sourceid, set, src in all_inputs: inpnode = E.input(offset=str(offset), semantic=semantic, source=sourceid) if set is not None: inpnode.set('set', str(set)) self.xmlnode.append(inpnode) vcountnode = E.vcount(' '.join(map(str, self.vcounts))) self.xmlnode.append(vcountnode) self.xmlnode.append(E.p(txtindices))
def __init__(self, sourcebyid, bind_shape_matrix, joint_source, joint_matrix_source, weight_source, weight_joint_source, vcounts, vertex_weight_index, offsets, geometry, controller_node=None, skin_node=None): """Create a skin. :Parameters: sourceById A dict mapping id's to a collada source bind_shape_matrix A numpy array of floats (pre-shape) joint_source The string id for the joint source joint_matrix_source The string id for the joint matrix source weight_source The string id for the weight source weight_joint_source The string id for the joint source of weights vcounts A list with the number of influences on each vertex vertex_weight_index An array with the indexes as they come from <v> array offsets A list with the offsets in the weight index array for each source in (joint, weight) geometry The source geometry this should be applied to (geometry.Geometry) controller_node XML node of the <controller> tag which is the parent of this skin_node XML node of the <skin> tag if this is from there """ self.sourcebyid = sourcebyid self.bind_shape_matrix = bind_shape_matrix self.joint_source = joint_source self.joint_matrix_source = joint_matrix_source self.weight_source = weight_source self.weight_joint_source = weight_joint_source self.vcounts = vcounts self.vertex_weight_index = vertex_weight_index self.offsets = offsets self.geometry = geometry self.controller_node = controller_node self.skin_node = skin_node self.xmlnode = controller_node if not type(self.geometry) is Geometry: raise DaeMalformedError('Invalid reference geometry in skin') self.id = controller_node.get('id') if self.id is None: raise DaeMalformedError('Controller node requires an ID') self.nindices = max(self.offsets) + 1 if len(bind_shape_matrix) != 16: raise DaeMalformedError('Corrupted bind shape matrix in skin') self.bind_shape_matrix.shape = (4,4) if not(joint_source in sourcebyid and joint_matrix_source in sourcebyid): raise DaeBrokenRefError("Input in joints not found") if not(type(sourcebyid[joint_source]) is source.NameSource or type(sourcebyid[joint_source]) is source.IDRefSource): raise DaeIncompleteError("Could not find joint name input for skin") if not type(sourcebyid[joint_matrix_source]) is source.FloatSource: raise DaeIncompleteError("Could not find joint matrix source for skin") joint_names = [j for j in sourcebyid[joint_source]] joint_matrices = sourcebyid[joint_matrix_source].data joint_matrices.shape = (-1,4,4) if len(joint_names) != len(joint_matrices): raise DaeMalformedError("Skin joint and matrix inputs must be same length") self.joint_matrices = {} for n,m in zip(joint_names, joint_matrices): self.joint_matrices[n] = m if not(weight_source in sourcebyid and weight_joint_source in sourcebyid): raise DaeBrokenRefError("Weights input in joints not found") if not type(sourcebyid[weight_source]) is source.FloatSource: raise DaeIncompleteError("Could not find weight inputs for skin") if not(type(sourcebyid[weight_joint_source]) is source.NameSource or type(sourcebyid[weight_joint_source]) is source.IDRefSource): raise DaeIncompleteError("Could not find weight joint source input for skin") self.weights = sourcebyid[weight_source] self.weight_joints = sourcebyid[weight_joint_source] try: newshape = [] at = 0 for ct in self.vcounts: this_set = self.vertex_weight_index[self.nindices*at:self.nindices*(at+ct)] this_set.shape = (ct, self.nindices) newshape.append(numpy.array(this_set)) at+=ct self.index = newshape except: raise DaeMalformedError('Corrupted vcounts or index in skin weights') try: self.joint_index = [influence[:, self.offsets[0]] for influence in self.index] self.weight_index = [influence[:, self.offsets[1]] for influence in self.index] except: raise DaeMalformedError('Corrupted joint or weight index in skin') self.max_joint_index = numpy.max( [numpy.max(joint) if len(joint) > 0 else 0 for joint in self.joint_index] ) self.max_weight_index = numpy.max( [numpy.max(weight) if len(weight) > 0 else 0 for weight in self.weight_index] ) checkSource(self.weight_joints, ('JOINT',), self.max_joint_index) checkSource(self.weights, ('WEIGHT',), self.max_weight_index)
def __init__(self, sourcebyid, bind_shape_matrix, joint_source, joint_matrix_source, weight_source, weight_joint_source, vcounts, vertex_weight_index, offsets, geometry, controller_node=None, skin_node=None, controllerID=None): """Create a skin. :Parameters: sourceById A dict mapping id's to a collada source bind_shape_matrix A numpy array of floats (pre-shape) joint_source The string id for the joint source joint_matrix_source The string id for the joint matrix source weight_source The string id for the weight source weight_joint_source The string id for the joint source of weights vcounts A list with the number of influences on each vertex vertex_weight_index An array with the indexes as they come from <v> array offsets A list with the offsets in the weight index array for each source in (joint, weight) geometry The source geometry this should be applied to (geometry.Geometry) controller_node XML node of the <controller> tag which is the parent of this skin_node XML node of the <skin> tag if this is from there controllerID The string id for current controller (optional) if controller_node is not provided, feed controllerID from here directly """ self.sourceById = sourcebyid self.bind_shape_matrix = bind_shape_matrix self.joint_source = joint_source self.joint_matrix_source = joint_matrix_source self.weight_source = weight_source self.weight_joint_source = weight_joint_source self.vcounts = vcounts self.vertex_weight_index = vertex_weight_index self.offsets = offsets self.geometry = geometry self.controller_node = controller_node self.skin_node = skin_node if not type(self.geometry) is Geometry: raise DaeMalformedError('Invalid reference geometry in skin') if controller_node is not None: self.id = controller_node.get('id') else: if controllerID: self.id = controllerID if self.id is None: raise DaeMalformedError('Controller node requires an ID') self.nindices = max(self.offsets) + 1 if len(bind_shape_matrix) != 16: raise DaeMalformedError('Corrupted bind shape matrix in skin') self.bind_shape_matrix.shape = (4, 4) if not (joint_source in sourcebyid and joint_matrix_source in sourcebyid): raise DaeBrokenRefError("Input in joints not found") if not (type(sourcebyid[joint_source]) is source.NameSource or type(sourcebyid[joint_source]) is source.IDRefSource): raise DaeIncompleteError( "Could not find joint name input for skin") if not type(sourcebyid[joint_matrix_source]) is source.FloatSource: raise DaeIncompleteError( "Could not find joint matrix source for skin") joint_names = [j for j in sourcebyid[joint_source]] joint_matrices = sourcebyid[joint_matrix_source].data joint_matrices.shape = (-1, 4, 4) if len(joint_names) != len(joint_matrices): raise DaeMalformedError( "Skin joint and matrix inputs must be same length") self.joint_matrices = {} for n, m in zip(joint_names, joint_matrices): self.joint_matrices[n] = m if not (weight_source in sourcebyid and weight_joint_source in sourcebyid): raise DaeBrokenRefError("Weights input in joints not found") if not type(sourcebyid[weight_source]) is source.FloatSource: raise DaeIncompleteError("Could not find weight inputs for skin") if not (type(sourcebyid[weight_joint_source]) is source.NameSource or type(sourcebyid[weight_joint_source]) is source.IDRefSource): raise DaeIncompleteError( "Could not find weight joint source input for skin") self.weights = sourcebyid[weight_source] self.weight_joints = sourcebyid[weight_joint_source] try: newshape = [] at = 0 for ct in self.vcounts: this_set = self.vertex_weight_index[self.nindices * at:self.nindices * (at + ct)] this_set.shape = (ct, self.nindices) newshape.append(numpy.array(this_set)) at += ct self.index = newshape except: raise DaeMalformedError( 'Corrupted vcounts or index in skin weights') try: self.joint_index = [ influence[:, self.offsets[0]] for influence in self.index ] self.weight_index = [ influence[:, self.offsets[1]] for influence in self.index ] except: raise DaeMalformedError('Corrupted joint or weight index in skin') self.max_joint_index = numpy.max([ numpy.max(joint) if len(joint) > 0 else 0 for joint in self.joint_index ]) self.max_weight_index = numpy.max([ numpy.max(weight) if len(weight) > 0 else 0 for weight in self.weight_index ]) checkSource(self.weight_joints, ('JOINT', ), self.max_joint_index) checkSource(self.weights, ('WEIGHT', ), self.max_weight_index) # original lib missing xml reconstruct clause if controller_node is not None: self.xmlnode = controller_node else: sourcenodes = [] for srcid, src in self.sourceById.items(): sourcenodes.append(src.xmlnode) controllernode = E.skin(*sourcenodes) if len(geometry.id) > 0: controllernode.set("source", '#' + geometry.id) #construct bind_shape_matrix xml node node = E.bind_shape_matrix() bind_shape_matrix.shape = (-1, ) node.text = ' '.join(map(str, bind_shape_matrix.tolist())) controllernode.append(node) #construct <joints> node node = E.joints() node.append( E.input(semantic="JOINT", source="#%s" % self.joint_source)) node.append( E.input(semantic="INV_BIND_MATRIX", source="#%s" % self.joint_matrix_source)) controllernode.append(node) #construct <vertex_weights> node node = E.vertex_weights() #todo: offset is hardcoded here. node.append( E.input(semantic="JOINT", offset="0", source="#%s" % self.weight_joint_source)) node.append( E.input(semantic="WEIGHT", offset="1", source="#%s" % self.weight_source)) nodevcount = E.vcount() nodevcount.text = ' '.join(map(str, self.vcounts)) node.append(nodevcount) nodev = E.v() nodev.text = ' '.join(map(str, self.vertex_weight_index)) node.set("count", str(len(self.vcounts))) node.append(nodev) controllernode.append(node) self.xmlnode = E.controller(controllernode) if len(self.id) > 0: self.xmlnode.set("id", self.id)