mirror of
https://github.com/ZDoom/Raze.git
synced 2024-11-15 00:42:08 +00:00
- Backend update from GZDoom-
This compiles but doesn't run.
This commit is contained in:
parent
f2740e434a
commit
82057bcd5a
117 changed files with 1218 additions and 763 deletions
|
@ -576,7 +576,8 @@ file( GLOB HEADER_FILES
|
||||||
common/statusbar/*.h
|
common/statusbar/*.h
|
||||||
common/fonts/*.h
|
common/fonts/*.h
|
||||||
common/objects/*.h
|
common/objects/*.h
|
||||||
common/filesystem/*.h
|
common/filesystem/include/*.h
|
||||||
|
common/filesystem/source/*.h
|
||||||
common/platform/posix/cocoa/*.h
|
common/platform/posix/cocoa/*.h
|
||||||
common/platform/posix/sdl/*.h
|
common/platform/posix/sdl/*.h
|
||||||
common/platform/win32/*.h
|
common/platform/win32/*.h
|
||||||
|
@ -1232,18 +1233,7 @@ else()
|
||||||
set( NOT_COMPILED_SOURCE_FILES ${NOT_COMPILED_SOURCE_FILES} ${VM_JIT_SOURCES} )
|
set( NOT_COMPILED_SOURCE_FILES ${NOT_COMPILED_SOURCE_FILES} ${VM_JIT_SOURCES} )
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
macro( use_precompiled_header )
|
set( GAME_SOURCES
|
||||||
if( MSVC )
|
|
||||||
enable_precompiled_headers( "${ARGV0}/g_pch.h" PCH_SOURCES )
|
|
||||||
else()
|
|
||||||
# Temporary solution for compilers other than MSVC
|
|
||||||
set_source_files_properties( ${PCH_SOURCES} PROPERTIES COMPILE_FLAGS "-include g_pch.h" )
|
|
||||||
endif()
|
|
||||||
endmacro()
|
|
||||||
|
|
||||||
use_precompiled_header(".")
|
|
||||||
|
|
||||||
add_executable( ${PROJECT_NAME} WIN32 MACOSX_BUNDLE
|
|
||||||
${HEADER_FILES}
|
${HEADER_FILES}
|
||||||
${NOT_COMPILED_SOURCE_FILES}
|
${NOT_COMPILED_SOURCE_FILES}
|
||||||
${SYSTEM_SOURCES}
|
${SYSTEM_SOURCES}
|
||||||
|
@ -1273,29 +1263,37 @@ add_executable( ${PROJECT_NAME} WIN32 MACOSX_BUNDLE
|
||||||
common/thirdparty/math/tanh.c
|
common/thirdparty/math/tanh.c
|
||||||
common/thirdparty/math/fastsin.cpp
|
common/thirdparty/math/fastsin.cpp
|
||||||
|
|
||||||
common/filesystem/filesystem.cpp
|
common/filesystem/source/filesystem.cpp
|
||||||
common/filesystem/ancientzip.cpp
|
common/filesystem/source/ancientzip.cpp
|
||||||
common/filesystem/file_7z.cpp
|
common/filesystem/source/file_7z.cpp
|
||||||
common/filesystem/file_grp.cpp
|
common/filesystem/source/file_grp.cpp
|
||||||
common/filesystem/file_lump.cpp
|
common/filesystem/source/file_lump.cpp
|
||||||
common/filesystem/file_rff.cpp
|
common/filesystem/source/file_rff.cpp
|
||||||
common/filesystem/file_wad.cpp
|
common/filesystem/source/file_wad.cpp
|
||||||
common/filesystem/file_zip.cpp
|
common/filesystem/source/file_zip.cpp
|
||||||
common/filesystem/file_pak.cpp
|
common/filesystem/source/file_pak.cpp
|
||||||
common/filesystem/file_whres.cpp
|
common/filesystem/source/file_whres.cpp
|
||||||
common/filesystem/file_ssi.cpp
|
common/filesystem/source/file_ssi.cpp
|
||||||
common/filesystem/file_directory.cpp
|
common/filesystem/source/file_directory.cpp
|
||||||
common/filesystem/resourcefile.cpp
|
common/filesystem/source/resourcefile.cpp
|
||||||
common/filesystem/files.cpp
|
common/filesystem/source/files.cpp
|
||||||
common/filesystem/files_decompress.cpp
|
common/filesystem/source/files_decompress.cpp
|
||||||
common/filesystem/fs_findfile.cpp
|
common/filesystem/source/fs_findfile.cpp
|
||||||
|
common/filesystem/source/fs_stringpool.cpp
|
||||||
|
|
||||||
)
|
)
|
||||||
|
|
||||||
|
set( GAME_NONPCH_SOURCES ${GAME_SOURCES} )
|
||||||
|
list( REMOVE_ITEM GAME_NONPCH_SOURCES ${PCH_SOURCES} )
|
||||||
|
|
||||||
|
add_executable( ${PROJECT_NAME} WIN32 MACOSX_BUNDLE ${GAME_SOURCES} )
|
||||||
|
|
||||||
|
target_precompile_headers( ${PROJECT_NAME} PRIVATE g_pch.h )
|
||||||
|
|
||||||
#set_source_files_properties( ${FASTMATH_SOURCES} PROPERTIES COMPILE_FLAGS ${DEM_FASTMATH_FLAG} )
|
#set_source_files_properties( ${FASTMATH_SOURCES} PROPERTIES COMPILE_FLAGS ${DEM_FASTMATH_FLAG} )
|
||||||
set_source_files_properties( xlat/parse_xlat.cpp PROPERTIES OBJECT_DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/xlat_parser.c" )
|
|
||||||
set_source_files_properties( common/engine/sc_man.cpp PROPERTIES OBJECT_DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h" )
|
set_source_files_properties( common/engine/sc_man.cpp PROPERTIES OBJECT_DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h" )
|
||||||
set_source_files_properties( ${NOT_COMPILED_SOURCE_FILES} PROPERTIES HEADER_FILE_ONLY TRUE )
|
set_source_files_properties( ${NOT_COMPILED_SOURCE_FILES} PROPERTIES HEADER_FILE_ONLY TRUE )
|
||||||
|
set_source_files_properties( ${GAME_NONPCH_SOURCES} common/textures/hires/hqresize.cpp PROPERTIES SKIP_PRECOMPILE_HEADERS TRUE )
|
||||||
|
|
||||||
|
|
||||||
if(${CMAKE_SYSTEM_NAME} STREQUAL "SunOS")
|
if(${CMAKE_SYSTEM_NAME} STREQUAL "SunOS")
|
||||||
|
@ -1345,7 +1343,7 @@ include_directories(
|
||||||
common/textures/hires
|
common/textures/hires
|
||||||
common/textures
|
common/textures
|
||||||
common/models
|
common/models
|
||||||
common/filesystem
|
common/filesystem/include
|
||||||
common/utility
|
common/utility
|
||||||
common/console
|
common/console
|
||||||
common/engine
|
common/engine
|
||||||
|
@ -1510,6 +1508,8 @@ source_group("Common\\Objects" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/
|
||||||
source_group("Common\\Menu" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/menu/.+")
|
source_group("Common\\Menu" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/menu/.+")
|
||||||
source_group("Common\\Fonts" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/fonts/.+")
|
source_group("Common\\Fonts" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/fonts/.+")
|
||||||
source_group("Common\\File System" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/filesystem/.+")
|
source_group("Common\\File System" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/filesystem/.+")
|
||||||
|
source_group("Common\\File System\\Include" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/filesystem/include/.+")
|
||||||
|
source_group("Common\\File System\\Source" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/filesystem/source/.+")
|
||||||
source_group("Common\\Scripting" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/scripting/.+")
|
source_group("Common\\Scripting" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/scripting/.+")
|
||||||
source_group("Common\\Scripting\\Interface" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/scripting/interface/.+")
|
source_group("Common\\Scripting\\Interface" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/scripting/interface/.+")
|
||||||
source_group("Common\\Scripting\\Frontend" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/scripting/frontend/.+" FILES ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.c ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.h)
|
source_group("Common\\Scripting\\Frontend" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/scripting/frontend/.+" FILES ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.c ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.h)
|
||||||
|
|
|
@ -53,6 +53,7 @@
|
||||||
#include "s_music.h"
|
#include "s_music.h"
|
||||||
#include "filereadermusicinterface.h"
|
#include "filereadermusicinterface.h"
|
||||||
|
|
||||||
|
using namespace FileSys;
|
||||||
|
|
||||||
|
|
||||||
void I_InitSoundFonts();
|
void I_InitSoundFonts();
|
||||||
|
@ -182,7 +183,7 @@ static void SetupGenMidi()
|
||||||
auto genmidi = fileSystem.ReadFile(lump);
|
auto genmidi = fileSystem.ReadFile(lump);
|
||||||
|
|
||||||
if (genmidi.GetSize() < 8 + 175 * 36 || memcmp(genmidi.GetMem(), "#OPL_II#", 8)) return;
|
if (genmidi.GetSize() < 8 + 175 * 36 || memcmp(genmidi.GetMem(), "#OPL_II#", 8)) return;
|
||||||
ZMusic_SetGenMidi(genmidi.GetBytes()+8);
|
ZMusic_SetGenMidi(genmidi.GetBytes() + 8);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetupWgOpn()
|
static void SetupWgOpn()
|
||||||
|
@ -192,7 +193,7 @@ static void SetupWgOpn()
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
FileData data = fileSystem.ReadFile(lump);
|
auto data = fileSystem.ReadFile(lump);
|
||||||
ZMusic_SetWgOpn(data.GetMem(), (uint32_t)data.GetSize());
|
ZMusic_SetWgOpn(data.GetMem(), (uint32_t)data.GetSize());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -204,7 +205,7 @@ static void SetupDMXGUS()
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
FileData data = fileSystem.ReadFile(lump);
|
auto data = fileSystem.ReadFile(lump);
|
||||||
ZMusic_SetDmxGus(data.GetMem(), (uint32_t)data.GetSize());
|
ZMusic_SetDmxGus(data.GetMem(), (uint32_t)data.GetSize());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -40,10 +40,9 @@
|
||||||
#include "i_system.h"
|
#include "i_system.h"
|
||||||
#include "filereadermusicinterface.h"
|
#include "filereadermusicinterface.h"
|
||||||
#include <zmusic.h>
|
#include <zmusic.h>
|
||||||
#include "resourcefile.h"
|
#include "fs_filesystem.h"
|
||||||
#include "version.h"
|
#include "version.h"
|
||||||
#include "fs_findfile.h"
|
#include "fs_findfile.h"
|
||||||
#include "resourcefile.h"
|
|
||||||
#include "i_interface.h"
|
#include "i_interface.h"
|
||||||
#include "configfile.h"
|
#include "configfile.h"
|
||||||
#include "printf.h"
|
#include "printf.h"
|
||||||
|
@ -332,7 +331,7 @@ FileReader FLumpPatchSetReader::OpenFile(const char *name)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
void FSoundFontManager::ProcessOneFile(const FString &fn)
|
void FSoundFontManager::ProcessOneFile(const char* fn)
|
||||||
{
|
{
|
||||||
auto fb = ExtractFileBase(fn, false);
|
auto fb = ExtractFileBase(fn, false);
|
||||||
auto fbe = ExtractFileBase(fn, true);
|
auto fbe = ExtractFileBase(fn, true);
|
||||||
|
@ -402,7 +401,7 @@ void FSoundFontManager::CollectSoundfonts()
|
||||||
{
|
{
|
||||||
if (stricmp (key, "Path") == 0)
|
if (stricmp (key, "Path") == 0)
|
||||||
{
|
{
|
||||||
FileList list;
|
FileSys::FileList list;
|
||||||
|
|
||||||
FString dir;
|
FString dir;
|
||||||
|
|
||||||
|
@ -410,7 +409,7 @@ void FSoundFontManager::CollectSoundfonts()
|
||||||
FixPathSeperator(dir);
|
FixPathSeperator(dir);
|
||||||
if (dir.IsNotEmpty())
|
if (dir.IsNotEmpty())
|
||||||
{
|
{
|
||||||
if (ScanDirectory(list, dir.GetChars(), "*", true))
|
if (FileSys::ScanDirectory(list, dir.GetChars(), "*", true))
|
||||||
{
|
{
|
||||||
for(auto& entry : list)
|
for(auto& entry : list)
|
||||||
{
|
{
|
||||||
|
|
|
@ -148,7 +148,7 @@ class FSoundFontManager
|
||||||
{
|
{
|
||||||
TArray<FSoundFontInfo> soundfonts;
|
TArray<FSoundFontInfo> soundfonts;
|
||||||
|
|
||||||
void ProcessOneFile(const FString & fn);
|
void ProcessOneFile(const char* fn);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
void CollectSoundfonts();
|
void CollectSoundfonts();
|
||||||
|
|
|
@ -55,6 +55,7 @@
|
||||||
#include "i_specialpaths.h"
|
#include "i_specialpaths.h"
|
||||||
#include "configfile.h"
|
#include "configfile.h"
|
||||||
#include "c_cvars.h"
|
#include "c_cvars.h"
|
||||||
|
#include "md5.h"
|
||||||
|
|
||||||
// EXTERNAL FUNCTION PROTOTYPES --------------------------------------------
|
// EXTERNAL FUNCTION PROTOTYPES --------------------------------------------
|
||||||
|
|
||||||
|
|
|
@ -5,9 +5,9 @@
|
||||||
#include "zstring.h"
|
#include "zstring.h"
|
||||||
#include "tarray.h"
|
#include "tarray.h"
|
||||||
#include "name.h"
|
#include "name.h"
|
||||||
|
#include "files.h"
|
||||||
#include <zmusic.h>
|
#include <zmusic.h>
|
||||||
|
|
||||||
class FileReader;
|
|
||||||
class SoundStream;
|
class SoundStream;
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -40,8 +40,8 @@
|
||||||
#include "i_soundinternal.h"
|
#include "i_soundinternal.h"
|
||||||
#include "zstring.h"
|
#include "zstring.h"
|
||||||
#include <zmusic.h>
|
#include <zmusic.h>
|
||||||
|
#include "files.h"
|
||||||
|
|
||||||
class FileReader;
|
|
||||||
struct FSoundChan;
|
struct FSoundChan;
|
||||||
|
|
||||||
enum EStartSoundFlags
|
enum EStartSoundFlags
|
||||||
|
|
|
@ -177,81 +177,47 @@ UNSAFE_CCMD (crashout)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
// commented out because it's very poorly implemented (it should not abuse I_ChDir like this!)
|
|
||||||
#if 0
|
|
||||||
UNSAFE_CCMD (dir)
|
UNSAFE_CCMD (dir)
|
||||||
{
|
{
|
||||||
FString dir, path;
|
FString path;
|
||||||
const char *match;
|
|
||||||
findstate_t c_file;
|
|
||||||
void *file;
|
|
||||||
|
|
||||||
FString curdir = I_GetCWD();
|
|
||||||
if (curdir.IsEmpty())
|
|
||||||
{
|
|
||||||
Printf ("Current path too long\n");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (argv.argc() > 1)
|
if (argv.argc() > 1)
|
||||||
{
|
{
|
||||||
path = NicePath(argv[1]);
|
path = NicePath(argv[1]);
|
||||||
if (!I_ChDir(path))
|
|
||||||
{
|
|
||||||
match = path;
|
|
||||||
dir = ExtractFilePath(path);
|
|
||||||
if (dir[0] != '\0')
|
|
||||||
{
|
|
||||||
match += dir.Len();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
dir = "./";
|
|
||||||
}
|
|
||||||
if (match[0] == '\0')
|
|
||||||
{
|
|
||||||
match = "*";
|
|
||||||
}
|
|
||||||
if (!I_ChDir(dir))
|
|
||||||
{
|
|
||||||
Printf ("%s not found\n", dir.GetChars());
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
match = "*";
|
|
||||||
dir = path;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
match = "*";
|
path = I_GetCWD();;
|
||||||
dir = curdir;
|
|
||||||
}
|
}
|
||||||
if (dir[dir.Len()-1] != '/')
|
auto base = ExtractFileBase(path, true);
|
||||||
|
FString bpath;
|
||||||
|
if (base.IndexOfAny("*?") >= 0)
|
||||||
{
|
{
|
||||||
dir += '/';
|
bpath = ExtractFilePath(path);
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( (file = I_FindFirst (match, &c_file)) == ((void *)(-1)))
|
|
||||||
Printf ("Nothing matching %s%s\n", dir.GetChars(), match);
|
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
Printf ("Listing of %s%s:\n", dir.GetChars(), match);
|
base = "*";
|
||||||
do
|
bpath = path;
|
||||||
{
|
|
||||||
if (I_FindAttr (&c_file) & FA_DIREC)
|
|
||||||
Printf (PRINT_BOLD, "%s <dir>\n", I_FindName (&c_file));
|
|
||||||
else
|
|
||||||
Printf ("%s\n", I_FindName (&c_file));
|
|
||||||
} while (I_FindNext (file, &c_file) == 0);
|
|
||||||
I_FindClose (file);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
I_ChDir(curdir);
|
FileSys::FileList list;
|
||||||
|
if (!FileSys::ScanDirectory(list, bpath, base, true))
|
||||||
|
{
|
||||||
|
Printf ("Nothing matching %s\n", path.GetChars());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Printf ("Listing of %s:\n", path.GetChars());
|
||||||
|
for(auto& entry : list)
|
||||||
|
{
|
||||||
|
if (entry.isDirectory)
|
||||||
|
Printf (PRINT_BOLD, "%s <dir>\n", entry.FileName.c_str());
|
||||||
|
else
|
||||||
|
Printf ("%s\n", entry.FileName.c_str());
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
|
|
6
source/common/engine/files.h
Normal file
6
source/common/engine/files.h
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
#pragma once
|
||||||
|
#include "fs_files.h"
|
||||||
|
|
||||||
|
using FileSys::FileReader;
|
||||||
|
using FileSys::FileWriter;
|
||||||
|
using FileSys::BufferWriter;
|
7
source/common/engine/filesystem.h
Normal file
7
source/common/engine/filesystem.h
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
#pragma once
|
||||||
|
#include "fs_filesystem.h"
|
||||||
|
|
||||||
|
using FileSys::FileSystem;
|
||||||
|
using FileSys::FResourceFile;
|
||||||
|
|
||||||
|
inline FileSys::FileSystem fileSystem;
|
|
@ -3,8 +3,7 @@
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include "memarena.h"
|
#include "memarena.h"
|
||||||
#include "palentry.h"
|
#include "palentry.h"
|
||||||
|
#include "files.h"
|
||||||
class FileReader;
|
|
||||||
|
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
|
|
|
@ -57,6 +57,8 @@
|
||||||
#include "base64.h"
|
#include "base64.h"
|
||||||
#include "vm.h"
|
#include "vm.h"
|
||||||
|
|
||||||
|
using namespace FileSys;
|
||||||
|
|
||||||
extern DObject *WP_NOCHANGE;
|
extern DObject *WP_NOCHANGE;
|
||||||
bool save_full = false; // for testing. Should be removed afterward.
|
bool save_full = false; // for testing. Should be removed afterward.
|
||||||
|
|
||||||
|
|
|
@ -4,7 +4,6 @@
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <type_traits>
|
#include <type_traits>
|
||||||
#include "tarray.h"
|
#include "tarray.h"
|
||||||
#include "file_zip.h"
|
|
||||||
#include "tflags.h"
|
#include "tflags.h"
|
||||||
#include "vectors.h"
|
#include "vectors.h"
|
||||||
#include "palentry.h"
|
#include "palentry.h"
|
||||||
|
@ -80,7 +79,7 @@ public:
|
||||||
void SetUniqueSoundNames() { soundNamesAreUnique = true; }
|
void SetUniqueSoundNames() { soundNamesAreUnique = true; }
|
||||||
bool OpenWriter(bool pretty = true);
|
bool OpenWriter(bool pretty = true);
|
||||||
bool OpenReader(const char *buffer, size_t length);
|
bool OpenReader(const char *buffer, size_t length);
|
||||||
bool OpenReader(FCompressedBuffer *input);
|
bool OpenReader(FileSys::FCompressedBuffer *input);
|
||||||
void Close();
|
void Close();
|
||||||
void ReadObjects(bool hubtravel);
|
void ReadObjects(bool hubtravel);
|
||||||
bool BeginObject(const char *name);
|
bool BeginObject(const char *name);
|
||||||
|
@ -91,7 +90,7 @@ public:
|
||||||
unsigned GetSize(const char *group);
|
unsigned GetSize(const char *group);
|
||||||
const char *GetKey();
|
const char *GetKey();
|
||||||
const char *GetOutput(unsigned *len = nullptr);
|
const char *GetOutput(unsigned *len = nullptr);
|
||||||
FCompressedBuffer GetCompressedOutput();
|
FileSys::FCompressedBuffer GetCompressedOutput();
|
||||||
// The sprite serializer is a special case because it is needed by the VM to handle its 'spriteid' type.
|
// The sprite serializer is a special case because it is needed by the VM to handle its 'spriteid' type.
|
||||||
virtual FSerializer &Sprite(const char *key, int32_t &spritenum, int32_t *def);
|
virtual FSerializer &Sprite(const char *key, int32_t &spritenum, int32_t *def);
|
||||||
// This is only needed by the type system.
|
// This is only needed by the type system.
|
||||||
|
|
|
@ -41,10 +41,13 @@
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdarg.h>
|
#include <stdarg.h>
|
||||||
#include <functional>
|
#include <functional>
|
||||||
|
#include <vector>
|
||||||
#include "fs_swap.h"
|
#include "fs_swap.h"
|
||||||
|
|
||||||
#include "tarray.h"
|
#include "tarray.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
class FileSystemException : public std::exception
|
class FileSystemException : public std::exception
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
|
@ -99,31 +102,6 @@ public:
|
||||||
long GetLength () const { return Length; }
|
long GetLength () const { return Length; }
|
||||||
};
|
};
|
||||||
|
|
||||||
class MemoryReader : public FileReaderInterface
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
const char * bufptr = nullptr;
|
|
||||||
long FilePos = 0;
|
|
||||||
|
|
||||||
MemoryReader()
|
|
||||||
{}
|
|
||||||
|
|
||||||
public:
|
|
||||||
MemoryReader(const char *buffer, long length)
|
|
||||||
{
|
|
||||||
bufptr = buffer;
|
|
||||||
Length = length;
|
|
||||||
FilePos = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
long Tell() const override;
|
|
||||||
long Seek(long offset, int origin) override;
|
|
||||||
long Read(void *buffer, long len) override;
|
|
||||||
char *Gets(char *strbuf, int len) override;
|
|
||||||
virtual const char *GetBuffer() const override { return bufptr; }
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
struct FResourceLump;
|
struct FResourceLump;
|
||||||
|
|
||||||
class FileReader
|
class FileReader
|
||||||
|
@ -217,8 +195,11 @@ public:
|
||||||
std::vector<uint8_t> Read(size_t len)
|
std::vector<uint8_t> Read(size_t len)
|
||||||
{
|
{
|
||||||
std::vector<uint8_t> buffer(len);
|
std::vector<uint8_t> buffer(len);
|
||||||
Size length = mReader->Read(&buffer[0], (long)len);
|
if (len > 0)
|
||||||
buffer.resize((size_t)length);
|
{
|
||||||
|
Size length = mReader->Read(&buffer[0], (long)len);
|
||||||
|
buffer.resize((size_t)length);
|
||||||
|
}
|
||||||
return buffer;
|
return buffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -231,9 +212,13 @@ public:
|
||||||
{
|
{
|
||||||
auto len = GetLength();
|
auto len = GetLength();
|
||||||
std::vector<uint8_t> buffer(len + padding);
|
std::vector<uint8_t> buffer(len + padding);
|
||||||
Size length = mReader->Read(&buffer[0], (long)len);
|
if (len > 0)
|
||||||
if (length < len) buffer.clear();
|
{
|
||||||
else memset(buffer.data() + len, 0, padding);
|
Size length = mReader->Read(&buffer[0], (long)len);
|
||||||
|
if (length < len) buffer.clear();
|
||||||
|
else memset(buffer.data() + len, 0, padding);
|
||||||
|
}
|
||||||
|
else buffer[0] = 0;
|
||||||
return buffer;
|
return buffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -271,7 +256,7 @@ public:
|
||||||
{
|
{
|
||||||
uint16_t v = 0;
|
uint16_t v = 0;
|
||||||
Read(&v, 2);
|
Read(&v, 2);
|
||||||
return fs_private::LittleShort(v);
|
return byteswap::LittleShort(v);
|
||||||
}
|
}
|
||||||
|
|
||||||
int16_t ReadInt16()
|
int16_t ReadInt16()
|
||||||
|
@ -283,7 +268,7 @@ public:
|
||||||
{
|
{
|
||||||
uint16_t v = 0;
|
uint16_t v = 0;
|
||||||
Read(&v, 2);
|
Read(&v, 2);
|
||||||
return fs_private::BigShort(v);
|
return byteswap::BigShort(v);
|
||||||
}
|
}
|
||||||
|
|
||||||
int16_t ReadInt16BE()
|
int16_t ReadInt16BE()
|
||||||
|
@ -295,7 +280,7 @@ public:
|
||||||
{
|
{
|
||||||
uint32_t v = 0;
|
uint32_t v = 0;
|
||||||
Read(&v, 4);
|
Read(&v, 4);
|
||||||
return fs_private::LittleLong(v);
|
return byteswap::LittleLong(v);
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t ReadInt32()
|
int32_t ReadInt32()
|
||||||
|
@ -307,7 +292,7 @@ public:
|
||||||
{
|
{
|
||||||
uint32_t v = 0;
|
uint32_t v = 0;
|
||||||
Read(&v, 4);
|
Read(&v, 4);
|
||||||
return fs_private::BigLong(v);
|
return byteswap::BigLong(v);
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t ReadInt32BE()
|
int32_t ReadInt32BE()
|
||||||
|
@ -327,24 +312,6 @@ public:
|
||||||
friend class FileSystem;
|
friend class FileSystem;
|
||||||
};
|
};
|
||||||
|
|
||||||
class DecompressorBase : public FileReaderInterface
|
|
||||||
{
|
|
||||||
bool exceptions = false;
|
|
||||||
public:
|
|
||||||
// These do not work but need to be defined to satisfy the FileReaderInterface.
|
|
||||||
// They will just error out when called.
|
|
||||||
long Tell() const override;
|
|
||||||
long Seek(long offset, int origin) override;
|
|
||||||
char* Gets(char* strbuf, int len) override;
|
|
||||||
void DecompressionError(const char* error, ...) const;
|
|
||||||
void SetOwnsReader();
|
|
||||||
void EnableExceptions(bool on) { exceptions = on; }
|
|
||||||
|
|
||||||
protected:
|
|
||||||
FileReader* File = nullptr;
|
|
||||||
FileReader OwnedFile;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
class FileWriter
|
class FileWriter
|
||||||
{
|
{
|
||||||
|
@ -394,5 +361,6 @@ public:
|
||||||
TArray<unsigned char>&& TakeBuffer() { return std::move(mBuffer); }
|
TArray<unsigned char>&& TakeBuffer() { return std::move(mBuffer); }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
|
@ -8,12 +8,11 @@
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#include "files.h"
|
#include "fs_files.h"
|
||||||
#include "resourcefile.h"
|
#include "resourcefile.h"
|
||||||
|
|
||||||
class FResourceFile;
|
namespace FileSys {
|
||||||
struct FResourceLump;
|
|
||||||
|
|
||||||
union LumpShortName
|
union LumpShortName
|
||||||
{
|
{
|
||||||
char String[9];
|
char String[9];
|
||||||
|
@ -91,31 +90,31 @@ public:
|
||||||
int GetLastEntry(int wadnum) const noexcept;
|
int GetLastEntry(int wadnum) const noexcept;
|
||||||
int GetEntryCount(int wadnum) const noexcept;
|
int GetEntryCount(int wadnum) const noexcept;
|
||||||
|
|
||||||
int CheckNumForName (const char *name, int namespc);
|
int CheckNumForName (const char *name, int namespc) const;
|
||||||
int CheckNumForName (const char *name, int namespc, int wadfile, bool exact = true);
|
int CheckNumForName (const char *name, int namespc, int wadfile, bool exact = true) const;
|
||||||
int GetNumForName (const char *name, int namespc);
|
int GetNumForName (const char *name, int namespc) const;
|
||||||
|
|
||||||
inline int CheckNumForName (const uint8_t *name) { return CheckNumForName ((const char *)name, ns_global); }
|
inline int CheckNumForName (const uint8_t *name) const { return CheckNumForName ((const char *)name, ns_global); }
|
||||||
inline int CheckNumForName (const char *name) { return CheckNumForName (name, ns_global); }
|
inline int CheckNumForName (const char *name) const { return CheckNumForName (name, ns_global); }
|
||||||
inline int CheckNumForName (const uint8_t *name, int ns) { return CheckNumForName ((const char *)name, ns); }
|
inline int CheckNumForName (const uint8_t *name, int ns) const { return CheckNumForName ((const char *)name, ns); }
|
||||||
inline int GetNumForName (const char *name) { return GetNumForName (name, ns_global); }
|
inline int GetNumForName (const char *name) const { return GetNumForName (name, ns_global); }
|
||||||
inline int GetNumForName (const uint8_t *name) { return GetNumForName ((const char *)name); }
|
inline int GetNumForName (const uint8_t *name) const { return GetNumForName ((const char *)name); }
|
||||||
inline int GetNumForName (const uint8_t *name, int ns) { return GetNumForName ((const char *)name, ns); }
|
inline int GetNumForName (const uint8_t *name, int ns) const { return GetNumForName ((const char *)name, ns); }
|
||||||
|
|
||||||
int CheckNumForFullName (const char *name, bool trynormal = false, int namespc = ns_global, bool ignoreext = false);
|
int CheckNumForFullName (const char *cname, bool trynormal = false, int namespc = ns_global, bool ignoreext = false) const;
|
||||||
int CheckNumForFullName (const char *name, int wadfile);
|
int CheckNumForFullName (const char *name, int wadfile) const;
|
||||||
int GetNumForFullName (const char *name);
|
int GetNumForFullName (const char *name) const;
|
||||||
int FindFile(const char* name)
|
int FindFile(const char* name) const
|
||||||
{
|
{
|
||||||
return CheckNumForFullName(name);
|
return CheckNumForFullName(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FileExists(const char* name)
|
bool FileExists(const char* name) const
|
||||||
{
|
{
|
||||||
return FindFile(name) >= 0;
|
return FindFile(name) >= 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FileExists(const std::string& name)
|
bool FileExists(const std::string& name) const
|
||||||
{
|
{
|
||||||
return FindFile(name.c_str()) >= 0;
|
return FindFile(name.c_str()) >= 0;
|
||||||
}
|
}
|
||||||
|
@ -139,10 +138,13 @@ public:
|
||||||
int FindLumpFullName(const char* name, int* lastlump, bool noext = false);
|
int FindLumpFullName(const char* name, int* lastlump, bool noext = false);
|
||||||
bool CheckFileName (int lump, const char *name); // [RH] True if lump's name == name
|
bool CheckFileName (int lump, const char *name); // [RH] True if lump's name == name
|
||||||
|
|
||||||
int FindFileWithExtensions(const char* name, const char* const* exts, int count);
|
int FindFileWithExtensions(const char* name, const char* const* exts, int count) const;
|
||||||
int FindResource(int resid, const char* type, int filenum = -1) const noexcept;
|
int FindResource(int resid, const char* type, int filenum = -1) const noexcept;
|
||||||
int GetResource(int resid, const char* type, int filenum = -1) const;
|
int GetResource(int resid, const char* type, int filenum = -1) const;
|
||||||
|
|
||||||
|
|
||||||
|
static uint32_t LumpNameHash (const char *name); // [RH] Create hash key from an 8-char name
|
||||||
|
|
||||||
int FileLength (int lump) const;
|
int FileLength (int lump) const;
|
||||||
int GetFileOffset (int lump); // [RH] Returns offset of lump in the wadfile
|
int GetFileOffset (int lump); // [RH] Returns offset of lump in the wadfile
|
||||||
int GetFileFlags (int lump); // Return the flags for this lump
|
int GetFileFlags (int lump); // Return the flags for this lump
|
||||||
|
@ -200,11 +202,12 @@ protected:
|
||||||
int IwadIndex = -1;
|
int IwadIndex = -1;
|
||||||
int MaxIwadIndex = -1;
|
int MaxIwadIndex = -1;
|
||||||
|
|
||||||
|
StringPool* stringpool;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void DeleteAll();
|
void DeleteAll();
|
||||||
void MoveLumpsInFolder(const char *);
|
void MoveLumpsInFolder(const char *);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
extern FileSystem fileSystem;
|
}
|
||||||
|
|
|
@ -5,6 +5,8 @@
|
||||||
#include <vector>
|
#include <vector>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
struct FileListEntry
|
struct FileListEntry
|
||||||
{
|
{
|
||||||
std::string FileName; // file name only
|
std::string FileName; // file name only
|
||||||
|
@ -34,3 +36,4 @@ inline void FixPathSeparator(char* path)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -17,9 +17,9 @@
|
||||||
#include <libkern/OSByteOrder.h>
|
#include <libkern/OSByteOrder.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
namespace fs_private
|
namespace FileSys {
|
||||||
{
|
namespace byteswap {
|
||||||
|
|
||||||
#ifdef __APPLE__
|
#ifdef __APPLE__
|
||||||
|
|
||||||
inline unsigned short LittleShort(unsigned short x)
|
inline unsigned short LittleShort(unsigned short x)
|
||||||
|
@ -117,5 +117,6 @@ inline unsigned int BigLong (unsigned int x)
|
||||||
|
|
||||||
#endif // __BIG_ENDIAN__
|
#endif // __BIG_ENDIAN__
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#endif // __M_SWAP_H__
|
#endif // __M_SWAP_H__
|
|
@ -6,8 +6,11 @@
|
||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
#include <string>
|
#include <string>
|
||||||
#include "files.h"
|
#include "fs_files.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
|
class StringPool;
|
||||||
std::string ExtractBaseName(const char* path, bool include_extension = false);
|
std::string ExtractBaseName(const char* path, bool include_extension = false);
|
||||||
void strReplace(std::string& str, const char* from, const char* to);
|
void strReplace(std::string& str, const char* from, const char* to);
|
||||||
|
|
||||||
|
@ -113,7 +116,7 @@ struct FResourceLump
|
||||||
int LumpSize;
|
int LumpSize;
|
||||||
int RefCount;
|
int RefCount;
|
||||||
protected:
|
protected:
|
||||||
std::string FullName;
|
const char* FullName;
|
||||||
public:
|
public:
|
||||||
uint8_t Flags;
|
uint8_t Flags;
|
||||||
char * Cache;
|
char * Cache;
|
||||||
|
@ -125,6 +128,7 @@ public:
|
||||||
Owner = NULL;
|
Owner = NULL;
|
||||||
Flags = 0;
|
Flags = 0;
|
||||||
RefCount = 0;
|
RefCount = 0;
|
||||||
|
FullName = "";
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual ~FResourceLump();
|
virtual ~FResourceLump();
|
||||||
|
@ -133,7 +137,7 @@ public:
|
||||||
virtual int GetFileOffset() { return -1; }
|
virtual int GetFileOffset() { return -1; }
|
||||||
virtual int GetIndexNum() const { return -1; }
|
virtual int GetIndexNum() const { return -1; }
|
||||||
virtual int GetNamespace() const { return 0; }
|
virtual int GetNamespace() const { return 0; }
|
||||||
void LumpNameSetup(const char* iname);
|
void LumpNameSetup(const char* iname, StringPool* allocator);
|
||||||
void CheckEmbedded(LumpFilterInfo* lfi);
|
void CheckEmbedded(LumpFilterInfo* lfi);
|
||||||
virtual FCompressedBuffer GetRawData();
|
virtual FCompressedBuffer GetRawData();
|
||||||
|
|
||||||
|
@ -142,7 +146,8 @@ public:
|
||||||
|
|
||||||
unsigned Size() const{ return LumpSize; }
|
unsigned Size() const{ return LumpSize; }
|
||||||
int LockCount() const { return RefCount; }
|
int LockCount() const { return RefCount; }
|
||||||
const char* getName() { return FullName.c_str(); }
|
const char* getName() { return FullName; }
|
||||||
|
void clearName() { FullName = ""; }
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
virtual int FillCache() { return -1; }
|
virtual int FillCache() { return -1; }
|
||||||
|
@ -153,13 +158,14 @@ class FResourceFile
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FileReader Reader;
|
FileReader Reader;
|
||||||
std::string FileName;
|
const char* FileName;
|
||||||
protected:
|
protected:
|
||||||
uint32_t NumLumps;
|
uint32_t NumLumps;
|
||||||
char Hash[48];
|
char Hash[48];
|
||||||
|
StringPool* stringpool;
|
||||||
|
|
||||||
FResourceFile(const char *filename);
|
FResourceFile(const char *filename, StringPool* sp);
|
||||||
FResourceFile(const char *filename, FileReader &r);
|
FResourceFile(const char *filename, FileReader &r, StringPool* sp);
|
||||||
|
|
||||||
// for archives that can contain directories
|
// for archives that can contain directories
|
||||||
void GenerateHash();
|
void GenerateHash();
|
||||||
|
@ -172,12 +178,12 @@ private:
|
||||||
int FilterLumpsByGameType(LumpFilterInfo *filter, void *lumps, size_t lumpsize, uint32_t max);
|
int FilterLumpsByGameType(LumpFilterInfo *filter, void *lumps, size_t lumpsize, uint32_t max);
|
||||||
bool FindPrefixRange(const char* filter, void *lumps, size_t lumpsize, uint32_t max, uint32_t &start, uint32_t &end);
|
bool FindPrefixRange(const char* filter, void *lumps, size_t lumpsize, uint32_t max, uint32_t &start, uint32_t &end);
|
||||||
void JunkLeftoverFilters(void *lumps, size_t lumpsize, uint32_t max);
|
void JunkLeftoverFilters(void *lumps, size_t lumpsize, uint32_t max);
|
||||||
static FResourceFile *DoOpenResourceFile(const char *filename, FileReader &file, bool containeronly, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
static FResourceFile *DoOpenResourceFile(const char *filename, FileReader &file, bool containeronly, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
static FResourceFile *OpenResourceFile(const char *filename, FileReader &file, bool containeronly = false, LumpFilterInfo* filter = nullptr, FileSystemMessageFunc Printf = nullptr);
|
static FResourceFile *OpenResourceFile(const char *filename, FileReader &file, bool containeronly = false, LumpFilterInfo* filter = nullptr, FileSystemMessageFunc Printf = nullptr, StringPool* sp = nullptr);
|
||||||
static FResourceFile *OpenResourceFile(const char *filename, bool containeronly = false, LumpFilterInfo* filter = nullptr, FileSystemMessageFunc Printf = nullptr);
|
static FResourceFile *OpenResourceFile(const char *filename, bool containeronly = false, LumpFilterInfo* filter = nullptr, FileSystemMessageFunc Printf = nullptr, StringPool* sp = nullptr);
|
||||||
static FResourceFile *OpenDirectory(const char *filename, LumpFilterInfo* filter = nullptr, FileSystemMessageFunc Printf = nullptr);
|
static FResourceFile *OpenDirectory(const char *filename, LumpFilterInfo* filter = nullptr, FileSystemMessageFunc Printf = nullptr, StringPool* sp = nullptr);
|
||||||
virtual ~FResourceFile();
|
virtual ~FResourceFile();
|
||||||
// If this FResourceFile represents a directory, the Reader object is not usable so don't return it.
|
// If this FResourceFile represents a directory, the Reader object is not usable so don't return it.
|
||||||
FileReader *GetReader() { return Reader.isOpen()? &Reader : nullptr; }
|
FileReader *GetReader() { return Reader.isOpen()? &Reader : nullptr; }
|
||||||
|
@ -191,57 +197,7 @@ public:
|
||||||
FResourceLump *FindLump(const char *name);
|
FResourceLump *FindLump(const char *name);
|
||||||
};
|
};
|
||||||
|
|
||||||
struct FUncompressedLump : public FResourceLump
|
|
||||||
{
|
|
||||||
int Position;
|
|
||||||
|
|
||||||
virtual FileReader *GetReader();
|
|
||||||
virtual int FillCache() override;
|
|
||||||
virtual int GetFileOffset() { return Position; }
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
// Base class for uncompressed resource files (WAD, GRP, PAK and single lumps)
|
|
||||||
class FUncompressedFile : public FResourceFile
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
TArray<FUncompressedLump> Lumps;
|
|
||||||
|
|
||||||
FUncompressedFile(const char *filename);
|
|
||||||
FUncompressedFile(const char *filename, FileReader &r);
|
|
||||||
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
struct FExternalLump : public FResourceLump
|
|
||||||
{
|
|
||||||
std::string Filename;
|
|
||||||
|
|
||||||
FExternalLump(const char *_filename, int filesize = -1);
|
|
||||||
virtual int FillCache() override;
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
struct FMemoryLump : public FResourceLump
|
|
||||||
{
|
|
||||||
FMemoryLump(const void* data, int length)
|
|
||||||
{
|
|
||||||
RefCount = INT_MAX / 2;
|
|
||||||
LumpSize = length;
|
|
||||||
Cache = new char[length];
|
|
||||||
memcpy(Cache, data, length);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual int FillCache() override
|
|
||||||
{
|
|
||||||
RefCount = INT_MAX / 2; // Make sure it never counts down to 0 by resetting it to something high each time it is used.
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
|
@ -46,6 +46,8 @@
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include "ancientzip.h"
|
#include "ancientzip.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
/****************************************************************
|
/****************************************************************
|
||||||
Bit-I/O variables and routines/macros
|
Bit-I/O variables and routines/macros
|
||||||
|
|
||||||
|
@ -433,3 +435,5 @@ int ShrinkLoop(unsigned char *out, unsigned int outsize, FileReader &_In, unsign
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -1,6 +1,8 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
#include "files.h"
|
#include "fs_files.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
class FZipExploder
|
class FZipExploder
|
||||||
{
|
{
|
||||||
unsigned int Hold, Bits;
|
unsigned int Hold, Bits;
|
||||||
|
@ -41,4 +43,5 @@ public:
|
||||||
int Explode(unsigned char *out, unsigned int outsize, FileReader &in, unsigned int insize, int flags);
|
int Explode(unsigned char *out, unsigned int outsize, FileReader &in, unsigned int insize, int flags);
|
||||||
};
|
};
|
||||||
|
|
||||||
int ShrinkLoop(unsigned char *out, unsigned int outsize, FileReader &in, unsigned int insize);
|
int ShrinkLoop(unsigned char *out, unsigned int outsize, FileReader &in, unsigned int insize);
|
||||||
|
}
|
|
@ -40,7 +40,8 @@
|
||||||
#include "fs_findfile.h"
|
#include "fs_findfile.h"
|
||||||
|
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
//-----------------------------------------------------------------------
|
//-----------------------------------------------------------------------
|
||||||
//
|
//
|
||||||
// Interface classes to 7z library
|
// Interface classes to 7z library
|
||||||
|
@ -186,7 +187,7 @@ class F7ZFile : public FResourceFile
|
||||||
C7zArchive *Archive;
|
C7zArchive *Archive;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
F7ZFile(const char * filename, FileReader &filer);
|
F7ZFile(const char * filename, FileReader &filer, StringPool* sp);
|
||||||
bool Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
bool Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
||||||
virtual ~F7ZFile();
|
virtual ~F7ZFile();
|
||||||
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
||||||
|
@ -200,8 +201,8 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
F7ZFile::F7ZFile(const char * filename, FileReader &filer)
|
F7ZFile::F7ZFile(const char * filename, FileReader &filer, StringPool* sp)
|
||||||
: FResourceFile(filename, filer)
|
: FResourceFile(filename, filer, sp)
|
||||||
{
|
{
|
||||||
Lumps = NULL;
|
Lumps = NULL;
|
||||||
Archive = NULL;
|
Archive = NULL;
|
||||||
|
@ -227,7 +228,7 @@ bool F7ZFile::Open(LumpFilterInfo *filter, FileSystemMessageFunc Printf)
|
||||||
Archive = NULL;
|
Archive = NULL;
|
||||||
if (res == SZ_ERROR_UNSUPPORTED)
|
if (res == SZ_ERROR_UNSUPPORTED)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Error, "%s: Decoder does not support this archive\n", FileName.c_str());
|
Printf(FSMessageLevel::Error, "%s: Decoder does not support this archive\n", FileName);
|
||||||
}
|
}
|
||||||
else if (res == SZ_ERROR_MEM)
|
else if (res == SZ_ERROR_MEM)
|
||||||
{
|
{
|
||||||
|
@ -280,7 +281,7 @@ bool F7ZFile::Open(LumpFilterInfo *filter, FileSystemMessageFunc Printf)
|
||||||
}
|
}
|
||||||
FixPathSeparator(&nameASCII.front());
|
FixPathSeparator(&nameASCII.front());
|
||||||
|
|
||||||
lump_p->LumpNameSetup(nameASCII.c_str());
|
lump_p->LumpNameSetup(nameASCII.c_str(), stringpool);
|
||||||
lump_p->LumpSize = static_cast<int>(SzArEx_GetFileSize(archPtr, i));
|
lump_p->LumpSize = static_cast<int>(SzArEx_GetFileSize(archPtr, i));
|
||||||
lump_p->Owner = this;
|
lump_p->Owner = this;
|
||||||
lump_p->Flags = LUMPF_FULLPATH|LUMPF_COMPRESSED;
|
lump_p->Flags = LUMPF_FULLPATH|LUMPF_COMPRESSED;
|
||||||
|
@ -300,7 +301,7 @@ bool F7ZFile::Open(LumpFilterInfo *filter, FileSystemMessageFunc Printf)
|
||||||
|
|
||||||
if (SZ_OK != Archive->Extract(Lumps[0].Position, &temp[0]))
|
if (SZ_OK != Archive->Extract(Lumps[0].Position, &temp[0]))
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Error, "%s: unsupported 7z/LZMA file!\n", FileName.c_str());
|
Printf(FSMessageLevel::Error, "%s: unsupported 7z/LZMA file!\n", FileName);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -352,7 +353,7 @@ int F7ZLump::FillCache()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *Check7Z(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *Check7Z(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
char head[k7zSignatureSize];
|
char head[k7zSignatureSize];
|
||||||
|
|
||||||
|
@ -363,7 +364,7 @@ FResourceFile *Check7Z(const char *filename, FileReader &file, LumpFilterInfo* f
|
||||||
file.Seek(0, FileReader::SeekSet);
|
file.Seek(0, FileReader::SeekSet);
|
||||||
if (!memcmp(head, k7zSignature, k7zSignatureSize))
|
if (!memcmp(head, k7zSignature, k7zSignatureSize))
|
||||||
{
|
{
|
||||||
auto rf = new F7ZFile(filename, file);
|
auto rf = new F7ZFile(filename, file, sp);
|
||||||
if (rf->Open(filter, Printf)) return rf;
|
if (rf->Open(filter, Printf)) return rf;
|
||||||
|
|
||||||
file = std::move(rf->Reader); // to avoid destruction of reader
|
file = std::move(rf->Reader); // to avoid destruction of reader
|
||||||
|
@ -374,4 +375,4 @@ FResourceFile *Check7Z(const char *filename, FileReader &file, LumpFilterInfo* f
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
|
@ -38,7 +38,10 @@
|
||||||
|
|
||||||
#include "resourcefile.h"
|
#include "resourcefile.h"
|
||||||
#include "fs_findfile.h"
|
#include "fs_findfile.h"
|
||||||
|
#include "fs_stringpool.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
std::string FS_FullPath(const char* directory);
|
std::string FS_FullPath(const char* directory);
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
|
@ -75,7 +78,7 @@ class FDirectory : public FResourceFile
|
||||||
void AddEntry(const char *fullpath, int size);
|
void AddEntry(const char *fullpath, int size);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
FDirectory(const char * dirname, bool nosubdirflag = false);
|
FDirectory(const char * dirname, StringPool* sp, bool nosubdirflag = false);
|
||||||
bool Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
bool Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
||||||
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
||||||
};
|
};
|
||||||
|
@ -88,11 +91,12 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FDirectory::FDirectory(const char * directory, bool nosubdirflag)
|
FDirectory::FDirectory(const char * directory, StringPool* sp, bool nosubdirflag)
|
||||||
: FResourceFile(NULL), nosubdir(nosubdirflag)
|
: FResourceFile("", sp), nosubdir(nosubdirflag)
|
||||||
{
|
{
|
||||||
FileName = FS_FullPath(directory);
|
auto fn = FS_FullPath(directory);
|
||||||
if (FileName[FileName.length()-1] != '/') FileName += '/';
|
if (fn.back() != '/') fn += '/';
|
||||||
|
FileName = sp->Strdup(fn.c_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -129,6 +133,7 @@ int FDirectory::AddDirectory(const char *dirpath, LumpFilterInfo* filter, FileSy
|
||||||
if (entry.Length > 0x7fffffff)
|
if (entry.Length > 0x7fffffff)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Warning, "%s is larger than 2GB and will be ignored\n", entry.FilePath.c_str());
|
Printf(FSMessageLevel::Warning, "%s is larger than 2GB and will be ignored\n", entry.FilePath.c_str());
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
AddEntry(entry.FilePathRel.c_str(), (int)entry.Length);
|
AddEntry(entry.FilePathRel.c_str(), (int)entry.Length);
|
||||||
count++;
|
count++;
|
||||||
|
@ -147,7 +152,7 @@ int FDirectory::AddDirectory(const char *dirpath, LumpFilterInfo* filter, FileSy
|
||||||
|
|
||||||
bool FDirectory::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
bool FDirectory::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
{
|
{
|
||||||
NumLumps = AddDirectory(FileName.c_str(), filter, Printf);
|
NumLumps = AddDirectory(FileName, filter, Printf);
|
||||||
PostProcessArchive(&Lumps[0], sizeof(FDirectoryLump), filter);
|
PostProcessArchive(&Lumps[0], sizeof(FDirectoryLump), filter);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -166,11 +171,11 @@ void FDirectory::AddEntry(const char *fullpath, int size)
|
||||||
lump_p->mFullPath = fullpath;
|
lump_p->mFullPath = fullpath;
|
||||||
|
|
||||||
// [mxd] Convert name to lowercase
|
// [mxd] Convert name to lowercase
|
||||||
std::string name = fullpath + FileName;
|
std::string name = fullpath + strlen(FileName);
|
||||||
for (auto& c : name) c = tolower(c);
|
for (auto& c : name) c = tolower(c);
|
||||||
|
|
||||||
// The lump's name is only the part relative to the main directory
|
// The lump's name is only the part relative to the main directory
|
||||||
lump_p->LumpNameSetup(name.c_str());
|
lump_p->LumpNameSetup(name.c_str(), stringpool);
|
||||||
lump_p->LumpSize = size;
|
lump_p->LumpSize = size;
|
||||||
lump_p->Owner = this;
|
lump_p->Owner = this;
|
||||||
lump_p->Flags = 0;
|
lump_p->Flags = 0;
|
||||||
|
@ -220,11 +225,12 @@ int FDirectoryLump::FillCache()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *CheckDir(const char *filename, bool nosubdirflag, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *CheckDir(const char *filename, bool nosubdirflag, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
auto rf = new FDirectory(filename, nosubdirflag);
|
auto rf = new FDirectory(filename, sp, nosubdirflag);
|
||||||
if (rf->Open(filter, Printf)) return rf;
|
if (rf->Open(filter, Printf)) return rf;
|
||||||
delete rf;
|
delete rf;
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -33,10 +33,11 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "resourcefile.h"
|
#include "resourcefile_internal.h"
|
||||||
#include "fs_swap.h"
|
#include "fs_swap.h"
|
||||||
|
|
||||||
using namespace fs_private;
|
namespace FileSys {
|
||||||
|
using namespace byteswap;
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
|
@ -73,7 +74,7 @@ struct GrpLump
|
||||||
class FGrpFile : public FUncompressedFile
|
class FGrpFile : public FUncompressedFile
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FGrpFile(const char * filename, FileReader &file);
|
FGrpFile(const char * filename, FileReader &file, StringPool* sp);
|
||||||
bool Open(LumpFilterInfo* filter);
|
bool Open(LumpFilterInfo* filter);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -84,8 +85,8 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FGrpFile::FGrpFile(const char *filename, FileReader &file)
|
FGrpFile::FGrpFile(const char *filename, FileReader &file, StringPool* sp)
|
||||||
: FUncompressedFile(filename, file)
|
: FUncompressedFile(filename, file, sp)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -117,7 +118,7 @@ bool FGrpFile::Open(LumpFilterInfo* filter)
|
||||||
Position += fileinfo[i].Size;
|
Position += fileinfo[i].Size;
|
||||||
Lumps[i].Flags = 0;
|
Lumps[i].Flags = 0;
|
||||||
fileinfo[i].NameWithZero[12] = '\0'; // Be sure filename is null-terminated
|
fileinfo[i].NameWithZero[12] = '\0'; // Be sure filename is null-terminated
|
||||||
Lumps[i].LumpNameSetup(fileinfo[i].NameWithZero);
|
Lumps[i].LumpNameSetup(fileinfo[i].NameWithZero, stringpool);
|
||||||
}
|
}
|
||||||
GenerateHash();
|
GenerateHash();
|
||||||
delete[] fileinfo;
|
delete[] fileinfo;
|
||||||
|
@ -131,7 +132,7 @@ bool FGrpFile::Open(LumpFilterInfo* filter)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *CheckGRP(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *CheckGRP(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
char head[12];
|
char head[12];
|
||||||
|
|
||||||
|
@ -142,7 +143,7 @@ FResourceFile *CheckGRP(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
file.Seek(0, FileReader::SeekSet);
|
file.Seek(0, FileReader::SeekSet);
|
||||||
if (!memcmp(head, "KenSilverman", 12))
|
if (!memcmp(head, "KenSilverman", 12))
|
||||||
{
|
{
|
||||||
auto rf = new FGrpFile(filename, file);
|
auto rf = new FGrpFile(filename, file, sp);
|
||||||
if (rf->Open(filter)) return rf;
|
if (rf->Open(filter)) return rf;
|
||||||
|
|
||||||
file = std::move(rf->Reader); // to avoid destruction of reader
|
file = std::move(rf->Reader); // to avoid destruction of reader
|
||||||
|
@ -152,3 +153,4 @@ FResourceFile *CheckGRP(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -32,8 +32,9 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "resourcefile.h"
|
#include "resourcefile_internal.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
// Single lump
|
// Single lump
|
||||||
|
@ -43,7 +44,7 @@
|
||||||
class FLumpFile : public FUncompressedFile
|
class FLumpFile : public FUncompressedFile
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FLumpFile(const char * filename, FileReader &file);
|
FLumpFile(const char * filename, FileReader &file, StringPool* sp);
|
||||||
bool Open(LumpFilterInfo* filter);
|
bool Open(LumpFilterInfo* filter);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -54,8 +55,8 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FLumpFile::FLumpFile(const char *filename, FileReader &file)
|
FLumpFile::FLumpFile(const char *filename, FileReader &file, StringPool* sp)
|
||||||
: FUncompressedFile(filename, file)
|
: FUncompressedFile(filename, file, sp)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -68,7 +69,7 @@ FLumpFile::FLumpFile(const char *filename, FileReader &file)
|
||||||
bool FLumpFile::Open(LumpFilterInfo*)
|
bool FLumpFile::Open(LumpFilterInfo*)
|
||||||
{
|
{
|
||||||
Lumps.Resize(1);
|
Lumps.Resize(1);
|
||||||
Lumps[0].LumpNameSetup(ExtractBaseName(FileName.c_str(), true).c_str());
|
Lumps[0].LumpNameSetup(ExtractBaseName(FileName, true).c_str(), stringpool);
|
||||||
Lumps[0].Owner = this;
|
Lumps[0].Owner = this;
|
||||||
Lumps[0].Position = 0;
|
Lumps[0].Position = 0;
|
||||||
Lumps[0].LumpSize = (int)Reader.GetLength();
|
Lumps[0].LumpSize = (int)Reader.GetLength();
|
||||||
|
@ -83,13 +84,14 @@ bool FLumpFile::Open(LumpFilterInfo*)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *CheckLump(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *CheckLump(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
// always succeeds
|
// always succeeds
|
||||||
auto rf = new FLumpFile(filename, file);
|
auto rf = new FLumpFile(filename, file, sp);
|
||||||
if (rf->Open(filter)) return rf;
|
if (rf->Open(filter)) return rf;
|
||||||
file = std::move(rf->Reader); // to avoid destruction of reader
|
file = std::move(rf->Reader); // to avoid destruction of reader
|
||||||
delete rf;
|
delete rf;
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -32,10 +32,11 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "resourcefile.h"
|
#include "resourcefile_internal.h"
|
||||||
|
|
||||||
using namespace fs_private;
|
namespace FileSys {
|
||||||
|
|
||||||
|
using namespace byteswap;
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
//
|
//
|
||||||
|
@ -65,7 +66,7 @@ struct dpackheader_t
|
||||||
class FPakFile : public FUncompressedFile
|
class FPakFile : public FUncompressedFile
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FPakFile(const char * filename, FileReader &file);
|
FPakFile(const char * filename, FileReader &file, StringPool* sp);
|
||||||
bool Open(LumpFilterInfo* filter);
|
bool Open(LumpFilterInfo* filter);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -78,8 +79,8 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FPakFile::FPakFile(const char *filename, FileReader &file)
|
FPakFile::FPakFile(const char *filename, FileReader &file, StringPool* sp)
|
||||||
: FUncompressedFile(filename, file)
|
: FUncompressedFile(filename, file, sp)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -105,7 +106,7 @@ bool FPakFile::Open(LumpFilterInfo* filter)
|
||||||
|
|
||||||
for(uint32_t i = 0; i < NumLumps; i++)
|
for(uint32_t i = 0; i < NumLumps; i++)
|
||||||
{
|
{
|
||||||
Lumps[i].LumpNameSetup(fileinfo[i].name);
|
Lumps[i].LumpNameSetup(fileinfo[i].name, stringpool);
|
||||||
Lumps[i].Flags = LUMPF_FULLPATH;
|
Lumps[i].Flags = LUMPF_FULLPATH;
|
||||||
Lumps[i].Owner = this;
|
Lumps[i].Owner = this;
|
||||||
Lumps[i].Position = LittleLong(fileinfo[i].filepos);
|
Lumps[i].Position = LittleLong(fileinfo[i].filepos);
|
||||||
|
@ -124,7 +125,7 @@ bool FPakFile::Open(LumpFilterInfo* filter)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *CheckPak(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *CheckPak(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
char head[4];
|
char head[4];
|
||||||
|
|
||||||
|
@ -135,7 +136,7 @@ FResourceFile *CheckPak(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
file.Seek(0, FileReader::SeekSet);
|
file.Seek(0, FileReader::SeekSet);
|
||||||
if (!memcmp(head, "PACK", 4))
|
if (!memcmp(head, "PACK", 4))
|
||||||
{
|
{
|
||||||
auto rf = new FPakFile(filename, file);
|
auto rf = new FPakFile(filename, file, sp);
|
||||||
if (rf->Open(filter)) return rf;
|
if (rf->Open(filter)) return rf;
|
||||||
|
|
||||||
file = std::move(rf->Reader); // to avoid destruction of reader
|
file = std::move(rf->Reader); // to avoid destruction of reader
|
||||||
|
@ -145,3 +146,4 @@ FResourceFile *CheckPak(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -33,10 +33,11 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "resourcefile.h"
|
#include "resourcefile_internal.h"
|
||||||
#include "fs_swap.h"
|
#include "fs_swap.h"
|
||||||
|
|
||||||
using namespace fs_private;
|
namespace FileSys {
|
||||||
|
using namespace byteswap;
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
|
@ -110,7 +111,7 @@ class FRFFFile : public FResourceFile
|
||||||
FRFFLump *Lumps;
|
FRFFLump *Lumps;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
FRFFFile(const char * filename, FileReader &file);
|
FRFFFile(const char * filename, FileReader &file, StringPool* sp);
|
||||||
virtual ~FRFFFile();
|
virtual ~FRFFFile();
|
||||||
virtual bool Open(LumpFilterInfo* filter);
|
virtual bool Open(LumpFilterInfo* filter);
|
||||||
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
||||||
|
@ -123,8 +124,8 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FRFFFile::FRFFFile(const char *filename, FileReader &file)
|
FRFFFile::FRFFFile(const char *filename, FileReader &file, StringPool* sp)
|
||||||
: FResourceFile(filename, file)
|
: FResourceFile(filename, file, sp)
|
||||||
{
|
{
|
||||||
Lumps = NULL;
|
Lumps = NULL;
|
||||||
}
|
}
|
||||||
|
@ -172,7 +173,7 @@ bool FRFFFile::Open(LumpFilterInfo*)
|
||||||
name[len+2] = lumps[i].Extension[1];
|
name[len+2] = lumps[i].Extension[1];
|
||||||
name[len+3] = lumps[i].Extension[2];
|
name[len+3] = lumps[i].Extension[2];
|
||||||
name[len+4] = 0;
|
name[len+4] = 0;
|
||||||
Lumps[i].LumpNameSetup(name);
|
Lumps[i].LumpNameSetup(name, stringpool);
|
||||||
}
|
}
|
||||||
delete[] lumps;
|
delete[] lumps;
|
||||||
GenerateHash();
|
GenerateHash();
|
||||||
|
@ -238,7 +239,7 @@ int FRFFLump::FillCache()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *CheckRFF(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *CheckRFF(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
char head[4];
|
char head[4];
|
||||||
|
|
||||||
|
@ -249,7 +250,7 @@ FResourceFile *CheckRFF(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
file.Seek(0, FileReader::SeekSet);
|
file.Seek(0, FileReader::SeekSet);
|
||||||
if (!memcmp(head, "RFF\x1a", 4))
|
if (!memcmp(head, "RFF\x1a", 4))
|
||||||
{
|
{
|
||||||
auto rf = new FRFFFile(filename, file);
|
auto rf = new FRFFFile(filename, file, sp);
|
||||||
if (rf->Open(filter)) return rf;
|
if (rf->Open(filter)) return rf;
|
||||||
|
|
||||||
file = std::move(rf->Reader); // to avoid destruction of reader
|
file = std::move(rf->Reader); // to avoid destruction of reader
|
||||||
|
@ -260,4 +261,4 @@ FResourceFile *CheckRFF(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
|
@ -33,8 +33,9 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "resourcefile.h"
|
#include "resourcefile_internal.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
// Build GRP file
|
// Build GRP file
|
||||||
|
@ -44,7 +45,7 @@
|
||||||
class FSSIFile : public FUncompressedFile
|
class FSSIFile : public FUncompressedFile
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FSSIFile(const char * filename, FileReader &file);
|
FSSIFile(const char * filename, FileReader &file, StringPool* sp);
|
||||||
bool Open(int version, int lumpcount, LumpFilterInfo* filter);
|
bool Open(int version, int lumpcount, LumpFilterInfo* filter);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -55,8 +56,8 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FSSIFile::FSSIFile(const char *filename, FileReader &file)
|
FSSIFile::FSSIFile(const char *filename, FileReader &file, StringPool* sp)
|
||||||
: FUncompressedFile(filename, file)
|
: FUncompressedFile(filename, file, sp)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -85,7 +86,7 @@ bool FSSIFile::Open(int version, int lumpcount, LumpFilterInfo*)
|
||||||
int flength = Reader.ReadInt32();
|
int flength = Reader.ReadInt32();
|
||||||
|
|
||||||
|
|
||||||
Lumps[i].LumpNameSetup(fn);
|
Lumps[i].LumpNameSetup(fn, stringpool);
|
||||||
Lumps[i].Position = j;
|
Lumps[i].Position = j;
|
||||||
Lumps[i].LumpSize = flength;
|
Lumps[i].LumpSize = flength;
|
||||||
Lumps[i].Owner = this;
|
Lumps[i].Owner = this;
|
||||||
|
@ -94,7 +95,7 @@ bool FSSIFile::Open(int version, int lumpcount, LumpFilterInfo*)
|
||||||
// SSI files can swap the order of the extension's characters - but there's no reliable detection for this and it can be mixed inside the same container,
|
// SSI files can swap the order of the extension's characters - but there's no reliable detection for this and it can be mixed inside the same container,
|
||||||
// so we have no choice but to create another file record for the altered name.
|
// so we have no choice but to create another file record for the altered name.
|
||||||
std::swap(fn[strlength - 1], fn[strlength - 3]);
|
std::swap(fn[strlength - 1], fn[strlength - 3]);
|
||||||
Lumps[i+1].LumpNameSetup(fn);
|
Lumps[i+1].LumpNameSetup(fn, stringpool);
|
||||||
Lumps[i+1].Position = j;
|
Lumps[i+1].Position = j;
|
||||||
Lumps[i+1].LumpSize = flength;
|
Lumps[i+1].LumpSize = flength;
|
||||||
Lumps[i+1].Owner = this;
|
Lumps[i+1].Owner = this;
|
||||||
|
@ -114,7 +115,7 @@ bool FSSIFile::Open(int version, int lumpcount, LumpFilterInfo*)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile* CheckSSI(const char* filename, FileReader& file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile* CheckSSI(const char* filename, FileReader& file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
char zerobuf[72];
|
char zerobuf[72];
|
||||||
char buf[72];
|
char buf[72];
|
||||||
|
@ -144,7 +145,7 @@ FResourceFile* CheckSSI(const char* filename, FileReader& file, LumpFilterInfo*
|
||||||
{
|
{
|
||||||
if (!skipstring(70)) return nullptr;
|
if (!skipstring(70)) return nullptr;
|
||||||
}
|
}
|
||||||
auto ssi = new FSSIFile(filename, file);
|
auto ssi = new FSSIFile(filename, file, sp);
|
||||||
if (ssi->Open(version, numfiles, filter)) return ssi;
|
if (ssi->Open(version, numfiles, filter)) return ssi;
|
||||||
file = std::move(ssi->Reader); // to avoid destruction of reader
|
file = std::move(ssi->Reader); // to avoid destruction of reader
|
||||||
delete ssi;
|
delete ssi;
|
||||||
|
@ -152,3 +153,5 @@ FResourceFile* CheckSSI(const char* filename, FileReader& file, LumpFilterInfo*
|
||||||
}
|
}
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -35,11 +35,11 @@
|
||||||
|
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include "resourcefile.h"
|
#include "resourcefile.h"
|
||||||
#include "filesystem.h"
|
#include "fs_filesystem.h"
|
||||||
#include "fs_swap.h"
|
#include "fs_swap.h"
|
||||||
|
|
||||||
using namespace fs_private;
|
namespace FileSys {
|
||||||
|
using namespace byteswap;
|
||||||
|
|
||||||
struct wadinfo_t
|
struct wadinfo_t
|
||||||
{
|
{
|
||||||
|
@ -136,7 +136,7 @@ class FWadFile : public FResourceFile
|
||||||
void SkinHack (FileSystemMessageFunc Printf);
|
void SkinHack (FileSystemMessageFunc Printf);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
FWadFile(const char * filename, FileReader &file);
|
FWadFile(const char * filename, FileReader &file, StringPool* sp);
|
||||||
FResourceLump *GetLump(int lump) { return &Lumps[lump]; }
|
FResourceLump *GetLump(int lump) { return &Lumps[lump]; }
|
||||||
bool Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
bool Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
||||||
};
|
};
|
||||||
|
@ -150,8 +150,8 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FWadFile::FWadFile(const char *filename, FileReader &file)
|
FWadFile::FWadFile(const char *filename, FileReader &file, StringPool* sp)
|
||||||
: FResourceFile(filename, file)
|
: FResourceFile(filename, file, sp)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -183,7 +183,7 @@ bool FWadFile::Open(LumpFilterInfo*, FileSystemMessageFunc Printf)
|
||||||
// Check again to detect broken wads
|
// Check again to detect broken wads
|
||||||
if (InfoTableOfs + NumLumps*sizeof(wadlump_t) > (unsigned)wadSize)
|
if (InfoTableOfs + NumLumps*sizeof(wadlump_t) > (unsigned)wadSize)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Error, "%s: Bad directory offset.\n", FileName.c_str());
|
Printf(FSMessageLevel::Error, "%s: Bad directory offset.\n", FileName);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -207,7 +207,7 @@ bool FWadFile::Open(LumpFilterInfo*, FileSystemMessageFunc Printf)
|
||||||
#else
|
#else
|
||||||
Lumps[i].Compressed = false;
|
Lumps[i].Compressed = false;
|
||||||
#endif
|
#endif
|
||||||
Lumps[i].LumpNameSetup(n);
|
Lumps[i].LumpNameSetup(n, stringpool);
|
||||||
|
|
||||||
Lumps[i].Owner = this;
|
Lumps[i].Owner = this;
|
||||||
Lumps[i].Position = isBigEndian ? BigLong(fileinfo[i].FilePos) : LittleLong(fileinfo[i].FilePos);
|
Lumps[i].Position = isBigEndian ? BigLong(fileinfo[i].FilePos) : LittleLong(fileinfo[i].FilePos);
|
||||||
|
@ -220,8 +220,8 @@ bool FWadFile::Open(LumpFilterInfo*, FileSystemMessageFunc Printf)
|
||||||
{
|
{
|
||||||
if (Lumps[i].LumpSize != 0)
|
if (Lumps[i].LumpSize != 0)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Warning, "%s: Lump %s contains invalid positioning info and will be ignored\n", FileName.c_str(), Lumps[i].getName());
|
Printf(FSMessageLevel::Warning, "%s: Lump %s contains invalid positioning info and will be ignored\n", FileName, Lumps[i].getName());
|
||||||
Lumps[i].LumpNameSetup("");
|
Lumps[i].clearName();
|
||||||
}
|
}
|
||||||
Lumps[i].LumpSize = Lumps[i].Position = 0;
|
Lumps[i].LumpSize = Lumps[i].Position = 0;
|
||||||
}
|
}
|
||||||
|
@ -305,7 +305,7 @@ void FWadFile::SetNamespace(const char *startmarker, const char *endmarker, name
|
||||||
{
|
{
|
||||||
if (numendmarkers == 0) return; // no markers found
|
if (numendmarkers == 0) return; // no markers found
|
||||||
|
|
||||||
Printf(FSMessageLevel::Warning, "%s: %s marker without corresponding %s found.\n", FileName.c_str(), endmarker, startmarker);
|
Printf(FSMessageLevel::Warning, "%s: %s marker without corresponding %s found.\n", FileName, endmarker, startmarker);
|
||||||
|
|
||||||
|
|
||||||
if (flathack)
|
if (flathack)
|
||||||
|
@ -319,7 +319,7 @@ void FWadFile::SetNamespace(const char *startmarker, const char *endmarker, name
|
||||||
{
|
{
|
||||||
// We can't add this to the flats namespace but
|
// We can't add this to the flats namespace but
|
||||||
// it needs to be flagged for the texture manager.
|
// it needs to be flagged for the texture manager.
|
||||||
Printf(FSMessageLevel::DebugNotify, "%s: Marking %s as potential flat\n", FileName.c_str(), Lumps[ii].getName());
|
Printf(FSMessageLevel::DebugNotify, "%s: Marking %s as potential flat\n", FileName, Lumps[ii].getName());
|
||||||
Lumps[ii].Flags |= LUMPF_MAYBEFLAT;
|
Lumps[ii].Flags |= LUMPF_MAYBEFLAT;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -333,7 +333,7 @@ void FWadFile::SetNamespace(const char *startmarker, const char *endmarker, name
|
||||||
int start, end;
|
int start, end;
|
||||||
if (markers[i].markertype != 0)
|
if (markers[i].markertype != 0)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Warning, "%s: %s marker without corresponding %s found.\n", FileName.c_str(), endmarker, startmarker);
|
Printf(FSMessageLevel::Warning, "%s: %s marker without corresponding %s found.\n", FileName, endmarker, startmarker);
|
||||||
i++;
|
i++;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -342,21 +342,21 @@ void FWadFile::SetNamespace(const char *startmarker, const char *endmarker, name
|
||||||
// skip over subsequent x_START markers
|
// skip over subsequent x_START markers
|
||||||
while (i < markers.Size() && markers[i].markertype == 0)
|
while (i < markers.Size() && markers[i].markertype == 0)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Warning, "%s: duplicate %s marker found.\n", FileName.c_str(), startmarker);
|
Printf(FSMessageLevel::Warning, "%s: duplicate %s marker found.\n", FileName, startmarker);
|
||||||
i++;
|
i++;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
// same for x_END markers
|
// same for x_END markers
|
||||||
while (i < markers.Size()-1 && (markers[i].markertype == 1 && markers[i+1].markertype == 1))
|
while (i < markers.Size()-1 && (markers[i].markertype == 1 && markers[i+1].markertype == 1))
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Warning, "%s: duplicate %s marker found.\n", FileName.c_str(), endmarker);
|
Printf(FSMessageLevel::Warning, "%s: duplicate %s marker found.\n", FileName, endmarker);
|
||||||
i++;
|
i++;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
// We found a starting marker but no end marker. Ignore this block.
|
// We found a starting marker but no end marker. Ignore this block.
|
||||||
if (i >= markers.Size())
|
if (i >= markers.Size())
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Warning, "%s: %s marker without corresponding %s found.\n", FileName.c_str(), startmarker, endmarker);
|
Printf(FSMessageLevel::Warning, "%s: %s marker without corresponding %s found.\n", FileName, startmarker, endmarker);
|
||||||
end = NumLumps;
|
end = NumLumps;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -365,14 +365,14 @@ void FWadFile::SetNamespace(const char *startmarker, const char *endmarker, name
|
||||||
}
|
}
|
||||||
|
|
||||||
// we found a marked block
|
// we found a marked block
|
||||||
Printf(FSMessageLevel::DebugNotify, "%s: Found %s block at (%d-%d)\n", FileName.c_str(), startmarker, markers[start].index, end);
|
Printf(FSMessageLevel::DebugNotify, "%s: Found %s block at (%d-%d)\n", FileName, startmarker, markers[start].index, end);
|
||||||
for(int j = markers[start].index + 1; j < end; j++)
|
for(int j = markers[start].index + 1; j < end; j++)
|
||||||
{
|
{
|
||||||
if (Lumps[j].Namespace != ns_global)
|
if (Lumps[j].Namespace != ns_global)
|
||||||
{
|
{
|
||||||
if (!warned)
|
if (!warned)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Warning, "%s: Overlapping namespaces found (lump %d)\n", FileName.c_str(), j);
|
Printf(FSMessageLevel::Warning, "%s: Overlapping namespaces found (lump %d)\n", FileName, j);
|
||||||
}
|
}
|
||||||
warned = true;
|
warned = true;
|
||||||
}
|
}
|
||||||
|
@ -382,7 +382,7 @@ void FWadFile::SetNamespace(const char *startmarker, const char *endmarker, name
|
||||||
// ignore sprite lumps smaller than 8 bytes (the smallest possible)
|
// ignore sprite lumps smaller than 8 bytes (the smallest possible)
|
||||||
// in size -- this was used by some dmadds wads
|
// in size -- this was used by some dmadds wads
|
||||||
// as an 'empty' graphics resource
|
// as an 'empty' graphics resource
|
||||||
Printf(FSMessageLevel::DebugWarn, "%s: Skipped empty sprite %s (lump %d)\n", FileName.c_str(), Lumps[j].getName(), j);
|
Printf(FSMessageLevel::DebugWarn, "%s: Skipped empty sprite %s (lump %d)\n", FileName, Lumps[j].getName(), j);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -420,7 +420,7 @@ void FWadFile::SkinHack (FileSystemMessageFunc Printf)
|
||||||
|
|
||||||
if (!strnicmp(lump->getName(), "S_SKIN", 6))
|
if (!strnicmp(lump->getName(), "S_SKIN", 6))
|
||||||
{ // Wad has at least one skin.
|
{ // Wad has at least one skin.
|
||||||
lump->LumpNameSetup("S_SKIN");
|
lump->LumpNameSetup("S_SKIN", nullptr);
|
||||||
if (!skinned)
|
if (!skinned)
|
||||||
{
|
{
|
||||||
skinned = true;
|
skinned = true;
|
||||||
|
@ -452,7 +452,7 @@ void FWadFile::SkinHack (FileSystemMessageFunc Printf)
|
||||||
}
|
}
|
||||||
if (skinned && hasmap)
|
if (skinned && hasmap)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Attention, "%s: The maps will not be loaded because it has a skin.\n", FileName.c_str());
|
Printf(FSMessageLevel::Attention, "%s: The maps will not be loaded because it has a skin.\n", FileName);
|
||||||
Printf(FSMessageLevel::Attention, "You should remove the skin from the wad to play these maps.\n");
|
Printf(FSMessageLevel::Attention, "You should remove the skin from the wad to play these maps.\n");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -464,7 +464,7 @@ void FWadFile::SkinHack (FileSystemMessageFunc Printf)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *CheckWad(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *CheckWad(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
char head[4];
|
char head[4];
|
||||||
|
|
||||||
|
@ -475,7 +475,7 @@ FResourceFile *CheckWad(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
file.Seek(0, FileReader::SeekSet);
|
file.Seek(0, FileReader::SeekSet);
|
||||||
if (!memcmp(head, "IWAD", 4) || !memcmp(head, "PWAD", 4))
|
if (!memcmp(head, "IWAD", 4) || !memcmp(head, "PWAD", 4))
|
||||||
{
|
{
|
||||||
auto rf = new FWadFile(filename, file);
|
auto rf = new FWadFile(filename, file, sp);
|
||||||
if (rf->Open(filter, Printf)) return rf;
|
if (rf->Open(filter, Printf)) return rf;
|
||||||
|
|
||||||
file = std::move(rf->Reader); // to avoid destruction of reader
|
file = std::move(rf->Reader); // to avoid destruction of reader
|
||||||
|
@ -485,3 +485,4 @@ FResourceFile *CheckWad(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -34,10 +34,12 @@
|
||||||
**
|
**
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "resourcefile.h"
|
#include "resourcefile_internal.h"
|
||||||
|
#include "fs_stringpool.h"
|
||||||
#include "fs_swap.h"
|
#include "fs_swap.h"
|
||||||
|
|
||||||
using namespace fs_private;
|
namespace FileSys {
|
||||||
|
using namespace byteswap;
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
|
@ -47,9 +49,9 @@ using namespace fs_private;
|
||||||
|
|
||||||
class FWHResFile : public FUncompressedFile
|
class FWHResFile : public FUncompressedFile
|
||||||
{
|
{
|
||||||
std::string basename;
|
const char* BaseName;
|
||||||
public:
|
public:
|
||||||
FWHResFile(const char * filename, FileReader &file);
|
FWHResFile(const char * filename, FileReader &file, StringPool* sp);
|
||||||
bool Open(LumpFilterInfo* filter);
|
bool Open(LumpFilterInfo* filter);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -60,10 +62,10 @@ public:
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FWHResFile::FWHResFile(const char *filename, FileReader &file)
|
FWHResFile::FWHResFile(const char *filename, FileReader &file, StringPool* sp)
|
||||||
: FUncompressedFile(filename, file)
|
: FUncompressedFile(filename, file, sp)
|
||||||
{
|
{
|
||||||
basename = ExtractBaseName(filename, false);
|
BaseName = stringpool->Strdup(ExtractBaseName(filename, false).c_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -91,8 +93,9 @@ bool FWHResFile::Open(LumpFilterInfo*)
|
||||||
if (length == 0) break;
|
if (length == 0) break;
|
||||||
char num[5];
|
char num[5];
|
||||||
snprintf(num, 5, "/%04d", k);
|
snprintf(num, 5, "/%04d", k);
|
||||||
std::string synthname = basename + num;
|
std::string synthname = BaseName;
|
||||||
Lumps[i].LumpNameSetup(synthname.c_str());
|
synthname += num;
|
||||||
|
Lumps[i].LumpNameSetup(synthname.c_str(), stringpool);
|
||||||
Lumps[i].Owner = this;
|
Lumps[i].Owner = this;
|
||||||
Lumps[i].Position = offset;
|
Lumps[i].Position = offset;
|
||||||
Lumps[i].LumpSize = length;
|
Lumps[i].LumpSize = length;
|
||||||
|
@ -111,7 +114,7 @@ bool FWHResFile::Open(LumpFilterInfo*)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *CheckWHRes(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *CheckWHRes(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
if (file.GetLength() >= 8192) // needs to be at least 8192 to contain one file and the directory.
|
if (file.GetLength() >= 8192) // needs to be at least 8192 to contain one file and the directory.
|
||||||
{
|
{
|
||||||
|
@ -131,11 +134,12 @@ FResourceFile *CheckWHRes(const char *filename, FileReader &file, LumpFilterInfo
|
||||||
if (offset != checkpos || length == 0 || offset + length >= (size_t)size - 4096 ) return nullptr;
|
if (offset != checkpos || length == 0 || offset + length >= (size_t)size - 4096 ) return nullptr;
|
||||||
checkpos += (length+4095) / 4096;
|
checkpos += (length+4095) / 4096;
|
||||||
}
|
}
|
||||||
auto rf = new FWHResFile(filename, file);
|
auto rf = new FWHResFile(filename, file, sp);
|
||||||
if (rf->Open(filter)) return rf;
|
if (rf->Open(filter)) return rf;
|
||||||
file = std::move(rf->Reader); // to avoid destruction of reader
|
file = std::move(rf->Reader); // to avoid destruction of reader
|
||||||
delete rf;
|
delete rf;
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -41,7 +41,8 @@
|
||||||
#include "fs_findfile.h"
|
#include "fs_findfile.h"
|
||||||
#include "fs_swap.h"
|
#include "fs_swap.h"
|
||||||
|
|
||||||
using namespace fs_private;
|
namespace FileSys {
|
||||||
|
using namespace byteswap;
|
||||||
|
|
||||||
#define BUFREADCOMMENT (0x400)
|
#define BUFREADCOMMENT (0x400)
|
||||||
|
|
||||||
|
@ -164,8 +165,8 @@ static uint32_t Zip_FindCentralDir(FileReader &fin, bool* zip64)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FZipFile::FZipFile(const char * filename, FileReader &file)
|
FZipFile::FZipFile(const char * filename, FileReader &file, StringPool* sp)
|
||||||
: FResourceFile(filename, file)
|
: FResourceFile(filename, file, sp)
|
||||||
{
|
{
|
||||||
Lumps = NULL;
|
Lumps = NULL;
|
||||||
}
|
}
|
||||||
|
@ -180,7 +181,7 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
|
|
||||||
if (centraldir == 0)
|
if (centraldir == 0)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Error, "%s: ZIP file corrupt!\n", FileName.c_str());
|
Printf(FSMessageLevel::Error, "%s: ZIP file corrupt!\n", FileName);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -196,7 +197,7 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
if (info.NumEntries != info.NumEntriesOnAllDisks ||
|
if (info.NumEntries != info.NumEntriesOnAllDisks ||
|
||||||
info.FirstDisk != 0 || info.DiskNumber != 0)
|
info.FirstDisk != 0 || info.DiskNumber != 0)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Error, "%s: Multipart Zip files are not supported.\n", FileName.c_str());
|
Printf(FSMessageLevel::Error, "%s: Multipart Zip files are not supported.\n", FileName);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -215,7 +216,7 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
if (info.NumEntries != info.NumEntriesOnAllDisks ||
|
if (info.NumEntries != info.NumEntriesOnAllDisks ||
|
||||||
info.FirstDisk != 0 || info.DiskNumber != 0)
|
info.FirstDisk != 0 || info.DiskNumber != 0)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Error, "%s: Multipart Zip files are not supported.\n", FileName.c_str());
|
Printf(FSMessageLevel::Error, "%s: Multipart Zip files are not supported.\n", FileName);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -254,35 +255,36 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
if (dirptr > ((char*)directory) + dirsize) // This directory entry goes beyond the end of the file.
|
if (dirptr > ((char*)directory) + dirsize) // This directory entry goes beyond the end of the file.
|
||||||
{
|
{
|
||||||
free(directory);
|
free(directory);
|
||||||
Printf(FSMessageLevel::Error, "%s: Central directory corrupted.", FileName.c_str());
|
Printf(FSMessageLevel::Error, "%s: Central directory corrupted.", FileName);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (auto& c : name) c = tolower(c);
|
for (auto& c : name) c = tolower(c);
|
||||||
|
|
||||||
if (name.find_first_of("filter/") == 0)
|
auto vv = name.find("__macosx");
|
||||||
|
if (name.find("filter/") == 0)
|
||||||
continue; // 'filter' is a reserved name of the file system.
|
continue; // 'filter' is a reserved name of the file system.
|
||||||
if (name.find_first_of("__macosx") == 0)
|
if (name.find("__macosx") == 0)
|
||||||
continue; // skip Apple garbage. At this stage only the root folder matters.
|
continue; // skip Apple garbage. At this stage only the root folder matters.
|
||||||
if (name.find_first_of(".bat") != std::string::npos || name.find_first_of(".exe") != std::string::npos)
|
if (name.find(".bat") != std::string::npos || name.find(".exe") != std::string::npos)
|
||||||
continue; // also ignore executables for this.
|
continue; // also ignore executables for this.
|
||||||
if (!foundprefix)
|
if (!foundprefix)
|
||||||
{
|
{
|
||||||
// check for special names, if one of these gets found this must be treated as a normal zip.
|
// check for special names, if one of these gets found this must be treated as a normal zip.
|
||||||
bool isspecial = name.find_first_of("/") == std::string::npos ||
|
bool isspecial = name.find("/") == std::string::npos ||
|
||||||
(filter && std::find(filter->reservedFolders.begin(), filter->reservedFolders.end(), name) != filter->reservedFolders.end());
|
(filter && std::find(filter->reservedFolders.begin(), filter->reservedFolders.end(), name) != filter->reservedFolders.end());
|
||||||
if (isspecial) break;
|
if (isspecial) break;
|
||||||
name0 = std::string(name, 0, name.find_last_of("/")+1);
|
name0 = std::string(name, 0, name.rfind("/")+1);
|
||||||
name1 = std::string(name, 0, name.find_first_of("/") + 1);
|
name1 = std::string(name, 0, name.find("/") + 1);
|
||||||
foundprefix = true;
|
foundprefix = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (name.find_first_of(name0) != 0)
|
if (name.find(name0) != 0)
|
||||||
{
|
{
|
||||||
if (!name1.empty())
|
if (!name1.empty())
|
||||||
{
|
{
|
||||||
name0 = name1;
|
name0 = name1;
|
||||||
if (name.find_first_of(name0) != 0)
|
if (name.find(name0) != 0)
|
||||||
{
|
{
|
||||||
name0 = "";
|
name0 = "";
|
||||||
}
|
}
|
||||||
|
@ -295,7 +297,7 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
// at least one of the more common definition lumps must be present.
|
// at least one of the more common definition lumps must be present.
|
||||||
for (auto &p : filter->requiredPrefixes)
|
for (auto &p : filter->requiredPrefixes)
|
||||||
{
|
{
|
||||||
if (name.find_first_of(name0 + p) == 0 || name.find_last_of(p) == ptrdiff_t(name.length() - p.length()))
|
if (name.find(name0 + p) == 0 || name.rfind(p) == ptrdiff_t(name.length() - p.length()))
|
||||||
{
|
{
|
||||||
foundspeciallump = true;
|
foundspeciallump = true;
|
||||||
break;
|
break;
|
||||||
|
@ -322,11 +324,11 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
if (dirptr > ((char*)directory) + dirsize) // This directory entry goes beyond the end of the file.
|
if (dirptr > ((char*)directory) + dirsize) // This directory entry goes beyond the end of the file.
|
||||||
{
|
{
|
||||||
free(directory);
|
free(directory);
|
||||||
Printf(FSMessageLevel::Error, "%s: Central directory corrupted.", FileName.c_str());
|
Printf(FSMessageLevel::Error, "%s: Central directory corrupted.", FileName);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (name.find_first_of("__macosx") == 0 || name.find_first_of("__MACOSX") == 0)
|
if (name.find("__macosx") == 0 || name.find("__MACOSX") == 0)
|
||||||
{
|
{
|
||||||
skipped++;
|
skipped++;
|
||||||
continue; // Weed out Apple's resource fork garbage right here because it interferes with safe operation.
|
continue; // Weed out Apple's resource fork garbage right here because it interferes with safe operation.
|
||||||
|
@ -349,7 +351,7 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
zip_fh->Method != METHOD_IMPLODE &&
|
zip_fh->Method != METHOD_IMPLODE &&
|
||||||
zip_fh->Method != METHOD_SHRINK)
|
zip_fh->Method != METHOD_SHRINK)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Error, "%s: '%s' uses an unsupported compression algorithm (#%d).\n", FileName.c_str(), name.c_str(), zip_fh->Method);
|
Printf(FSMessageLevel::Error, "%s: '%s' uses an unsupported compression algorithm (#%d).\n", FileName, name.c_str(), zip_fh->Method);
|
||||||
skipped++;
|
skipped++;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -357,7 +359,7 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
zip_fh->Flags = LittleShort(zip_fh->Flags);
|
zip_fh->Flags = LittleShort(zip_fh->Flags);
|
||||||
if (zip_fh->Flags & ZF_ENCRYPTED)
|
if (zip_fh->Flags & ZF_ENCRYPTED)
|
||||||
{
|
{
|
||||||
Printf(FSMessageLevel::Error, "%s: '%s' is encrypted. Encryption is not supported.\n", FileName.c_str(), name.c_str());
|
Printf(FSMessageLevel::Error, "%s: '%s' is encrypted. Encryption is not supported.\n", FileName, name.c_str());
|
||||||
skipped++;
|
skipped++;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -384,7 +386,7 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
if (zip_64->CompressedSize > 0x7fffffff || zip_64->UncompressedSize > 0x7fffffff)
|
if (zip_64->CompressedSize > 0x7fffffff || zip_64->UncompressedSize > 0x7fffffff)
|
||||||
{
|
{
|
||||||
// The file system is limited to 32 bit file sizes;
|
// The file system is limited to 32 bit file sizes;
|
||||||
Printf(FSMessageLevel::Warning, "%s: '%s' is too large.\n", FileName.c_str(), name.c_str());
|
Printf(FSMessageLevel::Warning, "%s: '%s' is too large.\n", FileName, name.c_str());
|
||||||
skipped++;
|
skipped++;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -395,7 +397,7 @@ bool FZipFile::Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
lump_p->LumpNameSetup(name.c_str());
|
lump_p->LumpNameSetup(name.c_str(), stringpool);
|
||||||
lump_p->LumpSize = UncompressedSize;
|
lump_p->LumpSize = UncompressedSize;
|
||||||
lump_p->Owner = this;
|
lump_p->Owner = this;
|
||||||
// The start of the Reader will be determined the first time it is accessed.
|
// The start of the Reader will be determined the first time it is accessed.
|
||||||
|
@ -531,7 +533,7 @@ int FZipLump::GetFileOffset()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile *CheckZip(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *CheckZip(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
char head[4];
|
char head[4];
|
||||||
|
|
||||||
|
@ -542,7 +544,7 @@ FResourceFile *CheckZip(const char *filename, FileReader &file, LumpFilterInfo*
|
||||||
file.Seek(0, FileReader::SeekSet);
|
file.Seek(0, FileReader::SeekSet);
|
||||||
if (!memcmp(head, "PK\x3\x4", 4))
|
if (!memcmp(head, "PK\x3\x4", 4))
|
||||||
{
|
{
|
||||||
auto rf = new FZipFile(filename, file);
|
auto rf = new FZipFile(filename, file, sp);
|
||||||
if (rf->Open(filter, Printf)) return rf;
|
if (rf->Open(filter, Printf)) return rf;
|
||||||
|
|
||||||
file = std::move(rf->Reader); // to avoid destruction of reader
|
file = std::move(rf->Reader); // to avoid destruction of reader
|
||||||
|
@ -719,3 +721,5 @@ bool WriteZip(const char* filename, const FCompressedBuffer* content, size_t con
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -3,6 +3,7 @@
|
||||||
|
|
||||||
#include "resourcefile.h"
|
#include "resourcefile.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
// Zip Lump
|
// Zip Lump
|
||||||
|
@ -39,11 +40,12 @@ class FZipFile : public FResourceFile
|
||||||
FZipLump *Lumps;
|
FZipLump *Lumps;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
FZipFile(const char * filename, FileReader &file);
|
FZipFile(const char * filename, FileReader &file, StringPool* sp);
|
||||||
virtual ~FZipFile();
|
virtual ~FZipFile();
|
||||||
bool Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
bool Open(LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
||||||
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
|
@ -34,10 +34,10 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
#include "files.h"
|
#include "files_internal.h"
|
||||||
|
|
||||||
using namespace fs_private;
|
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
std::wstring toWide(const char* str);
|
std::wstring toWide(const char* str);
|
||||||
#endif
|
#endif
|
||||||
|
@ -345,7 +345,7 @@ public:
|
||||||
|
|
||||||
void UpdateBuffer()
|
void UpdateBuffer()
|
||||||
{
|
{
|
||||||
bufptr = (const char*)&buf[0];
|
bufptr = (const char*)buf.data();
|
||||||
FilePos = 0;
|
FilePos = 0;
|
||||||
Length = (long)buf.size();
|
Length = (long)buf.size();
|
||||||
}
|
}
|
||||||
|
@ -476,12 +476,14 @@ long FileWriter::Seek(long offset, int mode)
|
||||||
|
|
||||||
size_t FileWriter::Printf(const char *fmt, ...)
|
size_t FileWriter::Printf(const char *fmt, ...)
|
||||||
{
|
{
|
||||||
|
char c[300];
|
||||||
va_list arglist;
|
va_list arglist;
|
||||||
va_start(arglist, fmt);
|
va_start(arglist, fmt);
|
||||||
auto n = snprintf(nullptr, 0, fmt, arglist);
|
auto n = vsnprintf(c, 300, fmt, arglist);
|
||||||
std::string buf;
|
std::string buf;
|
||||||
buf.resize(n);
|
buf.resize(n);
|
||||||
snprintf(&buf.front(), n, fmt, arglist);
|
va_start(arglist, fmt);
|
||||||
|
vsnprintf(&buf.front(), n, fmt, arglist);
|
||||||
va_end(arglist);
|
va_end(arglist);
|
||||||
return Write(buf.c_str(), n);
|
return Write(buf.c_str(), n);
|
||||||
}
|
}
|
||||||
|
@ -492,3 +494,5 @@ size_t BufferWriter::Write(const void *buffer, size_t len)
|
||||||
memcpy(&mBuffer[ofs], buffer, len);
|
memcpy(&mBuffer[ofs], buffer, len);
|
||||||
return len;
|
return len;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -41,7 +41,30 @@
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <stdexcept>
|
#include <stdexcept>
|
||||||
|
|
||||||
#include "files.h"
|
#include "fs_files.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
using namespace byteswap;
|
||||||
|
|
||||||
|
|
||||||
|
class DecompressorBase : public FileReaderInterface
|
||||||
|
{
|
||||||
|
bool exceptions = false;
|
||||||
|
public:
|
||||||
|
// These do not work but need to be defined to satisfy the FileReaderInterface.
|
||||||
|
// They will just error out when called.
|
||||||
|
long Tell() const override;
|
||||||
|
long Seek(long offset, int origin) override;
|
||||||
|
char* Gets(char* strbuf, int len) override;
|
||||||
|
void DecompressionError(const char* error, ...) const;
|
||||||
|
void SetOwnsReader();
|
||||||
|
void EnableExceptions(bool on) { exceptions = on; }
|
||||||
|
|
||||||
|
protected:
|
||||||
|
FileReader* File = nullptr;
|
||||||
|
FileReader OwnedFile;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
//
|
//
|
||||||
|
@ -538,7 +561,7 @@ class DecompressorLZSS : public DecompressorBase
|
||||||
return false;
|
return false;
|
||||||
Stream.AvailIn -= 2;
|
Stream.AvailIn -= 2;
|
||||||
|
|
||||||
uint16_t pos = fs_private::BigShort(*(uint16_t*)Stream.In);
|
uint16_t pos = BigShort(*(uint16_t*)Stream.In);
|
||||||
uint8_t len = (pos & 0xF)+1;
|
uint8_t len = (pos & 0xF)+1;
|
||||||
pos >>= 4;
|
pos >>= 4;
|
||||||
Stream.In += 2;
|
Stream.In += 2;
|
||||||
|
@ -752,3 +775,4 @@ bool FileReader::OpenDecompressor(FileReader &parent, Size length, int method, b
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
31
source/common/filesystem/source/files_internal.h
Normal file
31
source/common/filesystem/source/files_internal.h
Normal file
|
@ -0,0 +1,31 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "fs_files.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
|
class MemoryReader : public FileReaderInterface
|
||||||
|
{
|
||||||
|
protected:
|
||||||
|
const char * bufptr = nullptr;
|
||||||
|
long FilePos = 0;
|
||||||
|
|
||||||
|
MemoryReader()
|
||||||
|
{}
|
||||||
|
|
||||||
|
public:
|
||||||
|
MemoryReader(const char *buffer, long length)
|
||||||
|
{
|
||||||
|
bufptr = buffer;
|
||||||
|
Length = length;
|
||||||
|
FilePos = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
long Tell() const override;
|
||||||
|
long Seek(long offset, int origin) override;
|
||||||
|
long Read(void *buffer, long len) override;
|
||||||
|
char *Gets(char *strbuf, int len) override;
|
||||||
|
virtual const char *GetBuffer() const override { return bufptr; }
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
|
@ -41,10 +41,14 @@
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
#include "filesystem.h"
|
#include "resourcefile_internal.h"
|
||||||
|
#include "fs_filesystem.h"
|
||||||
#include "fs_findfile.h"
|
#include "fs_findfile.h"
|
||||||
#include "md5.hpp"
|
#include "md5.hpp"
|
||||||
|
#include "fs_stringpool.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
// MACROS ------------------------------------------------------------------
|
// MACROS ------------------------------------------------------------------
|
||||||
|
|
||||||
#define NULL_INDEX (0xffffffff)
|
#define NULL_INDEX (0xffffffff)
|
||||||
|
@ -59,15 +63,19 @@ static void UpperCopy(char* to, const char* from)
|
||||||
to[i] = 0;
|
to[i] = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int MakeHash(const void* data, unsigned length = -1)
|
|
||||||
|
//djb2
|
||||||
|
static uint32_t MakeHash(const char* str, size_t length = SIZE_MAX)
|
||||||
{
|
{
|
||||||
if (length == -1) length = (unsigned)strlen((const char*)data);
|
uint32_t hash = 5381;
|
||||||
return crc32(0, (const Bytef*)data, length);
|
uint32_t c;
|
||||||
|
while (length-- > 0 && (c = *str++)) hash = hash * 33 + (c | 32);
|
||||||
|
return hash;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void md5Hash(FileReader& reader, uint8_t* digest)
|
static void md5Hash(FileReader& reader, uint8_t* digest)
|
||||||
{
|
{
|
||||||
using namespace fs_private::md5;
|
using namespace md5;
|
||||||
|
|
||||||
md5_state_t state;
|
md5_state_t state;
|
||||||
md5_init(&state);
|
md5_init(&state);
|
||||||
|
@ -84,13 +92,13 @@ struct FileSystem::LumpRecord
|
||||||
{
|
{
|
||||||
FResourceLump *lump;
|
FResourceLump *lump;
|
||||||
LumpShortName shortName;
|
LumpShortName shortName;
|
||||||
std::string longName;
|
const char* LongName;
|
||||||
int rfnum;
|
int rfnum;
|
||||||
int Namespace;
|
int Namespace;
|
||||||
int resourceId;
|
int resourceId;
|
||||||
int flags;
|
int flags;
|
||||||
|
|
||||||
void SetFromLump(int filenum, FResourceLump* lmp)
|
void SetFromLump(int filenum, FResourceLump* lmp, StringPool* sp)
|
||||||
{
|
{
|
||||||
lump = lmp;
|
lump = lmp;
|
||||||
rfnum = filenum;
|
rfnum = filenum;
|
||||||
|
@ -100,73 +108,74 @@ struct FileSystem::LumpRecord
|
||||||
{
|
{
|
||||||
UpperCopy(shortName.String, lump->getName());
|
UpperCopy(shortName.String, lump->getName());
|
||||||
shortName.String[8] = 0;
|
shortName.String[8] = 0;
|
||||||
longName = "";
|
LongName = "";
|
||||||
Namespace = lump->GetNamespace();
|
Namespace = lump->GetNamespace();
|
||||||
resourceId = -1;
|
resourceId = -1;
|
||||||
}
|
}
|
||||||
else if ((lump->Flags & LUMPF_EMBEDDED) || !lump->getName() || !*lump->getName())
|
else if ((lump->Flags & LUMPF_EMBEDDED) || !lump->getName() || !*lump->getName())
|
||||||
{
|
{
|
||||||
shortName.qword = 0;
|
shortName.qword = 0;
|
||||||
longName = "";
|
LongName = "";
|
||||||
Namespace = ns_hidden;
|
Namespace = ns_hidden;
|
||||||
resourceId = -1;
|
resourceId = -1;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
longName = lump->getName();
|
LongName = lump->getName();
|
||||||
resourceId = lump->GetIndexNum();
|
resourceId = lump->GetIndexNum();
|
||||||
|
|
||||||
// Map some directories to WAD namespaces.
|
// Map some directories to WAD namespaces.
|
||||||
// Note that some of these namespaces don't exist in WADS.
|
// Note that some of these namespaces don't exist in WADS.
|
||||||
// CheckNumForName will handle any request for these namespaces accordingly.
|
// CheckNumForName will handle any request for these namespaces accordingly.
|
||||||
Namespace = !strncmp(longName.c_str(), "flats/", 6) ? ns_flats :
|
Namespace = !strncmp(LongName, "flats/", 6) ? ns_flats :
|
||||||
!strncmp(longName.c_str(), "textures/", 9) ? ns_newtextures :
|
!strncmp(LongName, "textures/", 9) ? ns_newtextures :
|
||||||
!strncmp(longName.c_str(), "hires/", 6) ? ns_hires :
|
!strncmp(LongName, "hires/", 6) ? ns_hires :
|
||||||
!strncmp(longName.c_str(), "sprites/", 8) ? ns_sprites :
|
!strncmp(LongName, "sprites/", 8) ? ns_sprites :
|
||||||
!strncmp(longName.c_str(), "voxels/", 7) ? ns_voxels :
|
!strncmp(LongName, "voxels/", 7) ? ns_voxels :
|
||||||
!strncmp(longName.c_str(), "colormaps/", 10) ? ns_colormaps :
|
!strncmp(LongName, "colormaps/", 10) ? ns_colormaps :
|
||||||
!strncmp(longName.c_str(), "acs/", 4) ? ns_acslibrary :
|
!strncmp(LongName, "acs/", 4) ? ns_acslibrary :
|
||||||
!strncmp(longName.c_str(), "voices/", 7) ? ns_strifevoices :
|
!strncmp(LongName, "voices/", 7) ? ns_strifevoices :
|
||||||
!strncmp(longName.c_str(), "patches/", 8) ? ns_patches :
|
!strncmp(LongName, "patches/", 8) ? ns_patches :
|
||||||
!strncmp(longName.c_str(), "graphics/", 9) ? ns_graphics :
|
!strncmp(LongName, "graphics/", 9) ? ns_graphics :
|
||||||
!strncmp(longName.c_str(), "sounds/", 7) ? ns_sounds :
|
!strncmp(LongName, "sounds/", 7) ? ns_sounds :
|
||||||
!strncmp(longName.c_str(), "music/", 6) ? ns_music :
|
!strncmp(LongName, "music/", 6) ? ns_music :
|
||||||
!strchr(longName.c_str(), '/') ? ns_global :
|
!strchr(LongName, '/') ? ns_global :
|
||||||
ns_hidden;
|
ns_hidden;
|
||||||
|
|
||||||
if (Namespace == ns_hidden) shortName.qword = 0;
|
if (Namespace == ns_hidden) shortName.qword = 0;
|
||||||
else
|
else if (strstr(LongName, ".{"))
|
||||||
{
|
{
|
||||||
|
std::string longName = LongName;
|
||||||
ptrdiff_t encodedResID = longName.find_last_of(".{");
|
ptrdiff_t encodedResID = longName.find_last_of(".{");
|
||||||
if (resourceId == -1 && encodedResID != std::string::npos)
|
if (resourceId == -1 && encodedResID != std::string::npos)
|
||||||
{
|
{
|
||||||
const char* p = longName.c_str() + encodedResID;
|
const char* p = LongName + encodedResID;
|
||||||
char* q;
|
char* q;
|
||||||
int id = (int)strtoull(p+2, &q, 10); // only decimal numbers allowed here.
|
int id = (int)strtoull(p + 2, &q, 10); // only decimal numbers allowed here.
|
||||||
if (q[0] == '}' && (q[1] == '.' || q[1] == 0))
|
if (q[0] == '}' && (q[1] == '.' || q[1] == 0))
|
||||||
{
|
{
|
||||||
longName.erase(longName.begin() + encodedResID, longName.begin() + (q - p) + 1);
|
longName.erase(longName.begin() + encodedResID, longName.begin() + (q - p) + 1);
|
||||||
resourceId = id;
|
resourceId = id;
|
||||||
}
|
}
|
||||||
|
LongName = sp->Strdup(longName.c_str());
|
||||||
}
|
}
|
||||||
ptrdiff_t slash = longName.find_last_of('/');
|
}
|
||||||
std::string base = (slash != std::string::npos) ? longName.c_str() + (slash + 1) : longName.c_str();
|
auto slash = strrchr(LongName, '/');
|
||||||
auto dot = base.find_last_of('.');
|
std::string base = slash ? (slash + 1) : LongName;
|
||||||
if (dot != std::string::npos) base.resize(dot);
|
auto dot = base.find_last_of('.');
|
||||||
UpperCopy(shortName.String, base.c_str());
|
if (dot != std::string::npos) base.resize(dot);
|
||||||
shortName.String[8] = 0;
|
UpperCopy(shortName.String, base.c_str());
|
||||||
|
|
||||||
// Since '\' can't be used as a file name's part inside a ZIP
|
// Since '\' can't be used as a file name's part inside a ZIP
|
||||||
// we have to work around this for sprites because it is a valid
|
// we have to work around this for sprites because it is a valid
|
||||||
// frame character.
|
// frame character.
|
||||||
if (Namespace == ns_sprites || Namespace == ns_voxels || Namespace == ns_hires)
|
if (Namespace == ns_sprites || Namespace == ns_voxels || Namespace == ns_hires)
|
||||||
|
{
|
||||||
|
char* c;
|
||||||
|
|
||||||
|
while ((c = (char*)memchr(shortName.String, '^', 8)))
|
||||||
{
|
{
|
||||||
char* c;
|
*c = '\\';
|
||||||
|
|
||||||
while ((c = (char*)memchr(shortName.String, '^', 8)))
|
|
||||||
{
|
|
||||||
*c = '\\';
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -181,13 +190,12 @@ static void PrintLastError (FileSystemMessageFunc Printf);
|
||||||
|
|
||||||
// PUBLIC DATA DEFINITIONS -------------------------------------------------
|
// PUBLIC DATA DEFINITIONS -------------------------------------------------
|
||||||
|
|
||||||
FileSystem fileSystem;
|
|
||||||
|
|
||||||
// CODE --------------------------------------------------------------------
|
// CODE --------------------------------------------------------------------
|
||||||
|
|
||||||
FileSystem::FileSystem()
|
FileSystem::FileSystem()
|
||||||
{
|
{
|
||||||
// Cannot be defaulted! This is needed to initialize the LumpRecord array, which depends on data only available here.
|
stringpool = new StringPool;
|
||||||
|
stringpool->shared = true; // will be used by all owned resource files.
|
||||||
}
|
}
|
||||||
|
|
||||||
FileSystem::~FileSystem ()
|
FileSystem::~FileSystem ()
|
||||||
|
@ -287,7 +295,7 @@ bool FileSystem::InitMultipleFiles (std::vector<std::string>& filenames, LumpFil
|
||||||
void FileSystem::AddLump(FResourceLump *lump)
|
void FileSystem::AddLump(FResourceLump *lump)
|
||||||
{
|
{
|
||||||
FileInfo.resize(FileInfo.size() + 1);
|
FileInfo.resize(FileInfo.size() + 1);
|
||||||
FileInfo.back().SetFromLump(-1, lump);
|
FileInfo.back().SetFromLump(-1, lump, stringpool);
|
||||||
}
|
}
|
||||||
|
|
||||||
//-----------------------------------------------------------------------
|
//-----------------------------------------------------------------------
|
||||||
|
@ -300,7 +308,7 @@ void FileSystem::AddLump(FResourceLump *lump)
|
||||||
|
|
||||||
int FileSystem::AddExternalFile(const char *filename)
|
int FileSystem::AddExternalFile(const char *filename)
|
||||||
{
|
{
|
||||||
FResourceLump *lump = new FExternalLump(filename);
|
FResourceLump *lump = new FExternalLump(filename, -1, stringpool);
|
||||||
AddLump(lump);
|
AddLump(lump);
|
||||||
return (int)FileInfo.size() - 1; // later
|
return (int)FileInfo.size() - 1; // later
|
||||||
}
|
}
|
||||||
|
@ -313,13 +321,24 @@ int FileSystem::AddExternalFile(const char *filename)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
|
struct FMemoryLump : public FResourceLump
|
||||||
|
{
|
||||||
|
FMemoryLump(const void* data, int length)
|
||||||
|
{
|
||||||
|
RefCount = -1;
|
||||||
|
LumpSize = length;
|
||||||
|
Cache = new char[length];
|
||||||
|
memcpy(Cache, data, length);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
int FileSystem::AddFromBuffer(const char* name, const char* type, char* data, int size, int id, int flags)
|
int FileSystem::AddFromBuffer(const char* name, const char* type, char* data, int size, int id, int flags)
|
||||||
{
|
{
|
||||||
std::string fullname = name;
|
std::string fullname = name;
|
||||||
fullname += ':';
|
fullname += '.';
|
||||||
fullname += type;
|
fullname += type;
|
||||||
auto newlump = new FMemoryLump(data, size);
|
auto newlump = new FMemoryLump(data, size);
|
||||||
newlump->LumpNameSetup(fullname.c_str());
|
newlump->LumpNameSetup(fullname.c_str(), stringpool);
|
||||||
AddLump(newlump);
|
AddLump(newlump);
|
||||||
FileInfo.back().resourceId = id;
|
FileInfo.back().resourceId = id;
|
||||||
return (int)FileInfo.size()-1;
|
return (int)FileInfo.size()-1;
|
||||||
|
@ -375,9 +394,9 @@ void FileSystem::AddFile (const char *filename, FileReader *filer, LumpFilterInf
|
||||||
|
|
||||||
|
|
||||||
if (!isdir)
|
if (!isdir)
|
||||||
resfile = FResourceFile::OpenResourceFile(filename, filereader, false, filter, Printf);
|
resfile = FResourceFile::OpenResourceFile(filename, filereader, false, filter, Printf, stringpool);
|
||||||
else
|
else
|
||||||
resfile = FResourceFile::OpenDirectory(filename, filter, Printf);
|
resfile = FResourceFile::OpenDirectory(filename, filter, Printf, stringpool);
|
||||||
|
|
||||||
if (resfile != NULL)
|
if (resfile != NULL)
|
||||||
{
|
{
|
||||||
|
@ -391,8 +410,8 @@ void FileSystem::AddFile (const char *filename, FileReader *filer, LumpFilterInf
|
||||||
{
|
{
|
||||||
FResourceLump *lump = resfile->GetLump(i);
|
FResourceLump *lump = resfile->GetLump(i);
|
||||||
FileInfo.resize(FileInfo.size() + 1);
|
FileInfo.resize(FileInfo.size() + 1);
|
||||||
FileSystem::LumpRecord *lump_p = &FileInfo.back();
|
FileSystem::LumpRecord* lump_p = &FileInfo.back();
|
||||||
lump_p->SetFromLump((int)Files.size(), lump);
|
lump_p->SetFromLump((int)Files.size(), lump, stringpool);
|
||||||
}
|
}
|
||||||
|
|
||||||
Files.push_back(resfile);
|
Files.push_back(resfile);
|
||||||
|
@ -504,7 +523,7 @@ int FileSystem::CheckIfResourceFileLoaded (const char *name) noexcept
|
||||||
// and namespace parameter
|
// and namespace parameter
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FileSystem::CheckNumForName (const char *name, int space)
|
int FileSystem::CheckNumForName (const char *name, int space) const
|
||||||
{
|
{
|
||||||
union
|
union
|
||||||
{
|
{
|
||||||
|
@ -549,7 +568,7 @@ int FileSystem::CheckNumForName (const char *name, int space)
|
||||||
return i != NULL_INDEX ? i : -1;
|
return i != NULL_INDEX ? i : -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FileSystem::CheckNumForName (const char *name, int space, int rfnum, bool exact)
|
int FileSystem::CheckNumForName (const char *name, int space, int rfnum, bool exact) const
|
||||||
{
|
{
|
||||||
union
|
union
|
||||||
{
|
{
|
||||||
|
@ -587,7 +606,7 @@ int FileSystem::CheckNumForName (const char *name, int space, int rfnum, bool ex
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FileSystem::GetNumForName (const char *name, int space)
|
int FileSystem::GetNumForName (const char *name, int space) const
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
@ -610,7 +629,7 @@ int FileSystem::GetNumForName (const char *name, int space)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FileSystem::CheckNumForFullName (const char *name, bool trynormal, int namespc, bool ignoreext)
|
int FileSystem::CheckNumForFullName (const char *name, bool trynormal, int namespc, bool ignoreext) const
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
|
|
||||||
|
@ -625,12 +644,12 @@ int FileSystem::CheckNumForFullName (const char *name, bool trynormal, int names
|
||||||
|
|
||||||
for (i = fli[MakeHash(name) % NumEntries]; i != NULL_INDEX; i = nli[i])
|
for (i = fli[MakeHash(name) % NumEntries]; i != NULL_INDEX; i = nli[i])
|
||||||
{
|
{
|
||||||
if (strnicmp(name, FileInfo[i].longName.c_str(), len)) continue;
|
if (strnicmp(name, FileInfo[i].LongName, len)) continue;
|
||||||
if (FileInfo[i].longName[len] == 0) break; // this is a full match
|
if (FileInfo[i].LongName[len] == 0) break; // this is a full match
|
||||||
if (ignoreext && FileInfo[i].longName[len] == '.')
|
if (ignoreext && FileInfo[i].LongName[len] == '.')
|
||||||
{
|
{
|
||||||
// is this the last '.' in the last path element, indicating that the remaining part of the name is only an extension?
|
// is this the last '.' in the last path element, indicating that the remaining part of the name is only an extension?
|
||||||
if (strpbrk(FileInfo[i].longName.c_str() + len + 1, "./") == nullptr) break;
|
if (strpbrk(FileInfo[i].LongName + len + 1, "./") == nullptr) break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -643,7 +662,7 @@ int FileSystem::CheckNumForFullName (const char *name, bool trynormal, int names
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FileSystem::CheckNumForFullName (const char *name, int rfnum)
|
int FileSystem::CheckNumForFullName (const char *name, int rfnum) const
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
|
|
||||||
|
@ -655,7 +674,7 @@ int FileSystem::CheckNumForFullName (const char *name, int rfnum)
|
||||||
i = FirstLumpIndex_FullName[MakeHash (name) % NumEntries];
|
i = FirstLumpIndex_FullName[MakeHash (name) % NumEntries];
|
||||||
|
|
||||||
while (i != NULL_INDEX &&
|
while (i != NULL_INDEX &&
|
||||||
(stricmp(name, FileInfo[i].longName.c_str()) || FileInfo[i].rfnum != rfnum))
|
(stricmp(name, FileInfo[i].LongName) || FileInfo[i].rfnum != rfnum))
|
||||||
{
|
{
|
||||||
i = NextLumpIndex_FullName[i];
|
i = NextLumpIndex_FullName[i];
|
||||||
}
|
}
|
||||||
|
@ -671,7 +690,7 @@ int FileSystem::CheckNumForFullName (const char *name, int rfnum)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FileSystem::GetNumForFullName (const char *name)
|
int FileSystem::GetNumForFullName (const char *name) const
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
@ -691,7 +710,7 @@ int FileSystem::GetNumForFullName (const char *name)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FileSystem::FindFileWithExtensions(const char* name, const char *const *exts, int count)
|
int FileSystem::FindFileWithExtensions(const char* name, const char *const *exts, int count) const
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
|
|
||||||
|
@ -706,10 +725,10 @@ int FileSystem::FindFileWithExtensions(const char* name, const char *const *exts
|
||||||
|
|
||||||
for (i = fli[MakeHash(name) % NumEntries]; i != NULL_INDEX; i = nli[i])
|
for (i = fli[MakeHash(name) % NumEntries]; i != NULL_INDEX; i = nli[i])
|
||||||
{
|
{
|
||||||
if (strnicmp(name, FileInfo[i].longName.c_str(), len)) continue;
|
if (strnicmp(name, FileInfo[i].LongName, len)) continue;
|
||||||
if (FileInfo[i].longName[len] != '.') continue; // we are looking for extensions but this file doesn't have one.
|
if (FileInfo[i].LongName[len] != '.') continue; // we are looking for extensions but this file doesn't have one.
|
||||||
|
|
||||||
auto cp = FileInfo[i].longName.c_str() + len + 1;
|
auto cp = FileInfo[i].LongName + len + 1;
|
||||||
// is this the last '.' in the last path element, indicating that the remaining part of the name is only an extension?
|
// is this the last '.' in the last path element, indicating that the remaining part of the name is only an extension?
|
||||||
if (strpbrk(cp, "./") != nullptr) continue; // No, so it cannot be a valid entry.
|
if (strpbrk(cp, "./") != nullptr) continue; // No, so it cannot be a valid entry.
|
||||||
|
|
||||||
|
@ -745,7 +764,7 @@ int FileSystem::FindResource (int resid, const char *type, int filenum) const no
|
||||||
{
|
{
|
||||||
if (filenum > 0 && FileInfo[i].rfnum != filenum) continue;
|
if (filenum > 0 && FileInfo[i].rfnum != filenum) continue;
|
||||||
if (FileInfo[i].resourceId != resid) continue;
|
if (FileInfo[i].resourceId != resid) continue;
|
||||||
auto extp = strrchr(FileInfo[i].longName.c_str(), '.');
|
auto extp = strrchr(FileInfo[i].LongName, '.');
|
||||||
if (!extp) continue;
|
if (!extp) continue;
|
||||||
if (!stricmp(extp + 1, type)) return i;
|
if (!stricmp(extp + 1, type)) return i;
|
||||||
}
|
}
|
||||||
|
@ -859,13 +878,13 @@ void FileSystem::InitHashChains (void)
|
||||||
FirstLumpIndex[j] = i;
|
FirstLumpIndex[j] = i;
|
||||||
|
|
||||||
// Do the same for the full paths
|
// Do the same for the full paths
|
||||||
if (!FileInfo[i].longName.empty())
|
if (FileInfo[i].LongName[0] != 0)
|
||||||
{
|
{
|
||||||
j = MakeHash(FileInfo[i].longName.c_str()) % NumEntries;
|
j = MakeHash(FileInfo[i].LongName) % NumEntries;
|
||||||
NextLumpIndex_FullName[i] = FirstLumpIndex_FullName[j];
|
NextLumpIndex_FullName[i] = FirstLumpIndex_FullName[j];
|
||||||
FirstLumpIndex_FullName[j] = i;
|
FirstLumpIndex_FullName[j] = i;
|
||||||
|
|
||||||
auto nameNoExt = FileInfo[i].longName;
|
std::string nameNoExt = FileInfo[i].LongName;
|
||||||
auto dot = nameNoExt.find_last_of('.');
|
auto dot = nameNoExt.find_last_of('.');
|
||||||
auto slash = nameNoExt.find_last_of('/');
|
auto slash = nameNoExt.find_last_of('/');
|
||||||
if ((dot > slash || slash == std::string::npos) && dot != std::string::npos) nameNoExt.resize(dot);
|
if ((dot > slash || slash == std::string::npos) && dot != std::string::npos) nameNoExt.resize(dot);
|
||||||
|
@ -900,7 +919,7 @@ LumpShortName& FileSystem::GetShortName(int i)
|
||||||
void FileSystem::RenameFile(int num, const char* newfn)
|
void FileSystem::RenameFile(int num, const char* newfn)
|
||||||
{
|
{
|
||||||
if ((unsigned)num >= NumEntries) throw FileSystemException("RenameFile: Invalid index");
|
if ((unsigned)num >= NumEntries) throw FileSystemException("RenameFile: Invalid index");
|
||||||
FileInfo[num].longName = newfn;
|
FileInfo[num].LongName = stringpool->Strdup(newfn);
|
||||||
// This does not alter the short name - call GetShortname to do that!
|
// This does not alter the short name - call GetShortname to do that!
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -934,13 +953,13 @@ void FileSystem::MoveLumpsInFolder(const char *path)
|
||||||
{
|
{
|
||||||
auto& li = FileInfo[i];
|
auto& li = FileInfo[i];
|
||||||
if (li.rfnum >= GetIwadNum()) break;
|
if (li.rfnum >= GetIwadNum()) break;
|
||||||
if (strnicmp(li.longName.c_str(), path, len) == 0)
|
if (strnicmp(li.LongName, path, len) == 0)
|
||||||
{
|
{
|
||||||
FileInfo.push_back(li);
|
FileInfo.push_back(li);
|
||||||
li.lump = &placeholderLump; // Make the old entry point to something empty. We cannot delete the lump record here because it'd require adjustment of all indices in the list.
|
li.lump = &placeholderLump; // Make the old entry point to something empty. We cannot delete the lump record here because it'd require adjustment of all indices in the list.
|
||||||
auto &ln = FileInfo.back();
|
auto &ln = FileInfo.back();
|
||||||
ln.lump->LumpNameSetup(ln.longName.c_str() + len);
|
ln.lump->LumpNameSetup(ln.LongName + len, stringpool); // may be able to avoid the string allocation!
|
||||||
ln.SetFromLump(rfnum, ln.lump);
|
ln.SetFromLump(rfnum, ln.lump, stringpool);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -956,6 +975,7 @@ void FileSystem::MoveLumpsInFolder(const char *path)
|
||||||
|
|
||||||
int FileSystem::FindLump (const char *name, int *lastlump, bool anyns)
|
int FileSystem::FindLump (const char *name, int *lastlump, bool anyns)
|
||||||
{
|
{
|
||||||
|
if (*lastlump >= FileInfo.size()) return -1;
|
||||||
union
|
union
|
||||||
{
|
{
|
||||||
char name8[8];
|
char name8[8];
|
||||||
|
@ -967,11 +987,11 @@ int FileSystem::FindLump (const char *name, int *lastlump, bool anyns)
|
||||||
|
|
||||||
assert(lastlump != NULL && *lastlump >= 0);
|
assert(lastlump != NULL && *lastlump >= 0);
|
||||||
lump_p = &FileInfo[*lastlump];
|
lump_p = &FileInfo[*lastlump];
|
||||||
while (lump_p < &FileInfo[NumEntries])
|
while (lump_p <= &FileInfo.back())
|
||||||
{
|
{
|
||||||
if ((anyns || lump_p->Namespace == ns_global) && lump_p->shortName.qword == qname)
|
if ((anyns || lump_p->Namespace == ns_global) && lump_p->shortName.qword == qname)
|
||||||
{
|
{
|
||||||
int lump = int(lump_p - &FileInfo[0]);
|
int lump = int(lump_p - FileInfo.data());
|
||||||
*lastlump = lump + 1;
|
*lastlump = lump + 1;
|
||||||
return lump;
|
return lump;
|
||||||
}
|
}
|
||||||
|
@ -997,7 +1017,7 @@ int FileSystem::FindLumpMulti (const char **names, int *lastlump, bool anyns, in
|
||||||
|
|
||||||
assert(lastlump != NULL && *lastlump >= 0);
|
assert(lastlump != NULL && *lastlump >= 0);
|
||||||
lump_p = &FileInfo[*lastlump];
|
lump_p = &FileInfo[*lastlump];
|
||||||
while (lump_p < &FileInfo[NumEntries])
|
while (lump_p <= &FileInfo.back())
|
||||||
{
|
{
|
||||||
if (anyns || lump_p->Namespace == ns_global)
|
if (anyns || lump_p->Namespace == ns_global)
|
||||||
{
|
{
|
||||||
|
@ -1006,7 +1026,7 @@ int FileSystem::FindLumpMulti (const char **names, int *lastlump, bool anyns, in
|
||||||
{
|
{
|
||||||
if (!strnicmp(*name, lump_p->shortName.String, 8))
|
if (!strnicmp(*name, lump_p->shortName.String, 8))
|
||||||
{
|
{
|
||||||
int lump = int(lump_p - &FileInfo[0]);
|
int lump = int(lump_p - FileInfo.data());
|
||||||
*lastlump = lump + 1;
|
*lastlump = lump + 1;
|
||||||
if (nameindex != NULL) *nameindex = int(name - names);
|
if (nameindex != NULL) *nameindex = int(name - names);
|
||||||
return lump;
|
return lump;
|
||||||
|
@ -1036,11 +1056,11 @@ int FileSystem::FindLumpFullName(const char* name, int* lastlump, bool noext)
|
||||||
|
|
||||||
if (!noext)
|
if (!noext)
|
||||||
{
|
{
|
||||||
while (lump_p < &FileInfo[NumEntries])
|
while (lump_p <= &FileInfo.back())
|
||||||
{
|
{
|
||||||
if (!stricmp(name, lump_p->longName.c_str()))
|
if (!stricmp(name, lump_p->LongName))
|
||||||
{
|
{
|
||||||
int lump = int(lump_p - &FileInfo[0]);
|
int lump = int(lump_p - FileInfo.data());
|
||||||
*lastlump = lump + 1;
|
*lastlump = lump + 1;
|
||||||
return lump;
|
return lump;
|
||||||
}
|
}
|
||||||
|
@ -1050,15 +1070,15 @@ int FileSystem::FindLumpFullName(const char* name, int* lastlump, bool noext)
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
auto len = strlen(name);
|
auto len = strlen(name);
|
||||||
while (lump_p < &FileInfo[NumEntries])
|
while (lump_p <= &FileInfo.back())
|
||||||
{
|
{
|
||||||
auto res = strnicmp(name, lump_p->longName.c_str(), len);
|
auto res = strnicmp(name, lump_p->LongName, len);
|
||||||
if (res == 0)
|
if (res == 0)
|
||||||
{
|
{
|
||||||
auto p = lump_p->longName.c_str() + len;
|
auto p = lump_p->LongName + len;
|
||||||
if (*p == 0 || (*p == '.' && strpbrk(p + 1, "./") == 0))
|
if (*p == 0 || (*p == '.' && strpbrk(p + 1, "./") == 0))
|
||||||
{
|
{
|
||||||
int lump = int(lump_p - &FileInfo[0]);
|
int lump = int(lump_p - FileInfo.data());
|
||||||
*lastlump = lump + 1;
|
*lastlump = lump + 1;
|
||||||
return lump;
|
return lump;
|
||||||
}
|
}
|
||||||
|
@ -1112,8 +1132,8 @@ const char *FileSystem::GetFileFullName (int lump, bool returnshort) const
|
||||||
{
|
{
|
||||||
if ((size_t)lump >= NumEntries)
|
if ((size_t)lump >= NumEntries)
|
||||||
return NULL;
|
return NULL;
|
||||||
else if (!FileInfo[lump].longName.empty())
|
else if (FileInfo[lump].LongName[0] != 0)
|
||||||
return FileInfo[lump].longName.c_str();
|
return FileInfo[lump].LongName;
|
||||||
else if (returnshort)
|
else if (returnshort)
|
||||||
return FileInfo[lump].shortName.String;
|
return FileInfo[lump].shortName.String;
|
||||||
else return nullptr;
|
else return nullptr;
|
||||||
|
@ -1191,7 +1211,7 @@ const char *FileSystem::GetResourceType(int lump) const
|
||||||
return nullptr;
|
return nullptr;
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
auto p = strrchr(FileInfo[lump].longName.c_str(), '.');
|
auto p = strrchr(FileInfo[lump].LongName, '.');
|
||||||
if (!p) return ""; // has no extension
|
if (!p) return ""; // has no extension
|
||||||
if (strchr(p, '/')) return ""; // the '.' is part of a directory.
|
if (strchr(p, '/')) return ""; // the '.' is part of a directory.
|
||||||
return p + 1;
|
return p + 1;
|
||||||
|
@ -1243,12 +1263,12 @@ unsigned FileSystem::GetFilesInFolder(const char *inpath, std::vector<FolderEntr
|
||||||
result.clear();
|
result.clear();
|
||||||
for (size_t i = 0; i < FileInfo.size(); i++)
|
for (size_t i = 0; i < FileInfo.size(); i++)
|
||||||
{
|
{
|
||||||
if (FileInfo[i].longName.find_first_of(path) == 0)
|
if (strncmp(FileInfo[i].LongName, path.c_str(), path.length()) == 0)
|
||||||
{
|
{
|
||||||
// Only if it hasn't been replaced.
|
// Only if it hasn't been replaced.
|
||||||
if ((unsigned)fileSystem.CheckNumForFullName(FileInfo[i].longName.c_str()) == i)
|
if ((unsigned)CheckNumForFullName(FileInfo[i].LongName) == i)
|
||||||
{
|
{
|
||||||
FolderEntry fe{ FileInfo[i].longName.c_str(), (uint32_t)i };
|
FolderEntry fe{ FileInfo[i].LongName, (uint32_t)i };
|
||||||
result.push_back(fe);
|
result.push_back(fe);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1261,13 +1281,13 @@ unsigned FileSystem::GetFilesInFolder(const char *inpath, std::vector<FolderEntr
|
||||||
// Find the highest resource file having content in the given folder.
|
// Find the highest resource file having content in the given folder.
|
||||||
for (auto & entry : result)
|
for (auto & entry : result)
|
||||||
{
|
{
|
||||||
int thisfile = fileSystem.GetFileContainer(entry.lumpnum);
|
int thisfile = GetFileContainer(entry.lumpnum);
|
||||||
if (thisfile > maxfile) maxfile = thisfile;
|
if (thisfile > maxfile) maxfile = thisfile;
|
||||||
}
|
}
|
||||||
// Delete everything from older files.
|
// Delete everything from older files.
|
||||||
for (int i = (int)result.size() - 1; i >= 0; i--)
|
for (int i = (int)result.size() - 1; i >= 0; i--)
|
||||||
{
|
{
|
||||||
if (fileSystem.GetFileContainer(result[i].lumpnum) != maxfile) result.erase(result.begin() + i);
|
if (GetFileContainer(result[i].lumpnum) != maxfile) result.erase(result.begin() + i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
qsort(result.data(), result.size(), sizeof(FolderEntry), folderentrycmp);
|
qsort(result.data(), result.size(), sizeof(FolderEntry), folderentrycmp);
|
||||||
|
@ -1292,7 +1312,7 @@ void FileSystem::ReadFile (int lump, void *dest)
|
||||||
if (numread != size)
|
if (numread != size)
|
||||||
{
|
{
|
||||||
throw FileSystemException("W_ReadFile: only read %ld of %ld on '%s'\n",
|
throw FileSystemException("W_ReadFile: only read %ld of %ld on '%s'\n",
|
||||||
numread, size, FileInfo[lump].longName.c_str());
|
numread, size, FileInfo[lump].LongName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1356,8 +1376,8 @@ FileReader FileSystem::ReopenFileReader(int lump, bool alwayscache)
|
||||||
|
|
||||||
if (rl->RefCount == 0 && rd != nullptr && !rd->GetBuffer() && !alwayscache && !(rl->Flags & LUMPF_COMPRESSED))
|
if (rl->RefCount == 0 && rd != nullptr && !rd->GetBuffer() && !alwayscache && !(rl->Flags & LUMPF_COMPRESSED))
|
||||||
{
|
{
|
||||||
int fileno = fileSystem.GetFileContainer(lump);
|
int fileno = GetFileContainer(lump);
|
||||||
const char *filename = fileSystem.GetResourceFileFullName(fileno);
|
const char *filename = GetResourceFileFullName(fileno);
|
||||||
FileReader fr;
|
FileReader fr;
|
||||||
if (fr.OpenFile(filename, rl->GetFileOffset(), rl->LumpSize))
|
if (fr.OpenFile(filename, rl->GetFileOffset(), rl->LumpSize))
|
||||||
{
|
{
|
||||||
|
@ -1410,7 +1430,7 @@ const char *FileSystem::GetResourceFileName (int rfnum) const noexcept
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
name = Files[rfnum]->FileName.c_str();
|
name = Files[rfnum]->FileName;
|
||||||
slash = strrchr (name, '/');
|
slash = strrchr (name, '/');
|
||||||
return (slash != nullptr && slash[1] != 0) ? slash+1 : name;
|
return (slash != nullptr && slash[1] != 0) ? slash+1 : name;
|
||||||
}
|
}
|
||||||
|
@ -1476,7 +1496,7 @@ const char *FileSystem::GetResourceFileFullName (int rfnum) const noexcept
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
return Files[rfnum]->FileName.c_str();
|
return Files[rfnum]->FileName;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1496,9 +1516,9 @@ bool FileSystem::CreatePathlessCopy(const char *name, int id, int /*flags*/)
|
||||||
if (lump < 0) return false; // Does not exist.
|
if (lump < 0) return false; // Does not exist.
|
||||||
|
|
||||||
auto oldlump = FileInfo[lump];
|
auto oldlump = FileInfo[lump];
|
||||||
ptrdiff_t slash = oldlump.longName.find_last_of('/');
|
auto slash = strrchr(oldlump.LongName, '/');
|
||||||
|
|
||||||
if (slash == std::string::npos)
|
if (slash == nullptr)
|
||||||
{
|
{
|
||||||
FileInfo[lump].flags = LUMPF_FULLPATH;
|
FileInfo[lump].flags = LUMPF_FULLPATH;
|
||||||
return true; // already is pathless.
|
return true; // already is pathless.
|
||||||
|
@ -1506,7 +1526,7 @@ bool FileSystem::CreatePathlessCopy(const char *name, int id, int /*flags*/)
|
||||||
|
|
||||||
|
|
||||||
// just create a new reference to the original data with a different name.
|
// just create a new reference to the original data with a different name.
|
||||||
oldlump.longName.erase(oldlump.longName.begin(), oldlump.longName.begin() + (slash + 1));
|
oldlump.LongName = slash + 1;
|
||||||
oldlump.resourceId = id;
|
oldlump.resourceId = id;
|
||||||
oldlump.flags = LUMPF_FULLPATH;
|
oldlump.flags = LUMPF_FULLPATH;
|
||||||
FileInfo.push_back(oldlump);
|
FileInfo.push_back(oldlump);
|
||||||
|
@ -1571,3 +1591,5 @@ FResourceLump* FileSystem::GetFileAt(int no)
|
||||||
{
|
{
|
||||||
return FileInfo[no].lump;
|
return FileInfo[no].lump;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -33,9 +33,11 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "fs_findfile.h"
|
#include "fs_findfile.h"
|
||||||
|
#include <string.h>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
ZPATH_MAX = 260
|
ZPATH_MAX = 260
|
||||||
|
@ -61,6 +63,8 @@ enum
|
||||||
|
|
||||||
#ifndef _WIN32
|
#ifndef _WIN32
|
||||||
|
|
||||||
|
#include <limits.h>
|
||||||
|
#include <stdlib.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <fnmatch.h>
|
#include <fnmatch.h>
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
|
@ -163,7 +167,7 @@ static int FS_FindAttr(findstate_t *const fileinfo)
|
||||||
const std::string path = fileinfo->path + ent->d_name;
|
const std::string path = fileinfo->path + ent->d_name;
|
||||||
bool isdir;
|
bool isdir;
|
||||||
|
|
||||||
if (DirEntryExists(path.c_str(), &isdir))
|
if (FS_DirEntryExists(path.c_str(), &isdir))
|
||||||
{
|
{
|
||||||
return isdir ? FA_DIREC : 0;
|
return isdir ? FA_DIREC : 0;
|
||||||
}
|
}
|
||||||
|
@ -173,8 +177,12 @@ static int FS_FindAttr(findstate_t *const fileinfo)
|
||||||
|
|
||||||
std::string FS_FullPath(const char* directory)
|
std::string FS_FullPath(const char* directory)
|
||||||
{
|
{
|
||||||
// todo
|
char fullpath[PATH_MAX];
|
||||||
return directory
|
|
||||||
|
if (realpath(directory, fullpath) != nullptr)
|
||||||
|
return fullpath;
|
||||||
|
|
||||||
|
return directory;
|
||||||
}
|
}
|
||||||
|
|
||||||
static size_t FS_GetFileSize(findstate_t* handle, const char* pathname)
|
static size_t FS_GetFileSize(findstate_t* handle, const char* pathname)
|
||||||
|
@ -303,7 +311,7 @@ std::string FS_FullPath(const char* directory)
|
||||||
|
|
||||||
static size_t FS_GetFileSize(findstate_t* handle, const char* pathname)
|
static size_t FS_GetFileSize(findstate_t* handle, const char* pathname)
|
||||||
{
|
{
|
||||||
return handle->FindData.Size[0] + ((uint64_t)handle->FindData.Size[1] << 32);
|
return handle->FindData.Size[1] + ((uint64_t)handle->FindData.Size[0] << 32);
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -315,7 +323,7 @@ static size_t FS_GetFileSize(findstate_t* handle, const char* pathname)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
static bool ScanDirectory(FileList& list, const char* dirpath, const char* match, const char* relpath, bool nosubdir, bool readhidden)
|
static bool DoScanDirectory(FileList& list, const char* dirpath, const char* match, const char* relpath, bool nosubdir, bool readhidden)
|
||||||
{
|
{
|
||||||
findstate_t find;
|
findstate_t find;
|
||||||
|
|
||||||
|
@ -323,7 +331,7 @@ static bool ScanDirectory(FileList& list, const char* dirpath, const char* match
|
||||||
FixPathSeparator(&dirpathn.front());
|
FixPathSeparator(&dirpathn.front());
|
||||||
if (dirpathn[dirpathn.length() - 1] != '/') dirpathn += '/';
|
if (dirpathn[dirpathn.length() - 1] != '/') dirpathn += '/';
|
||||||
|
|
||||||
std::string dirmatch = dirpath;
|
std::string dirmatch = dirpathn;
|
||||||
dirmatch += match;
|
dirmatch += match;
|
||||||
|
|
||||||
auto handle = FS_FindFirst(dirmatch.c_str(), &find);
|
auto handle = FS_FindFirst(dirmatch.c_str(), &find);
|
||||||
|
@ -353,7 +361,7 @@ static bool ScanDirectory(FileList& list, const char* dirpath, const char* match
|
||||||
fl.FileName = fn;
|
fl.FileName = fn;
|
||||||
fl.FilePath = dirpathn + fn;
|
fl.FilePath = dirpathn + fn;
|
||||||
fl.FilePathRel = relpath;
|
fl.FilePathRel = relpath;
|
||||||
fl.FilePathRel += '/';
|
if (fl.FilePathRel.length() > 0) fl.FilePathRel += '/';
|
||||||
fl.FilePathRel += fn;
|
fl.FilePathRel += fn;
|
||||||
fl.isDirectory = !!(attr & FA_DIREC);
|
fl.isDirectory = !!(attr & FA_DIREC);
|
||||||
fl.isReadonly = !!(attr & FA_RDONLY);
|
fl.isReadonly = !!(attr & FA_RDONLY);
|
||||||
|
@ -363,8 +371,7 @@ static bool ScanDirectory(FileList& list, const char* dirpath, const char* match
|
||||||
list.push_back(fl);
|
list.push_back(fl);
|
||||||
if (!nosubdir && (attr & FA_DIREC))
|
if (!nosubdir && (attr & FA_DIREC))
|
||||||
{
|
{
|
||||||
std::string rel = relpath + '/' + fl.FileName;
|
DoScanDirectory(list, fl.FilePath.c_str(), match, fl.FilePathRel.c_str(), false, readhidden);
|
||||||
ScanDirectory(list, fl.FilePath.c_str(), match);
|
|
||||||
fl.Length = 0;
|
fl.Length = 0;
|
||||||
}
|
}
|
||||||
} while (FS_FindNext(handle, &find) == 0);
|
} while (FS_FindNext(handle, &find) == 0);
|
||||||
|
@ -375,7 +382,7 @@ static bool ScanDirectory(FileList& list, const char* dirpath, const char* match
|
||||||
|
|
||||||
bool ScanDirectory(std::vector<FileListEntry>& list, const char* dirpath, const char* match, bool nosubdir, bool readhidden)
|
bool ScanDirectory(std::vector<FileListEntry>& list, const char* dirpath, const char* match, bool nosubdir, bool readhidden)
|
||||||
{
|
{
|
||||||
return ScanDirectory(list, dirpath, match, "", nosubdir, readhidden);
|
return DoScanDirectory(list, dirpath, match, "", nosubdir, readhidden);
|
||||||
}
|
}
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -405,3 +412,4 @@ bool FS_DirEntryExists(const char* pathname, bool* isdir)
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
130
source/common/filesystem/source/fs_stringpool.cpp
Normal file
130
source/common/filesystem/source/fs_stringpool.cpp
Normal file
|
@ -0,0 +1,130 @@
|
||||||
|
/*
|
||||||
|
** stringpool.cpp
|
||||||
|
** allocate static strings from larger blocks
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** Copyright 2010 Randy Heit
|
||||||
|
** Copyright 2023 Christoph Oelckers
|
||||||
|
** All rights reserved.
|
||||||
|
**
|
||||||
|
** Redistribution and use in source and binary forms, with or without
|
||||||
|
** modification, are permitted provided that the following conditions
|
||||||
|
** are met:
|
||||||
|
**
|
||||||
|
** 1. Redistributions of source code must retain the above copyright
|
||||||
|
** notice, this list of conditions and the following disclaimer.
|
||||||
|
** 2. Redistributions in binary form must reproduce the above copyright
|
||||||
|
** notice, this list of conditions and the following disclaimer in the
|
||||||
|
** documentation and/or other materials provided with the distribution.
|
||||||
|
** 3. The name of the author may not be used to endorse or promote products
|
||||||
|
** derived from this software without specific prior written permission.
|
||||||
|
**
|
||||||
|
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
||||||
|
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||||
|
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||||
|
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||||
|
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||||
|
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||||
|
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||||
|
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||||
|
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
**
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include "fs_stringpool.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
|
struct StringPool::Block
|
||||||
|
{
|
||||||
|
Block *NextBlock;
|
||||||
|
void *Limit; // End of this block
|
||||||
|
void *Avail; // Start of free space in this block
|
||||||
|
void *alignme; // align to 16 bytes.
|
||||||
|
|
||||||
|
void *Alloc(size_t size);
|
||||||
|
};
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// StringPool Destructor
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
StringPool::~StringPool()
|
||||||
|
{
|
||||||
|
for (Block *next, *block = TopBlock; block != nullptr; block = next)
|
||||||
|
{
|
||||||
|
next = block->NextBlock;
|
||||||
|
free(block);
|
||||||
|
}
|
||||||
|
TopBlock = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// StringPool :: Alloc
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
void *StringPool::Block::Alloc(size_t size)
|
||||||
|
{
|
||||||
|
if ((char *)Avail + size > Limit)
|
||||||
|
{
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
void *res = Avail;
|
||||||
|
Avail = ((char *)Avail + size);
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
StringPool::Block *StringPool::AddBlock(size_t size)
|
||||||
|
{
|
||||||
|
size += sizeof(Block); // Account for header size
|
||||||
|
|
||||||
|
// Allocate a new block
|
||||||
|
if (size < BlockSize)
|
||||||
|
{
|
||||||
|
size = BlockSize;
|
||||||
|
}
|
||||||
|
auto mem = (Block *)malloc(size);
|
||||||
|
if (mem == nullptr)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
mem->Limit = (uint8_t *)mem + size;
|
||||||
|
mem->Avail = &mem[1];
|
||||||
|
mem->NextBlock = TopBlock;
|
||||||
|
TopBlock = mem;
|
||||||
|
return mem;
|
||||||
|
}
|
||||||
|
|
||||||
|
void *StringPool::iAlloc(size_t size)
|
||||||
|
{
|
||||||
|
Block *block;
|
||||||
|
|
||||||
|
for (block = TopBlock; block != nullptr; block = block->NextBlock)
|
||||||
|
{
|
||||||
|
void *res = block->Alloc(size);
|
||||||
|
if (res != nullptr)
|
||||||
|
{
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
block = AddBlock(size);
|
||||||
|
return block->Alloc(size);
|
||||||
|
}
|
||||||
|
|
||||||
|
const char* StringPool::Strdup(const char* str)
|
||||||
|
{
|
||||||
|
char* p = (char*)iAlloc((strlen(str) + 8) & ~7 );
|
||||||
|
strcpy(p, str);
|
||||||
|
return p;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
29
source/common/filesystem/source/fs_stringpool.h
Normal file
29
source/common/filesystem/source/fs_stringpool.h
Normal file
|
@ -0,0 +1,29 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
// Storage for all the static strings the file system must hold.
|
||||||
|
class StringPool
|
||||||
|
{
|
||||||
|
// do not allow externally defining this.
|
||||||
|
friend class FileSystem;
|
||||||
|
friend class FResourceFile;
|
||||||
|
private:
|
||||||
|
StringPool(size_t blocksize = 10*1024) : TopBlock(nullptr), FreeBlocks(nullptr), BlockSize(blocksize) {}
|
||||||
|
public:
|
||||||
|
~StringPool();
|
||||||
|
const char* Strdup(const char*);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
struct Block;
|
||||||
|
|
||||||
|
Block *AddBlock(size_t size);
|
||||||
|
void *iAlloc(size_t size);
|
||||||
|
|
||||||
|
Block *TopBlock;
|
||||||
|
Block *FreeBlocks;
|
||||||
|
size_t BlockSize;
|
||||||
|
public:
|
||||||
|
bool shared;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
|
@ -69,7 +69,7 @@
|
||||||
#include <stddef.h>
|
#include <stddef.h>
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
|
|
||||||
namespace fs_private {
|
namespace FileSys {
|
||||||
/// Provides MD5 hashing functionality
|
/// Provides MD5 hashing functionality
|
||||||
namespace md5 {
|
namespace md5 {
|
||||||
|
|
|
@ -35,9 +35,13 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <zlib.h>
|
#include <zlib.h>
|
||||||
#include "resourcefile.h"
|
#include "resourcefile_internal.h"
|
||||||
#include "md5.hpp"
|
#include "md5.hpp"
|
||||||
|
#include "fs_stringpool.h"
|
||||||
|
#include "files_internal.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
std::string ExtractBaseName(const char* path, bool include_extension)
|
std::string ExtractBaseName(const char* path, bool include_extension)
|
||||||
{
|
{
|
||||||
const char* src, * dot;
|
const char* src, * dot;
|
||||||
|
@ -122,13 +126,17 @@ FResourceLump::~FResourceLump()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
void FResourceLump::LumpNameSetup(const char *iname)
|
void FResourceLump::LumpNameSetup(const char *iname, StringPool* allocator)
|
||||||
{
|
{
|
||||||
// this causes interference with real Dehacked lumps.
|
// this causes interference with real Dehacked lumps.
|
||||||
if (!stricmp(iname, "dehacked.exe"))
|
if (!stricmp(iname, "dehacked.exe"))
|
||||||
{
|
{
|
||||||
iname = "";
|
iname = "";
|
||||||
}
|
}
|
||||||
|
else if (allocator)
|
||||||
|
{
|
||||||
|
iname = allocator->Strdup(iname);
|
||||||
|
}
|
||||||
|
|
||||||
FullName = iname;
|
FullName = iname;
|
||||||
}
|
}
|
||||||
|
@ -149,7 +157,7 @@ static bool IsWadInFolder(const FResourceFile* const archive, const char* const
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto dirName = ExtractBaseName(archive->FileName.c_str());
|
const auto dirName = ExtractBaseName(archive->FileName);
|
||||||
const auto fileName = ExtractBaseName(resPath, true);
|
const auto fileName = ExtractBaseName(resPath, true);
|
||||||
const std::string filePath = dirName + '/' + fileName;
|
const std::string filePath = dirName + '/' + fileName;
|
||||||
|
|
||||||
|
@ -159,14 +167,14 @@ static bool IsWadInFolder(const FResourceFile* const archive, const char* const
|
||||||
void FResourceLump::CheckEmbedded(LumpFilterInfo* lfi)
|
void FResourceLump::CheckEmbedded(LumpFilterInfo* lfi)
|
||||||
{
|
{
|
||||||
// Checks for embedded archives
|
// Checks for embedded archives
|
||||||
const char *c = strstr(FullName.c_str(), ".wad");
|
const char *c = strstr(FullName, ".wad");
|
||||||
if (c && strlen(c) == 4 && (!strchr(FullName.c_str(), '/') || IsWadInFolder(Owner, FullName.c_str())))
|
if (c && strlen(c) == 4 && (!strchr(FullName, '/') || IsWadInFolder(Owner, FullName)))
|
||||||
{
|
{
|
||||||
Flags |= LUMPF_EMBEDDED;
|
Flags |= LUMPF_EMBEDDED;
|
||||||
}
|
}
|
||||||
else if (lfi) for (auto& fstr : lfi->embeddings)
|
else if (lfi) for (auto& fstr : lfi->embeddings)
|
||||||
{
|
{
|
||||||
if (!stricmp(FullName.c_str(), fstr.c_str()))
|
if (!stricmp(FullName, fstr.c_str()))
|
||||||
{
|
{
|
||||||
Flags |= LUMPF_EMBEDDED;
|
Flags |= LUMPF_EMBEDDED;
|
||||||
}
|
}
|
||||||
|
@ -234,7 +242,7 @@ void *FResourceLump::Lock()
|
||||||
catch (const FileSystemException& err)
|
catch (const FileSystemException& err)
|
||||||
{
|
{
|
||||||
// enrich the message with info about this lump.
|
// enrich the message with info about this lump.
|
||||||
throw FileSystemException("%s, file '%s': %s", getName(), Owner->FileName.c_str(), err.what());
|
throw FileSystemException("%s, file '%s': %s", getName(), Owner->FileName, err.what());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return Cache;
|
return Cache;
|
||||||
|
@ -265,18 +273,18 @@ int FResourceLump::Unlock()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
typedef FResourceFile * (*CheckFunc)(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
typedef FResourceFile * (*CheckFunc)(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
|
|
||||||
FResourceFile *CheckWad(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile *CheckWad(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile *CheckGRP(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile *CheckGRP(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile *CheckRFF(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile *CheckRFF(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile *CheckPak(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile *CheckPak(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile *CheckZip(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile *CheckZip(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile *Check7Z(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile *Check7Z(const char *filename, FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile* CheckSSI(const char* filename, FileReader& file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile* CheckSSI(const char* filename, FileReader& file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile* CheckWHRes(const char* filename, FileReader& file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile* CheckWHRes(const char* filename, FileReader& file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile *CheckLump(const char *filename,FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile *CheckLump(const char *filename,FileReader &file, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
FResourceFile *CheckDir(const char *filename, bool nosub, LumpFilterInfo* filter, FileSystemMessageFunc Printf);
|
FResourceFile *CheckDir(const char *filename, bool nosub, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp);
|
||||||
|
|
||||||
static CheckFunc funcs[] = { CheckWad, CheckZip, Check7Z, CheckPak, CheckGRP, CheckRFF, CheckSSI, CheckWHRes, CheckLump };
|
static CheckFunc funcs[] = { CheckWad, CheckZip, Check7Z, CheckPak, CheckGRP, CheckRFF, CheckSSI, CheckWHRes, CheckLump };
|
||||||
|
|
||||||
|
@ -285,35 +293,35 @@ static int nulPrintf(FSMessageLevel msg, const char* fmt, ...)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
FResourceFile *FResourceFile::DoOpenResourceFile(const char *filename, FileReader &file, bool containeronly, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *FResourceFile::DoOpenResourceFile(const char *filename, FileReader &file, bool containeronly, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
if (Printf == nullptr) Printf = nulPrintf;
|
if (Printf == nullptr) Printf = nulPrintf;
|
||||||
for(auto func : funcs)
|
for(auto func : funcs)
|
||||||
{
|
{
|
||||||
if (containeronly && func == CheckLump) break;
|
if (containeronly && func == CheckLump) break;
|
||||||
FResourceFile *resfile = func(filename, file, filter, Printf);
|
FResourceFile *resfile = func(filename, file, filter, Printf, sp);
|
||||||
if (resfile != NULL) return resfile;
|
if (resfile != NULL) return resfile;
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
FResourceFile *FResourceFile::OpenResourceFile(const char *filename, FileReader &file, bool containeronly, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *FResourceFile::OpenResourceFile(const char *filename, FileReader &file, bool containeronly, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
return DoOpenResourceFile(filename, file, containeronly, filter, Printf);
|
return DoOpenResourceFile(filename, file, containeronly, filter, Printf, sp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
FResourceFile *FResourceFile::OpenResourceFile(const char *filename, bool containeronly, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *FResourceFile::OpenResourceFile(const char *filename, bool containeronly, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
FileReader file;
|
FileReader file;
|
||||||
if (!file.OpenFile(filename)) return nullptr;
|
if (!file.OpenFile(filename)) return nullptr;
|
||||||
return DoOpenResourceFile(filename, file, containeronly, filter, Printf);
|
return DoOpenResourceFile(filename, file, containeronly, filter, Printf, sp);
|
||||||
}
|
}
|
||||||
|
|
||||||
FResourceFile *FResourceFile::OpenDirectory(const char *filename, LumpFilterInfo* filter, FileSystemMessageFunc Printf)
|
FResourceFile *FResourceFile::OpenDirectory(const char *filename, LumpFilterInfo* filter, FileSystemMessageFunc Printf, StringPool* sp)
|
||||||
{
|
{
|
||||||
if (Printf == nullptr) Printf = nulPrintf;
|
if (Printf == nullptr) Printf = nulPrintf;
|
||||||
return CheckDir(filename, false, filter, Printf);
|
return CheckDir(filename, false, filter, Printf, sp);
|
||||||
}
|
}
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -322,19 +330,21 @@ FResourceFile *FResourceFile::OpenDirectory(const char *filename, LumpFilterInfo
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FResourceFile::FResourceFile(const char *filename)
|
FResourceFile::FResourceFile(const char *filename, StringPool* sp)
|
||||||
: FileName(filename)
|
|
||||||
{
|
{
|
||||||
|
stringpool = sp ? sp : new StringPool;
|
||||||
|
FileName = stringpool->Strdup(filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
FResourceFile::FResourceFile(const char *filename, FileReader &r)
|
FResourceFile::FResourceFile(const char *filename, FileReader &r, StringPool* sp)
|
||||||
: FResourceFile(filename)
|
: FResourceFile(filename,sp)
|
||||||
{
|
{
|
||||||
Reader = std::move(r);
|
Reader = std::move(r);
|
||||||
}
|
}
|
||||||
|
|
||||||
FResourceFile::~FResourceFile()
|
FResourceFile::~FResourceFile()
|
||||||
{
|
{
|
||||||
|
if (!stringpool->shared) delete stringpool;
|
||||||
}
|
}
|
||||||
|
|
||||||
int lumpcmp(const void * a, const void * b)
|
int lumpcmp(const void * a, const void * b)
|
||||||
|
@ -357,7 +367,7 @@ int lumpcmp(const void * a, const void * b)
|
||||||
void FResourceFile::GenerateHash()
|
void FResourceFile::GenerateHash()
|
||||||
{
|
{
|
||||||
// hash the lump directory after sorting
|
// hash the lump directory after sorting
|
||||||
using namespace fs_private::md5;
|
using namespace FileSys::md5;
|
||||||
|
|
||||||
auto n = snprintf(Hash, 48, "%08X-%04X-", (unsigned)Reader.GetLength(), NumLumps);
|
auto n = snprintf(Hash, 48, "%08X-%04X-", (unsigned)Reader.GetLength(), NumLumps);
|
||||||
|
|
||||||
|
@ -368,7 +378,7 @@ void FResourceFile::GenerateHash()
|
||||||
for(uint32_t i = 0; i < NumLumps; i++)
|
for(uint32_t i = 0; i < NumLumps; i++)
|
||||||
{
|
{
|
||||||
auto lump = GetLump(i);
|
auto lump = GetLump(i);
|
||||||
md5_append(&state, (const uint8_t*)lump->FullName.c_str(), (unsigned)lump->FullName.length() + 1);
|
md5_append(&state, (const uint8_t*)lump->FullName, (unsigned)strlen(lump->FullName) + 1);
|
||||||
md5_append(&state, (const uint8_t*)&lump->LumpSize, 4);
|
md5_append(&state, (const uint8_t*)&lump->LumpSize, 4);
|
||||||
}
|
}
|
||||||
md5_finish(&state, digest);
|
md5_finish(&state, digest);
|
||||||
|
@ -438,7 +448,7 @@ int FResourceFile::FilterLumps(const std::string& filtername, void *lumps, size_
|
||||||
bool found = FindPrefixRange(filter.c_str(), lumps, lumpsize, max, start, end);
|
bool found = FindPrefixRange(filter.c_str(), lumps, lumpsize, max, start, end);
|
||||||
|
|
||||||
// Workaround for old Doom filter names (todo: move out of here.)
|
// Workaround for old Doom filter names (todo: move out of here.)
|
||||||
if (!found && filtername.find_first_of("doom.id.doom") == 0)
|
if (!found && filtername.find("doom.id.doom") == 0)
|
||||||
{
|
{
|
||||||
strReplace(filter, "doom.id.doom", "doom.doom");
|
strReplace(filter, "doom.id.doom", "doom.doom");
|
||||||
found = FindPrefixRange(filter.c_str(), lumps, lumpsize, max, start, end);
|
found = FindPrefixRange(filter.c_str(), lumps, lumpsize, max, start, end);
|
||||||
|
@ -453,8 +463,8 @@ int FResourceFile::FilterLumps(const std::string& filtername, void *lumps, size_
|
||||||
for (uint32_t i = start; i < end; ++i, lump_p = (uint8_t *)lump_p + lumpsize)
|
for (uint32_t i = start; i < end; ++i, lump_p = (uint8_t *)lump_p + lumpsize)
|
||||||
{
|
{
|
||||||
FResourceLump *lump = (FResourceLump *)lump_p;
|
FResourceLump *lump = (FResourceLump *)lump_p;
|
||||||
assert(strnicmp(lump->FullName.c_str(), filter.c_str(), filter.length()) == 0);
|
assert(strnicmp(lump->FullName, filter.c_str(), filter.length()) == 0);
|
||||||
lump->LumpNameSetup(lump->FullName.c_str() + filter.length());
|
lump->LumpNameSetup(lump->FullName + filter.length(), nullptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Move filtered lumps to the end of the lump list.
|
// Move filtered lumps to the end of the lump list.
|
||||||
|
@ -523,7 +533,7 @@ void FResourceFile::JunkLeftoverFilters(void *lumps, size_t lumpsize, uint32_t m
|
||||||
for (void *p = (uint8_t *)lumps + start * lumpsize; p < stop; p = (uint8_t *)p + lumpsize)
|
for (void *p = (uint8_t *)lumps + start * lumpsize; p < stop; p = (uint8_t *)p + lumpsize)
|
||||||
{
|
{
|
||||||
FResourceLump *lump = (FResourceLump *)p;
|
FResourceLump *lump = (FResourceLump *)p;
|
||||||
lump->FullName = "";
|
lump->clearName();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -556,7 +566,7 @@ bool FResourceFile::FindPrefixRange(const char* filter, void *lumps, size_t lump
|
||||||
{
|
{
|
||||||
mid = min + (max - min) / 2;
|
mid = min + (max - min) / 2;
|
||||||
lump = (FResourceLump *)((uint8_t *)lumps + mid * lumpsize);
|
lump = (FResourceLump *)((uint8_t *)lumps + mid * lumpsize);
|
||||||
cmp = strnicmp(lump->FullName.c_str(), filter, (int)strlen(filter));
|
cmp = strnicmp(lump->FullName, filter, (int)strlen(filter));
|
||||||
if (cmp == 0)
|
if (cmp == 0)
|
||||||
break;
|
break;
|
||||||
else if (cmp < 0)
|
else if (cmp < 0)
|
||||||
|
@ -576,7 +586,7 @@ bool FResourceFile::FindPrefixRange(const char* filter, void *lumps, size_t lump
|
||||||
{
|
{
|
||||||
mid = min + (max - min) / 2;
|
mid = min + (max - min) / 2;
|
||||||
lump = (FResourceLump *)((uint8_t *)lumps + mid * lumpsize);
|
lump = (FResourceLump *)((uint8_t *)lumps + mid * lumpsize);
|
||||||
cmp = strnicmp(lump->FullName.c_str(), filter, (int)strlen(filter));
|
cmp = strnicmp(lump->FullName, filter, (int)strlen(filter));
|
||||||
// Go left on matches and right on misses.
|
// Go left on matches and right on misses.
|
||||||
if (cmp == 0)
|
if (cmp == 0)
|
||||||
max = mid - 1;
|
max = mid - 1;
|
||||||
|
@ -591,7 +601,7 @@ bool FResourceFile::FindPrefixRange(const char* filter, void *lumps, size_t lump
|
||||||
{
|
{
|
||||||
mid = min + (max - min) / 2;
|
mid = min + (max - min) / 2;
|
||||||
lump = (FResourceLump *)((uint8_t *)lumps + mid * lumpsize);
|
lump = (FResourceLump *)((uint8_t *)lumps + mid * lumpsize);
|
||||||
cmp = strnicmp(lump->FullName.c_str(), filter, (int)strlen(filter));
|
cmp = strnicmp(lump->FullName, filter, (int)strlen(filter));
|
||||||
// Go right on matches and left on misses.
|
// Go right on matches and left on misses.
|
||||||
if (cmp == 0)
|
if (cmp == 0)
|
||||||
min = mid + 1;
|
min = mid + 1;
|
||||||
|
@ -613,7 +623,7 @@ FResourceLump *FResourceFile::FindLump(const char *name)
|
||||||
for (unsigned i = 0; i < NumLumps; i++)
|
for (unsigned i = 0; i < NumLumps; i++)
|
||||||
{
|
{
|
||||||
FResourceLump *lump = GetLump(i);
|
FResourceLump *lump = GetLump(i);
|
||||||
if (!stricmp(name, lump->FullName.c_str()))
|
if (!stricmp(name, lump->FullName))
|
||||||
{
|
{
|
||||||
return lump;
|
return lump;
|
||||||
}
|
}
|
||||||
|
@ -670,12 +680,12 @@ int FUncompressedLump::FillCache()
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FUncompressedFile::FUncompressedFile(const char *filename)
|
FUncompressedFile::FUncompressedFile(const char *filename, StringPool* sp)
|
||||||
: FResourceFile(filename)
|
: FResourceFile(filename, sp)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
FUncompressedFile::FUncompressedFile(const char *filename, FileReader &r)
|
FUncompressedFile::FUncompressedFile(const char *filename, FileReader &r, StringPool* sp)
|
||||||
: FResourceFile(filename, r)
|
: FResourceFile(filename, r, sp)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
|
||||||
|
@ -685,9 +695,10 @@ FUncompressedFile::FUncompressedFile(const char *filename, FileReader &r)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FExternalLump::FExternalLump(const char *_filename, int filesize)
|
FExternalLump::FExternalLump(const char *_filename, int filesize, StringPool* stringpool)
|
||||||
: Filename(_filename)
|
|
||||||
{
|
{
|
||||||
|
FileName = stringpool->Strdup(_filename);
|
||||||
|
|
||||||
if (filesize == -1)
|
if (filesize == -1)
|
||||||
{
|
{
|
||||||
FileReader f;
|
FileReader f;
|
||||||
|
@ -720,7 +731,7 @@ int FExternalLump::FillCache()
|
||||||
Cache = new char[LumpSize];
|
Cache = new char[LumpSize];
|
||||||
FileReader f;
|
FileReader f;
|
||||||
|
|
||||||
if (f.OpenFile(Filename.c_str()))
|
if (f.OpenFile(FileName))
|
||||||
{
|
{
|
||||||
auto read = f.Read(Cache, LumpSize);
|
auto read = f.Read(Cache, LumpSize);
|
||||||
if (read != LumpSize)
|
if (read != LumpSize)
|
||||||
|
@ -737,4 +748,4 @@ int FExternalLump::FillCache()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
38
source/common/filesystem/source/resourcefile_internal.h
Normal file
38
source/common/filesystem/source/resourcefile_internal.h
Normal file
|
@ -0,0 +1,38 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "resourcefile.h"
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
struct FUncompressedLump : public FResourceLump
|
||||||
|
{
|
||||||
|
int Position;
|
||||||
|
|
||||||
|
virtual FileReader *GetReader();
|
||||||
|
virtual int FillCache() override;
|
||||||
|
virtual int GetFileOffset() { return Position; }
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
// Base class for uncompressed resource files (WAD, GRP, PAK and single lumps)
|
||||||
|
class FUncompressedFile : public FResourceFile
|
||||||
|
{
|
||||||
|
protected:
|
||||||
|
TArray<FUncompressedLump> Lumps;
|
||||||
|
|
||||||
|
FUncompressedFile(const char *filename, StringPool* sp);
|
||||||
|
FUncompressedFile(const char *filename, FileReader &r, StringPool* sp);
|
||||||
|
virtual FResourceLump *GetLump(int no) { return ((unsigned)no < NumLumps)? &Lumps[no] : NULL; }
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// should only be used internally.
|
||||||
|
struct FExternalLump : public FResourceLump
|
||||||
|
{
|
||||||
|
const char* FileName;
|
||||||
|
|
||||||
|
FExternalLump(const char *_filename, int filesize, StringPool* sp);
|
||||||
|
virtual int FillCache() override;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
|
@ -7,6 +7,8 @@
|
||||||
#define FORCE_PACKED
|
#define FORCE_PACKED
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
namespace FileSys {
|
||||||
|
|
||||||
#pragma pack(1)
|
#pragma pack(1)
|
||||||
// FZipCentralInfo
|
// FZipCentralInfo
|
||||||
struct FZipEndOfCentralDirectory
|
struct FZipEndOfCentralDirectory
|
||||||
|
@ -105,4 +107,5 @@ struct FZipLocalFileHeader
|
||||||
// File header flags.
|
// File header flags.
|
||||||
#define ZF_ENCRYPTED 0x1
|
#define ZF_ENCRYPTED 0x1
|
||||||
|
|
||||||
|
}
|
||||||
#endif
|
#endif
|
|
@ -91,7 +91,7 @@ FFont::FFont (const char *name, const char *nametemplate, const char *filetempla
|
||||||
// Read the font's configuration.
|
// Read the font's configuration.
|
||||||
// This will not be done for the default fonts, because they are not atomic and the default content does not need it.
|
// This will not be done for the default fonts, because they are not atomic and the default content does not need it.
|
||||||
|
|
||||||
std::vector<FolderEntry> folderdata;
|
std::vector<FileSys::FolderEntry> folderdata;
|
||||||
if (filetemplate != nullptr)
|
if (filetemplate != nullptr)
|
||||||
{
|
{
|
||||||
FStringf path("fonts/%s/", filetemplate);
|
FStringf path("fonts/%s/", filetemplate);
|
||||||
|
@ -398,7 +398,7 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
};
|
};
|
||||||
void FFont::ReadSheetFont(std::vector<FolderEntry> &folderdata, int width, int height, const DVector2 &Scale)
|
void FFont::ReadSheetFont(std::vector<FileSys::FolderEntry> &folderdata, int width, int height, const DVector2 &Scale)
|
||||||
{
|
{
|
||||||
TMap<int, FGameTexture*> charMap;
|
TMap<int, FGameTexture*> charMap;
|
||||||
int minchar = INT_MAX;
|
int minchar = INT_MAX;
|
||||||
|
|
|
@ -58,7 +58,7 @@ struct HexDataSource
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
void ParseDefinition(FResourceLump* font)
|
void ParseDefinition(FileSys::FResourceLump* font)
|
||||||
{
|
{
|
||||||
FScanner sc;
|
FScanner sc;
|
||||||
|
|
||||||
|
@ -109,8 +109,8 @@ class FHexFontChar : public FImageSource
|
||||||
public:
|
public:
|
||||||
FHexFontChar(uint8_t *sourcedata, int swidth, int width, int height);
|
FHexFontChar(uint8_t *sourcedata, int swidth, int width, int height);
|
||||||
|
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap* bmp, int conversion);
|
int CopyPixels(FBitmap* bmp, int conversion, int frame = 0);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
int SourceWidth;
|
int SourceWidth;
|
||||||
|
@ -144,7 +144,7 @@ FHexFontChar::FHexFontChar (uint8_t *sourcedata, int swidth, int width, int heig
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FHexFontChar::CreatePalettedPixels(int)
|
PalettedPixels FHexFontChar::CreatePalettedPixels(int, int)
|
||||||
{
|
{
|
||||||
int destSize = Width * Height;
|
int destSize = Width * Height;
|
||||||
PalettedPixels Pixels(destSize);
|
PalettedPixels Pixels(destSize);
|
||||||
|
@ -175,7 +175,7 @@ PalettedPixels FHexFontChar::CreatePalettedPixels(int)
|
||||||
return Pixels;
|
return Pixels;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FHexFontChar::CopyPixels(FBitmap* bmp, int conversion)
|
int FHexFontChar::CopyPixels(FBitmap* bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
if (conversion == luminance) conversion = normal; // luminance images have no use as an RGB source.
|
if (conversion == luminance) conversion = normal; // luminance images have no use as an RGB source.
|
||||||
PalEntry* palette = hexdata.ConsolePal;
|
PalEntry* palette = hexdata.ConsolePal;
|
||||||
|
@ -190,8 +190,8 @@ class FHexFontChar2 : public FHexFontChar
|
||||||
public:
|
public:
|
||||||
FHexFontChar2(uint8_t *sourcedata, int swidth, int width, int height);
|
FHexFontChar2(uint8_t *sourcedata, int swidth, int width, int height);
|
||||||
|
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap* bmp, int conversion);
|
int CopyPixels(FBitmap* bmp, int conversion, int frame = 0);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -216,7 +216,7 @@ FHexFontChar2::FHexFontChar2(uint8_t *sourcedata, int swidth, int width, int hei
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FHexFontChar2::CreatePalettedPixels(int)
|
PalettedPixels FHexFontChar2::CreatePalettedPixels(int, int)
|
||||||
{
|
{
|
||||||
int destSize = Width * Height;
|
int destSize = Width * Height;
|
||||||
PalettedPixels Pixels(destSize);
|
PalettedPixels Pixels(destSize);
|
||||||
|
@ -255,7 +255,7 @@ PalettedPixels FHexFontChar2::CreatePalettedPixels(int)
|
||||||
return Pixels;
|
return Pixels;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FHexFontChar2::CopyPixels(FBitmap* bmp, int conversion)
|
int FHexFontChar2::CopyPixels(FBitmap* bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
if (conversion == luminance) conversion = normal; // luminance images have no use as an RGB source.
|
if (conversion == luminance) conversion = normal; // luminance images have no use as an RGB source.
|
||||||
PalEntry* palette = hexdata.SmallPal;
|
PalEntry* palette = hexdata.SmallPal;
|
||||||
|
|
|
@ -124,7 +124,7 @@ FSingleLumpFont::FSingleLumpFont (const char *name, int lump) : FFont(lump)
|
||||||
|
|
||||||
FontName = name;
|
FontName = name;
|
||||||
|
|
||||||
FileData data1 = fileSystem.ReadFile (lump);
|
auto data1 = fileSystem.ReadFile (lump);
|
||||||
auto data = data1.GetBytes();
|
auto data = data1.GetBytes();
|
||||||
|
|
||||||
if (data[0] == 0xE1 && data[1] == 0xE6 && data[2] == 0xD5 && data[3] == 0x1A)
|
if (data[0] == 0xE1 && data[1] == 0xE6 && data[2] == 0xD5 && data[3] == 0x1A)
|
||||||
|
@ -474,7 +474,7 @@ void FSingleLumpFont::LoadBMF(int lump, const uint8_t *data)
|
||||||
|
|
||||||
void FSingleLumpFont::CheckFON1Chars()
|
void FSingleLumpFont::CheckFON1Chars()
|
||||||
{
|
{
|
||||||
FileData memLump = fileSystem.ReadFile(Lump);
|
auto memLump = fileSystem.ReadFile(Lump);
|
||||||
auto data = memLump.GetBytes();
|
auto data = memLump.GetBytes();
|
||||||
const uint8_t* data_p;
|
const uint8_t* data_p;
|
||||||
|
|
||||||
|
|
|
@ -109,7 +109,7 @@ FFont *V_GetFont(const char *name, const char *fontlumpname)
|
||||||
int lump = -1;
|
int lump = -1;
|
||||||
int folderfile = -1;
|
int folderfile = -1;
|
||||||
|
|
||||||
std::vector<FolderEntry> folderdata;
|
std::vector<FileSys::FolderEntry> folderdata;
|
||||||
FStringf path("fonts/%s/", name);
|
FStringf path("fonts/%s/", name);
|
||||||
|
|
||||||
// Use a folder-based font only if it comes from a later file than the single lump version.
|
// Use a folder-based font only if it comes from a later file than the single lump version.
|
||||||
|
|
|
@ -175,7 +175,7 @@ protected:
|
||||||
|
|
||||||
void FixXMoves();
|
void FixXMoves();
|
||||||
|
|
||||||
void ReadSheetFont(std::vector<FolderEntry> &folderdata, int width, int height, const DVector2 &Scale);
|
void ReadSheetFont(std::vector<FileSys::FolderEntry> &folderdata, int width, int height, const DVector2 &Scale);
|
||||||
|
|
||||||
EFontType Type = EFontType::Unknown;
|
EFontType Type = EFontType::Unknown;
|
||||||
FName AltFontName = NAME_None;
|
FName AltFontName = NAME_None;
|
||||||
|
|
|
@ -1519,7 +1519,7 @@ void M_ParseMenuDefs()
|
||||||
DefaultOptionMenuSettings->Reset();
|
DefaultOptionMenuSettings->Reset();
|
||||||
OptionSettings.mLinespacing = 17;
|
OptionSettings.mLinespacing = 17;
|
||||||
|
|
||||||
int IWADMenu = fileSystem.CheckNumForName("MENUDEF", ns_global, fileSystem.GetIwadNum());
|
int IWADMenu = fileSystem.CheckNumForName("MENUDEF", FileSys::ns_global, fileSystem.GetIwadNum());
|
||||||
|
|
||||||
while ((lump = fileSystem.FindLump ("MENUDEF", &lastlump)) != -1)
|
while ((lump = fileSystem.FindLump ("MENUDEF", &lastlump)) != -1)
|
||||||
{
|
{
|
||||||
|
|
|
@ -297,7 +297,7 @@ unsigned FSavegameManagerBase::ExtractSaveData(int index)
|
||||||
!node->bOldVersion &&
|
!node->bOldVersion &&
|
||||||
(resf = FResourceFile::OpenResourceFile(node->Filename.GetChars(), true)) != nullptr)
|
(resf = FResourceFile::OpenResourceFile(node->Filename.GetChars(), true)) != nullptr)
|
||||||
{
|
{
|
||||||
FResourceLump *info = resf->FindLump("info.json");
|
auto info = resf->FindLump("info.json");
|
||||||
if (info == nullptr)
|
if (info == nullptr)
|
||||||
{
|
{
|
||||||
// this should not happen because the file has already been verified.
|
// this should not happen because the file has already been verified.
|
||||||
|
@ -315,7 +315,7 @@ unsigned FSavegameManagerBase::ExtractSaveData(int index)
|
||||||
|
|
||||||
SaveCommentString = ExtractSaveComment(arc);
|
SaveCommentString = ExtractSaveComment(arc);
|
||||||
|
|
||||||
FResourceLump *pic = resf->FindLump("savepic.png");
|
auto pic = resf->FindLump("savepic.png");
|
||||||
if (pic != nullptr)
|
if (pic != nullptr)
|
||||||
{
|
{
|
||||||
FileReader picreader;
|
FileReader picreader;
|
||||||
|
|
|
@ -172,7 +172,7 @@ unsigned FindModel(const char * path, const char * modelfile, bool silent)
|
||||||
}
|
}
|
||||||
|
|
||||||
int len = fileSystem.FileLength(lump);
|
int len = fileSystem.FileLength(lump);
|
||||||
FileData lumpd = fileSystem.ReadFile(lump);
|
auto lumpd = fileSystem.ReadFile(lump);
|
||||||
const char * buffer = lumpd.GetString();
|
const char * buffer = lumpd.GetString();
|
||||||
|
|
||||||
if ( (size_t)fullname.LastIndexOf("_d.3d") == fullname.Len()-5 )
|
if ( (size_t)fullname.LastIndexOf("_d.3d") == fullname.Len()-5 )
|
||||||
|
|
|
@ -270,7 +270,7 @@ void IQMModel::LoadGeometry()
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
FileData lumpdata = fileSystem.ReadFile(mLumpNum);
|
auto lumpdata = fileSystem.ReadFile(mLumpNum);
|
||||||
IQMFileReader reader(lumpdata.GetMem(), (int)lumpdata.GetSize());
|
IQMFileReader reader(lumpdata.GetMem(), (int)lumpdata.GetSize());
|
||||||
|
|
||||||
Vertices.Resize(NumVertices);
|
Vertices.Resize(NumVertices);
|
||||||
|
|
|
@ -177,7 +177,7 @@ bool FDMDModel::Load(const char * path, int lumpnum, const char * buffer, int le
|
||||||
void FDMDModel::LoadGeometry()
|
void FDMDModel::LoadGeometry()
|
||||||
{
|
{
|
||||||
static int axis[3] = { VX, VY, VZ };
|
static int axis[3] = { VX, VY, VZ };
|
||||||
FileData lumpdata = fileSystem.ReadFile(mLumpNum);
|
auto lumpdata = fileSystem.ReadFile(mLumpNum);
|
||||||
auto buffer = lumpdata.GetString();
|
auto buffer = lumpdata.GetString();
|
||||||
texCoords = new FTexCoord[info.numTexCoords];
|
texCoords = new FTexCoord[info.numTexCoords];
|
||||||
memcpy(texCoords, buffer + info.offsetTexCoords, info.numTexCoords * sizeof(FTexCoord));
|
memcpy(texCoords, buffer + info.offsetTexCoords, info.numTexCoords * sizeof(FTexCoord));
|
||||||
|
@ -501,7 +501,7 @@ void FMD2Model::LoadGeometry()
|
||||||
{
|
{
|
||||||
static int axis[3] = { VX, VY, VZ };
|
static int axis[3] = { VX, VY, VZ };
|
||||||
uint8_t *md2_frames;
|
uint8_t *md2_frames;
|
||||||
FileData lumpdata = fileSystem.ReadFile(mLumpNum);
|
auto lumpdata = fileSystem.ReadFile(mLumpNum);
|
||||||
auto buffer = lumpdata.GetString();
|
auto buffer = lumpdata.GetString();
|
||||||
|
|
||||||
texCoords = new FTexCoord[info.numTexCoords];
|
texCoords = new FTexCoord[info.numTexCoords];
|
||||||
|
|
|
@ -189,7 +189,7 @@ bool FMD3Model::Load(const char * path, int lumpnum, const char * buffer, int le
|
||||||
|
|
||||||
void FMD3Model::LoadGeometry()
|
void FMD3Model::LoadGeometry()
|
||||||
{
|
{
|
||||||
FileData lumpdata = fileSystem.ReadFile(mLumpNum);
|
auto lumpdata = fileSystem.ReadFile(mLumpNum);
|
||||||
auto buffer = lumpdata.GetString();
|
auto buffer = lumpdata.GetString();
|
||||||
md3_header_t * hdr = (md3_header_t *)buffer;
|
md3_header_t * hdr = (md3_header_t *)buffer;
|
||||||
md3_surface_t * surf = (md3_surface_t*)(buffer + LittleLong(hdr->Ofs_Surfaces));
|
md3_surface_t * surf = (md3_surface_t*)(buffer + LittleLong(hdr->Ofs_Surfaces));
|
||||||
|
|
|
@ -70,9 +70,9 @@ bool FUE1Model::Load( const char *filename, int lumpnum, const char *buffer, int
|
||||||
void FUE1Model::LoadGeometry()
|
void FUE1Model::LoadGeometry()
|
||||||
{
|
{
|
||||||
const char *buffer, *buffer2;
|
const char *buffer, *buffer2;
|
||||||
FileData lump = fileSystem.ReadFile(mDataLump);
|
auto lump = fileSystem.ReadFile(mDataLump);
|
||||||
buffer = lump.GetString();
|
buffer = lump.GetString();
|
||||||
FileData lump2 = fileSystem.ReadFile(mAnivLump);
|
auto lump2 = fileSystem.ReadFile(mAnivLump);
|
||||||
buffer2 = lump2.GetString();
|
buffer2 = lump2.GetString();
|
||||||
// map structures
|
// map structures
|
||||||
dhead = (const d3dhead*)(buffer);
|
dhead = (const d3dhead*)(buffer);
|
||||||
|
|
|
@ -57,8 +57,8 @@ class FVoxelTexture : public FImageSource
|
||||||
public:
|
public:
|
||||||
FVoxelTexture(FVoxel *voxel);
|
FVoxelTexture(FVoxel *voxel);
|
||||||
|
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
FVoxel *SourceVox;
|
FVoxel *SourceVox;
|
||||||
|
@ -84,7 +84,7 @@ FVoxelTexture::FVoxelTexture(FVoxel *vox)
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
PalettedPixels FVoxelTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FVoxelTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
// GetPixels gets called when a translated palette is used so we still need to implement it here.
|
// GetPixels gets called when a translated palette is used so we still need to implement it here.
|
||||||
PalettedPixels Pixels(256);
|
PalettedPixels Pixels(256);
|
||||||
|
@ -123,7 +123,7 @@ PalettedPixels FVoxelTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
int FVoxelTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FVoxelTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalEntry pe[256];
|
PalEntry pe[256];
|
||||||
uint8_t bitmap[256];
|
uint8_t bitmap[256];
|
||||||
|
|
|
@ -161,7 +161,7 @@ FVoxel *R_LoadKVX(int lumpnum)
|
||||||
int mip, maxmipsize;
|
int mip, maxmipsize;
|
||||||
int i, j, n;
|
int i, j, n;
|
||||||
|
|
||||||
FileData lump = fileSystem.ReadFile(lumpnum); // FileData adds an extra 0 byte to the end.
|
auto lump = fileSystem.ReadFile(lumpnum); // FileData adds an extra 0 byte to the end.
|
||||||
auto rawvoxel = lump.GetBytes();
|
auto rawvoxel = lump.GetBytes();
|
||||||
int voxelsize = (int)(lump.GetSize()-1);
|
int voxelsize = (int)(lump.GetSize()-1);
|
||||||
|
|
||||||
|
|
|
@ -282,7 +282,8 @@ extern bool AppActive;
|
||||||
{
|
{
|
||||||
ZD_UNUSED(aNotification);
|
ZD_UNUSED(aNotification);
|
||||||
|
|
||||||
S_SetSoundPaused(1);
|
if (GSnd)
|
||||||
|
S_SetSoundPaused(1);
|
||||||
|
|
||||||
AppActive = true;
|
AppActive = true;
|
||||||
}
|
}
|
||||||
|
@ -291,7 +292,8 @@ extern bool AppActive;
|
||||||
{
|
{
|
||||||
ZD_UNUSED(aNotification);
|
ZD_UNUSED(aNotification);
|
||||||
|
|
||||||
S_SetSoundPaused(0);
|
if (GSnd)
|
||||||
|
S_SetSoundPaused(0);
|
||||||
|
|
||||||
AppActive = false;
|
AppActive = false;
|
||||||
}
|
}
|
||||||
|
|
|
@ -171,6 +171,17 @@ unsigned int I_MakeRNGSeed()
|
||||||
return static_cast<unsigned int>(arc4random());
|
return static_cast<unsigned int>(arc4random());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FString I_GetCWD()
|
||||||
|
{
|
||||||
|
NSString *currentpath = [[NSFileManager defaultManager] currentDirectoryPath];
|
||||||
|
return currentpath.UTF8String;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool I_ChDir(const char* path)
|
||||||
|
{
|
||||||
|
return [[NSFileManager defaultManager] changeCurrentDirectoryPath:[NSString stringWithUTF8String:path]];
|
||||||
|
}
|
||||||
|
|
||||||
void I_OpenShellFolder(const char* folder)
|
void I_OpenShellFolder(const char* folder)
|
||||||
{
|
{
|
||||||
NSFileManager *filemgr = [NSFileManager defaultManager];
|
NSFileManager *filemgr = [NSFileManager defaultManager];
|
||||||
|
|
|
@ -406,6 +406,23 @@ FString I_GetFromClipboard (bool use_primary_selection)
|
||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FString I_GetCWD()
|
||||||
|
{
|
||||||
|
char* curdir = getcwd(NULL,0);
|
||||||
|
if (!curdir)
|
||||||
|
{
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
FString ret(curdir);
|
||||||
|
free(curdir);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool I_ChDir(const char* path)
|
||||||
|
{
|
||||||
|
return chdir(path) == 0;
|
||||||
|
}
|
||||||
|
|
||||||
// Return a random seed, preferably one with lots of entropy.
|
// Return a random seed, preferably one with lots of entropy.
|
||||||
unsigned int I_MakeRNGSeed()
|
unsigned int I_MakeRNGSeed()
|
||||||
{
|
{
|
||||||
|
|
|
@ -958,6 +958,25 @@ void I_SetThreadNumaNode(std::thread &thread, int numaNode)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FString I_GetCWD()
|
||||||
|
{
|
||||||
|
auto len = GetCurrentDirectoryW(0, nullptr);
|
||||||
|
TArray<wchar_t> curdir(len + 1, true);
|
||||||
|
if (!GetCurrentDirectoryW(len + 1, curdir.Data()))
|
||||||
|
{
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
FString returnv(curdir.Data());
|
||||||
|
FixPathSeperator(returnv);
|
||||||
|
return returnv;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool I_ChDir(const char* path)
|
||||||
|
{
|
||||||
|
return SetCurrentDirectoryW(WideString(path).c_str());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void I_OpenShellFolder(const char* infolder)
|
void I_OpenShellFolder(const char* infolder)
|
||||||
{
|
{
|
||||||
auto len = GetCurrentDirectoryW(0, nullptr);
|
auto len = GetCurrentDirectoryW(0, nullptr);
|
||||||
|
|
|
@ -80,5 +80,7 @@ int I_GetNumaNodeThreadCount(int numaNode);
|
||||||
void I_SetThreadNumaNode(std::thread &thread, int numaNode);
|
void I_SetThreadNumaNode(std::thread &thread, int numaNode);
|
||||||
|
|
||||||
void I_OpenShellFolder(const char*);
|
void I_OpenShellFolder(const char*);
|
||||||
|
FString I_GetCWD();
|
||||||
|
bool I_ChDir(const char* path);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -431,17 +431,13 @@ bool FShader::Load(const char * name, const char * vert_prog_lump, const char *
|
||||||
{
|
{
|
||||||
int pl_lump = fileSystem.CheckNumForFullName("shaders/glsl/func_defaultmat2.fp", 0);
|
int pl_lump = fileSystem.CheckNumForFullName("shaders/glsl/func_defaultmat2.fp", 0);
|
||||||
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders/glsl/func_defaultmat2.fp");
|
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders/glsl/func_defaultmat2.fp");
|
||||||
FileData pl_data = fileSystem.ReadFile(pl_lump);
|
fp_comb << "\n" << GetStringFromLump(pl_lump);
|
||||||
fp_comb << "\n";
|
|
||||||
fp_comb.AppendCStrPart(pl_data.GetString(), pl_data.GetSize());
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
int pl_lump = fileSystem.CheckNumForFullName("shaders/glsl/func_defaultmat.fp", 0);
|
int pl_lump = fileSystem.CheckNumForFullName("shaders/glsl/func_defaultmat.fp", 0);
|
||||||
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders/glsl/func_defaultmat.fp");
|
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders/glsl/func_defaultmat.fp");
|
||||||
FileData pl_data = fileSystem.ReadFile(pl_lump);
|
fp_comb << "\n" << GetStringFromLump(pl_lump);
|
||||||
fp_comb << "\n";
|
|
||||||
fp_comb.AppendCStrPart(pl_data.GetString(), pl_data.GetSize());
|
|
||||||
|
|
||||||
if (pp_data.IndexOf("ProcessTexel") < 0)
|
if (pp_data.IndexOf("ProcessTexel") < 0)
|
||||||
{
|
{
|
||||||
|
@ -467,9 +463,7 @@ bool FShader::Load(const char * name, const char * vert_prog_lump, const char *
|
||||||
{
|
{
|
||||||
int pl_lump = fileSystem.CheckNumForFullName("shaders/glsl/func_defaultlight.fp", 0);
|
int pl_lump = fileSystem.CheckNumForFullName("shaders/glsl/func_defaultlight.fp", 0);
|
||||||
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders/glsl/func_defaultlight.fp");
|
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders/glsl/func_defaultlight.fp");
|
||||||
FileData pl_data = fileSystem.ReadFile(pl_lump);
|
fp_comb << "\n" << GetStringFromLump(pl_lump);
|
||||||
fp_comb << "\n";
|
|
||||||
fp_comb.AppendCStrPart(pl_data.GetString(), pl_data.GetSize());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// ProcessMaterial must be considered broken because it requires the user to fill in data they possibly cannot know all about.
|
// ProcessMaterial must be considered broken because it requires the user to fill in data they possibly cannot know all about.
|
||||||
|
@ -491,8 +485,7 @@ bool FShader::Load(const char * name, const char * vert_prog_lump, const char *
|
||||||
{
|
{
|
||||||
int pp_lump = fileSystem.CheckNumForFullName(light_fragprog, 0);
|
int pp_lump = fileSystem.CheckNumForFullName(light_fragprog, 0);
|
||||||
if (pp_lump == -1) I_Error("Unable to load '%s'", light_fragprog);
|
if (pp_lump == -1) I_Error("Unable to load '%s'", light_fragprog);
|
||||||
FileData pp_data = fileSystem.ReadFile(pp_lump);
|
fp_comb << GetStringFromLump(pp_lump) << "\n";
|
||||||
fp_comb.AppendCStrPart(pp_data.GetString(), pp_data.GetSize()) << "\n";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (gl.flags & RFL_NO_CLIP_PLANES)
|
if (gl.flags & RFL_NO_CLIP_PLANES)
|
||||||
|
|
|
@ -383,11 +383,11 @@ bool FShader::Load(const char * name, const char * vert_prog_lump_, const char *
|
||||||
|
|
||||||
int vp_lump = fileSystem.CheckNumForFullName(vert_prog_lump, 0);
|
int vp_lump = fileSystem.CheckNumForFullName(vert_prog_lump, 0);
|
||||||
if (vp_lump == -1) I_Error("Unable to load '%s'", vert_prog_lump.GetChars());
|
if (vp_lump == -1) I_Error("Unable to load '%s'", vert_prog_lump.GetChars());
|
||||||
FileData vp_data = fileSystem.ReadFile(vp_lump);
|
auto vp_data = fileSystem.ReadFile(vp_lump);
|
||||||
|
|
||||||
int fp_lump = fileSystem.CheckNumForFullName(frag_prog_lump, 0);
|
int fp_lump = fileSystem.CheckNumForFullName(frag_prog_lump, 0);
|
||||||
if (fp_lump == -1) I_Error("Unable to load '%s'", frag_prog_lump.GetChars());
|
if (fp_lump == -1) I_Error("Unable to load '%s'", frag_prog_lump.GetChars());
|
||||||
FileData fp_data = fileSystem.ReadFile(fp_lump);
|
auto fp_data = fileSystem.ReadFile(fp_lump);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -433,17 +433,13 @@ bool FShader::Load(const char * name, const char * vert_prog_lump_, const char *
|
||||||
{
|
{
|
||||||
int pl_lump = fileSystem.CheckNumForFullName("shaders_gles/glsl/func_defaultmat2.fp", 0);
|
int pl_lump = fileSystem.CheckNumForFullName("shaders_gles/glsl/func_defaultmat2.fp", 0);
|
||||||
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders_gles/glsl/func_defaultmat2.fp");
|
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders_gles/glsl/func_defaultmat2.fp");
|
||||||
FileData pl_data = fileSystem.ReadFile(pl_lump);
|
fp_comb << "\n" << GetStringFromLump(pl_lump);
|
||||||
fp_comb << "\n";
|
|
||||||
fp_comb.AppendCStrPart(pl_data.GetString(), pl_data.GetSize());
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
int pl_lump = fileSystem.CheckNumForFullName("shaders_gles/glsl/func_defaultmat.fp", 0);
|
int pl_lump = fileSystem.CheckNumForFullName("shaders_gles/glsl/func_defaultmat.fp", 0);
|
||||||
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders_gles/glsl/func_defaultmat.fp");
|
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders_gles/glsl/func_defaultmat.fp");
|
||||||
FileData pl_data = fileSystem.ReadFile(pl_lump);
|
fp_comb << "\n" << GetStringFromLump(pl_lump);
|
||||||
fp_comb << "\n";
|
|
||||||
fp_comb.AppendCStrPart(pl_data.GetString(), pl_data.GetSize());
|
|
||||||
|
|
||||||
if (pp_data.IndexOf("ProcessTexel") < 0)
|
if (pp_data.IndexOf("ProcessTexel") < 0)
|
||||||
{
|
{
|
||||||
|
@ -469,9 +465,7 @@ bool FShader::Load(const char * name, const char * vert_prog_lump_, const char *
|
||||||
{
|
{
|
||||||
int pl_lump = fileSystem.CheckNumForFullName("shaders_gles/glsl/func_defaultlight.fp", 0);
|
int pl_lump = fileSystem.CheckNumForFullName("shaders_gles/glsl/func_defaultlight.fp", 0);
|
||||||
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders_gles/glsl/func_defaultlight.fp");
|
if (pl_lump == -1) I_Error("Unable to load '%s'", "shaders_gles/glsl/func_defaultlight.fp");
|
||||||
FileData pl_data = fileSystem.ReadFile(pl_lump);
|
fp_comb << "\n" << GetStringFromLump(pl_lump);
|
||||||
fp_comb << "\n";
|
|
||||||
fp_comb.AppendCStrPart(pl_data.GetString(), pl_data.GetSize());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// ProcessMaterial must be considered broken because it requires the user to fill in data they possibly cannot know all about.
|
// ProcessMaterial must be considered broken because it requires the user to fill in data they possibly cannot know all about.
|
||||||
|
@ -493,8 +487,7 @@ bool FShader::Load(const char * name, const char * vert_prog_lump_, const char *
|
||||||
{
|
{
|
||||||
int pp_lump = fileSystem.CheckNumForFullName(light_fragprog, 0);
|
int pp_lump = fileSystem.CheckNumForFullName(light_fragprog, 0);
|
||||||
if (pp_lump == -1) I_Error("Unable to load '%s'", light_fragprog.GetChars());
|
if (pp_lump == -1) I_Error("Unable to load '%s'", light_fragprog.GetChars());
|
||||||
FileData pp_data = fileSystem.ReadFile(pp_lump);
|
fp_comb << GetStringFromLump(pp_lump) << "\n";
|
||||||
fp_comb.AppendCStrPart(pp_data.GetString(), pp_data.GetSize()) << "\n";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (gles.flags & RFL_NO_CLIP_PLANES)
|
if (gles.flags & RFL_NO_CLIP_PLANES)
|
||||||
|
|
|
@ -45,6 +45,7 @@
|
||||||
#include "hw_shadowmap.h"
|
#include "hw_shadowmap.h"
|
||||||
#include "hw_levelmesh.h"
|
#include "hw_levelmesh.h"
|
||||||
#include "buffers.h"
|
#include "buffers.h"
|
||||||
|
#include "files.h"
|
||||||
|
|
||||||
|
|
||||||
struct FPortalSceneState;
|
struct FPortalSceneState;
|
||||||
|
@ -90,7 +91,6 @@ EXTERN_CVAR(Int, win_h)
|
||||||
EXTERN_CVAR(Bool, win_maximized)
|
EXTERN_CVAR(Bool, win_maximized)
|
||||||
|
|
||||||
struct FColormap;
|
struct FColormap;
|
||||||
class FileWriter;
|
|
||||||
enum FTextureFormat : uint32_t;
|
enum FTextureFormat : uint32_t;
|
||||||
class FModelRenderer;
|
class FModelRenderer;
|
||||||
struct SamplerUniform;
|
struct SamplerUniform;
|
||||||
|
|
|
@ -473,7 +473,7 @@ FString VkShaderManager::LoadPrivateShaderLump(const char *lumpname)
|
||||||
{
|
{
|
||||||
int lump = fileSystem.CheckNumForFullName(lumpname, 0);
|
int lump = fileSystem.CheckNumForFullName(lumpname, 0);
|
||||||
if (lump == -1) I_Error("Unable to load '%s'", lumpname);
|
if (lump == -1) I_Error("Unable to load '%s'", lumpname);
|
||||||
FileData data = fileSystem.ReadFile(lump);
|
auto data = fileSystem.ReadFile(lump);
|
||||||
return GetStringFromLump(lump);
|
return GetStringFromLump(lump);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -72,7 +72,7 @@ FGenericStartScreen::FGenericStartScreen(int max_progress)
|
||||||
: FStartScreen(max_progress)
|
: FStartScreen(max_progress)
|
||||||
{
|
{
|
||||||
// at this point we do not have a working texture manager yet, so we have to do the lookup via the file system
|
// at this point we do not have a working texture manager yet, so we have to do the lookup via the file system
|
||||||
int startup_lump = fileSystem.CheckNumForName("GZDOOM", ns_graphics);
|
int startup_lump = fileSystem.CheckNumForName("GZDOOM", FileSys::ns_graphics);
|
||||||
|
|
||||||
StartupBitmap.Create(640, 480);
|
StartupBitmap.Create(640, 480);
|
||||||
ClearBlock(StartupBitmap, { 0, 0, 0, 255 }, 0, 0, 640, 480);
|
ClearBlock(StartupBitmap, { 0, 0, 0, 255 }, 0, 0, 640, 480);
|
||||||
|
|
|
@ -81,9 +81,9 @@ FHexenStartScreen::FHexenStartScreen(int max_progress)
|
||||||
: FStartScreen(max_progress)
|
: FStartScreen(max_progress)
|
||||||
{
|
{
|
||||||
// at this point we do not have a working texture manager yet, so we have to do the lookup via the file system
|
// at this point we do not have a working texture manager yet, so we have to do the lookup via the file system
|
||||||
int startup_lump = fileSystem.CheckNumForName("STARTUP", ns_graphics);
|
int startup_lump = fileSystem.CheckNumForName("STARTUP", FileSys::ns_graphics);
|
||||||
int netnotch_lump = fileSystem.CheckNumForName("NETNOTCH", ns_graphics);
|
int netnotch_lump = fileSystem.CheckNumForName("NETNOTCH", FileSys::ns_graphics);
|
||||||
int notch_lump = fileSystem.CheckNumForName("NOTCH", ns_graphics);
|
int notch_lump = fileSystem.CheckNumForName("NOTCH", FileSys::ns_graphics);
|
||||||
|
|
||||||
// For backwards compatibility we also need to look in the default namespace, because these were previously not handled as graphics.
|
// For backwards compatibility we also need to look in the default namespace, because these were previously not handled as graphics.
|
||||||
if (startup_lump == -1) startup_lump = fileSystem.CheckNumForName("STARTUP");
|
if (startup_lump == -1) startup_lump = fileSystem.CheckNumForName("STARTUP");
|
||||||
|
|
|
@ -119,7 +119,7 @@ FStrifeStartScreen::FStrifeStartScreen(int max_progress)
|
||||||
// Load the animated overlays.
|
// Load the animated overlays.
|
||||||
for (size_t i = 0; i < countof(StrifeStartupPicNames); ++i)
|
for (size_t i = 0; i < countof(StrifeStartupPicNames); ++i)
|
||||||
{
|
{
|
||||||
int lumpnum = fileSystem.CheckNumForName(StrifeStartupPicNames[i], ns_graphics);
|
int lumpnum = fileSystem.CheckNumForName(StrifeStartupPicNames[i], FileSys::ns_graphics);
|
||||||
if (lumpnum < 0) lumpnum = fileSystem.CheckNumForName(StrifeStartupPicNames[i]);
|
if (lumpnum < 0) lumpnum = fileSystem.CheckNumForName(StrifeStartupPicNames[i]);
|
||||||
|
|
||||||
if (lumpnum >= 0)
|
if (lumpnum >= 0)
|
||||||
|
|
|
@ -51,8 +51,8 @@ class FAnmTexture : public FImageSource
|
||||||
public:
|
public:
|
||||||
FAnmTexture (int lumpnum, int w, int h);
|
FAnmTexture (int lumpnum, int w, int h);
|
||||||
void ReadFrame(uint8_t *buffer, uint8_t *palette);
|
void ReadFrame(uint8_t *buffer, uint8_t *palette);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -103,7 +103,7 @@ FAnmTexture::FAnmTexture (int lumpnum, int w, int h)
|
||||||
|
|
||||||
void FAnmTexture::ReadFrame(uint8_t *pixels, uint8_t *palette)
|
void FAnmTexture::ReadFrame(uint8_t *pixels, uint8_t *palette)
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
|
|
||||||
anim_t anim;
|
anim_t anim;
|
||||||
|
@ -127,7 +127,7 @@ void FAnmTexture::ReadFrame(uint8_t *pixels, uint8_t *palette)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FAnmTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FAnmTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalettedPixels pixels(Width*Height);
|
PalettedPixels pixels(Width*Height);
|
||||||
uint8_t buffer[64000];
|
uint8_t buffer[64000];
|
||||||
|
@ -149,7 +149,7 @@ PalettedPixels FAnmTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FAnmTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FAnmTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
uint8_t buffer[64000];
|
uint8_t buffer[64000];
|
||||||
uint8_t palette[768];
|
uint8_t palette[768];
|
||||||
|
|
|
@ -50,7 +50,7 @@ class FAutomapTexture : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FAutomapTexture(int lumpnum);
|
FAutomapTexture(int lumpnum);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -89,10 +89,10 @@ FAutomapTexture::FAutomapTexture (int lumpnum)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FAutomapTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FAutomapTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
int x, y;
|
int x, y;
|
||||||
FileData data = fileSystem.ReadFile (SourceLump);
|
auto data = fileSystem.ReadFile (SourceLump);
|
||||||
auto indata = data.GetBytes();
|
auto indata = data.GetBytes();
|
||||||
|
|
||||||
PalettedPixels Pixels(Width * Height);
|
PalettedPixels Pixels(Width * Height);
|
||||||
|
|
|
@ -43,7 +43,7 @@ class FBrightmapTexture : public FImageSource
|
||||||
public:
|
public:
|
||||||
FBrightmapTexture (FImageSource *source);
|
FBrightmapTexture (FImageSource *source);
|
||||||
|
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
FImageSource *SourcePic;
|
FImageSource *SourcePic;
|
||||||
|
@ -65,7 +65,7 @@ FBrightmapTexture::FBrightmapTexture (FImageSource *source)
|
||||||
bMasked = false;
|
bMasked = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FBrightmapTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FBrightmapTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
SourcePic->CopyTranslatedPixels(bmp, GPalette.GlobalBrightmap.Palette);
|
SourcePic->CopyTranslatedPixels(bmp, GPalette.GlobalBrightmap.Palette);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -55,7 +55,7 @@ FBuildTexture::FBuildTexture(const FString &pathprefix, int tilenum, const uint8
|
||||||
TopOffset = top;
|
TopOffset = top;
|
||||||
}
|
}
|
||||||
|
|
||||||
PalettedPixels FBuildTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FBuildTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalettedPixels Pixels(Width * Height);
|
PalettedPixels Pixels(Width * Height);
|
||||||
FRemapTable *Remap = Translation;
|
FRemapTable *Remap = Translation;
|
||||||
|
@ -67,7 +67,7 @@ PalettedPixels FBuildTexture::CreatePalettedPixels(int conversion)
|
||||||
return Pixels;
|
return Pixels;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FBuildTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FBuildTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalEntry *Remap = Translation->Palette;
|
PalEntry *Remap = Translation->Palette;
|
||||||
bmp->CopyPixelData(0, 0, RawPixels, Width, Height, Height, 1, 0, Remap);
|
bmp->CopyPixelData(0, 0, RawPixels, Width, Height, Height, 1, 0, Remap);
|
||||||
|
|
|
@ -164,7 +164,7 @@ class FDDSTexture : public FImageSource
|
||||||
public:
|
public:
|
||||||
FDDSTexture (FileReader &lump, int lumpnum, void *surfdesc);
|
FDDSTexture (FileReader &lump, int lumpnum, void *surfdesc);
|
||||||
|
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
uint32_t Format;
|
uint32_t Format;
|
||||||
|
@ -183,7 +183,7 @@ protected:
|
||||||
void DecompressDXT3 (FileReader &lump, bool premultiplied, uint8_t *buffer, int pixelmode);
|
void DecompressDXT3 (FileReader &lump, bool premultiplied, uint8_t *buffer, int pixelmode);
|
||||||
void DecompressDXT5 (FileReader &lump, bool premultiplied, uint8_t *buffer, int pixelmode);
|
void DecompressDXT5 (FileReader &lump, bool premultiplied, uint8_t *buffer, int pixelmode);
|
||||||
|
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
|
|
||||||
friend class FTexture;
|
friend class FTexture;
|
||||||
};
|
};
|
||||||
|
@ -372,7 +372,7 @@ void FDDSTexture::CalcBitShift (uint32_t mask, uint8_t *lshiftp, uint8_t *rshift
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FDDSTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FDDSTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
auto lump = fileSystem.OpenFileReader (SourceLump);
|
auto lump = fileSystem.OpenFileReader (SourceLump);
|
||||||
|
|
||||||
|
@ -781,7 +781,7 @@ void FDDSTexture::DecompressDXT5 (FileReader &lump, bool premultiplied, uint8_t
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
int FDDSTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FDDSTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
auto lump = fileSystem.OpenFileReader (SourceLump);
|
auto lump = fileSystem.OpenFileReader (SourceLump);
|
||||||
|
|
||||||
|
|
|
@ -49,7 +49,7 @@ class FEmptyTexture : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FEmptyTexture (int lumpnum);
|
FEmptyTexture (int lumpnum);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -94,7 +94,7 @@ FEmptyTexture::FEmptyTexture (int lumpnum)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FEmptyTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FEmptyTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
static uint8_t p;
|
static uint8_t p;
|
||||||
PalettedPixels Pixel(&p, 1);
|
PalettedPixels Pixel(&p, 1);
|
||||||
|
|
|
@ -48,7 +48,7 @@ class FFlatTexture : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FFlatTexture (int lumpnum);
|
FFlatTexture (int lumpnum);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -102,7 +102,7 @@ FFlatTexture::FFlatTexture (int lumpnum)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FFlatTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FFlatTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
auto lump = fileSystem.OpenFileReader (SourceLump);
|
auto lump = fileSystem.OpenFileReader (SourceLump);
|
||||||
PalettedPixels Pixels(Width*Height);
|
PalettedPixels Pixels(Width*Height);
|
||||||
|
|
|
@ -66,7 +66,7 @@ FFontChar2::FFontChar2(int sourcelump, int sourcepos, int width, int height, int
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FFontChar2::CreatePalettedPixels(int)
|
PalettedPixels FFontChar2::CreatePalettedPixels(int, int)
|
||||||
{
|
{
|
||||||
auto lump = fileSystem.OpenFileReader(SourceLump);
|
auto lump = fileSystem.OpenFileReader(SourceLump);
|
||||||
int destSize = Width * Height;
|
int destSize = Width * Height;
|
||||||
|
@ -170,7 +170,7 @@ PalettedPixels FFontChar2::CreatePalettedPixels(int)
|
||||||
return Pixels;
|
return Pixels;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FFontChar2::CopyPixels(FBitmap* bmp, int conversion)
|
int FFontChar2::CopyPixels(FBitmap* bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
if (conversion == luminance) conversion = normal; // luminance images have no use as an RGB source.
|
if (conversion == luminance) conversion = normal; // luminance images have no use as an RGB source.
|
||||||
auto ppix = CreatePalettedPixels(conversion);
|
auto ppix = CreatePalettedPixels(conversion);
|
||||||
|
|
|
@ -6,8 +6,8 @@ class FFontChar2 : public FImageSource
|
||||||
public:
|
public:
|
||||||
FFontChar2 (int sourcelump, int sourcepos, int width, int height, int leftofs=0, int topofs=0);
|
FFontChar2 (int sourcelump, int sourcepos, int width, int height, int leftofs=0, int topofs=0);
|
||||||
|
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap* bmp, int conversion);
|
int CopyPixels(FBitmap* bmp, int conversion, int frame = 0);
|
||||||
|
|
||||||
void SetSourceRemap(const PalEntry* sourceremap)
|
void SetSourceRemap(const PalEntry* sourceremap)
|
||||||
{
|
{
|
||||||
|
|
|
@ -66,8 +66,8 @@ class FIMGZTexture : public FImageSource
|
||||||
|
|
||||||
public:
|
public:
|
||||||
FIMGZTexture (int lumpnum, uint16_t w, uint16_t h, int16_t l, int16_t t, bool isalpha);
|
FIMGZTexture (int lumpnum, uint16_t w, uint16_t h, int16_t l, int16_t t, bool isalpha);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -118,9 +118,9 @@ FIMGZTexture::FIMGZTexture (int lumpnum, uint16_t w, uint16_t h, int16_t l, int1
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FIMGZTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FIMGZTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto imgz = (const ImageHeader *)lump.GetMem();
|
auto imgz = (const ImageHeader *)lump.GetMem();
|
||||||
const uint8_t *data = (const uint8_t *)&imgz[1];
|
const uint8_t *data = (const uint8_t *)&imgz[1];
|
||||||
|
|
||||||
|
@ -198,7 +198,7 @@ PalettedPixels FIMGZTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FIMGZTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FIMGZTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
if (!isalpha) return FImageSource::CopyPixels(bmp, conversion);
|
if (!isalpha) return FImageSource::CopyPixels(bmp, conversion);
|
||||||
else return CopyTranslatedPixels(bmp, GPalette.GrayscaleMap.Palette);
|
else return CopyTranslatedPixels(bmp, GPalette.GrayscaleMap.Palette);
|
||||||
|
|
|
@ -185,8 +185,8 @@ class FJPEGTexture : public FImageSource
|
||||||
public:
|
public:
|
||||||
FJPEGTexture (int lumpnum, int width, int height);
|
FJPEGTexture (int lumpnum, int width, int height);
|
||||||
|
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -260,7 +260,7 @@ FJPEGTexture::FJPEGTexture (int lumpnum, int width, int height)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FJPEGTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FJPEGTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
auto lump = fileSystem.OpenFileReader (SourceLump);
|
auto lump = fileSystem.OpenFileReader (SourceLump);
|
||||||
JSAMPLE *buff = NULL;
|
JSAMPLE *buff = NULL;
|
||||||
|
@ -401,7 +401,7 @@ PalettedPixels FJPEGTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
int FJPEGTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FJPEGTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalEntry pe[256];
|
PalEntry pe[256];
|
||||||
|
|
||||||
|
|
|
@ -201,7 +201,7 @@ void FMultiPatchTexture::CopyToBlock(uint8_t *dest, int dwidth, int dheight, FIm
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FMultiPatchTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FMultiPatchTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
int numpix = Width * Height;
|
int numpix = Width * Height;
|
||||||
uint8_t blendwork[256];
|
uint8_t blendwork[256];
|
||||||
|
@ -278,7 +278,7 @@ PalettedPixels FMultiPatchTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
int FMultiPatchTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FMultiPatchTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
int retv = -1;
|
int retv = -1;
|
||||||
|
|
||||||
|
|
|
@ -74,8 +74,8 @@ protected:
|
||||||
TexPart *Parts;
|
TexPart *Parts;
|
||||||
|
|
||||||
// The getters must optionally redirect if it's a simple one-patch texture.
|
// The getters must optionally redirect if it's a simple one-patch texture.
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
void CopyToBlock(uint8_t *dest, int dwidth, int dheight, FImageSource *source, int xpos, int ypos, int rotate, const uint8_t *translation, int style);
|
void CopyToBlock(uint8_t *dest, int dwidth, int dheight, FImageSource *source, int xpos, int ypos, int rotate, const uint8_t *translation, int style);
|
||||||
void CollectForPrecache(PrecacheInfo &info, bool requiretruecolor) override;
|
void CollectForPrecache(PrecacheInfo &info, bool requiretruecolor) override;
|
||||||
|
|
||||||
|
|
|
@ -62,8 +62,8 @@ class FPatchTexture : public FImageSource
|
||||||
bool isalpha = false;
|
bool isalpha = false;
|
||||||
public:
|
public:
|
||||||
FPatchTexture (int lumpnum, int w, int h, int lo, int to, bool isalphatex);
|
FPatchTexture (int lumpnum, int w, int h, int lo, int to, bool isalphatex);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
bool SupportRemap0() override { return !badflag; }
|
bool SupportRemap0() override { return !badflag; }
|
||||||
void DetectBadPatches();
|
void DetectBadPatches();
|
||||||
};
|
};
|
||||||
|
@ -167,14 +167,14 @@ FPatchTexture::FPatchTexture (int lumpnum, int w, int h, int lo, int to, bool is
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FPatchTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FPatchTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
uint8_t *remap, remaptable[256];
|
uint8_t *remap, remaptable[256];
|
||||||
int numspans;
|
int numspans;
|
||||||
const column_t *maxcol;
|
const column_t *maxcol;
|
||||||
int x;
|
int x;
|
||||||
|
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
const patch_t *patch = (const patch_t *)lump.GetMem();
|
const patch_t *patch = (const patch_t *)lump.GetMem();
|
||||||
|
|
||||||
maxcol = (const column_t *)((const uint8_t *)patch + fileSystem.FileLength (SourceLump) - 3);
|
maxcol = (const column_t *)((const uint8_t *)patch + fileSystem.FileLength (SourceLump) - 3);
|
||||||
|
@ -264,7 +264,7 @@ PalettedPixels FPatchTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FPatchTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FPatchTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
if (!isalpha) return FImageSource::CopyPixels(bmp, conversion);
|
if (!isalpha) return FImageSource::CopyPixels(bmp, conversion);
|
||||||
else return CopyTranslatedPixels(bmp, GPalette.GrayscaleMap.Palette);
|
else return CopyTranslatedPixels(bmp, GPalette.GrayscaleMap.Palette);
|
||||||
|
@ -284,7 +284,7 @@ void FPatchTexture::DetectBadPatches ()
|
||||||
// Check if this patch is likely to be a problem.
|
// Check if this patch is likely to be a problem.
|
||||||
// It must be 256 pixels tall, and all its columns must have exactly
|
// It must be 256 pixels tall, and all its columns must have exactly
|
||||||
// one post, where each post has a supposed length of 0.
|
// one post, where each post has a supposed length of 0.
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
const patch_t *realpatch = (patch_t *)lump.GetMem();
|
const patch_t *realpatch = (patch_t *)lump.GetMem();
|
||||||
const uint32_t *cofs = realpatch->columnofs;
|
const uint32_t *cofs = realpatch->columnofs;
|
||||||
int x, x2 = LittleShort(realpatch->width);
|
int x, x2 = LittleShort(realpatch->width);
|
||||||
|
|
|
@ -84,7 +84,7 @@ class FPCXTexture : public FImageSource
|
||||||
public:
|
public:
|
||||||
FPCXTexture (int lumpnum, PCXHeader &);
|
FPCXTexture (int lumpnum, PCXHeader &);
|
||||||
|
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void ReadPCX1bit (uint8_t *dst, FileReader & lump, PCXHeader *hdr);
|
void ReadPCX1bit (uint8_t *dst, FileReader & lump, PCXHeader *hdr);
|
||||||
|
@ -92,7 +92,7 @@ protected:
|
||||||
void ReadPCX8bits (uint8_t *dst, FileReader & lump, PCXHeader *hdr);
|
void ReadPCX8bits (uint8_t *dst, FileReader & lump, PCXHeader *hdr);
|
||||||
void ReadPCX24bits (uint8_t *dst, FileReader & lump, PCXHeader *hdr, int planes);
|
void ReadPCX24bits (uint8_t *dst, FileReader & lump, PCXHeader *hdr, int planes);
|
||||||
|
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -345,7 +345,7 @@ void FPCXTexture::ReadPCX24bits (uint8_t *dst, FileReader & lump, PCXHeader *hdr
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FPCXTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FPCXTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
uint8_t PaletteMap[256];
|
uint8_t PaletteMap[256];
|
||||||
PCXHeader header;
|
PCXHeader header;
|
||||||
|
@ -433,7 +433,7 @@ PalettedPixels FPCXTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
int FPCXTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FPCXTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalEntry pe[256];
|
PalEntry pe[256];
|
||||||
PCXHeader header;
|
PCXHeader header;
|
||||||
|
|
|
@ -56,8 +56,8 @@ class FPNGTexture : public FImageSource
|
||||||
public:
|
public:
|
||||||
FPNGTexture (FileReader &lump, int lumpnum, int width, int height, uint8_t bitdepth, uint8_t colortype, uint8_t interlace);
|
FPNGTexture (FileReader &lump, int lumpnum, int width, int height, uint8_t bitdepth, uint8_t colortype, uint8_t interlace);
|
||||||
|
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void ReadAlphaRemap(FileReader *lump, uint8_t *alpharemap);
|
void ReadAlphaRemap(FileReader *lump, uint8_t *alpharemap);
|
||||||
|
@ -412,7 +412,7 @@ void FPNGTexture::ReadAlphaRemap(FileReader *lump, uint8_t *alpharemap)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FPNGTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FPNGTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
FileReader *lump;
|
FileReader *lump;
|
||||||
FileReader lfr;
|
FileReader lfr;
|
||||||
|
@ -553,7 +553,7 @@ PalettedPixels FPNGTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
int FPNGTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FPNGTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
// Parse pre-IDAT chunks. I skip the CRCs. Is that bad?
|
// Parse pre-IDAT chunks. I skip the CRCs. Is that bad?
|
||||||
PalEntry pe[256];
|
PalEntry pe[256];
|
||||||
|
|
|
@ -51,8 +51,8 @@ class FQOITexture : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FQOITexture(int lumpnum, QOIHeader& header);
|
FQOITexture(int lumpnum, QOIHeader& header);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
FImageSource *QOIImage_TryCreate(FileReader &file, int lumpnum)
|
FImageSource *QOIImage_TryCreate(FileReader &file, int lumpnum)
|
||||||
|
@ -89,7 +89,7 @@ FQOITexture::FQOITexture(int lumpnum, QOIHeader& header)
|
||||||
if (header.channels == 3) bMasked = bTranslucent = false;
|
if (header.channels == 3) bMasked = bTranslucent = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
PalettedPixels FQOITexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FQOITexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
FBitmap bitmap;
|
FBitmap bitmap;
|
||||||
bitmap.Create(Width, Height);
|
bitmap.Create(Width, Height);
|
||||||
|
@ -124,7 +124,7 @@ PalettedPixels FQOITexture::CreatePalettedPixels(int conversion)
|
||||||
return Pixels;
|
return Pixels;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FQOITexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FQOITexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
|
|
|
@ -52,8 +52,8 @@ class FRawPageTexture : public FImageSource
|
||||||
int mPaletteLump = -1;
|
int mPaletteLump = -1;
|
||||||
public:
|
public:
|
||||||
FRawPageTexture (int lumpnum);
|
FRawPageTexture (int lumpnum);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -170,9 +170,9 @@ FRawPageTexture::FRawPageTexture (int lumpnum)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FRawPageTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FRawPageTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
const uint8_t *source_p = source;
|
const uint8_t *source_p = source;
|
||||||
uint8_t *dest_p;
|
uint8_t *dest_p;
|
||||||
|
@ -199,13 +199,13 @@ PalettedPixels FRawPageTexture::CreatePalettedPixels(int conversion)
|
||||||
return Pixels;
|
return Pixels;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FRawPageTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FRawPageTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
if (mPaletteLump < 0) return FImageSource::CopyPixels(bmp, conversion);
|
if (mPaletteLump < 0) return FImageSource::CopyPixels(bmp, conversion);
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile(SourceLump);
|
auto lump = fileSystem.ReadFile(SourceLump);
|
||||||
FileData plump = fileSystem.ReadFile(mPaletteLump);
|
auto plump = fileSystem.ReadFile(mPaletteLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
auto psource = plump.GetBytes();
|
auto psource = plump.GetBytes();
|
||||||
PalEntry paldata[256];
|
PalEntry paldata[256];
|
||||||
|
|
|
@ -98,7 +98,7 @@ public:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override
|
||||||
{
|
{
|
||||||
PalettedPixels Pix(512);
|
PalettedPixels Pix(512);
|
||||||
if (conversion == luminance)
|
if (conversion == luminance)
|
||||||
|
@ -118,7 +118,7 @@ public:
|
||||||
return Pix;
|
return Pix;
|
||||||
}
|
}
|
||||||
|
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override
|
||||||
{
|
{
|
||||||
bmp->CopyPixelData(0, 0, Pixels, Width, Height, Height, 1, 0, GPalette.GrayRamp.Palette);
|
bmp->CopyPixelData(0, 0, Pixels, Width, Height, Height, 1, 0, GPalette.GrayRamp.Palette);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -60,7 +60,7 @@ public:
|
||||||
Height = srcdata.GetHeight();
|
Height = srcdata.GetHeight();
|
||||||
bUseGamePalette = false;
|
bUseGamePalette = false;
|
||||||
}
|
}
|
||||||
int CopyPixels(FBitmap* bmp, int conversion)
|
int CopyPixels(FBitmap* bmp, int conversion, int frame = 0)
|
||||||
{
|
{
|
||||||
bmp->Blit(0, 0, info);
|
bmp->Blit(0, 0, info);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -77,30 +77,30 @@ class FStartupTexture : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FStartupTexture (int lumpnum);
|
FStartupTexture (int lumpnum);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
class FNotchTexture : public FImageSource
|
class FNotchTexture : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FNotchTexture (int lumpnum, int width, int height);
|
FNotchTexture (int lumpnum, int width, int height);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
class FStrifeStartupTexture : public FImageSource
|
class FStrifeStartupTexture : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FStrifeStartupTexture (int lumpnum, int w, int h);
|
FStrifeStartupTexture (int lumpnum, int w, int h);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
class FStrifeStartupBackground : public FImageSource
|
class FStrifeStartupBackground : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FStrifeStartupBackground (int lumpnum);
|
FStrifeStartupBackground (int lumpnum);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -164,7 +164,7 @@ FStartupTexture::FStartupTexture (int lumpnum)
|
||||||
Height = 480;
|
Height = 480;
|
||||||
bUseGamePalette = false;
|
bUseGamePalette = false;
|
||||||
|
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
|
|
||||||
// Initialize the bitmap palette.
|
// Initialize the bitmap palette.
|
||||||
|
@ -231,9 +231,9 @@ void PlanarToChunky(T* dest, const uint8_t* src, const T* remap, int width, int
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FStartupTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FStartupTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
const uint8_t *remap = ImageHelpers::GetRemap(conversion == luminance);
|
const uint8_t *remap = ImageHelpers::GetRemap(conversion == luminance);
|
||||||
|
|
||||||
|
@ -251,9 +251,9 @@ PalettedPixels FStartupTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FStartupTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FStartupTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
PlanarToChunky((uint32_t*)bmp->GetPixels(), source + 48, startuppalette32, Width, Height);
|
PlanarToChunky((uint32_t*)bmp->GetPixels(), source + 48, startuppalette32, Width, Height);
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -279,9 +279,9 @@ FNotchTexture::FNotchTexture (int lumpnum, int width, int height)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FNotchTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FNotchTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
const uint8_t *remap = ImageHelpers::GetRemap(conversion == luminance);
|
const uint8_t *remap = ImageHelpers::GetRemap(conversion == luminance);
|
||||||
|
|
||||||
|
@ -302,9 +302,9 @@ PalettedPixels FNotchTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FNotchTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FNotchTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
|
|
||||||
auto Work = (uint32_t*)bmp->GetPixels();
|
auto Work = (uint32_t*)bmp->GetPixels();
|
||||||
|
@ -336,9 +336,9 @@ FStrifeStartupTexture::FStrifeStartupTexture (int lumpnum, int w, int h)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FStrifeStartupTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FStrifeStartupTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
FileData lump = fileSystem.ReadFile (SourceLump);
|
auto lump = fileSystem.ReadFile (SourceLump);
|
||||||
auto source = lump.GetBytes();
|
auto source = lump.GetBytes();
|
||||||
PalettedPixels Pixels(Width*Height);
|
PalettedPixels Pixels(Width*Height);
|
||||||
const uint8_t *remap = ImageHelpers::GetRemap(conversion == luminance);
|
const uint8_t *remap = ImageHelpers::GetRemap(conversion == luminance);
|
||||||
|
@ -366,7 +366,7 @@ FStrifeStartupBackground::FStrifeStartupBackground (int lumpnum)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FStrifeStartupBackground::CreatePalettedPixels(int conversion)
|
PalettedPixels FStrifeStartupBackground::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
TArray<uint8_t> source(64000, true);
|
TArray<uint8_t> source(64000, true);
|
||||||
memset(source.Data(), 0xF0, 64000);
|
memset(source.Data(), 0xF0, 64000);
|
||||||
|
|
|
@ -67,8 +67,8 @@ class FStbTexture : public FImageSource
|
||||||
|
|
||||||
public:
|
public:
|
||||||
FStbTexture (int lumpnum, int w, int h);
|
FStbTexture (int lumpnum, int w, int h);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -117,7 +117,7 @@ FStbTexture::FStbTexture (int lumpnum, int w, int h)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FStbTexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FStbTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
FBitmap bitmap;
|
FBitmap bitmap;
|
||||||
bitmap.Create(Width, Height);
|
bitmap.Create(Width, Height);
|
||||||
|
@ -156,7 +156,7 @@ PalettedPixels FStbTexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
int FStbTexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FStbTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
auto lump = fileSystem.OpenFileReader (SourceLump);
|
auto lump = fileSystem.OpenFileReader (SourceLump);
|
||||||
int x, y, chan;
|
int x, y, chan;
|
||||||
|
|
|
@ -80,11 +80,11 @@ class FTGATexture : public FImageSource
|
||||||
public:
|
public:
|
||||||
FTGATexture (int lumpnum, TGAHeader *);
|
FTGATexture (int lumpnum, TGAHeader *);
|
||||||
|
|
||||||
int CopyPixels(FBitmap *bmp, int conversion) override;
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void ReadCompressed(FileReader &lump, uint8_t * buffer, int bytesperpixel);
|
void ReadCompressed(FileReader &lump, uint8_t * buffer, int bytesperpixel);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -178,7 +178,7 @@ void FTGATexture::ReadCompressed(FileReader &lump, uint8_t * buffer, int bytespe
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
PalettedPixels FTGATexture::CreatePalettedPixels(int conversion)
|
PalettedPixels FTGATexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
uint8_t PaletteMap[256];
|
uint8_t PaletteMap[256];
|
||||||
auto lump = fileSystem.OpenFileReader (SourceLump);
|
auto lump = fileSystem.OpenFileReader (SourceLump);
|
||||||
|
@ -385,7 +385,7 @@ PalettedPixels FTGATexture::CreatePalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
int FTGATexture::CopyPixels(FBitmap *bmp, int conversion)
|
int FTGATexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalEntry pe[256];
|
PalEntry pe[256];
|
||||||
auto lump = fileSystem.OpenFileReader (SourceLump);
|
auto lump = fileSystem.OpenFileReader (SourceLump);
|
||||||
|
|
148
source/common/textures/formats/webptexture.cpp
Normal file
148
source/common/textures/formats/webptexture.cpp
Normal file
|
@ -0,0 +1,148 @@
|
||||||
|
/*
|
||||||
|
** webptexture.cpp
|
||||||
|
** Texture class for WebP images.
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** Copyright 2023 Cacodemon345
|
||||||
|
** All rights reserved.
|
||||||
|
**
|
||||||
|
** Redistribution and use in source and binary forms, with or without
|
||||||
|
** modification, are permitted provided that the following conditions
|
||||||
|
** are met:
|
||||||
|
**
|
||||||
|
** 1. Redistributions of source code must retain the above copyright
|
||||||
|
** notice, this list of conditions and the following disclaimer.
|
||||||
|
** 2. Redistributions in binary form must reproduce the above copyright
|
||||||
|
** notice, this list of conditions and the following disclaimer in the
|
||||||
|
** documentation and/or other materials provided with the distribution.
|
||||||
|
** 3. The name of the author may not be used to endorse or promote products
|
||||||
|
** derived from this software without specific prior written permission.
|
||||||
|
**
|
||||||
|
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
||||||
|
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||||
|
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||||
|
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||||
|
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||||
|
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||||
|
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||||
|
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||||
|
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
**
|
||||||
|
**
|
||||||
|
*/
|
||||||
|
#include "webp/decode.h"
|
||||||
|
#include "webp/mux.h"
|
||||||
|
|
||||||
|
#include "files.h"
|
||||||
|
#include "filesystem.h"
|
||||||
|
#include "bitmap.h"
|
||||||
|
#include "imagehelpers.h"
|
||||||
|
#include "image.h"
|
||||||
|
#include "printf.h"
|
||||||
|
|
||||||
|
class FWebPTexture : public FImageSource
|
||||||
|
{
|
||||||
|
|
||||||
|
public:
|
||||||
|
FWebPTexture(int lumpnum, int w, int h, int xoff, int yoff);
|
||||||
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
|
int CopyPixels(FBitmap *bmp, int conversion, int frame = 0) override;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
FImageSource *WebPImage_TryCreate(FileReader &file, int lumpnum)
|
||||||
|
{
|
||||||
|
int width = 0, height = 0;
|
||||||
|
int xoff = 0, yoff = 0;
|
||||||
|
file.Seek(0, FileReader::SeekSet);
|
||||||
|
|
||||||
|
uint8_t header[12];
|
||||||
|
if (file.Read(header, 12) != 12) return nullptr;
|
||||||
|
if (memcmp(header, "RIFF", 4) || memcmp(header + 8, "WEBP", 4)) return nullptr;
|
||||||
|
|
||||||
|
file.Seek(0, FileReader::SeekSet);
|
||||||
|
auto bytes = file.Read();
|
||||||
|
|
||||||
|
if (WebPGetInfo(bytes.data(), bytes.size(), &width, &height))
|
||||||
|
{
|
||||||
|
WebPData data{ bytes.data(), bytes.size() };
|
||||||
|
WebPData chunk_data;
|
||||||
|
auto mux = WebPMuxCreate(&data, 0);
|
||||||
|
if (mux)
|
||||||
|
{
|
||||||
|
const char fourcc[4] = { 'g', 'r', 'A', 'b' };
|
||||||
|
if (WebPMuxGetChunk(mux, fourcc, &chunk_data) == WEBP_MUX_OK && chunk_data.size >= 4)
|
||||||
|
{
|
||||||
|
xoff = chunk_data.bytes[0] | (chunk_data.bytes[1] << 8);
|
||||||
|
yoff = chunk_data.bytes[2] | (chunk_data.bytes[3] << 8);
|
||||||
|
}
|
||||||
|
WebPMuxDelete(mux);
|
||||||
|
}
|
||||||
|
return new FWebPTexture(lumpnum, width, height, xoff, yoff);
|
||||||
|
}
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
FWebPTexture::FWebPTexture(int lumpnum, int w, int h, int xoff, int yoff)
|
||||||
|
: FImageSource(lumpnum)
|
||||||
|
{
|
||||||
|
Width = w;
|
||||||
|
Height = h;
|
||||||
|
LeftOffset = xoff;
|
||||||
|
TopOffset = yoff;
|
||||||
|
}
|
||||||
|
|
||||||
|
PalettedPixels FWebPTexture::CreatePalettedPixels(int conversion, int frame)
|
||||||
|
{
|
||||||
|
FBitmap bitmap;
|
||||||
|
bitmap.Create(Width, Height);
|
||||||
|
CopyPixels(&bitmap, conversion);
|
||||||
|
const uint8_t *data = bitmap.GetPixels();
|
||||||
|
|
||||||
|
uint8_t *dest_p;
|
||||||
|
int dest_adv = Height;
|
||||||
|
int dest_rew = Width * Height - 1;
|
||||||
|
|
||||||
|
PalettedPixels Pixels(Width*Height);
|
||||||
|
dest_p = Pixels.Data();
|
||||||
|
|
||||||
|
bool doalpha = conversion == luminance;
|
||||||
|
// Convert the source image from row-major to column-major format and remap it
|
||||||
|
for (int y = Height; y != 0; --y)
|
||||||
|
{
|
||||||
|
for (int x = Width; x != 0; --x)
|
||||||
|
{
|
||||||
|
int b = *data++;
|
||||||
|
int g = *data++;
|
||||||
|
int r = *data++;
|
||||||
|
int a = *data++;
|
||||||
|
if (a < 128) *dest_p = 0;
|
||||||
|
else *dest_p = ImageHelpers::RGBToPalette(doalpha, r, g, b);
|
||||||
|
dest_p += dest_adv;
|
||||||
|
}
|
||||||
|
dest_p -= dest_rew;
|
||||||
|
}
|
||||||
|
return Pixels;
|
||||||
|
}
|
||||||
|
|
||||||
|
int FWebPTexture::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
|
{
|
||||||
|
WebPDecoderConfig config;
|
||||||
|
auto bytes = fileSystem.ReadFile(SourceLump);
|
||||||
|
|
||||||
|
if (WebPInitDecoderConfig(&config) == false)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
config.options.no_fancy_upsampling = 0;
|
||||||
|
config.output.colorspace = MODE_BGRA;
|
||||||
|
config.output.u.RGBA.rgba = (uint8_t*)bmp->GetPixels();
|
||||||
|
config.output.u.RGBA.size = bmp->GetBufferSize();
|
||||||
|
config.output.u.RGBA.stride = bmp->GetPitch();
|
||||||
|
config.output.is_external_memory = 1;
|
||||||
|
|
||||||
|
(void)WebPDecode(bytes.GetBytes(), bytes.GetSize(), &config);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
|
@ -182,7 +182,7 @@ void FGameTexture::AddAutoMaterials()
|
||||||
if (this->*(layer.pointer) == nullptr) // only if no explicit assignment had been done.
|
if (this->*(layer.pointer) == nullptr) // only if no explicit assignment had been done.
|
||||||
{
|
{
|
||||||
FStringf lookup("%s%s%s", layer.path, fullname ? "" : "auto/", searchname.GetChars());
|
FStringf lookup("%s%s%s", layer.path, fullname ? "" : "auto/", searchname.GetChars());
|
||||||
auto lump = fileSystem.CheckNumForFullName(lookup, false, ns_global, true);
|
auto lump = fileSystem.CheckNumForFullName(lookup, false, FileSys::ns_global, true);
|
||||||
if (lump != -1)
|
if (lump != -1)
|
||||||
{
|
{
|
||||||
auto bmtex = TexMan.FindGameTexture(fileSystem.GetFileFullName(lump), ETextureType::Any, FTextureManager::TEXMAN_TryAny);
|
auto bmtex = TexMan.FindGameTexture(fileSystem.GetFileFullName(lump), ETextureType::Any, FTextureManager::TEXMAN_TryAny);
|
||||||
|
@ -199,7 +199,7 @@ void FGameTexture::AddAutoMaterials()
|
||||||
if (!this->Layers || this->Layers.get()->*(layer.pointer) == nullptr) // only if no explicit assignment had been done.
|
if (!this->Layers || this->Layers.get()->*(layer.pointer) == nullptr) // only if no explicit assignment had been done.
|
||||||
{
|
{
|
||||||
FStringf lookup("%s%s%s", layer.path, fullname ? "" : "auto/", searchname.GetChars());
|
FStringf lookup("%s%s%s", layer.path, fullname ? "" : "auto/", searchname.GetChars());
|
||||||
auto lump = fileSystem.CheckNumForFullName(lookup, false, ns_global, true);
|
auto lump = fileSystem.CheckNumForFullName(lookup, false, FileSys::ns_global, true);
|
||||||
if (lump != -1)
|
if (lump != -1)
|
||||||
{
|
{
|
||||||
auto bmtex = TexMan.FindGameTexture(fileSystem.GetFileFullName(lump), ETextureType::Any, FTextureManager::TEXMAN_TryAny);
|
auto bmtex = TexMan.FindGameTexture(fileSystem.GetFileFullName(lump), ETextureType::Any, FTextureManager::TEXMAN_TryAny);
|
||||||
|
|
|
@ -51,6 +51,7 @@ struct PrecacheDataPaletted
|
||||||
PalettedPixels Pixels;
|
PalettedPixels Pixels;
|
||||||
int RefCount;
|
int RefCount;
|
||||||
int ImageID;
|
int ImageID;
|
||||||
|
int Frame;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct PrecacheDataRgba
|
struct PrecacheDataRgba
|
||||||
|
@ -59,6 +60,7 @@ struct PrecacheDataRgba
|
||||||
int TransInfo;
|
int TransInfo;
|
||||||
int RefCount;
|
int RefCount;
|
||||||
int ImageID;
|
int ImageID;
|
||||||
|
int Frame;
|
||||||
};
|
};
|
||||||
|
|
||||||
// TMap doesn't handle this kind of data well. std::map neither. The linear search is still faster, even for a few 100 entries because it doesn't have to access the heap as often..
|
// TMap doesn't handle this kind of data well. std::map neither. The linear search is still faster, even for a few 100 entries because it doesn't have to access the heap as often..
|
||||||
|
@ -71,21 +73,21 @@ TArray<PrecacheDataRgba> precacheDataRgba;
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
PalettedPixels FImageSource::CreatePalettedPixels(int conversion)
|
PalettedPixels FImageSource::CreatePalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalettedPixels Pixels(Width * Height);
|
PalettedPixels Pixels(Width * Height);
|
||||||
memset(Pixels.Data(), 0, Width * Height);
|
memset(Pixels.Data(), 0, Width * Height);
|
||||||
return Pixels;
|
return Pixels;
|
||||||
}
|
}
|
||||||
|
|
||||||
PalettedPixels FImageSource::GetCachedPalettedPixels(int conversion)
|
PalettedPixels FImageSource::GetCachedPalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
PalettedPixels ret;
|
PalettedPixels ret;
|
||||||
|
|
||||||
auto imageID = ImageID;
|
auto imageID = ImageID;
|
||||||
|
|
||||||
// Do we have this image in the cache?
|
// Do we have this image in the cache?
|
||||||
unsigned index = conversion != normal? UINT_MAX : precacheDataPaletted.FindEx([=](PrecacheDataPaletted &entry) { return entry.ImageID == imageID; });
|
unsigned index = conversion != normal? UINT_MAX : precacheDataPaletted.FindEx([=](PrecacheDataPaletted &entry) { return entry.ImageID == imageID && entry.Frame == frame; });
|
||||||
if (index < precacheDataPaletted.Size())
|
if (index < precacheDataPaletted.Size())
|
||||||
{
|
{
|
||||||
auto cache = &precacheDataPaletted[index];
|
auto cache = &precacheDataPaletted[index];
|
||||||
|
@ -115,7 +117,7 @@ PalettedPixels FImageSource::GetCachedPalettedPixels(int conversion)
|
||||||
{
|
{
|
||||||
// This is either the only copy needed or some access outside the caching block. In these cases create a new one and directly return it.
|
// This is either the only copy needed or some access outside the caching block. In these cases create a new one and directly return it.
|
||||||
//Printf("returning fresh copy of %s\n", name.GetChars());
|
//Printf("returning fresh copy of %s\n", name.GetChars());
|
||||||
return CreatePalettedPixels(conversion);
|
return CreatePalettedPixels(conversion, frame);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -126,16 +128,16 @@ PalettedPixels FImageSource::GetCachedPalettedPixels(int conversion)
|
||||||
pdp->ImageID = imageID;
|
pdp->ImageID = imageID;
|
||||||
pdp->RefCount = info->second - 1;
|
pdp->RefCount = info->second - 1;
|
||||||
info->second = 0;
|
info->second = 0;
|
||||||
pdp->Pixels = CreatePalettedPixels(normal);
|
pdp->Pixels = CreatePalettedPixels(normal, frame);
|
||||||
ret.Pixels.Set(pdp->Pixels.Data(), pdp->Pixels.Size());
|
ret.Pixels.Set(pdp->Pixels.Data(), pdp->Pixels.Size());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
TArray<uint8_t> FImageSource::GetPalettedPixels(int conversion)
|
TArray<uint8_t> FImageSource::GetPalettedPixels(int conversion, int frame)
|
||||||
{
|
{
|
||||||
auto pix = GetCachedPalettedPixels(conversion);
|
auto pix = GetCachedPalettedPixels(conversion, frame);
|
||||||
if (pix.ownsPixels())
|
if (pix.ownsPixels())
|
||||||
{
|
{
|
||||||
// return the pixel store of the returned data directly if this was the last reference.
|
// return the pixel store of the returned data directly if this was the last reference.
|
||||||
|
@ -165,19 +167,19 @@ TArray<uint8_t> FImageSource::GetPalettedPixels(int conversion)
|
||||||
//
|
//
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
int FImageSource::CopyPixels(FBitmap *bmp, int conversion)
|
int FImageSource::CopyPixels(FBitmap *bmp, int conversion, int frame)
|
||||||
{
|
{
|
||||||
if (conversion == luminance) conversion = normal; // luminance images have no use as an RGB source.
|
if (conversion == luminance) conversion = normal; // luminance images have no use as an RGB source.
|
||||||
PalEntry *palette = GPalette.BaseColors;
|
PalEntry *palette = GPalette.BaseColors;
|
||||||
|
|
||||||
auto ppix = CreatePalettedPixels(conversion);
|
auto ppix = CreatePalettedPixels(conversion, frame);
|
||||||
bmp->CopyPixelData(0, 0, ppix.Data(), Width, Height, Height, 1, 0, palette, nullptr);
|
bmp->CopyPixelData(0, 0, ppix.Data(), Width, Height, Height, 1, 0, palette, nullptr);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FImageSource::CopyTranslatedPixels(FBitmap *bmp, const PalEntry *remap)
|
int FImageSource::CopyTranslatedPixels(FBitmap *bmp, const PalEntry *remap, int frame)
|
||||||
{
|
{
|
||||||
auto ppix = CreatePalettedPixels(normal);
|
auto ppix = CreatePalettedPixels(normal, frame);
|
||||||
bmp->CopyPixelData(0, 0, ppix.Data(), Width, Height, Height, 1, 0, remap, nullptr);
|
bmp->CopyPixelData(0, 0, ppix.Data(), Width, Height, Height, 1, 0, remap, nullptr);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -188,26 +190,31 @@ int FImageSource::CopyTranslatedPixels(FBitmap *bmp, const PalEntry *remap)
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FBitmap FImageSource::GetCachedBitmap(const PalEntry *remap, int conversion, int *ptrans)
|
FBitmap FImageSource::GetCachedBitmap(const PalEntry *remap, int conversion, int *ptrans, int frame)
|
||||||
{
|
{
|
||||||
FBitmap ret;
|
FBitmap ret;
|
||||||
|
|
||||||
int trans = -1;
|
int trans = -1;
|
||||||
auto imageID = ImageID;
|
auto imageID = ImageID;
|
||||||
|
|
||||||
|
if (NumOfFrames == 1 && frame == 1)
|
||||||
|
{
|
||||||
|
frame = 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (remap != nullptr)
|
if (remap != nullptr)
|
||||||
{
|
{
|
||||||
// Remapped images are never run through the cache because they would complicate matters too much for very little gain.
|
// Remapped images are never run through the cache because they would complicate matters too much for very little gain.
|
||||||
// Translated images are normally sprites which normally just consist of a single image and use no composition.
|
// Translated images are normally sprites which normally just consist of a single image and use no composition.
|
||||||
// Additionally, since translation requires the base palette, the really time consuming stuff will never be subjected to it.
|
// Additionally, since translation requires the base palette, the really time consuming stuff will never be subjected to it.
|
||||||
ret.Create(Width, Height);
|
ret.Create(Width, Height);
|
||||||
trans = CopyTranslatedPixels(&ret, remap);
|
trans = CopyTranslatedPixels(&ret, remap, frame);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (conversion == luminance) conversion = normal; // luminance has no meaning for true color.
|
if (conversion == luminance) conversion = normal; // luminance has no meaning for true color.
|
||||||
// Do we have this image in the cache?
|
// Do we have this image in the cache?
|
||||||
unsigned index = conversion != normal? UINT_MAX : precacheDataRgba.FindEx([=](PrecacheDataRgba &entry) { return entry.ImageID == imageID; });
|
unsigned index = conversion != normal? UINT_MAX : precacheDataRgba.FindEx([=](PrecacheDataRgba &entry) { return entry.ImageID == imageID && entry.Frame == frame; });
|
||||||
if (index < precacheDataRgba.Size())
|
if (index < precacheDataRgba.Size())
|
||||||
{
|
{
|
||||||
auto cache = &precacheDataRgba[index];
|
auto cache = &precacheDataRgba[index];
|
||||||
|
@ -230,7 +237,7 @@ FBitmap FImageSource::GetCachedBitmap(const PalEntry *remap, int conversion, int
|
||||||
// This should never happen if the function is implemented correctly
|
// This should never happen if the function is implemented correctly
|
||||||
//Printf("something bad happened for %s, refcount = %d\n", name.GetChars(), cache->RefCount);
|
//Printf("something bad happened for %s, refcount = %d\n", name.GetChars(), cache->RefCount);
|
||||||
ret.Create(Width, Height);
|
ret.Create(Width, Height);
|
||||||
trans = CopyPixels(&ret, normal);
|
trans = CopyPixels(&ret, normal, frame);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -242,7 +249,7 @@ FBitmap FImageSource::GetCachedBitmap(const PalEntry *remap, int conversion, int
|
||||||
// This is either the only copy needed or some access outside the caching block. In these cases create a new one and directly return it.
|
// This is either the only copy needed or some access outside the caching block. In these cases create a new one and directly return it.
|
||||||
//Printf("returning fresh copy of %s\n", name.GetChars());
|
//Printf("returning fresh copy of %s\n", name.GetChars());
|
||||||
ret.Create(Width, Height);
|
ret.Create(Width, Height);
|
||||||
trans = CopyPixels(&ret, conversion);
|
trans = CopyPixels(&ret, conversion, frame);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -251,10 +258,11 @@ FBitmap FImageSource::GetCachedBitmap(const PalEntry *remap, int conversion, int
|
||||||
PrecacheDataRgba *pdr = &precacheDataRgba[precacheDataRgba.Reserve(1)];
|
PrecacheDataRgba *pdr = &precacheDataRgba[precacheDataRgba.Reserve(1)];
|
||||||
|
|
||||||
pdr->ImageID = imageID;
|
pdr->ImageID = imageID;
|
||||||
|
pdr->Frame = frame;
|
||||||
pdr->RefCount = info->first - 1;
|
pdr->RefCount = info->first - 1;
|
||||||
info->first = 0;
|
info->first = 0;
|
||||||
pdr->Pixels.Create(Width, Height);
|
pdr->Pixels.Create(Width, Height);
|
||||||
trans = pdr->TransInfo = CopyPixels(&pdr->Pixels, normal);
|
trans = pdr->TransInfo = CopyPixels(&pdr->Pixels, normal, frame);
|
||||||
ret.Copy(pdr->Pixels, false);
|
ret.Copy(pdr->Pixels, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -67,12 +67,13 @@ protected:
|
||||||
int LeftOffset = 0, TopOffset = 0; // Offsets stored in the image.
|
int LeftOffset = 0, TopOffset = 0; // Offsets stored in the image.
|
||||||
bool bUseGamePalette = false; // true if this is an image without its own color set.
|
bool bUseGamePalette = false; // true if this is an image without its own color set.
|
||||||
int ImageID = -1;
|
int ImageID = -1;
|
||||||
|
int NumOfFrames = 1;
|
||||||
|
|
||||||
// Internal image creation functions. All external access should go through the cache interface,
|
// Internal image creation functions. All external access should go through the cache interface,
|
||||||
// so that all code can benefit from future improvements to that.
|
// so that all code can benefit from future improvements to that.
|
||||||
|
|
||||||
virtual PalettedPixels CreatePalettedPixels(int conversion);
|
virtual PalettedPixels CreatePalettedPixels(int conversion, int frame = 0);
|
||||||
int CopyTranslatedPixels(FBitmap *bmp, const PalEntry *remap);
|
int CopyTranslatedPixels(FBitmap *bmp, const PalEntry *remap, int frame = 0);
|
||||||
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
@ -101,19 +102,25 @@ public:
|
||||||
// 'noremap0' will only be looked at by FPatchTexture and forwarded by FMultipatchTexture.
|
// 'noremap0' will only be looked at by FPatchTexture and forwarded by FMultipatchTexture.
|
||||||
|
|
||||||
// Either returns a reference to the cache, or a newly created item. The return of this has to be considered transient. If you need to store the result, use GetPalettedPixels
|
// Either returns a reference to the cache, or a newly created item. The return of this has to be considered transient. If you need to store the result, use GetPalettedPixels
|
||||||
PalettedPixels GetCachedPalettedPixels(int conversion);
|
PalettedPixels GetCachedPalettedPixels(int conversion, int frame = 0);
|
||||||
|
|
||||||
// tries to get a buffer from the cache. If not available, create a new one. If further references are pending, create a copy.
|
// tries to get a buffer from the cache. If not available, create a new one. If further references are pending, create a copy.
|
||||||
TArray<uint8_t> GetPalettedPixels(int conversion);
|
TArray<uint8_t> GetPalettedPixels(int conversion, int frame = 0);
|
||||||
|
|
||||||
virtual int CopyPixels(FBitmap* bmp, int conversion);
|
virtual int CopyPixels(FBitmap* bmp, int conversion, int frame = 0);
|
||||||
|
|
||||||
FBitmap GetCachedBitmap(const PalEntry *remap, int conversion, int *trans = nullptr);
|
FBitmap GetCachedBitmap(const PalEntry *remap, int conversion, int *trans = nullptr, int frame = 0);
|
||||||
|
|
||||||
static void ClearImages() { ImageArena.FreeAll(); ImageForLump.Clear(); NextID = 0; }
|
static void ClearImages() { ImageArena.FreeAll(); ImageForLump.Clear(); NextID = 0; }
|
||||||
static FImageSource * GetImage(int lumpnum, bool checkflat);
|
static FImageSource * GetImage(int lumpnum, bool checkflat);
|
||||||
|
|
||||||
|
// Frame functions
|
||||||
|
|
||||||
|
// Gets number of frames.
|
||||||
|
int GetNumOfFrames() { return NumOfFrames; }
|
||||||
|
|
||||||
|
// Gets duration of frame in miliseconds.
|
||||||
|
virtual int GetDurationOfFrame(int frame) { return 1000; }
|
||||||
|
|
||||||
// Conversion option
|
// Conversion option
|
||||||
enum EType
|
enum EType
|
||||||
|
@ -180,8 +187,8 @@ class FBuildTexture : public FImageSource
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FBuildTexture(const FString& pathprefix, int tilenum, const uint8_t* pixels, FRemapTable* translation, int width, int height, int left, int top);
|
FBuildTexture(const FString& pathprefix, int tilenum, const uint8_t* pixels, FRemapTable* translation, int width, int height, int left, int top);
|
||||||
PalettedPixels CreatePalettedPixels(int conversion) override;
|
PalettedPixels CreatePalettedPixels(int conversion, int frame = 0) override;
|
||||||
int CopyPixels(FBitmap* bmp, int conversion) override;
|
int CopyPixels(FBitmap* bmp, int conversion, int frame = 0) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
const uint8_t* RawPixels;
|
const uint8_t* RawPixels;
|
||||||
|
@ -191,4 +198,4 @@ protected:
|
||||||
|
|
||||||
class FTexture;
|
class FTexture;
|
||||||
|
|
||||||
FTexture* CreateImageTexture(FImageSource* img) noexcept;
|
FTexture* CreateImageTexture(FImageSource* img, int frame = 0) noexcept;
|
||||||
|
|
|
@ -47,10 +47,11 @@
|
||||||
//
|
//
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
|
||||||
FImageTexture::FImageTexture(FImageSource *img) noexcept
|
FImageTexture::FImageTexture(FImageSource *img, int frame) noexcept
|
||||||
: FTexture(img? img->LumpNum() : 0)
|
: FTexture(img? img->LumpNum() : 0)
|
||||||
{
|
{
|
||||||
mImage = img;
|
mImage = img;
|
||||||
|
TexFrame = frame;
|
||||||
if (img != nullptr)
|
if (img != nullptr)
|
||||||
{
|
{
|
||||||
SetFromImage();
|
SetFromImage();
|
||||||
|
@ -79,7 +80,7 @@ void FImageTexture::SetFromImage()
|
||||||
|
|
||||||
FBitmap FImageTexture::GetBgraBitmap(const PalEntry *p, int *trans)
|
FBitmap FImageTexture::GetBgraBitmap(const PalEntry *p, int *trans)
|
||||||
{
|
{
|
||||||
return mImage->GetCachedBitmap(p, bNoRemap0? FImageSource::noremap0 : FImageSource::normal, trans);
|
return mImage->GetCachedBitmap(p, bNoRemap0? FImageSource::noremap0 : FImageSource::normal, trans, TexFrame);
|
||||||
}
|
}
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
@ -90,7 +91,7 @@ FBitmap FImageTexture::GetBgraBitmap(const PalEntry *p, int *trans)
|
||||||
|
|
||||||
TArray<uint8_t> FImageTexture::Get8BitPixels(bool alpha)
|
TArray<uint8_t> FImageTexture::Get8BitPixels(bool alpha)
|
||||||
{
|
{
|
||||||
return mImage->GetPalettedPixels(alpha? FImageSource::luminance : bNoRemap0 ? FImageSource::noremap0 : FImageSource::normal);
|
return mImage->GetPalettedPixels(alpha? FImageSource::luminance : bNoRemap0 ? FImageSource::noremap0 : FImageSource::normal, TexFrame);
|
||||||
}
|
}
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
@ -113,8 +114,8 @@ bool FImageTexture::DetermineTranslucency()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
FTexture* CreateImageTexture(FImageSource* img) noexcept
|
FTexture* CreateImageTexture(FImageSource* img, int frame) noexcept
|
||||||
{
|
{
|
||||||
return new FImageTexture(img);
|
return new FImageTexture(img, frame);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -47,7 +47,6 @@ enum ESSType
|
||||||
SS_BGRA
|
SS_BGRA
|
||||||
};
|
};
|
||||||
|
|
||||||
class FileWriter;
|
|
||||||
// PNG Writing --------------------------------------------------------------
|
// PNG Writing --------------------------------------------------------------
|
||||||
|
|
||||||
// Start writing an 8-bit palettized PNG file.
|
// Start writing an 8-bit palettized PNG file.
|
||||||
|
@ -82,13 +81,13 @@ struct PNGHandle
|
||||||
uint32_t Size;
|
uint32_t Size;
|
||||||
};
|
};
|
||||||
|
|
||||||
FileReader File;
|
FileSys::FileReader File;
|
||||||
bool bDeleteFilePtr;
|
bool bDeleteFilePtr;
|
||||||
TArray<Chunk> Chunks;
|
TArray<Chunk> Chunks;
|
||||||
TArray<char *> TextChunks;
|
TArray<char *> TextChunks;
|
||||||
unsigned int ChunkPt;
|
unsigned int ChunkPt;
|
||||||
|
|
||||||
PNGHandle(FileReader &file);
|
PNGHandle(FileSys::FileReader &file);
|
||||||
~PNGHandle();
|
~PNGHandle();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -96,7 +95,7 @@ struct PNGHandle
|
||||||
// the signature, but also checking for the IEND chunk. CRC checking of
|
// the signature, but also checking for the IEND chunk. CRC checking of
|
||||||
// each chunk is not done. If it is valid, you get a PNGHandle to pass to
|
// each chunk is not done. If it is valid, you get a PNGHandle to pass to
|
||||||
// the following functions.
|
// the following functions.
|
||||||
PNGHandle *M_VerifyPNG (FileReader &file);
|
PNGHandle *M_VerifyPNG (FileSys::FileReader &file);
|
||||||
|
|
||||||
// Finds a chunk in a PNG file. The file pointer will be positioned at the
|
// Finds a chunk in a PNG file. The file pointer will be positioned at the
|
||||||
// beginning of the chunk data, and its length will be returned. A return
|
// beginning of the chunk data, and its length will be returned. A return
|
||||||
|
@ -115,7 +114,7 @@ bool M_GetPNGText (PNGHandle *png, const char *keyword, char *buffer, size_t buf
|
||||||
|
|
||||||
// The file must be positioned at the start of the first IDAT. It reads
|
// The file must be positioned at the start of the first IDAT. It reads
|
||||||
// image data into the provided buffer. Returns true on success.
|
// image data into the provided buffer. Returns true on success.
|
||||||
bool M_ReadIDAT (FileReader &file, uint8_t *buffer, int width, int height, int pitch,
|
bool M_ReadIDAT (FileSys::FileReader &file, uint8_t *buffer, int width, int height, int pitch,
|
||||||
uint8_t bitdepth, uint8_t colortype, uint8_t interlace, unsigned int idatlen);
|
uint8_t bitdepth, uint8_t colortype, uint8_t interlace, unsigned int idatlen);
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -397,12 +397,12 @@ void FMultipatchTextureBuilder::AddTexturesLumps(int lump1, int lump2, int patch
|
||||||
|
|
||||||
if (lump1 >= 0)
|
if (lump1 >= 0)
|
||||||
{
|
{
|
||||||
FileData texdir = fileSystem.ReadFile(lump1);
|
auto texdir = fileSystem.ReadFile(lump1);
|
||||||
AddTexturesLump(texdir.GetMem(), fileSystem.FileLength(lump1), lump1, patcheslump, firstdup, true);
|
AddTexturesLump(texdir.GetMem(), fileSystem.FileLength(lump1), lump1, patcheslump, firstdup, true);
|
||||||
}
|
}
|
||||||
if (lump2 >= 0)
|
if (lump2 >= 0)
|
||||||
{
|
{
|
||||||
FileData texdir = fileSystem.ReadFile(lump2);
|
auto texdir = fileSystem.ReadFile(lump2);
|
||||||
AddTexturesLump(texdir.GetMem(), fileSystem.FileLength(lump2), lump2, patcheslump, firstdup, false);
|
AddTexturesLump(texdir.GetMem(), fileSystem.FileLength(lump2), lump2, patcheslump, firstdup, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -50,6 +50,7 @@
|
||||||
#include "basics.h"
|
#include "basics.h"
|
||||||
#include "cmdlib.h"
|
#include "cmdlib.h"
|
||||||
|
|
||||||
|
using namespace FileSys;
|
||||||
FTextureManager TexMan;
|
FTextureManager TexMan;
|
||||||
|
|
||||||
|
|
||||||
|
@ -681,15 +682,15 @@ void FTextureManager::AddHiresTextures (int wadnum)
|
||||||
|
|
||||||
void FTextureManager::LoadTextureDefs(int wadnum, const char *lumpname, FMultipatchTextureBuilder &build)
|
void FTextureManager::LoadTextureDefs(int wadnum, const char *lumpname, FMultipatchTextureBuilder &build)
|
||||||
{
|
{
|
||||||
int remapLump, lastLump;
|
int texLump, lastLump;
|
||||||
|
|
||||||
lastLump = 0;
|
lastLump = 0;
|
||||||
|
|
||||||
while ((remapLump = fileSystem.FindLump(lumpname, &lastLump)) != -1)
|
while ((texLump = fileSystem.FindLump(lumpname, &lastLump)) != -1)
|
||||||
{
|
{
|
||||||
if (fileSystem.GetFileContainer(remapLump) == wadnum)
|
if (fileSystem.GetFileContainer(texLump) == wadnum)
|
||||||
{
|
{
|
||||||
ParseTextureDef(remapLump, build);
|
ParseTextureDef(texLump, build);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -379,10 +379,11 @@ class FImageTexture : public FTexture
|
||||||
{
|
{
|
||||||
FImageSource* mImage;
|
FImageSource* mImage;
|
||||||
bool bNoRemap0 = false;
|
bool bNoRemap0 = false;
|
||||||
|
int TexFrame = 0;
|
||||||
protected:
|
protected:
|
||||||
void SetFromImage();
|
void SetFromImage();
|
||||||
public:
|
public:
|
||||||
FImageTexture(FImageSource* image) noexcept;
|
FImageTexture(FImageSource* image, int frame = 0) noexcept;
|
||||||
~FImageTexture();
|
~FImageTexture();
|
||||||
TArray<uint8_t> Get8BitPixels(bool alphatex) override;
|
TArray<uint8_t> Get8BitPixels(bool alphatex) override;
|
||||||
|
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue