1
0
mirror of https://github.com/Escartem/AnimeWwise.git synced 2026-06-04 23:40:25 +08:00

switch from bms to wavescan script

This commit is contained in:
Escartem
2023-10-13 11:01:25 +02:00
parent 3f5b041164
commit 4feeb907aa
7 changed files with 32 additions and 4794 deletions

3
.gitignore vendored
View File

@@ -2,4 +2,5 @@ output/
temp/
*.pck
*.hdiff
tools.zip
tools.zip
__pycache__/

View File

@@ -2,6 +2,7 @@ import os
import shutil
import zipfile
import filecmp
import wavescan
import subprocess
from halo import Halo
from progress.bar import PixelBar
@@ -60,20 +61,10 @@ def main():
if alone:
output_path = "wem"
# prepare args
args = [
path("tools/quickbms/quickbms.exe"),
"-o",
"-Y",
path("tools/quickbms/wavescan.bms"),
path(f"temp/{file}"),
path(f"temp/{output_path}")
]
# update spinner and call program
spinner.text = f"[{curr}/{steps}] Extracting"
spinner.start()
call(args)
wavescan.extract(path(f"temp/{file}"), path(f"temp/{output_path}"))
spinner.stop()
print(f"[{curr}/{steps}] Extracting")
@@ -114,20 +105,10 @@ def main():
if not alone:
curr += 1
# prepare args
args = [
path("tools/quickbms/quickbms.exe"),
"-o",
"-Y",
path("tools/quickbms/wavescan.bms"),
path(f"temp/{file}"),
path(f"temp/patched_decoded")
]
# update spinner and call program
spinner.text = f"[{curr}/{steps}] Extracting patch"
spinner.start()
call(args)
wavescan.extract(path(f"temp/{file}"), path(f"temp/patched_decoded"))
spinner.stop()
print(f"[{curr}/{steps}] Extracting patch")

View File

@@ -3,16 +3,15 @@ import struct
class FileReader:
"""
Simplified byte file reader with buffer
Not particularly optimised, contains repetitive functions
In the scope of this project, not everything will be used either
Simplified byte file reader with buffer, it's not particularly optimised but good enough
In the scope of this project, not everything will be used in here
"""
def __init__(self, file, endianness: str):
def __init__(self, file, endianness:str):
self.stream = file
self.endianness = endianness
def _read(self, mode:str, bufferLength:int, endianness=None) -> bytes:
def _read(self, mode:str, bufferLength:int, endianness:str=None) -> bytes:
# endianness override
if endianness is None:
endianness = self.endianness
@@ -22,31 +21,31 @@ class FileReader:
return struct.unpack(f"{endianness}{mode}", bytearray(self.stream.read(bufferLength)))[0]
# read methods
def ReadInt16(self, endianness=None) -> int:
def ReadInt16(self, endianness:str=None) -> int:
return self._read("h", 2, endianness)
def ReadUInt16(self, endianness=None) -> int:
def ReadUInt16(self, endianness:str=None) -> int:
return self._read("H", 2, endianness)
def ReadInt32(self, endianness=None) -> int:
def ReadInt32(self, endianness:str=None) -> int:
return self._read("i", 4, endianness)
def ReadUInt32(self, endianness=None) -> int:
def ReadUInt32(self, endianness:str=None) -> int:
return self._read("I", 4, endianness)
def ReadLong(self, endianness=None) -> int:
def ReadLong(self, endianness:str=None) -> int:
return self._read("l", 4, endianness)
def ReadULong(self, endianness=None) -> int:
def ReadULong(self, endianness:str=None) -> int:
return self._read("L", 4, endianness)
def ReadLongLong(self, endianness=None) -> int:
def ReadLongLong(self, endianness:str=None) -> int:
return self._read("q", 8, endianness)
def ReadULongLong(self, endianness=None) -> int:
def ReadULongLong(self, endianness:str=None) -> int:
return self._read("Q", 8, endianness)
def ReadBytes(self, length:int, endianness=None) -> bytes:
def ReadBytes(self, length:int, endianness:str=None) -> bytes:
return self._read(f"{str(length)}s", int(length), endianness)
# buffer utils

Binary file not shown.

File diff suppressed because it is too large Load Diff

View File

