def unpack(self, pat0, binfile): super().unpack(pat0, binfile) origPathOffset, pat0.framecount, num_mats, num_tex, num_plt, pat0.loop = binfile.read('I4HI', 24) if num_plt: raise ValueError('Palettes unsupported! Detected palette while parsing') assert origPathOffset == 0 binfile.recall() # section 0 folder = Folder(binfile) folder.unpack(binfile) unpacked = [] while len(folder): name = folder.recallEntryI() anim = Pat0MatAnimation(name, pat0.parent, pat0.framecount, pat0.loop) unpacked.append(UnpackPat0Animation(anim, binfile)) pat0.mat_anims.append(anim) binfile.recall() # section 1 textures = [] binfile.start() for i in range(num_tex): textures.append(binfile.unpack_name()) binfile.end() binfile.recall() binfile.recall() for x in unpacked: x.hook_textures(textures) binfile.end()
def generateRoot(self, subfiles): """ Generates the root folders Does not hook up data pointers except the head group, returns (rootFolders, bytesize) """ rootFolders = [] # for storing Index Groups byteSize = 0 # Create folder indexing folders rootFolder = Folder(self.binfile, 'root') rootFolders.append(rootFolder) offsets = [] # for tracking offsets from first group to others # Create folder for each section the brres has for i in range(len(subfiles)): folder_name, folder = subfiles[i] size = len(folder) if size: f = Folder(self.binfile, folder_name) for j in range(size): f.addEntry(folder[j].name) # might not have name? rootFolder.addEntry(f.name) rootFolders.append(f) offsets.append(byteSize) byteSize += f.byteSize() # now update the dataptrs rtsize = rootFolder.byteSize() entries = rootFolder.entries for i in range(len(offsets)): entries[i].dataPtr = offsets[i] + rtsize return rootFolders
def unpack(self, brres, binfile): """ Unpacks the brres """ self.offset = binfile.start() magic = binfile.readMagic() if magic != 'bres': raise UnpackingError(brres, '"{}" not a brres file'.format(brres.name)) bom = binfile.read("H", 2) binfile.bom = "<" if bom == 0xfffe else ">" binfile.advance(2) l = binfile.readLen() rootoffset, numSections = binfile.read("2h", 4) binfile.offset = rootoffset root = binfile.readMagic() assert (root == 'root') section_length = binfile.read("I", 4) root = Folder(binfile, root) root.unpack(binfile) self.section_offsets = [] # open all the folders for i in range(len(root)): self.unpack_folder(root.recallEntryI()) self.section_offsets.append(binfile.names_offset) brres.unknown = self.unpack_unknown() binfile.end() self.post_unpacking(brres)
def unpack_subfiles(self, klass, binfile): subfolder = Folder(binfile, self.folder_name) subfolder.unpack(binfile) r = [] for i in range(len(subfolder)): name = subfolder.recallEntryI() self.section_offsets.append(binfile.offset) r.append(klass(name, self.node, binfile)) return r
def recursive_add_unknown(self, parent_dir, node): parent_dir.addEntry(node.name) if type(node) == UnknownFolder: f = Folder(self.binfile, node.name) node.folder = f for x in node.subfiles: self.recursive_add_unknown(f, x) return f.byteSize() return 0
def unpack(self, clr0, binfile): super().unpack(clr0, binfile) _, clr0.framecount, num_entries, clr0.loop = binfile.read('i2Hi', 12) binfile.recall() # section 0 folder = Folder(binfile) folder.unpack(binfile) while len(folder): anim = Clr0Animation(folder.recallEntryI(), clr0) self.UnpackSub(anim, binfile) clr0.animations.append(anim) binfile.end()
def unpack(self, chr0, binfile): super().unpack(chr0, binfile) _, chr0.framecount, num_entries, chr0.loop, chr0.scaling_rule = binfile.read( 'I2H2I', 16) binfile.recall() # section 0 f = Folder(binfile) f.unpack(binfile) chr0.data = binfile.readRemaining() # printCollectionHex(self.data) while len(f): name = f.recallEntryI() chr0.animations.append( chr0.ModelAnim(name, binfile.offset - binfile.beginOffset)) binfile.end()
def unpackSection(self, binfile, section_klass, name, return_nodes=True): """ unpacks section by creating items of type section_klass and adding them to section list index """ # ignore fur sections for v8 mdl0s group = [] if binfile.recall(): # from offset header folder = Folder(binfile, name) folder.unpack(binfile) while len(folder.entries): name = folder.recallEntryI() k = section_klass(name, self.node, binfile=binfile) group.append(k) if not return_nodes else group.append(k.node) return group
def pack(self, pat0, binfile): super().pack(pat0, binfile) textures = pat0.getTextures() anims = pat0.mat_anims binfile.write('I4HI', 0, pat0.framecount, len(anims), len(textures), 0, pat0.loop) binfile.createRef() # section 0: data folder = Folder(binfile) # index group for x in anims: folder.addEntry(x.name) folder.pack(binfile) packing = [] for x in anims: # Headers/flags folder.createEntryRefI() packing.append(PackPat0Animation(x, binfile)) for x in packing: # key frame lists x.pack_frames(binfile, textures) binfile.createRef() # section 1: textures binfile.start() for x in textures: binfile.storeNameRef(x) binfile.end() binfile.createRef() # section 2: palettes binfile.createRef() # section 3: nulls binfile.advance(len(textures) * 4) binfile.createRef() # section 4: palette ptr table binfile.end()
def unpack_shaders(self, binfile): # special treatment for shader unpacking, track offsets so as to unpack once only shader_offset_map = {} if binfile.recall(): # from offset header folder = Folder(binfile, 'Shaders') folder.unpack(binfile) while len(folder.entries): name = folder.recallEntryI() offset = binfile.offset if offset in shader_offset_map: continue shader_offset_map[offset] = UnpackShader(name, self.node, binfile=binfile).node return shader_offset_map
def unpack(self, chr0, binfile): super().unpack(chr0, binfile) _, chr0.framecount, num_entries, chr0.loop, chr0.scaling_rule = binfile.read( 'I2H2I', 16) binfile.recall() # section 0 (animation data) f = Folder(binfile) f.unpack(binfile) chr0.data = binfile.readRemaining() while len(f): name = f.recallEntryI() bone_anim = chr0.BoneAnimation(name, self.node, binfile, chr0.framecount, chr0.loop) bone_anim.offset = binfile.offset - binfile.beginOffset # UnpackChr0BoneAnim(bone_anim, binfile) chr0.animations.append(bone_anim) # chr0.animations.append(chr0.BoneAnimation(name, binfile.offset - binfile.beginOffset)) binfile.end()
def unpack(self, srt0, binfile): super().unpack(srt0, binfile) uk, srt0.framecount, size, srt0.matrixmode, srt0.loop = binfile.read( "I2H2I", 16) # advance to section 0 binfile.recall() folder = Folder(binfile, "srt0root") folder.unpack(binfile) while True: e = folder.openI() if not e: break mat = SRTMatAnim(e, srt0.framecount) UnpackSrt0Material(mat, binfile) srt0.matAnimations.append(mat) # binfile.recall() # section 1 (unknown) # self.section1 = binfile.readRemaining(self.byte_len) binfile.end()
def unpack(self, shp0, binfile): # print('{} Warning: Shp0 not supported, unable to edit'.format(self.parent.name)) super().unpack(shp0, binfile) orig_path, shp0.framecount, num_anim, shp0.loop = binfile.read( 'I2HI', 12) binfile.recall(1) # Section 1 string list binfile.start() for i in range(num_anim): shp0.strings.append(binfile.unpack_name()) binfile.end() binfile.recall() # Section 0 Data folder = Folder(binfile) folder.unpack(binfile) while len(folder): anim = Shp0Animation(folder.recallEntryI(), shp0) self.UnpackSub(anim, binfile) shp0.animations.append(anim) binfile.end()
def pack(self, clr0, binfile): super().pack(clr0, binfile) animations = clr0.animations binfile.write('i2Hi', 0, clr0.framecount, len(animations), clr0.loop) binfile.createRef() # section 0 folder = Folder(binfile) for x in animations: folder.addEntry(x.name) folder.pack(binfile) for x in animations: folder.createEntryRefI() self.PackSub(x, binfile) binfile.end()
def unpack(self, node, binfile): """Returns tuple(name, data, is_folder)""" if self.is_folder: folder = Folder(binfile, node) folder.unpack(binfile) entries = [] for i in range(len(folder)): entries.append((folder.recallEntryI(), binfile.offset)) self.boundary_offsets.append(binfile.offset) entries = sorted(entries, key=lambda x: x[1]) nodes = [] for i in range(len(entries)): x = entries[i] binfile.offset = x[1] nodes.append( UnknownUnpacker(binfile, self.boundary_offsets, x[0]).node) self.node = UnknownFolder(node, nodes) else: self.node = UnknownFile(node, binfile.read('{}B'.format(self.length), 0))
def generateRoot(self, subfiles): """ Generates the root folders Does not hook up data pointers, returns (rootFolders, bytesize) """ rootFolders = [] # for storing Index Groups # Create folder indexing folders self.rootFolder = rootFolder = Folder(self.binfile, 'root') # Create folder for each section the brres has for i in range(len(subfiles)): folder_name, folder = subfiles[i] size = len(folder) if size: f = Folder(self.binfile, folder_name) for j in range(size): f.addEntry(folder[j].name) # might not have name? rootFolder.addEntry(f.name) rootFolders.append(f) for uk in self.node.unknown: self.recursive_add_unknown(rootFolder, uk) return rootFolders
def packFolders(self, binfile): """ Generates the root folders Does not hook up data pointers except the head group, returns rootFolders """ root_folders = [] # for storing Index Groups sections = self.sections # Create folder for each section the MDL0 has i = 0 while i < len(sections): section = sections[i] if i == len( sections ) - 3: # special case for shaders: must add entry for each material section = sections[i - 1] if section: f = Folder(binfile, self.section_names[i]) for x in section: assert x f.addEntry(x.name) root_folders.append(f) binfile.createRef(i, False) # create the ref from stored offsets f.pack(binfile) else: root_folders.append(None) # create placeholder i += 1 return root_folders
def pack(self, chr0, binfile): super().pack(chr0, binfile) binfile.write('I2H2I', 0, chr0.framecount, len(chr0.animations), chr0.loop, chr0.scaling_rule) f = Folder(binfile) for x in chr0.animations: f.addEntry(x.name) binfile.createRef() f.pack(binfile) binfile.writeRemaining(chr0.data) for x in chr0.animations: # hackish way of overwriting the string offsets binfile.offset = binfile.beginOffset + x.offset f.createEntryRefI() binfile.storeNameRef(x.name) binfile.end()
def pack(self, shp0, binfile): super().pack(shp0, binfile) binfile.write('I2HI', 0, shp0.framecount, len(shp0.strings), shp0.loop) binfile.createRef() # section 0 folder = Folder(binfile) for x in shp0.animations: folder.addEntry(x.name) folder.pack(binfile) for x in shp0.animations: folder.createEntryRefI() self.PackSub(x, binfile) binfile.createRef() # section 1 binfile.start() for x in shp0.strings: binfile.storeNameRef(x) binfile.end() binfile.end()
def pack(self, srt0, binfile): """ Packs the data for SRT file """ super().pack(srt0, binfile) binfile.write("I2H2I", 0, srt0.framecount, len(srt0.matAnimations), srt0.matrixmode, srt0.loop) binfile.createRef() # create ref to section 0 # create index group folder = Folder(binfile, "srt0root") for x in srt0.matAnimations: folder.addEntry(x.name) folder.pack(binfile) packers = [] for x in srt0.matAnimations: folder.createEntryRefI() packers.append(PackSrt0Material(x, binfile)) # Now for key frames key_frame_lists = {} # map of offsets to frame lists for x in packers: x.consolidate(binfile, key_frame_lists) # binfile.createRef() # section 1 (unknown) # binfile.writeRemaining(self.section1) binfile.end()
def pack_root(self, scn0, binfile, packing_items): binfile.createRef() # section root root = Folder(binfile) index_groups = [] for i in range(5): if packing_items[i]: root.addEntry(scn0.FOLDERS[i]) f = Folder(binfile, scn0.FOLDERS[i]) index_groups.append(f) for item in packing_items[i]: f.addEntry(item.name) root.pack(binfile) for x in index_groups: root.createEntryRefI() x.pack(binfile) # doesn't create data pointers return index_groups
def unpack_subfiles(self, klass): subfolder = Folder(self.binfile, self.folder_name) subfolder.unpack(self.binfile) return [klass(subfolder.recallEntryI(), self.node, self.binfile) for i in range(len(subfolder))]