mirror of
https://github.com/coop-deluxe/sm64coopdx.git
synced 2024-11-21 19:45:10 +00:00
DynOS Bin Compression (#131)
This commit is contained in:
parent
4da9812d9b
commit
f0c6668423
24 changed files with 665 additions and 310 deletions
3
Makefile
3
Makefile
|
@ -938,6 +938,9 @@ endif
|
|||
|
||||
# Coop specific libraries
|
||||
|
||||
# Zlib
|
||||
LDFLAGS += -lz
|
||||
|
||||
# Lua
|
||||
ifeq ($(WINDOWS_BUILD),1)
|
||||
ifeq ($(TARGET_BITS), 32)
|
||||
|
|
248
data/dynos.cpp.h
248
data/dynos.cpp.h
|
@ -65,6 +65,129 @@ enum {
|
|||
DOPT_CHOICEPARAM,
|
||||
};
|
||||
|
||||
//
|
||||
// DynOS Binary file struct
|
||||
//
|
||||
|
||||
class BinFile {
|
||||
private:
|
||||
void Grow(s32 newSize) {
|
||||
if (newSize >= mCapacity) {
|
||||
mCapacity = MAX(newSize, MAX(256, mCapacity * 2));
|
||||
u8 *newBuffer = (u8 *) calloc(mCapacity, 1);
|
||||
if (mData) {
|
||||
memcpy(newBuffer, mData, mSize);
|
||||
free(mData);
|
||||
}
|
||||
mData = newBuffer;
|
||||
}
|
||||
mSize = MAX(mSize, newSize);
|
||||
}
|
||||
|
||||
public:
|
||||
inline s32 Size() const { return mSize; }
|
||||
inline s32 Offset() const { return mOffset; }
|
||||
inline bool EoF() const { return mOffset >= mSize; }
|
||||
inline void SetOffset(s32 aOffset) const { mOffset = aOffset; }
|
||||
|
||||
public:
|
||||
static BinFile *OpenR(const char *aFilename) {
|
||||
FILE *f = fopen(aFilename, "rb");
|
||||
if (f) {
|
||||
fseek(f, 0, SEEK_END);
|
||||
BinFile *_BinFile = (BinFile *) calloc(1, sizeof(BinFile));
|
||||
_BinFile->mFilename = (const char *) memcpy(calloc(strlen(aFilename) + 1, 1), aFilename, strlen(aFilename));
|
||||
_BinFile->mReadOnly = true;
|
||||
_BinFile->Grow(ftell(f));
|
||||
rewind(f);
|
||||
fread(_BinFile->mData, 1, _BinFile->mSize, f);
|
||||
fclose(f);
|
||||
return _BinFile;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static BinFile *OpenW(const char *aFilename) {
|
||||
BinFile *_BinFile = (BinFile *) calloc(1, sizeof(BinFile));
|
||||
_BinFile->mFilename = (const char *) memcpy(calloc(strlen(aFilename) + 1, 1), aFilename, strlen(aFilename));
|
||||
_BinFile->mReadOnly = false;
|
||||
return _BinFile;
|
||||
}
|
||||
|
||||
static BinFile *OpenB(const u8 *aBuffer, s32 aSize) {
|
||||
BinFile *_BinFile = (BinFile *) calloc(1, sizeof(BinFile));
|
||||
_BinFile->mReadOnly = true;
|
||||
_BinFile->Grow(aSize);
|
||||
memcpy(_BinFile->mData, aBuffer, aSize);
|
||||
return _BinFile;
|
||||
}
|
||||
|
||||
static void Close(BinFile *&aBinFile) {
|
||||
if (aBinFile) {
|
||||
if (!aBinFile->mReadOnly && aBinFile->mFilename && aBinFile->mData && aBinFile->mSize) {
|
||||
FILE *f = fopen(aBinFile->mFilename, "wb");
|
||||
if (f) {
|
||||
fwrite(aBinFile->mData, 1, aBinFile->mSize, f);
|
||||
fclose(f);
|
||||
}
|
||||
}
|
||||
if (aBinFile->mFilename) free((void *) aBinFile->mFilename);
|
||||
if (aBinFile->mData) free(aBinFile->mData);
|
||||
free(aBinFile);
|
||||
}
|
||||
}
|
||||
|
||||
public:
|
||||
template <typename T>
|
||||
T Read() const {
|
||||
T _Item = { 0 };
|
||||
if (mOffset + sizeof(T) <= mSize) {
|
||||
memcpy(&_Item, mData + mOffset, sizeof(T));
|
||||
mOffset += sizeof(T);
|
||||
}
|
||||
return _Item;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
T *Read(T *aBuffer, s32 aCount) const {
|
||||
if (mOffset + aCount * sizeof(T) <= mSize) {
|
||||
memcpy(aBuffer, mData + mOffset, aCount * sizeof(T));
|
||||
mOffset += aCount * sizeof(T);
|
||||
}
|
||||
return aBuffer;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
void Write(const T& aItem) {
|
||||
if (!mReadOnly) {
|
||||
Grow(mOffset + sizeof(T));
|
||||
memcpy(mData + mOffset, &aItem, sizeof(T));
|
||||
mOffset += sizeof(T);
|
||||
}
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
void Write(const T *aBuffer, s32 aCount) {
|
||||
if (!mReadOnly) {
|
||||
Grow(mOffset + aCount * sizeof(T));
|
||||
memcpy(mData + mOffset, aBuffer, aCount * sizeof(T));
|
||||
mOffset += aCount * sizeof(T);
|
||||
}
|
||||
}
|
||||
|
||||
void Skip(s32 aAmount) const {
|
||||
mOffset += aAmount;
|
||||
}
|
||||
|
||||
private:
|
||||
const char *mFilename;
|
||||
u8 *mData;
|
||||
s32 mSize;
|
||||
s32 mCapacity;
|
||||
mutable s32 mOffset;
|
||||
bool mReadOnly;
|
||||
};
|
||||
|
||||
//
|
||||
// DynOS Array
|
||||
// A vector-like array, implemented to be processed really fast, but cannot handle C++ complex classes like std::string
|
||||
|
@ -171,15 +294,15 @@ public:
|
|||
inline bool Empty() const { return mCount == 0; }
|
||||
|
||||
public:
|
||||
void Read(FILE *aFile) {
|
||||
s32 _Length = 0; fread(&_Length, sizeof(s32), 1, aFile);
|
||||
void Read(BinFile *aFile) {
|
||||
s32 _Length = aFile->Read<s32>();
|
||||
Resize(_Length);
|
||||
fread(mBuffer, sizeof(T), _Length, aFile);
|
||||
aFile->Read<T>(mBuffer, _Length);
|
||||
}
|
||||
|
||||
void Write(FILE *aFile) const {
|
||||
fwrite(&mCount, sizeof(s32), 1, aFile);
|
||||
fwrite(mBuffer, sizeof(T), mCount, aFile);
|
||||
void Write(BinFile *aFile) const {
|
||||
aFile->Write<s32>(mCount);
|
||||
aFile->Write<T>(mBuffer, mCount);
|
||||
}
|
||||
|
||||
private:
|
||||
|
@ -193,7 +316,7 @@ private:
|
|||
// A fixed-size string that doesn't require heap memory allocation
|
||||
//
|
||||
|
||||
#define STRING_SIZE 256
|
||||
#define STRING_SIZE 255
|
||||
class String {
|
||||
public:
|
||||
inline String() : mCount(0) {
|
||||
|
@ -315,15 +438,15 @@ public:
|
|||
}
|
||||
|
||||
public:
|
||||
void Read(FILE *aFile) {
|
||||
fread(&mCount, sizeof(u8), 1, aFile);
|
||||
fread(mBuffer, sizeof(char), mCount, aFile);
|
||||
void Read(BinFile *aFile) {
|
||||
mCount = aFile->Read<u8>();
|
||||
aFile->Read<char>(mBuffer, mCount);
|
||||
mBuffer[mCount] = 0;
|
||||
}
|
||||
|
||||
void Write(FILE *aFile) const {
|
||||
fwrite(&mCount, sizeof(u8), 1, aFile);
|
||||
fwrite(mBuffer, sizeof(char), mCount, aFile);
|
||||
void Write(BinFile *aFile) const {
|
||||
aFile->Write<u8>(mCount);
|
||||
aFile->Write<char>(mBuffer, mCount);
|
||||
}
|
||||
|
||||
s32 ParseInt() const {
|
||||
|
@ -520,7 +643,6 @@ struct DynosOption : NoCopy {
|
|||
};
|
||||
typedef bool (*DynosLoopFunc)(DynosOption *, void *);
|
||||
|
||||
|
||||
struct BuiltinTexInfo {
|
||||
const char* identifier;
|
||||
const void* pointer;
|
||||
|
@ -589,28 +711,6 @@ T *CopyBytes(const T *aPtr, u64 aSize) {
|
|||
return _Ptr;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
T ReadBytes(FILE* aFile) {
|
||||
T _Item = { 0 };
|
||||
|
||||
// If we're at end of file. Just return the default.
|
||||
if (feof(aFile)) { return _Item; }
|
||||
|
||||
size_t nread = fread(&_Item, sizeof(T), 1, aFile);
|
||||
// If we failed to read bytes. Print the error.
|
||||
//if (nread != sizeof(T)) { perror("The following error occured when reading bytes"); }
|
||||
return _Item;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
void WriteBytes(FILE* aFile, const T& aItem) {
|
||||
size_t nwrote = fwrite(&aItem, sizeof(T), 1, aFile);
|
||||
// If we failed to write bytes. Print the error.
|
||||
//if (nwrote != sizeof(T)) { perror("The following error occured when writing bytes"); }
|
||||
}
|
||||
|
||||
void SkipBytes(FILE *aFile, size_t amount);
|
||||
|
||||
template <typename... Args>
|
||||
void PrintNoNewLine(const char *aFmt, Args... aArgs) {
|
||||
printf(aFmt, aArgs...);
|
||||
|
@ -869,79 +969,79 @@ char *DynOS_Read_Buffer(FILE* aFile, GfxData* aGfxData);
|
|||
s64 DynOS_Misc_ParseInteger(const String& _Arg, bool* found);
|
||||
|
||||
void DynOS_Anim_ScanFolder(GfxData *aGfxData, const SysPath &aAnimsFolder);
|
||||
void DynOS_Anim_Table_Write(FILE* aFile, GfxData* aGfxData);
|
||||
void DynOS_Anim_Write(FILE* aFile, GfxData* aGfxData);
|
||||
void DynOS_Anim_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Anim_Table_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Anim_Table_Write(BinFile* aFile, GfxData* aGfxData);
|
||||
void DynOS_Anim_Write(BinFile* aFile, GfxData* aGfxData);
|
||||
void DynOS_Anim_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
void DynOS_Anim_Table_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<Collision>* DynOS_Col_Parse(GfxData* aGfxData, DataNode<Collision>* aNode, bool aDisplayPercent);
|
||||
void DynOS_Col_Write(FILE* aFile, GfxData* aGfxData, DataNode<Collision> *aNode);
|
||||
DataNode<Collision>* DynOS_Col_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Col_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Collision> *aNode);
|
||||
DataNode<Collision>* DynOS_Col_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
DataNode<Collision>* DynOS_Col_LoadFromBinary(const SysPath &aFilename, const char *aCollisionName);
|
||||
void DynOS_Col_Generate(const SysPath &aPackFolder, Array<Pair<u64, String>> _ActorsFolders, GfxData *_GfxData);
|
||||
|
||||
DataNode<GeoLayout>* DynOS_Geo_Parse(GfxData* aGfxData, DataNode<GeoLayout>* aNode, bool aDisplayPercent);
|
||||
void DynOS_Geo_Write(FILE *aFile, GfxData *aGfxData, DataNode<GeoLayout> *aNode);
|
||||
void DynOS_Geo_Write(BinFile *aFile, GfxData *aGfxData, DataNode<GeoLayout> *aNode);
|
||||
DataNode<GeoLayout>** DynOS_Geo_GetLoading(void);
|
||||
void DynOS_Geo_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Geo_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<Gfx>* DynOS_Gfx_Parse(GfxData* aGfxData, DataNode<Gfx>* aNode);
|
||||
void DynOS_Gfx_Write(FILE *aFile, GfxData *aGfxData, DataNode<Gfx> *aNode);
|
||||
void DynOS_Gfx_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Gfx_Write(BinFile *aFile, GfxData *aGfxData, DataNode<Gfx> *aNode);
|
||||
void DynOS_Gfx_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
s64 DynOS_Gfx_ParseGfxConstants(const String& _Arg, bool* found);
|
||||
|
||||
DataNode<Lights1>* DynOS_Lights_Parse(GfxData* aGfxData, DataNode<Lights1>* aNode);
|
||||
void DynOS_Lights_Write(FILE* aFile, GfxData* aGfxData, DataNode<Lights1> *aNode);
|
||||
void DynOS_Lights_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Lights_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Lights1> *aNode);
|
||||
void DynOS_Lights_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<Light_t>* DynOS_LightT_Parse(GfxData* aGfxData, DataNode<Light_t>* aNode);
|
||||
void DynOS_LightT_Write(FILE* aFile, GfxData* aGfxData, DataNode<Light_t> *aNode);
|
||||
void DynOS_LightT_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_LightT_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Light_t> *aNode);
|
||||
void DynOS_LightT_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<Ambient_t>* DynOS_AmbientT_Parse(GfxData* aGfxData, DataNode<Ambient_t>* aNode);
|
||||
void DynOS_AmbientT_Write(FILE* aFile, GfxData* aGfxData, DataNode<Ambient_t> *aNode);
|
||||
void DynOS_AmbientT_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_AmbientT_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Ambient_t> *aNode);
|
||||
void DynOS_AmbientT_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<MacroObject>* DynOS_MacroObject_Parse(GfxData* aGfxData, DataNode<MacroObject>* aNode, bool aDisplayPercent);
|
||||
void DynOS_MacroObject_Write(FILE* aFile, GfxData* aGfxData, DataNode<MacroObject> *aNode);
|
||||
DataNode<MacroObject>* DynOS_MacroObject_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_MacroObject_Write(BinFile* aFile, GfxData* aGfxData, DataNode<MacroObject> *aNode);
|
||||
DataNode<MacroObject>* DynOS_MacroObject_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<Trajectory>* DynOS_Trajectory_Parse(GfxData* aGfxData, DataNode<Trajectory>* aNode, bool aDisplayPercent);
|
||||
void DynOS_Trajectory_Write(FILE* aFile, GfxData* aGfxData, DataNode<Trajectory> *aNode);
|
||||
DataNode<Trajectory>* DynOS_Trajectory_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Trajectory_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Trajectory> *aNode);
|
||||
DataNode<Trajectory>* DynOS_Trajectory_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<Movtex>* DynOS_Movtex_Parse(GfxData* aGfxData, DataNode<Movtex>* aNode, bool aDisplayPercent);
|
||||
void DynOS_Movtex_Write(FILE* aFile, GfxData* aGfxData, DataNode<Movtex> *aNode);
|
||||
DataNode<Movtex>* DynOS_Movtex_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Movtex_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Movtex> *aNode);
|
||||
DataNode<Movtex>* DynOS_Movtex_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<MovtexQC>* DynOS_MovtexQC_Parse(GfxData* aGfxData, DataNode<MovtexQC>* aNode);
|
||||
void DynOS_MovtexQC_Write(FILE* aFile, GfxData* aGfxData, DataNode<MovtexQC> *aNode);
|
||||
DataNode<MovtexQC>* DynOS_MovtexQC_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_MovtexQC_Write(BinFile* aFile, GfxData* aGfxData, DataNode<MovtexQC> *aNode);
|
||||
DataNode<MovtexQC>* DynOS_MovtexQC_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<u8>* DynOS_Rooms_Parse(GfxData* aGfxData, DataNode<u8>* aNode);
|
||||
void DynOS_Rooms_Write(FILE* aFile, GfxData* aGfxData, DataNode<u8> *aNode);
|
||||
DataNode<u8>* DynOS_Rooms_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Rooms_Write(BinFile* aFile, GfxData* aGfxData, DataNode<u8> *aNode);
|
||||
DataNode<u8>* DynOS_Rooms_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<TexData>* DynOS_Tex_Parse(GfxData* aGfxData, DataNode<TexData>* aNode);
|
||||
void DynOS_Tex_Write(FILE* aFile, GfxData* aGfxData, DataNode<TexData> *aNode);
|
||||
DataNode<TexData>* DynOS_Tex_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Tex_Write(BinFile* aFile, GfxData* aGfxData, DataNode<TexData> *aNode);
|
||||
DataNode<TexData>* DynOS_Tex_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
DataNode<TexData>* DynOS_Tex_LoadFromBinary(const SysPath &aPackFolder, const SysPath &aFilename, const char *aTexName, bool aAddToPack);
|
||||
void DynOS_Tex_ConvertTextureDataToPng(GfxData *aGfxData, TexData* aTexture);
|
||||
void DynOS_Tex_GeneratePack(const SysPath &aPackFolder, SysPath &aOutputFolder, bool aAllowCustomTextures);
|
||||
|
||||
DataNode<TexData*>* DynOS_TexList_Parse(GfxData* aGfxData, DataNode<TexData*>* aNode);
|
||||
void DynOS_TexList_Write(FILE* aFile, GfxData* aGfxData, DataNode<TexData*> *aNode);
|
||||
DataNode<TexData*>* DynOS_TexList_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_TexList_Write(BinFile* aFile, GfxData* aGfxData, DataNode<TexData*> *aNode);
|
||||
DataNode<TexData*>* DynOS_TexList_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
DataNode<Vtx>* DynOS_Vtx_Parse(GfxData* aGfxData, DataNode<Vtx>* aNode);
|
||||
void DynOS_Vtx_Write(FILE* aFile, GfxData* aGfxData, DataNode<Vtx> *aNode);
|
||||
void DynOS_Vtx_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_Vtx_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Vtx> *aNode);
|
||||
void DynOS_Vtx_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
void DynOS_Pointer_Lua_Write(FILE* aFile, u32 index, GfxData* aGfxData);
|
||||
void DynOS_Pointer_Write(FILE* aFile, const void* aPtr, GfxData* aGfxData);
|
||||
void *DynOS_Pointer_Load(FILE *aFile, GfxData *aGfxData, u32 aValue, u8* outFlags);
|
||||
void DynOS_Pointer_Lua_Write(BinFile* aFile, u32 index, GfxData* aGfxData);
|
||||
void DynOS_Pointer_Write(BinFile* aFile, const void* aPtr, GfxData* aGfxData);
|
||||
void *DynOS_Pointer_Load(BinFile *aFile, GfxData *aGfxData, u32 aValue, u8* outFlags);
|
||||
|
||||
void DynOS_GfxDynCmd_Load(FILE *aFile, GfxData *aGfxData);
|
||||
void DynOS_GfxDynCmd_Load(BinFile *aFile, GfxData *aGfxData);
|
||||
|
||||
GfxData *DynOS_Actor_LoadFromBinary(const SysPath &aPackFolder, const char *aActorName, const SysPath &aFilename, bool aAddToPack);
|
||||
void DynOS_Actor_GeneratePack(const SysPath &aPackFolder);
|
||||
|
@ -960,5 +1060,9 @@ s64 DynOS_Bhv_ParseBehaviorIntegerScriptConstants(const String &_Arg, bool *foun
|
|||
s64 DynOS_Common_ParseBhvConstants(const String &_Arg, bool *found);
|
||||
s64 DynOS_Common_ParseModelConstants(const String &_Arg, bool *found);
|
||||
|
||||
bool DynOS_Bin_IsCompressed(const SysPath &aFilename);
|
||||
bool DynOS_Bin_Compress(const SysPath &aFilename);
|
||||
BinFile *DynOS_Bin_Decompress(const SysPath &aFilename);
|
||||
|
||||
#endif
|
||||
#endif
|
||||
|
|
|
@ -14,7 +14,7 @@ void ClearGfxDataNodes(DataNodes<T> &aDataNodes) {
|
|||
/////////////
|
||||
|
||||
static bool DynOS_Actor_WriteBinary(const SysPath &aOutputFilename, GfxData *aGfxData) {
|
||||
FILE *_File = fopen(aOutputFilename.c_str(), "wb");
|
||||
BinFile *_File = BinFile::OpenW(aOutputFilename.c_str());
|
||||
if (!_File) {
|
||||
PrintError(" ERROR: Unable to create file \"%s\"", aOutputFilename.c_str());
|
||||
return false;
|
||||
|
@ -64,8 +64,8 @@ static bool DynOS_Actor_WriteBinary(const SysPath &aOutputFilename, GfxData *aGf
|
|||
}
|
||||
DynOS_Anim_Write(_File, aGfxData);
|
||||
DynOS_Anim_Table_Write(_File, aGfxData);
|
||||
fclose(_File);
|
||||
return true;
|
||||
BinFile::Close(_File);
|
||||
return DynOS_Bin_Compress(aOutputFilename);
|
||||
}
|
||||
|
||||
/////////////
|
||||
|
@ -86,11 +86,11 @@ GfxData *DynOS_Actor_LoadFromBinary(const SysPath &aPackFolder, const char *aAct
|
|||
|
||||
// Load data from binary file
|
||||
GfxData *_GfxData = NULL;
|
||||
FILE *_File = fopen(aFilename.c_str(), "rb");
|
||||
BinFile *_File = DynOS_Bin_Decompress(aFilename);
|
||||
if (_File) {
|
||||
_GfxData = New<GfxData>();
|
||||
for (bool _Done = false; !_Done;) {
|
||||
switch (ReadBytes<u8>(_File)) {
|
||||
switch (_File->Read<u8>()) {
|
||||
case DATA_TYPE_LIGHT: DynOS_Lights_Load (_File, _GfxData); break;
|
||||
case DATA_TYPE_LIGHT_T: DynOS_LightT_Load (_File, _GfxData); break;
|
||||
case DATA_TYPE_AMBIENT_T: DynOS_AmbientT_Load (_File, _GfxData); break;
|
||||
|
@ -105,7 +105,7 @@ GfxData *DynOS_Actor_LoadFromBinary(const SysPath &aPackFolder, const char *aAct
|
|||
default: _Done = true; break;
|
||||
}
|
||||
}
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
}
|
||||
|
||||
// Add data to cache, even if not loaded
|
||||
|
@ -143,6 +143,12 @@ static void DynOS_Actor_Generate(const SysPath &aPackFolder, Array<Pair<u64, Str
|
|||
// If there is an existing binary file for this layout, skip and go to the next actor
|
||||
SysPath _BinFilename = fstring("%s/%s.bin", aPackFolder.c_str(), _GeoRootName.begin());
|
||||
if (fs_sys_file_exists(_BinFilename.c_str())) {
|
||||
#ifdef DEVELOPMENT
|
||||
// Compress file to gain some space
|
||||
if (!DynOS_Bin_IsCompressed(_BinFilename)) {
|
||||
DynOS_Bin_Compress(_BinFilename);
|
||||
}
|
||||
#endif
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -246,6 +252,15 @@ void DynOS_Actor_GeneratePack(const SysPath &aPackFolder) {
|
|||
if (SysPath(_PackEnt->d_name) == ".") continue;
|
||||
if (SysPath(_PackEnt->d_name) == "..") continue;
|
||||
|
||||
#ifdef DEVELOPMENT
|
||||
// Compress .bin files to gain some space
|
||||
SysPath _Filename = fstring("%s/%s", aPackFolder.c_str(), _PackEnt->d_name);
|
||||
if (SysPath(_PackEnt->d_name).find(".bin") != SysPath::npos && !DynOS_Bin_IsCompressed(_Filename)) {
|
||||
DynOS_Bin_Compress(_Filename);
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
// For each subfolder, read tokens from model.inc.c and geo.inc.c
|
||||
SysPath _Folder = fstring("%s/%s", aPackFolder.c_str(), _PackEnt->d_name);
|
||||
if (fs_sys_dir_exists(_Folder.c_str())) {
|
||||
|
|
|
@ -33,22 +33,22 @@ DataNode<Ambient_t>* DynOS_AmbientT_Parse(GfxData* aGfxData, DataNode<Ambient_t>
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_AmbientT_Write(FILE* aFile, GfxData* aGfxData, DataNode<Ambient_t> *aNode) {
|
||||
void DynOS_AmbientT_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Ambient_t> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_AMBIENT_T);
|
||||
aFile->Write<u8>(DATA_TYPE_AMBIENT_T);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<Ambient_t>(aFile, *aNode->mData);
|
||||
aFile->Write<Ambient_t>(*aNode->mData);
|
||||
}
|
||||
|
||||
/////////////
|
||||
// Reading //
|
||||
/////////////
|
||||
|
||||
void DynOS_AmbientT_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_AmbientT_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<Ambient_t> *_Node = New<DataNode<Ambient_t>>();
|
||||
|
||||
// Name
|
||||
|
@ -56,7 +56,7 @@ void DynOS_AmbientT_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
|
||||
// Data
|
||||
_Node->mData = New<Ambient_t>();
|
||||
*_Node->mData = ReadBytes<Ambient_t>(aFile);
|
||||
*_Node->mData = aFile->Read<Ambient_t>();
|
||||
|
||||
// Append
|
||||
aGfxData->mAmbientTs.Add(_Node);
|
||||
|
|
|
@ -160,7 +160,7 @@ void DynOS_Anim_ScanFolder(GfxData *aGfxData, const SysPath &aAnimsFolder) {
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Anim_Write(FILE* aFile, GfxData* aGfxData) {
|
||||
void DynOS_Anim_Write(BinFile* aFile, GfxData* aGfxData) {
|
||||
for (auto& _Node : aGfxData->mAnimations) {
|
||||
|
||||
// Value buffer
|
||||
|
@ -182,27 +182,27 @@ void DynOS_Anim_Write(FILE* aFile, GfxData* aGfxData) {
|
|||
}
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_ANIMATION);
|
||||
aFile->Write<u8>(DATA_TYPE_ANIMATION);
|
||||
_Node->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<s16>(aFile, _Node->mData->mFlags);
|
||||
WriteBytes<s16>(aFile, _Node->mData->mUnk02);
|
||||
WriteBytes<s16>(aFile, _Node->mData->mUnk04);
|
||||
WriteBytes<s16>(aFile, _Node->mData->mUnk06);
|
||||
WriteBytes<s16>(aFile, _Node->mData->mUnk08);
|
||||
WriteBytes<s16>(aFile, (aGfxData->mAnimIndices[_Unk0ABufferIdx]->second.Count() / 6) - 1);
|
||||
WriteBytes<u32>(aFile, _Node->mData->mLength);
|
||||
aFile->Write<s16>(_Node->mData->mFlags);
|
||||
aFile->Write<s16>(_Node->mData->mUnk02);
|
||||
aFile->Write<s16>(_Node->mData->mUnk04);
|
||||
aFile->Write<s16>(_Node->mData->mUnk06);
|
||||
aFile->Write<s16>(_Node->mData->mUnk08);
|
||||
aFile->Write<s16>((aGfxData->mAnimIndices[_Unk0ABufferIdx]->second.Count() / 6) - 1);
|
||||
aFile->Write<u32>(_Node->mData->mLength);
|
||||
aGfxData->mAnimValues[_ValueBufferIdx]->second.Write(aFile);
|
||||
aGfxData->mAnimIndices[_IndexBufferIdx]->second.Write(aFile);
|
||||
}
|
||||
}
|
||||
|
||||
void DynOS_Anim_Table_Write(FILE* aFile, GfxData* aGfxData) {
|
||||
void DynOS_Anim_Table_Write(BinFile* aFile, GfxData* aGfxData) {
|
||||
for (auto& _AnimName : aGfxData->mAnimationTable) {
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_ANIMATION_TABLE);
|
||||
aFile->Write<u8>(DATA_TYPE_ANIMATION_TABLE);
|
||||
|
||||
// Data
|
||||
_AnimName.first.Write(aFile);
|
||||
|
@ -213,7 +213,7 @@ void DynOS_Anim_Table_Write(FILE* aFile, GfxData* aGfxData) {
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
void DynOS_Anim_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_Anim_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<AnimData> *_Node = New<DataNode<AnimData>>();
|
||||
|
||||
// Name
|
||||
|
@ -221,13 +221,13 @@ void DynOS_Anim_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
|
||||
// Data
|
||||
_Node->mData = New<AnimData>();
|
||||
_Node->mData->mFlags = ReadBytes<s16>(aFile);
|
||||
_Node->mData->mUnk02 = ReadBytes<s16>(aFile);
|
||||
_Node->mData->mUnk04 = ReadBytes<s16>(aFile);
|
||||
_Node->mData->mUnk06 = ReadBytes<s16>(aFile);
|
||||
_Node->mData->mUnk08 = ReadBytes<s16>(aFile);
|
||||
_Node->mData->mUnk0A.second = ReadBytes<s16>(aFile);
|
||||
_Node->mData->mLength = ReadBytes<u32>(aFile);
|
||||
_Node->mData->mFlags = aFile->Read<s16>();
|
||||
_Node->mData->mUnk02 = aFile->Read<s16>();
|
||||
_Node->mData->mUnk04 = aFile->Read<s16>();
|
||||
_Node->mData->mUnk06 = aFile->Read<s16>();
|
||||
_Node->mData->mUnk08 = aFile->Read<s16>();
|
||||
_Node->mData->mUnk0A.second = aFile->Read<s16>();
|
||||
_Node->mData->mLength = aFile->Read<u32>();
|
||||
_Node->mData->mValues.second.Read(aFile);
|
||||
_Node->mData->mIndex.second.Read(aFile);
|
||||
|
||||
|
@ -235,7 +235,7 @@ void DynOS_Anim_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
aGfxData->mAnimations.Add(_Node);
|
||||
}
|
||||
|
||||
void DynOS_Anim_Table_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_Anim_Table_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
void *_AnimationPtr = NULL;
|
||||
|
||||
// Data
|
||||
|
|
|
@ -2432,20 +2432,20 @@ static DataNode<BehaviorScript> *GetBehaviorScript(GfxData *aGfxData, const Stri
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
static void DynOS_Bhv_Write(FILE* aFile, GfxData* aGfxData, DataNode<BehaviorScript> *aNode) {
|
||||
static void DynOS_Bhv_Write(BinFile* aFile, GfxData* aGfxData, DataNode<BehaviorScript> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_BEHAVIOR_SCRIPT);
|
||||
aFile->Write<u8>(DATA_TYPE_BEHAVIOR_SCRIPT);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Version
|
||||
WriteBytes<u8>(aFile, BEHAVIOR_MAJOR_VER);
|
||||
WriteBytes<u8>(aFile, BEHAVIOR_MINOR_VER);
|
||||
WriteBytes<u8>(aFile, BEHAVIOR_PATCH_VER);
|
||||
aFile->Write<u8>(BEHAVIOR_MAJOR_VER);
|
||||
aFile->Write<u8>(BEHAVIOR_MINOR_VER);
|
||||
aFile->Write<u8>(BEHAVIOR_PATCH_VER);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
BehaviorScript *_Head = &aNode->mData[i];
|
||||
if (aGfxData->mPointerList.Find((void *) _Head) != -1) {
|
||||
|
@ -2453,14 +2453,14 @@ static void DynOS_Bhv_Write(FILE* aFile, GfxData* aGfxData, DataNode<BehaviorScr
|
|||
} else if (aGfxData->mLuaPointerList.Find((void *) _Head) != -1) {
|
||||
DynOS_Pointer_Lua_Write(aFile, *(u32 *)_Head, aGfxData);
|
||||
} else {
|
||||
WriteBytes<u32>(aFile, *((u32 *) _Head));
|
||||
aFile->Write<u32>(*((u32 *) _Head));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static bool DynOS_Bhv_WriteBinary(const SysPath &aOutputFilename, GfxData *aGfxData) {
|
||||
FILE *_File = fopen(aOutputFilename.c_str(), "wb");
|
||||
BinFile *_File = BinFile::OpenW(aOutputFilename.c_str());
|
||||
if (!_File) {
|
||||
PrintError(" ERROR: Unable to create file \"%s\"", aOutputFilename.c_str());
|
||||
return false;
|
||||
|
@ -2474,7 +2474,7 @@ static bool DynOS_Bhv_WriteBinary(const SysPath &aOutputFilename, GfxData *aGfxD
|
|||
}
|
||||
}
|
||||
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -2482,28 +2482,28 @@ static bool DynOS_Bhv_WriteBinary(const SysPath &aOutputFilename, GfxData *aGfxD
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
static DataNode<BehaviorScript> *DynOS_Bhv_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
static DataNode<BehaviorScript> *DynOS_Bhv_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<BehaviorScript> *_Node = New<DataNode<BehaviorScript>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Version
|
||||
u8 majorVersion = ReadBytes<u8>(aFile);
|
||||
u8 minorVersion = ReadBytes<u8>(aFile);
|
||||
u8 patchVersion = ReadBytes<u8>(aFile);
|
||||
u8 majorVersion = aFile->Read<u8>();
|
||||
u8 minorVersion = aFile->Read<u8>();
|
||||
u8 patchVersion = aFile->Read<u8>();
|
||||
|
||||
// Version Sanity Check
|
||||
//
|
||||
// If the major version doesn't match, then a drasitc change has happened and
|
||||
// we can't read it no matter what. If it's just minor or patch. We might have
|
||||
// code to support it.
|
||||
u32 dataSize = ReadBytes<u32>(aFile);
|
||||
u32 dataSize = aFile->Read<u32>();
|
||||
if (majorVersion != BEHAVIOR_MIN_MAJOR_VER || (minorVersion < BEHAVIOR_MIN_MINOR_VER || patchVersion < BEHAVIOR_MIN_PATCH_VER)) {
|
||||
PrintError(" ERROR: Behavior version is %u.%u.%u, but reading behaviors under %u.%u.%u is not supported!", majorVersion, minorVersion, patchVersion, BEHAVIOR_MIN_MAJOR_VER, BEHAVIOR_MIN_MINOR_VER, BEHAVIOR_MIN_PATCH_VER);
|
||||
|
||||
// Skip the rest of the bytes saved for this behavior.
|
||||
SkipBytes(aFile, dataSize);
|
||||
aFile->Skip(dataSize);
|
||||
// We don't return this since we failed to read the behavior.
|
||||
Delete(_Node);
|
||||
// We have nothing to return, So return NULL.
|
||||
|
@ -2521,11 +2521,11 @@ static DataNode<BehaviorScript> *DynOS_Bhv_Load(FILE *aFile, GfxData *aGfxData)
|
|||
|
||||
// Read it
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
if (feof(aFile)) {
|
||||
if (aFile->EoF()) {
|
||||
PrintError(" ERROR: Reached EOF when reading file! Expected %llx bytes!", _Node->mSize * sizeof(u32));
|
||||
break;
|
||||
}
|
||||
u32 _Value = ReadBytes<u32>(aFile);
|
||||
u32 _Value = aFile->Read<u32>();
|
||||
void *_Ptr = DynOS_Pointer_Load(aFile, aGfxData, _Value, &_Node->mFlags);
|
||||
if (_Ptr) {
|
||||
_Node->mData[i] = (uintptr_t) _Ptr;
|
||||
|
@ -2541,16 +2541,16 @@ GfxData *DynOS_Bhv_LoadFromBinary(const SysPath &aFilename, const char *aBehavio
|
|||
|
||||
// Load data from binary file
|
||||
GfxData *_GfxData = NULL;
|
||||
FILE *_File = fopen(aFilename.c_str(), "rb");
|
||||
BinFile *_File = BinFile::OpenR(aFilename.c_str());
|
||||
if (_File != NULL) {
|
||||
_GfxData = New<GfxData>();
|
||||
for (bool _Done = false; !_Done;) {
|
||||
switch (ReadBytes<u8>(_File)) {
|
||||
switch (_File->Read<u8>()) {
|
||||
case DATA_TYPE_BEHAVIOR_SCRIPT: DynOS_Bhv_Load(_File, _GfxData); break;
|
||||
default: _Done = true; break;
|
||||
}
|
||||
}
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
}
|
||||
|
||||
return _GfxData;
|
||||
|
|
|
@ -612,22 +612,22 @@ DataNode<Collision>* DynOS_Col_Parse(GfxData* aGfxData, DataNode<Collision>* aNo
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Col_Write(FILE* aFile, GfxData* aGfxData, DataNode<Collision> *aNode) {
|
||||
void DynOS_Col_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Collision> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_COLLISION);
|
||||
aFile->Write<u8>(DATA_TYPE_COLLISION);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
WriteBytes<Collision>(aFile, aNode->mData[i]);
|
||||
aFile->Write<Collision>(aNode->mData[i]);
|
||||
}
|
||||
}
|
||||
|
||||
static bool DynOS_Col_WriteBinary(const SysPath &aOutputFilename, GfxData *aGfxData, DataNode<Collision>* _Node) {
|
||||
FILE *_File = fopen(aOutputFilename.c_str(), "wb");
|
||||
BinFile *_File = BinFile::OpenW(aOutputFilename.c_str());
|
||||
if (!_File) {
|
||||
PrintError(" ERROR: Unable to create file \"%s\"", aOutputFilename.c_str());
|
||||
return false;
|
||||
|
@ -635,25 +635,25 @@ static bool DynOS_Col_WriteBinary(const SysPath &aOutputFilename, GfxData *aGfxD
|
|||
|
||||
DynOS_Col_Write(_File, aGfxData, _Node);
|
||||
|
||||
fclose(_File);
|
||||
return true;
|
||||
BinFile::Close(_File);
|
||||
return DynOS_Bin_Compress(aOutputFilename);
|
||||
}
|
||||
|
||||
/////////////
|
||||
// Loading //
|
||||
/////////////
|
||||
|
||||
DataNode<Collision>* DynOS_Col_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
DataNode<Collision>* DynOS_Col_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<Collision> *_Node = New<DataNode<Collision>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<Collision>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
_Node->mData[i] = ReadBytes<Collision>(aFile);
|
||||
_Node->mData[i] = aFile->Read<Collision>();
|
||||
}
|
||||
|
||||
// Add it
|
||||
|
@ -667,13 +667,13 @@ DataNode<Collision>* DynOS_Col_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
DataNode<Collision>* DynOS_Col_LoadFromBinary(const SysPath &aFilename, const char *aCollisionName) {
|
||||
// Load data from binary file
|
||||
DataNode<Collision>* collisionNode = NULL;
|
||||
FILE *_File = fopen(aFilename.c_str(), "rb");
|
||||
BinFile *_File = DynOS_Bin_Decompress(aFilename);
|
||||
if (_File) {
|
||||
u8 type = ReadBytes<u8>(_File);
|
||||
u8 type = _File->Read<u8>();
|
||||
if (type == DATA_TYPE_COLLISION) {
|
||||
collisionNode = DynOS_Col_Load(_File, NULL);
|
||||
}
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
}
|
||||
|
||||
return collisionNode;
|
||||
|
@ -690,6 +690,12 @@ void DynOS_Col_Generate(const SysPath &aPackFolder, Array<Pair<u64, String>> _Ac
|
|||
// If there is an existing binary file for this collision, skip and go to the next actor
|
||||
SysPath _ColFilename = fstring("%s/%s.col", aPackFolder.c_str(), _ColRootName.begin());
|
||||
if (fs_sys_file_exists(_ColFilename.c_str())) {
|
||||
#ifdef DEVELOPMENT
|
||||
// Compress file to gain some space
|
||||
if (!DynOS_Bin_IsCompressed(_ColFilename)) {
|
||||
DynOS_Bin_Compress(_ColFilename);
|
||||
}
|
||||
#endif
|
||||
continue;
|
||||
}
|
||||
|
||||
|
|
222
data/dynos_bin_compress.cpp
Normal file
222
data/dynos_bin_compress.cpp
Normal file
|
@ -0,0 +1,222 @@
|
|||
#include "dynos.cpp.h"
|
||||
#include <zlib.h>
|
||||
|
||||
static const u64 DYNOS_BIN_COMPRESS_MAGIC = 0x4E4942534F4E5944llu;
|
||||
static FILE *sFile = NULL;
|
||||
static Bytef *sBufferUncompressed = NULL;
|
||||
static Bytef *sBufferCompressed = NULL;
|
||||
static uLongf sLengthUncompressed = 0;
|
||||
static uLongf sLengthCompressed = 0;
|
||||
|
||||
static inline void DynOS_Bin_Compress_Init() {
|
||||
sFile = NULL;
|
||||
sBufferUncompressed = NULL;
|
||||
sBufferCompressed = NULL;
|
||||
sLengthUncompressed = 0;
|
||||
sLengthCompressed = 0;
|
||||
}
|
||||
|
||||
static inline void DynOS_Bin_Compress_Free() {
|
||||
if (sBufferCompressed) free(sBufferCompressed);
|
||||
if (sBufferUncompressed) free(sBufferUncompressed);
|
||||
if (sFile) fclose(sFile);
|
||||
}
|
||||
|
||||
static inline bool DynOS_Bin_Compress_Check(bool condition, const char *function, const char *filename, const char *message) {
|
||||
if (!condition) {
|
||||
Print("ERROR: %s: File \"%s\": %s", function, filename, message);
|
||||
DynOS_Bin_Compress_Free();
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool DynOS_Bin_IsCompressed(const SysPath &aFilename) {
|
||||
DynOS_Bin_Compress_Init();
|
||||
|
||||
// Open input file
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sFile = fopen(aFilename.c_str(), "rb")) != NULL,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot open file"
|
||||
)) return false;
|
||||
|
||||
// Read magic
|
||||
u64 _Magic = 0;
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fread(&_Magic, sizeof(u64), 1, sFile) == 1,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot read magic"
|
||||
)) return false;
|
||||
|
||||
// Compare with magic constant
|
||||
if (_Magic != DYNOS_BIN_COMPRESS_MAGIC) {
|
||||
DynOS_Bin_Compress_Free();
|
||||
return false;
|
||||
}
|
||||
|
||||
// It is a compressed file
|
||||
DynOS_Bin_Compress_Free();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool DynOS_Bin_Compress(const SysPath &aFilename) {
|
||||
DynOS_Bin_Compress_Init();
|
||||
PrintNoNewLine("Compressing file \"%s\"...", aFilename.c_str());
|
||||
|
||||
// Open input file
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sFile = fopen(aFilename.c_str(), "rb")) != NULL,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot open file"
|
||||
)) return false;
|
||||
|
||||
// Retrieve file length
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fseek(sFile, 0, SEEK_END) == 0,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot retrieve file length"
|
||||
)) return false;
|
||||
|
||||
// Check file length
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sLengthUncompressed = (uLongf) ftell(sFile)) != 0,
|
||||
__FUNCTION__, aFilename.c_str(), "Empty file"
|
||||
)) return false;
|
||||
|
||||
// Allocate memory for uncompressed buffer
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sBufferUncompressed = (Bytef *) calloc(sLengthUncompressed, sizeof(Bytef))) != NULL,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot allocate memory for compression"
|
||||
)) return false; else rewind(sFile);
|
||||
|
||||
// Read input data
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fread(sBufferUncompressed, sizeof(Bytef), sLengthUncompressed, sFile) == sLengthUncompressed,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot read uncompressed data"
|
||||
)) return false; else fclose(sFile);
|
||||
|
||||
// Compute maximum output file size
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sLengthCompressed = compressBound(sLengthUncompressed)) != 0,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot compute compressed size"
|
||||
)) return false;
|
||||
|
||||
// Allocate memory for compressed buffer
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sBufferCompressed = (Bytef *) calloc(sLengthCompressed, sizeof(Bytef))) != NULL,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot allocate memory for compression"
|
||||
)) return false;
|
||||
|
||||
// Compress data
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
compress2(sBufferCompressed, &sLengthCompressed, sBufferUncompressed, sLengthUncompressed, Z_BEST_COMPRESSION) == Z_OK,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot compress data"
|
||||
)) return false;
|
||||
|
||||
// Check output length
|
||||
// If the compression generates a bigger file, skip the process, but don't return a failure
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
sLengthCompressed < sLengthUncompressed,
|
||||
__FUNCTION__, aFilename.c_str(), "Compressed data is bigger than uncompressed; Skipping compression"
|
||||
)) return true;
|
||||
|
||||
// Open output file
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sFile = fopen(aFilename.c_str(), "wb")) != NULL,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot open file"
|
||||
)) return false;
|
||||
|
||||
// Write magic
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fwrite(&DYNOS_BIN_COMPRESS_MAGIC, sizeof(u64), 1, sFile) == 1,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot write magic"
|
||||
)) return false;
|
||||
|
||||
// Write uncompressed file size
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fwrite(&sLengthUncompressed, sizeof(uLongf), 1, sFile) == 1,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot write uncompressed file size"
|
||||
)) return false;
|
||||
|
||||
// Write compressed data
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fwrite(sBufferCompressed, sizeof(Bytef), sLengthCompressed, sFile) == sLengthCompressed,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot write compressed data"
|
||||
)) return false;
|
||||
|
||||
// Done, free buffers and files
|
||||
DynOS_Bin_Compress_Free();
|
||||
Print(" Done.");
|
||||
return true;
|
||||
}
|
||||
|
||||
BinFile *DynOS_Bin_Decompress(const SysPath &aFilename) {
|
||||
DynOS_Bin_Compress_Init();
|
||||
|
||||
// Open input file
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sFile = fopen(aFilename.c_str(), "rb")) != NULL,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot open file"
|
||||
)) return NULL;
|
||||
|
||||
// Read magic
|
||||
u64 _Magic = 0;
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fread(&_Magic, sizeof(u64), 1, sFile) == 1,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot read magic"
|
||||
)) return NULL;
|
||||
|
||||
// Compare with magic constant
|
||||
// If not equal, it's not a compressed file
|
||||
if (_Magic != DYNOS_BIN_COMPRESS_MAGIC) {
|
||||
DynOS_Bin_Compress_Free();
|
||||
return BinFile::OpenR(aFilename.c_str());
|
||||
}
|
||||
PrintNoNewLine("Decompressing file \"%s\"...", aFilename.c_str());
|
||||
|
||||
// Read expected uncompressed file size
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fread(&sLengthUncompressed, sizeof(uLongf), 1, sFile) == 1,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot read uncompressed file size"
|
||||
)) return NULL;
|
||||
|
||||
// Retrieve file length
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fseek(sFile, 0, SEEK_END) == 0,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot retrieve file length"
|
||||
)) return NULL;
|
||||
|
||||
// Check file length
|
||||
uLongf _LengthHeader = (uLongf) (sizeof(u64) + sizeof(uLongf));
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sLengthCompressed = (uLongf) ftell(sFile)) >= _LengthHeader,
|
||||
__FUNCTION__, aFilename.c_str(), "Empty file"
|
||||
)) return NULL;
|
||||
|
||||
// Allocate memory for compressed buffer
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sBufferCompressed = (Bytef *) calloc(sLengthCompressed - _LengthHeader, sizeof(Bytef))) != NULL,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot allocate memory for decompression"
|
||||
)) return NULL; else fseek(sFile, _LengthHeader, SEEK_SET);
|
||||
|
||||
// Read input data
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
fread(sBufferCompressed, sizeof(Bytef), sLengthCompressed - _LengthHeader, sFile) == sLengthCompressed - _LengthHeader,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot read compressed data"
|
||||
)) return NULL; else fclose(sFile);
|
||||
|
||||
// Allocate memory for uncompressed buffer
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
(sBufferUncompressed = (Bytef *) calloc(sLengthUncompressed, sizeof(Bytef))) != NULL,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot allocate memory for decompression"
|
||||
)) return NULL;
|
||||
|
||||
// Uncompress data
|
||||
if (!DynOS_Bin_Compress_Check(
|
||||
uncompress(sBufferUncompressed, &sLengthUncompressed, sBufferCompressed, sLengthCompressed) == Z_OK,
|
||||
__FUNCTION__, aFilename.c_str(), "Cannot uncompress data"
|
||||
)) return NULL;
|
||||
|
||||
// Return uncompressed data as a BinFile
|
||||
BinFile *_BinFile = BinFile::OpenB(sBufferUncompressed, sLengthUncompressed);
|
||||
DynOS_Bin_Compress_Free();
|
||||
Print(" Done.");
|
||||
return _BinFile;
|
||||
}
|
|
@ -431,21 +431,21 @@ DataNode<GeoLayout>* DynOS_Geo_Parse(GfxData* aGfxData, DataNode<GeoLayout>* aNo
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Geo_Write(FILE *aFile, GfxData *aGfxData, DataNode<GeoLayout> *aNode) {
|
||||
void DynOS_Geo_Write(BinFile *aFile, GfxData *aGfxData, DataNode<GeoLayout> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_GEO_LAYOUT);
|
||||
aFile->Write<u8>(DATA_TYPE_GEO_LAYOUT);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
GeoLayout *_Head = &aNode->mData[i];
|
||||
if (aGfxData->mPointerList.Find((void *) _Head) != -1) {
|
||||
DynOS_Pointer_Write(aFile, (const void *) (*_Head), aGfxData);
|
||||
} else {
|
||||
WriteBytes<u32>(aFile, *((u32 *) _Head));
|
||||
aFile->Write<u32>(*((u32 *) _Head));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -454,17 +454,17 @@ void DynOS_Geo_Write(FILE *aFile, GfxData *aGfxData, DataNode<GeoLayout> *aNode)
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
void DynOS_Geo_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_Geo_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<GeoLayout> *_Node = New<DataNode<GeoLayout>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<GeoLayout>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
u32 _Value = ReadBytes<u32>(aFile);
|
||||
u32 _Value = aFile->Read<u32>();
|
||||
void *_Ptr = DynOS_Pointer_Load(aFile, aGfxData, _Value, &_Node->mFlags);
|
||||
if (_Ptr) {
|
||||
_Node->mData[i] = (uintptr_t) _Ptr;
|
||||
|
|
|
@ -937,23 +937,23 @@ DataNode<Gfx>* DynOS_Gfx_Parse(GfxData* aGfxData, DataNode<Gfx>* aNode) {
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Gfx_Write(FILE *aFile, GfxData *aGfxData, DataNode<Gfx> *aNode) {
|
||||
void DynOS_Gfx_Write(BinFile *aFile, GfxData *aGfxData, DataNode<Gfx> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_DISPLAY_LIST);
|
||||
aFile->Write<u8>(DATA_TYPE_DISPLAY_LIST);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
Gfx *_Head = &aNode->mData[i];
|
||||
if (aGfxData->mPointerList.Find((void *) _Head) != -1) {
|
||||
WriteBytes<u32>(aFile, _Head->words.w0);
|
||||
aFile->Write<u32>(_Head->words.w0);
|
||||
DynOS_Pointer_Write(aFile, (const void *) _Head->words.w1, aGfxData);
|
||||
} else {
|
||||
WriteBytes<u32>(aFile, _Head->words.w0);
|
||||
WriteBytes<u32>(aFile, _Head->words.w1);
|
||||
aFile->Write<u32>(_Head->words.w0);
|
||||
aFile->Write<u32>(_Head->words.w1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -961,18 +961,18 @@ void DynOS_Gfx_Write(FILE *aFile, GfxData *aGfxData, DataNode<Gfx> *aNode) {
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
void DynOS_Gfx_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_Gfx_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<Gfx> *_Node = New<DataNode<Gfx>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<Gfx>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
u32 _WordsW0 = ReadBytes<u32>(aFile);
|
||||
u32 _WordsW1 = ReadBytes<u32>(aFile);
|
||||
u32 _WordsW0 = aFile->Read<u32>();
|
||||
u32 _WordsW1 = aFile->Read<u32>();
|
||||
void *_Ptr = DynOS_Pointer_Load(aFile, aGfxData, _WordsW1, &_Node->mFlags);
|
||||
if (_Ptr) {
|
||||
_Node->mData[i].words.w0 = (uintptr_t) _WordsW0;
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
/////////////
|
||||
|
||||
// For retro-compatibility
|
||||
void DynOS_GfxDynCmd_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_GfxDynCmd_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
Gfx *_Data = NULL;
|
||||
String _DisplayListName; _DisplayListName.Read(aFile);
|
||||
for (auto& _DisplayList : aGfxData->mDisplayLists) {
|
||||
|
@ -25,6 +25,6 @@ void DynOS_GfxDynCmd_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
if (!_Data) {
|
||||
sys_fatal("Display list not found: %s", _DisplayListName.begin());
|
||||
}
|
||||
ReadBytes<u32>(aFile);
|
||||
ReadBytes<u8>(aFile);
|
||||
aFile->Read<u32>();
|
||||
aFile->Read<u8>();
|
||||
}
|
||||
|
|
|
@ -37,22 +37,22 @@ DataNode<Light_t>* DynOS_LightT_Parse(GfxData* aGfxData, DataNode<Light_t>* aNod
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_LightT_Write(FILE* aFile, GfxData* aGfxData, DataNode<Light_t> *aNode) {
|
||||
void DynOS_LightT_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Light_t> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_LIGHT_T);
|
||||
aFile->Write<u8>(DATA_TYPE_LIGHT_T);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<Light_t>(aFile, *aNode->mData);
|
||||
aFile->Write<Light_t>(*aNode->mData);
|
||||
}
|
||||
|
||||
/////////////
|
||||
// Reading //
|
||||
/////////////
|
||||
|
||||
void DynOS_LightT_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_LightT_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<Light_t> *_Node = New<DataNode<Light_t>>();
|
||||
|
||||
// Name
|
||||
|
@ -60,7 +60,7 @@ void DynOS_LightT_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
|
||||
// Data
|
||||
_Node->mData = New<Light_t>();
|
||||
*_Node->mData = ReadBytes<Light_t>(aFile);
|
||||
*_Node->mData = aFile->Read<Light_t>();
|
||||
|
||||
// Append
|
||||
aGfxData->mLightTs.Add(_Node);
|
||||
|
|
|
@ -39,22 +39,22 @@ DataNode<Lights1>* DynOS_Lights_Parse(GfxData* aGfxData, DataNode<Lights1>* aNod
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Lights_Write(FILE* aFile, GfxData* aGfxData, DataNode<Lights1> *aNode) {
|
||||
void DynOS_Lights_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Lights1> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_LIGHT);
|
||||
aFile->Write<u8>(DATA_TYPE_LIGHT);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<Lights1>(aFile, *aNode->mData);
|
||||
aFile->Write<Lights1>(*aNode->mData);
|
||||
}
|
||||
|
||||
/////////////
|
||||
// Reading //
|
||||
/////////////
|
||||
|
||||
void DynOS_Lights_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_Lights_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<Lights1> *_Node = New<DataNode<Lights1>>();
|
||||
|
||||
// Name
|
||||
|
@ -62,7 +62,7 @@ void DynOS_Lights_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
|
||||
// Data
|
||||
_Node->mData = New<Lights1>();
|
||||
*_Node->mData = ReadBytes<Lights1>(aFile);
|
||||
*_Node->mData = aFile->Read<Lights1>();
|
||||
|
||||
// Append
|
||||
aGfxData->mLights.Add(_Node);
|
||||
|
|
|
@ -857,15 +857,15 @@ static DataNode<LevelScript> *GetLevelScript(GfxData *aGfxData, const String& aG
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
static void DynOS_Lvl_Write(FILE* aFile, GfxData* aGfxData, DataNode<LevelScript> *aNode) {
|
||||
static void DynOS_Lvl_Write(BinFile* aFile, GfxData* aGfxData, DataNode<LevelScript> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_LEVEL_SCRIPT);
|
||||
aFile->Write<u8>(DATA_TYPE_LEVEL_SCRIPT);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
LevelScript *_Head = &aNode->mData[i];
|
||||
if (aGfxData->mPointerList.Find((void *) _Head) != -1) {
|
||||
|
@ -873,13 +873,13 @@ static void DynOS_Lvl_Write(FILE* aFile, GfxData* aGfxData, DataNode<LevelScript
|
|||
} else if (aGfxData->mLuaPointerList.Find((void *) _Head) != -1) {
|
||||
DynOS_Pointer_Lua_Write(aFile, *(u32 *)_Head, aGfxData);
|
||||
} else {
|
||||
WriteBytes<u32>(aFile, *((u32 *) _Head));
|
||||
aFile->Write<u32>(*((u32 *) _Head));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static bool DynOS_Lvl_WriteBinary(const SysPath &aOutputFilename, GfxData *aGfxData) {
|
||||
FILE *_File = fopen(aOutputFilename.c_str(), "wb");
|
||||
BinFile *_File = BinFile::OpenW(aOutputFilename.c_str());
|
||||
if (!_File) {
|
||||
PrintError(" ERROR: Unable to create file \"%s\"", aOutputFilename.c_str());
|
||||
return false;
|
||||
|
@ -962,22 +962,22 @@ static bool DynOS_Lvl_WriteBinary(const SysPath &aOutputFilename, GfxData *aGfxD
|
|||
}
|
||||
}
|
||||
}
|
||||
fclose(_File);
|
||||
return true;
|
||||
BinFile::Close(_File);
|
||||
return DynOS_Bin_Compress(aOutputFilename);
|
||||
}
|
||||
|
||||
/////////////
|
||||
// Reading //
|
||||
/////////////
|
||||
|
||||
static DataNode<LevelScript>* DynOS_Lvl_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
static DataNode<LevelScript>* DynOS_Lvl_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<LevelScript> *_Node = New<DataNode<LevelScript>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<LevelScript>(_Node->mSize);
|
||||
|
||||
// Add it
|
||||
|
@ -987,7 +987,7 @@ static DataNode<LevelScript>* DynOS_Lvl_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
|
||||
// Read it
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
u32 _Value = ReadBytes<u32>(aFile);
|
||||
u32 _Value = aFile->Read<u32>();
|
||||
void *_Ptr = DynOS_Pointer_Load(aFile, aGfxData, _Value, &_Node->mFlags);
|
||||
if (_Ptr) {
|
||||
_Node->mData[i] = (uintptr_t) _Ptr;
|
||||
|
@ -1005,11 +1005,11 @@ GfxData *DynOS_Lvl_LoadFromBinary(const SysPath &aFilename, const char *aLevelNa
|
|||
|
||||
// Load data from binary file
|
||||
GfxData *_GfxData = NULL;
|
||||
FILE *_File = fopen(aFilename.c_str(), "rb");
|
||||
BinFile *_File = DynOS_Bin_Decompress(aFilename);
|
||||
if (_File) {
|
||||
_GfxData = New<GfxData>();
|
||||
for (bool _Done = false; !_Done;) {
|
||||
switch (ReadBytes<u8>(_File)) {
|
||||
switch (_File->Read<u8>()) {
|
||||
case DATA_TYPE_LIGHT: DynOS_Lights_Load (_File, _GfxData); break;
|
||||
case DATA_TYPE_LIGHT_T: DynOS_LightT_Load (_File, _GfxData); break;
|
||||
case DATA_TYPE_AMBIENT_T: DynOS_AmbientT_Load (_File, _GfxData); break;
|
||||
|
@ -1031,7 +1031,7 @@ GfxData *DynOS_Lvl_LoadFromBinary(const SysPath &aFilename, const char *aLevelNa
|
|||
default: _Done = true; break;
|
||||
}
|
||||
}
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
}
|
||||
|
||||
return _GfxData;
|
||||
|
@ -1051,6 +1051,12 @@ static bool DynOS_Lvl_GeneratePack_Internal(const SysPath &aPackFolder, Array<Pa
|
|||
// If there is an existing binary file for this level, skip and go to the next level
|
||||
SysPath _LvlFilename = fstring("%s/%s.lvl", aPackFolder.c_str(), _LvlRootName.begin());
|
||||
if (fs_sys_file_exists(_LvlFilename.c_str())) {
|
||||
#ifdef DEVELOPMENT
|
||||
// Compress file to gain some space
|
||||
if (!DynOS_Bin_IsCompressed(_LvlFilename)) {
|
||||
DynOS_Bin_Compress(_LvlFilename);
|
||||
}
|
||||
#endif
|
||||
continue;
|
||||
}
|
||||
|
||||
|
@ -1171,6 +1177,15 @@ void DynOS_Lvl_GeneratePack(const SysPath &aPackFolder) {
|
|||
if (SysPath(_PackEnt->d_name) == ".") continue;
|
||||
if (SysPath(_PackEnt->d_name) == "..") continue;
|
||||
|
||||
#ifdef DEVELOPMENT
|
||||
// Compress .lvl files to gain some space
|
||||
SysPath _Filename = fstring("%s/%s", aPackFolder.c_str(), _PackEnt->d_name);
|
||||
if (SysPath(_PackEnt->d_name).find(".lvl") != SysPath::npos && !DynOS_Bin_IsCompressed(_Filename)) {
|
||||
DynOS_Bin_Compress(_Filename);
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
// For each subfolder, read tokens from script.c
|
||||
SysPath _Folder = fstring("%s/%s", aPackFolder.c_str(), _PackEnt->d_name);
|
||||
if (!fs_sys_dir_exists(_Folder.c_str())) continue;
|
||||
|
|
|
@ -477,17 +477,17 @@ DataNode<MacroObject>* DynOS_MacroObject_Parse(GfxData* aGfxData, DataNode<Macro
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_MacroObject_Write(FILE* aFile, GfxData* aGfxData, DataNode<MacroObject> *aNode) {
|
||||
void DynOS_MacroObject_Write(BinFile* aFile, GfxData* aGfxData, DataNode<MacroObject> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_MACRO_OBJECT);
|
||||
aFile->Write<u8>(DATA_TYPE_MACRO_OBJECT);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
WriteBytes<MacroObject>(aFile, aNode->mData[i]);
|
||||
aFile->Write<MacroObject>(aNode->mData[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -495,17 +495,17 @@ void DynOS_MacroObject_Write(FILE* aFile, GfxData* aGfxData, DataNode<MacroObjec
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
DataNode<MacroObject>* DynOS_MacroObject_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
DataNode<MacroObject>* DynOS_MacroObject_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<MacroObject> *_Node = New<DataNode<MacroObject>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<MacroObject>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
_Node->mData[i] = ReadBytes<MacroObject>(aFile);
|
||||
_Node->mData[i] = aFile->Read<MacroObject>();
|
||||
}
|
||||
|
||||
// Add it
|
||||
|
|
|
@ -169,17 +169,17 @@ DataNode<Movtex>* DynOS_Movtex_Parse(GfxData* aGfxData, DataNode<Movtex>* aNode,
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Movtex_Write(FILE* aFile, GfxData* aGfxData, DataNode<Movtex> *aNode) {
|
||||
void DynOS_Movtex_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Movtex> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_MOVTEX);
|
||||
aFile->Write<u8>(DATA_TYPE_MOVTEX);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
WriteBytes<Movtex>(aFile, aNode->mData[i]);
|
||||
aFile->Write<Movtex>(aNode->mData[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -187,17 +187,17 @@ void DynOS_Movtex_Write(FILE* aFile, GfxData* aGfxData, DataNode<Movtex> *aNode)
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
DataNode<Movtex>* DynOS_Movtex_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
DataNode<Movtex>* DynOS_Movtex_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<Movtex> *_Node = New<DataNode<Movtex>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<Movtex>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
_Node->mData[i] = ReadBytes<Movtex>(aFile);
|
||||
_Node->mData[i] = aFile->Read<Movtex>();
|
||||
}
|
||||
|
||||
// Add it
|
||||
|
|
|
@ -53,17 +53,17 @@ DataNode<MovtexQC>* DynOS_MovtexQC_Parse(GfxData* aGfxData, DataNode<MovtexQC>*
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_MovtexQC_Write(FILE* aFile, GfxData* aGfxData, DataNode<MovtexQC> *aNode) {
|
||||
void DynOS_MovtexQC_Write(BinFile* aFile, GfxData* aGfxData, DataNode<MovtexQC> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_MOVTEXQC);
|
||||
aFile->Write<u8>(DATA_TYPE_MOVTEXQC);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
WriteBytes<s16>(aFile, aNode->mData[i].id);
|
||||
aFile->Write<s16>(aNode->mData[i].id);
|
||||
DynOS_Pointer_Write(aFile, (const void *) (aNode->mData[i].quadArraySegmented), aGfxData);
|
||||
}
|
||||
}
|
||||
|
@ -72,18 +72,18 @@ void DynOS_MovtexQC_Write(FILE* aFile, GfxData* aGfxData, DataNode<MovtexQC> *aN
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
DataNode<MovtexQC>* DynOS_MovtexQC_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
DataNode<MovtexQC>* DynOS_MovtexQC_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<MovtexQC> *_Node = New<DataNode<MovtexQC>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<MovtexQC>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
_Node->mData[i].id = ReadBytes<s16>(aFile);
|
||||
u32 _Value = ReadBytes<u32>(aFile);
|
||||
_Node->mData[i].id = aFile->Read<s16>();
|
||||
u32 _Value = aFile->Read<u32>();
|
||||
void *_Ptr = DynOS_Pointer_Load(aFile, aGfxData, _Value, &_Node->mFlags);
|
||||
_Node->mData[i].quadArraySegmented = (Movtex*)_Ptr;
|
||||
}
|
||||
|
|
|
@ -187,17 +187,17 @@ static PointerData GetDataFromPointer(const void* aPtr, GfxData* aGfxData) {
|
|||
return { "", 0 };
|
||||
}
|
||||
|
||||
void DynOS_Pointer_Lua_Write(FILE* aFile, u32 index, GfxData* aGfxData) {
|
||||
void DynOS_Pointer_Lua_Write(BinFile* aFile, u32 index, GfxData* aGfxData) {
|
||||
String& token = aGfxData->mLuaTokenList[index];
|
||||
WriteBytes<u32>(aFile, LUA_VAR_CODE);
|
||||
aFile->Write<u32>(LUA_VAR_CODE);
|
||||
token.Write(aFile);
|
||||
}
|
||||
|
||||
void DynOS_Pointer_Write(FILE* aFile, const void* aPtr, GfxData* aGfxData) {
|
||||
void DynOS_Pointer_Write(BinFile* aFile, const void* aPtr, GfxData* aGfxData) {
|
||||
|
||||
// NULL
|
||||
if (!aPtr) {
|
||||
WriteBytes<u32>(aFile, 0);
|
||||
aFile->Write<u32>(0);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -206,7 +206,7 @@ void DynOS_Pointer_Write(FILE* aFile, const void* aPtr, GfxData* aGfxData) {
|
|||
if (aPtr == aGfxData->mLuaPointerList[i]) {
|
||||
u32 index = *((u32*)aPtr);
|
||||
String& token = aGfxData->mLuaTokenList[index];
|
||||
WriteBytes<u32>(aFile, LUA_VAR_CODE);
|
||||
aFile->Write<u32>(LUA_VAR_CODE);
|
||||
token.Write(aFile);
|
||||
return;
|
||||
}
|
||||
|
@ -215,16 +215,16 @@ void DynOS_Pointer_Write(FILE* aFile, const void* aPtr, GfxData* aGfxData) {
|
|||
// Built-in functions
|
||||
s32 _GeoFunctionIndex = DynOS_Builtin_Func_GetIndexFromData(aPtr);
|
||||
if (_GeoFunctionIndex != -1) {
|
||||
WriteBytes<u32>(aFile, FUNCTION_CODE);
|
||||
WriteBytes<s32>(aFile, _GeoFunctionIndex);
|
||||
aFile->Write<u32>(FUNCTION_CODE);
|
||||
aFile->Write<s32>(_GeoFunctionIndex);
|
||||
return;
|
||||
}
|
||||
|
||||
// Pointer
|
||||
PointerData _PtrData = GetDataFromPointer(aPtr, aGfxData);
|
||||
WriteBytes<u32>(aFile, POINTER_CODE);
|
||||
aFile->Write<u32>(POINTER_CODE);
|
||||
_PtrData.first.Write(aFile);
|
||||
WriteBytes<u32>(aFile, _PtrData.second);
|
||||
aFile->Write<u32>(_PtrData.second);
|
||||
}
|
||||
|
||||
/////////////
|
||||
|
@ -416,7 +416,7 @@ static void *GetPointerFromData(GfxData *aGfxData, const String &aPtrName, u32 a
|
|||
return NULL;
|
||||
}
|
||||
|
||||
void *DynOS_Pointer_Load(FILE *aFile, GfxData *aGfxData, u32 aValue, u8* outFlags) {
|
||||
void *DynOS_Pointer_Load(BinFile *aFile, GfxData *aGfxData, u32 aValue, u8* outFlags) {
|
||||
|
||||
// LUAV
|
||||
if (aValue == LUA_VAR_CODE) {
|
||||
|
@ -433,14 +433,14 @@ void *DynOS_Pointer_Load(FILE *aFile, GfxData *aGfxData, u32 aValue, u8* outFlag
|
|||
|
||||
// FUNC
|
||||
if (aValue == FUNCTION_CODE) {
|
||||
s32 _FunctionIndex = ReadBytes<s32>(aFile);
|
||||
s32 _FunctionIndex = aFile->Read<s32>();
|
||||
return (void*) DynOS_Builtin_Func_GetFromIndex(_FunctionIndex);
|
||||
}
|
||||
|
||||
// PNTR
|
||||
if (aValue == POINTER_CODE) {
|
||||
String _PtrName; _PtrName.Read(aFile);
|
||||
u32 _PtrData = ReadBytes<u32>(aFile);
|
||||
u32 _PtrData = aFile->Read<u32>();
|
||||
return GetPointerFromData(aGfxData, _PtrName, _PtrData, outFlags);
|
||||
}
|
||||
|
||||
|
|
|
@ -24,17 +24,17 @@ DataNode<u8>* DynOS_Rooms_Parse(GfxData* aGfxData, DataNode<u8>* aNode) {
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Rooms_Write(FILE* aFile, GfxData* aGfxData, DataNode<u8> *aNode) {
|
||||
void DynOS_Rooms_Write(BinFile* aFile, GfxData* aGfxData, DataNode<u8> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_ROOMS);
|
||||
aFile->Write<u8>(DATA_TYPE_ROOMS);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
WriteBytes<u8>(aFile, aNode->mData[i]);
|
||||
aFile->Write<u8>(aNode->mData[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -42,17 +42,17 @@ void DynOS_Rooms_Write(FILE* aFile, GfxData* aGfxData, DataNode<u8> *aNode) {
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
DataNode<u8>* DynOS_Rooms_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
DataNode<u8>* DynOS_Rooms_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<u8> *_Node = New<DataNode<u8>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<u8>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
_Node->mData[i] = ReadBytes<u8>(aFile);
|
||||
_Node->mData[i] = aFile->Read<u8>();
|
||||
}
|
||||
|
||||
// Add it
|
||||
|
|
|
@ -151,11 +151,11 @@ DataNode<TexData>* DynOS_Tex_Parse(GfxData* aGfxData, DataNode<TexData>* aNode)
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Tex_Write(FILE* aFile, GfxData* aGfxData, DataNode<TexData> *aNode) {
|
||||
void DynOS_Tex_Write(BinFile* aFile, GfxData* aGfxData, DataNode<TexData> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_TEXTURE);
|
||||
aFile->Write<u8>(DATA_TYPE_TEXTURE);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
|
@ -169,7 +169,7 @@ void DynOS_Tex_Write(FILE* aFile, GfxData* aGfxData, DataNode<TexData> *aNode) {
|
|||
aNode->mData->mPngData.Count() == _Node->mData->mPngData.Count() && // Check PNG data lengths
|
||||
memcmp(aNode->mData->mPngData.begin(), _Node->mData->mPngData.begin(), aNode->mData->mPngData.Count()) == 0) // Check PNG data content
|
||||
{
|
||||
WriteBytes<u32>(aFile, TEX_REF_CODE);
|
||||
aFile->Write<u32>(TEX_REF_CODE);
|
||||
_Node->mName.Write(aFile);
|
||||
return;
|
||||
}
|
||||
|
@ -179,7 +179,7 @@ void DynOS_Tex_Write(FILE* aFile, GfxData* aGfxData, DataNode<TexData> *aNode) {
|
|||
}
|
||||
|
||||
static bool DynOS_Tex_WriteBinary(GfxData* aGfxData, const SysPath &aOutputFilename, String& aName, TexData* aTexData, bool aRawTexture) {
|
||||
FILE *_File = fopen(aOutputFilename.c_str(), "wb");
|
||||
BinFile *_File = BinFile::OpenW(aOutputFilename.c_str());
|
||||
if (!_File) {
|
||||
PrintError(" ERROR: Unable to create file \"%s\"", aOutputFilename.c_str());
|
||||
return false;
|
||||
|
@ -189,20 +189,20 @@ static bool DynOS_Tex_WriteBinary(GfxData* aGfxData, const SysPath &aOutputFilen
|
|||
// Write png-texture
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(_File, DATA_TYPE_TEXTURE);
|
||||
_File->Write<u8>(DATA_TYPE_TEXTURE);
|
||||
aName.Write(_File);
|
||||
|
||||
// Data
|
||||
aTexData->mPngData.Write(_File);
|
||||
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Write raw-texture
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(_File, DATA_TYPE_TEXTURE_RAW);
|
||||
_File->Write<u8>(DATA_TYPE_TEXTURE_RAW);
|
||||
aName.Write(_File);
|
||||
|
||||
// load
|
||||
|
@ -213,13 +213,13 @@ static bool DynOS_Tex_WriteBinary(GfxData* aGfxData, const SysPath &aOutputFilen
|
|||
free(_RawData);
|
||||
|
||||
// Data
|
||||
WriteBytes<s32>(_File, aTexData->mRawFormat);
|
||||
WriteBytes<s32>(_File, aTexData->mRawSize);
|
||||
WriteBytes<s32>(_File, aTexData->mRawWidth);
|
||||
WriteBytes<s32>(_File, aTexData->mRawHeight);
|
||||
_File->Write<s32>(aTexData->mRawFormat);
|
||||
_File->Write<s32>(aTexData->mRawSize);
|
||||
_File->Write<s32>(aTexData->mRawWidth);
|
||||
_File->Write<s32>(aTexData->mRawHeight);
|
||||
aTexData->mRawData.Write(_File);
|
||||
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -227,7 +227,7 @@ static bool DynOS_Tex_WriteBinary(GfxData* aGfxData, const SysPath &aOutputFilen
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
DataNode<TexData>* DynOS_Tex_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
DataNode<TexData>* DynOS_Tex_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<TexData> *_Node = New<DataNode<TexData>>();
|
||||
|
||||
// Name
|
||||
|
@ -238,8 +238,8 @@ DataNode<TexData>* DynOS_Tex_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
_Node->mData->mUploaded = false;
|
||||
|
||||
// Check for the texture ref magic
|
||||
s32 _FileOffset = (s32) ftell(aFile);
|
||||
u32 _TexRefCode = ReadBytes<u32>(aFile);
|
||||
s32 _FileOffset = aFile->Offset();
|
||||
u32 _TexRefCode = aFile->Read<u32>();
|
||||
if (_TexRefCode == TEX_REF_CODE) {
|
||||
|
||||
// That's a duplicate, find the original node and copy its content
|
||||
|
@ -256,7 +256,7 @@ DataNode<TexData>* DynOS_Tex_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
}
|
||||
}
|
||||
} else {
|
||||
fseek(aFile, _FileOffset, SEEK_SET);
|
||||
aFile->SetOffset(_FileOffset);
|
||||
_Node->mData->mPngData.Read(aFile);
|
||||
if (!_Node->mData->mPngData.Empty()) {
|
||||
u8 *_RawData = stbi_load_from_memory(_Node->mData->mPngData.begin(), _Node->mData->mPngData.Count(), &_Node->mData->mRawWidth, &_Node->mData->mRawHeight, NULL, 4);
|
||||
|
@ -295,10 +295,10 @@ DataNode<TexData>* DynOS_Tex_LoadFromBinary(const SysPath &aPackFolder, const Sy
|
|||
|
||||
// Load data from binary file
|
||||
DataNode<TexData>* _TexNode = NULL;
|
||||
FILE *_File = fopen(aFilename.c_str(), "rb");
|
||||
BinFile *_File = BinFile::OpenR(aFilename.c_str());
|
||||
if (!_File) { return NULL; }
|
||||
|
||||
u8 type = ReadBytes<u8>(_File);
|
||||
u8 type = _File->Read<u8>();
|
||||
if (type == DATA_TYPE_TEXTURE) {
|
||||
// load png-texture
|
||||
_TexNode = New<DataNode<TexData>>();
|
||||
|
@ -306,7 +306,7 @@ DataNode<TexData>* DynOS_Tex_LoadFromBinary(const SysPath &aPackFolder, const Sy
|
|||
|
||||
_TexNode->mName.Read(_File);
|
||||
_TexNode->mData->mPngData.Read(_File);
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
|
||||
if (aAddToPack) {
|
||||
if (!_Pack) { _Pack = DynOS_Pack_Add(aPackFolder); }
|
||||
|
@ -315,7 +315,7 @@ DataNode<TexData>* DynOS_Tex_LoadFromBinary(const SysPath &aPackFolder, const Sy
|
|||
|
||||
return _TexNode;
|
||||
} else if (type != DATA_TYPE_TEXTURE_RAW) {
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@ -324,13 +324,13 @@ DataNode<TexData>* DynOS_Tex_LoadFromBinary(const SysPath &aPackFolder, const Sy
|
|||
_TexNode->mData = New<TexData>();
|
||||
|
||||
_TexNode->mName.Read(_File);
|
||||
_TexNode->mData->mRawFormat = ReadBytes<s32>(_File);
|
||||
_TexNode->mData->mRawSize = ReadBytes<s32>(_File);
|
||||
_TexNode->mData->mRawWidth = ReadBytes<s32>(_File);
|
||||
_TexNode->mData->mRawHeight = ReadBytes<s32>(_File);
|
||||
_TexNode->mData->mRawFormat = _File->Read<s32>();
|
||||
_TexNode->mData->mRawSize = _File->Read<s32>();
|
||||
_TexNode->mData->mRawWidth = _File->Read<s32>();
|
||||
_TexNode->mData->mRawHeight = _File->Read<s32>();
|
||||
_TexNode->mData->mRawData.Read(_File);
|
||||
|
||||
fclose(_File);
|
||||
BinFile::Close(_File);
|
||||
|
||||
if (aAddToPack) {
|
||||
if (!_Pack) { _Pack = DynOS_Pack_Add(aPackFolder); }
|
||||
|
|
|
@ -36,15 +36,15 @@ DataNode<TexData*>* DynOS_TexList_Parse(GfxData* aGfxData, DataNode<TexData*>* a
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_TexList_Write(FILE* aFile, GfxData* aGfxData, DataNode<TexData*> *aNode) {
|
||||
void DynOS_TexList_Write(BinFile* aFile, GfxData* aGfxData, DataNode<TexData*> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_TEXTURE_LIST);
|
||||
aFile->Write<u8>(DATA_TYPE_TEXTURE_LIST);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
// find node
|
||||
bool found = false;
|
||||
|
@ -65,17 +65,17 @@ void DynOS_TexList_Write(FILE* aFile, GfxData* aGfxData, DataNode<TexData*> *aNo
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
DataNode<TexData*>* DynOS_TexList_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
DataNode<TexData*>* DynOS_TexList_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<TexData*> *_Node = New<DataNode<TexData*>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<TexData*>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
u32 _Value = ReadBytes<u32>(aFile);
|
||||
u32 _Value = aFile->Read<u32>();
|
||||
void *_Ptr = DynOS_Pointer_Load(aFile, aGfxData, _Value, &_Node->mFlags);
|
||||
if (_Ptr == NULL) {
|
||||
PrintError("Could not read texture in texlist");
|
||||
|
|
|
@ -85,17 +85,17 @@ DataNode<Trajectory>* DynOS_Trajectory_Parse(GfxData* aGfxData, DataNode<Traject
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Trajectory_Write(FILE* aFile, GfxData* aGfxData, DataNode<Trajectory> *aNode) {
|
||||
void DynOS_Trajectory_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Trajectory> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Name
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_TRAJECTORY);
|
||||
aFile->Write<u8>(DATA_TYPE_TRAJECTORY);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
WriteBytes<Trajectory>(aFile, aNode->mData[i]);
|
||||
aFile->Write<Trajectory>(aNode->mData[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -103,17 +103,17 @@ void DynOS_Trajectory_Write(FILE* aFile, GfxData* aGfxData, DataNode<Trajectory>
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
DataNode<Trajectory>* DynOS_Trajectory_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
DataNode<Trajectory>* DynOS_Trajectory_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<Trajectory> *_Node = New<DataNode<Trajectory>>();
|
||||
|
||||
// Name
|
||||
_Node->mName.Read(aFile);
|
||||
|
||||
// Data
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<Trajectory>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
_Node->mData[i] = ReadBytes<Trajectory>(aFile);
|
||||
_Node->mData[i] = aFile->Read<Trajectory>();
|
||||
}
|
||||
|
||||
// Add it
|
||||
|
|
|
@ -56,49 +56,49 @@ DataNode<Vtx>* DynOS_Vtx_Parse(GfxData* aGfxData, DataNode<Vtx>* aNode) {
|
|||
// Writing //
|
||||
/////////////
|
||||
|
||||
void DynOS_Vtx_Write(FILE* aFile, GfxData* aGfxData, DataNode<Vtx> *aNode) {
|
||||
void DynOS_Vtx_Write(BinFile* aFile, GfxData* aGfxData, DataNode<Vtx> *aNode) {
|
||||
if (!aNode->mData) return;
|
||||
|
||||
// Header
|
||||
WriteBytes<u8>(aFile, DATA_TYPE_VERTEX);
|
||||
aFile->Write<u8>(DATA_TYPE_VERTEX);
|
||||
aNode->mName.Write(aFile);
|
||||
|
||||
// Data
|
||||
bool shouldUseF32Vtx = ShouldUseF32Vtx(aNode);
|
||||
if (shouldUseF32Vtx) {
|
||||
WriteBytes<u32>(aFile, aNode->mSize + 1);
|
||||
aFile->Write<u32>(aNode->mSize + 1);
|
||||
|
||||
// Write sentinel
|
||||
WriteBytes<s16>(aFile, F32VTX_SENTINEL_0);
|
||||
WriteBytes<s16>(aFile, F32VTX_SENTINEL_1);
|
||||
WriteBytes<s16>(aFile, F32VTX_SENTINEL_2);
|
||||
WriteBytes<s16>(aFile, 0);
|
||||
WriteBytes<s16>(aFile, 0);
|
||||
WriteBytes<s16>(aFile, 0);
|
||||
WriteBytes<s8> (aFile, 0);
|
||||
WriteBytes<s8> (aFile, 0);
|
||||
WriteBytes<s8> (aFile, 0);
|
||||
WriteBytes<u8> (aFile, 0);
|
||||
aFile->Write<s16>(F32VTX_SENTINEL_0);
|
||||
aFile->Write<s16>(F32VTX_SENTINEL_1);
|
||||
aFile->Write<s16>(F32VTX_SENTINEL_2);
|
||||
aFile->Write<s16>(0);
|
||||
aFile->Write<s16>(0);
|
||||
aFile->Write<s16>(0);
|
||||
aFile->Write<s8> (0);
|
||||
aFile->Write<s8> (0);
|
||||
aFile->Write<s8> (0);
|
||||
aFile->Write<u8> (0);
|
||||
} else {
|
||||
WriteBytes<u32>(aFile, aNode->mSize);
|
||||
aFile->Write<u32>(aNode->mSize);
|
||||
}
|
||||
for (u32 i = 0; i != aNode->mSize; ++i) {
|
||||
if (shouldUseF32Vtx) {
|
||||
WriteBytes<f32>(aFile, aNode->mData[i].n.ob[0]);
|
||||
WriteBytes<f32>(aFile, aNode->mData[i].n.ob[1]);
|
||||
WriteBytes<f32>(aFile, aNode->mData[i].n.ob[2]);
|
||||
aFile->Write<f32>(aNode->mData[i].n.ob[0]);
|
||||
aFile->Write<f32>(aNode->mData[i].n.ob[1]);
|
||||
aFile->Write<f32>(aNode->mData[i].n.ob[2]);
|
||||
} else {
|
||||
WriteBytes<s16>(aFile, aNode->mData[i].n.ob[0]);
|
||||
WriteBytes<s16>(aFile, aNode->mData[i].n.ob[1]);
|
||||
WriteBytes<s16>(aFile, aNode->mData[i].n.ob[2]);
|
||||
aFile->Write<s16>(aNode->mData[i].n.ob[0]);
|
||||
aFile->Write<s16>(aNode->mData[i].n.ob[1]);
|
||||
aFile->Write<s16>(aNode->mData[i].n.ob[2]);
|
||||
}
|
||||
WriteBytes<s16>(aFile, aNode->mData[i].n.flag);
|
||||
WriteBytes<s16>(aFile, aNode->mData[i].n.tc[0]);
|
||||
WriteBytes<s16>(aFile, aNode->mData[i].n.tc[1]);
|
||||
WriteBytes<s8> (aFile, aNode->mData[i].n.n[0]);
|
||||
WriteBytes<s8> (aFile, aNode->mData[i].n.n[1]);
|
||||
WriteBytes<s8> (aFile, aNode->mData[i].n.n[2]);
|
||||
WriteBytes<u8> (aFile, aNode->mData[i].n.a);
|
||||
aFile->Write<s16>(aNode->mData[i].n.flag);
|
||||
aFile->Write<s16>(aNode->mData[i].n.tc[0]);
|
||||
aFile->Write<s16>(aNode->mData[i].n.tc[1]);
|
||||
aFile->Write<s8> (aNode->mData[i].n.n[0]);
|
||||
aFile->Write<s8> (aNode->mData[i].n.n[1]);
|
||||
aFile->Write<s8> (aNode->mData[i].n.n[2]);
|
||||
aFile->Write<u8> (aNode->mData[i].n.a);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -106,7 +106,7 @@ void DynOS_Vtx_Write(FILE* aFile, GfxData* aGfxData, DataNode<Vtx> *aNode) {
|
|||
// Reading //
|
||||
/////////////
|
||||
|
||||
void DynOS_Vtx_Load(FILE *aFile, GfxData *aGfxData) {
|
||||
void DynOS_Vtx_Load(BinFile *aFile, GfxData *aGfxData) {
|
||||
DataNode<Vtx> *_Node = New<DataNode<Vtx>>();
|
||||
|
||||
// Name
|
||||
|
@ -114,25 +114,25 @@ void DynOS_Vtx_Load(FILE *aFile, GfxData *aGfxData) {
|
|||
|
||||
// Data
|
||||
bool isUsingF32Vtx = false;
|
||||
_Node->mSize = ReadBytes<u32>(aFile);
|
||||
_Node->mSize = aFile->Read<u32>();
|
||||
_Node->mData = New<Vtx>(_Node->mSize);
|
||||
for (u32 i = 0; i != _Node->mSize; ++i) {
|
||||
if (isUsingF32Vtx) {
|
||||
_Node->mData[i].n.ob[0] = ReadBytes<f32>(aFile);
|
||||
_Node->mData[i].n.ob[1] = ReadBytes<f32>(aFile);
|
||||
_Node->mData[i].n.ob[2] = ReadBytes<f32>(aFile);
|
||||
_Node->mData[i].n.ob[0] = aFile->Read<f32>();
|
||||
_Node->mData[i].n.ob[1] = aFile->Read<f32>();
|
||||
_Node->mData[i].n.ob[2] = aFile->Read<f32>();
|
||||
} else {
|
||||
_Node->mData[i].n.ob[0] = ReadBytes<s16>(aFile);
|
||||
_Node->mData[i].n.ob[1] = ReadBytes<s16>(aFile);
|
||||
_Node->mData[i].n.ob[2] = ReadBytes<s16>(aFile);
|
||||
_Node->mData[i].n.ob[0] = aFile->Read<s16>();
|
||||
_Node->mData[i].n.ob[1] = aFile->Read<s16>();
|
||||
_Node->mData[i].n.ob[2] = aFile->Read<s16>();
|
||||
}
|
||||
_Node->mData[i].n.flag = ReadBytes<s16>(aFile);
|
||||
_Node->mData[i].n.tc[0] = ReadBytes<s16>(aFile);
|
||||
_Node->mData[i].n.tc[1] = ReadBytes<s16>(aFile);
|
||||
_Node->mData[i].n.n[0] = ReadBytes<s8> (aFile);
|
||||
_Node->mData[i].n.n[1] = ReadBytes<s8> (aFile);
|
||||
_Node->mData[i].n.n[2] = ReadBytes<s8> (aFile);
|
||||
_Node->mData[i].n.a = ReadBytes<u8> (aFile);
|
||||
_Node->mData[i].n.flag = aFile->Read<s16>();
|
||||
_Node->mData[i].n.tc[0] = aFile->Read<s16>();
|
||||
_Node->mData[i].n.tc[1] = aFile->Read<s16>();
|
||||
_Node->mData[i].n.n[0] = aFile->Read<s8> ();
|
||||
_Node->mData[i].n.n[1] = aFile->Read<s8> ();
|
||||
_Node->mData[i].n.n[2] = aFile->Read<s8> ();
|
||||
_Node->mData[i].n.a = aFile->Read<u8> ();
|
||||
|
||||
// Check sentinel on first vertex
|
||||
if (!isUsingF32Vtx && i == 0 && IsUsingF32Vtx(_Node->mData[i].n.ob)) {
|
||||
|
|
|
@ -1,10 +0,0 @@
|
|||
#include "dynos.cpp.h"
|
||||
|
||||
void SkipBytes(FILE *aFile, size_t amount) {
|
||||
// If we're at end of file. There is no more to skip.
|
||||
if (feof(aFile)) { return; }
|
||||
|
||||
int failure = fseek(aFile, amount, SEEK_CUR);
|
||||
// If we failed to skip bytes. Print the error.
|
||||
if (failure) { perror("The following error occured when skipping bytes"); }
|
||||
}
|
Loading…
Reference in a new issue