@@ -1,67 +0,0 @@
# modified version to ignore filenames (and wav)
#
# scan data for wave files
# RIFF and RIFX header supported
# note: There are wave files with a wrong file size after RIFF/RIFX
# This script takes the stream size, adds the header size and writes the correct size after RIFF/RIFX
# (c) 2012-06-26 by AlphaTwentyThree
#
# future update plans:
# - option to also write data between found wave files to disk
# - option to automatically transform the file to a playable or at least decodable format
for i = 1 # run through loop with count variable i
FindLoc OFFSET string "WAVE" 0 "" # search for "WAVE", save position as variable OFFSET
if OFFSET == "" # when nothing is found
cleanexit # the script exits (e.g. at end of file)
endif
math OFFSET -= 8 # jump to possible
goto OFFSET # RIFF/RIFX file start
getDstring IDENT 4 # read string of 4 bytes, save variable as IDENT
if IDENT == "RIFX" # differentiate between header possibilities
endian big # set endianness to big, if file has RIFX identifier
callfunction write 1 # see function section below
elif IDENT == "RIFF" # endianness stays little
callfunction write 1 # also run function
else # string "WAVE" found, but doesn't belong to wave file
set SIZE 0xc # do as if something with 0xc bytes was found to continue search from the right position
endif
set SEARCH OFFSET # set marker to position from where to search next
math SEARCH += SIZE # (that would be after the file that was found)
if SEARCH == FSIZE # in case the last found file ends with the main file, we exit
cleanexit
endif
goto SEARCH # if we haven't exited the script above, we set out cursor to after the last found file
next i
startfunction write # function "write" starts here, is called when a wave file is found above
get NAME basename # save name without extension under variable NAME
string NAME += "_" # add underscore to the name
string NAME += i # add the loop variable to the name
goto OFFSET # set cursor to the beginning of the found file
get DUMMY long # RIFF/RIFX identifier, not needed
get DUMMY long # riff size, not needed
get DUMMY long # "WAVE", not needed, we arrive at the "fmt " section
for # loop search for the "data" section at the start of the stream (get the stream size from there)
getDstring AREA_NAME 4 # name of area in header
get AREA_SIZE long # size of area in header
savepos MYOFF # save position we are at
if AREA_NAME == "data" # when we arrive at the needed "data" area:
break # we exit the loop
else # otherwise:
math MYOFF += AREA_SIZE # not reached "data" area -> adjust cursor position...
goto MYOFF # ... and go there
endif
next # remember: the cursor is now directly at the stream start
set STREAMSIZE AREA_SIZE # the last AREA_SIZE is the size we need (size of the audio stream)
set HEADERSIZE MYOFF #
math HEADERSIZE -= OFFSET # calculate the size of the stream header (offset - offset = size)
set SIZE HEADERSIZE #
math SIZE += STREAMSIZE # calculate complete file size (header + stream = file)
log MEMORY_FILE OFFSET SIZE # write file to memory
math SIZE -= 8 # subtract 8 bytes to get the riff size
putVarChr MEMORY_FILE 4 SIZE long # write the correct riff size to the header inside the memory
string NAME += ".wem" # add extension to the name (the name could contain the name of the first marker if the file has markers)
math SIZE += 8 # add the subtracted 8 bytes again
log NAME 0 SIZE MEMORY_FILE # write file in memory to disk
endfunction # remember that we continue with our next i now!

View File

@@ -1,16 +1,18 @@
# Custom rewrite of the Wwise AKPK packages extractor, original by Nicknine and bnnm
# TODO: use extracted files id with the mapping table to restore file names
# TODO: make this script callable by the main one
from filereader import FileReader
import os
filename = "External0.pck"
cwd = os.getcwd()
reader = FileReader(open(filename, "rb"), "little") # defaults to little endian
reader = None
bank_version = 0
def main():
def extract(input_file, output_folder):
global bank_version
global reader
reader = FileReader(open(input_file, "rb"), "little") # defaults to little endian
# check file
if reader.ReadBytes(4) != b"AKPK":
@@ -50,7 +52,7 @@ def main():
# extract each sector
for sector in sectors:
extract_sector(*sector[1:], endianness, lang_array, bank_version)
extract_sector(*sector[1:], endianness, lang_array, bank_version, output_folder)
if sector[0] and bank_version == 0:
if externals_sector_size == 0:
@@ -109,7 +111,7 @@ def detect_bank_version(offset):
reader.SetBufferPos(current)
def extract_sector(section_size, is_sounds, is_externals, ext, endianness, lang_array, bank_version, filter_bnk_only=0, filter_wem_only=0):
def extract_sector(section_size, is_sounds, is_externals, ext, endianness, lang_array, bank_version, output_folder, filter_bnk_only=0, filter_wem_only=0):
# check sector validity
if section_size == 0:
return
@@ -193,20 +195,18 @@ def extract_sector(section_size, is_sounds, is_externals, ext, endianness, lang_
if filter_wem_only == 1 and ext != "wem":
continue
print(f"NAME - {name} | OFFSET - {offset} | SIZE - {size}")
# file infos
# print(f"NAME - {name} | OFFSET - {offset} | SIZE - {size}")
# save file into disk
current = reader.GetBufferPos()
reader.SetBufferPos(offset)
file_data = reader.ReadBytes(size)
os.makedirs(os.path.join(cwd, os.path.dirname(name)), exist_ok=True)
os.makedirs(output_folder, exist_ok=True)
with open(os.path.join(cwd, name), "wb+") as f:
with open(os.path.join(output_folder, os.path.basename(name)), "wb+") as f:
f.write(file_data)
f.close()
reader.SetBufferPos(current)
if __name__ == "__main__":
main()