- Blood: Savegame fully transitioned to JSON

not tested yet.
This commit is contained in:
Christoph Oelckers 2020-11-22 16:47:08 +01:00
parent 572d3c9944
commit 9a4073508d
29 changed files with 763 additions and 912 deletions

View file

@ -46,7 +46,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "gib.h" #include "gib.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "player.h" #include "player.h"
#include "seq.h" #include "seq.h"
#include "sound.h" #include "sound.h"

View file

@ -41,7 +41,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "gib.h" #include "gib.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "player.h" #include "player.h"
#include "seq.h" #include "seq.h"
#include "sound.h" #include "sound.h"
@ -1773,56 +1772,13 @@ FSerializer& Serialize(FSerializer& arc, const char* keyname, DUDEEXTRA& w, DUDE
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
FSerializer& Serialize(FSerializer& arc, const char* keyname, GENDUDEEXTRA& w, GENDUDEEXTRA* def)
{
if (arc.BeginObject(keyname))
{
arc.Array("initvals", w.initVals, 3)
.Array("availdeaths", w.availDeaths, kDamageMax)
("movespeed", w.moveSpeed)
("firedist", w.fireDist)
("throwdist", w.throwDist)
("curweapon", w.curWeapon)
("weapontype", w.weaponType)
("basedispersion", w.baseDispersion)
("slavecount", w.slaveCount)
("lifeleech", w.nLifeLeech)
.Array("slaves", w.slave, w.slaveCount)
.Array("dmgcontrol", w.dmgControl, kDamageMax)
.Array("updreq", w.updReq, kGenDudePropertyMax)
("flags", w.flags)
.EndObject();
}
return arc;
}
//---------------------------------------------------------------------------
//
//
//
//---------------------------------------------------------------------------
void SerializeAI(FSerializer& arc) void SerializeAI(FSerializer& arc)
{ {
if (arc.BeginObject("ai")) if (arc.BeginObject("ai"))
{ {
arc.SparseArray("dudeslope", gDudeSlope, kMaxSprites, activeXSprites) arc.SparseArray("dudeslope", gDudeSlope, kMaxSprites, activeXSprites)
.SparseArray("dudeextra", gDudeExtra, kMaxSprites, activeXSprites); .SparseArray("dudeextra", gDudeExtra, kMaxSprites, activeXSprites)
.EndObject();
// the GenDudeArray only contains valid info for kDudeModernCustom and kDudeModernCustomBurning so only save the relevant entries as these are not small.
bool foundsome = false;
for (int i = 0; i < kMaxSprites; i++)
{
if (activeSprites[i] && (sprite[i].type == kDudeModernCustom || sprite[i].type == kDudeModernCustomBurning))
{
if (!foundsome) arc.BeginArray("gendudeextra");
foundsome = true;
arc(nullptr, gGenDudeExtra[i]);
}
}
if (foundsome) arc.EndArray();
arc.EndObject();
} }
} }

View file

@ -33,7 +33,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "endgame.h" #include "endgame.h"
#include "aistate.h" #include "aistate.h"
#include "loadsave.h"
#include "sectorfx.h" #include "sectorfx.h"
#include "choke.h" #include "choke.h"
#include "view.h" #include "view.h"

View file

@ -31,7 +31,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "db.h" #include "db.h"
#include "player.h" #include "player.h"
#include "sound.h" #include "sound.h"
#include "loadsave.h"
#include "raze_sound.h" #include "raze_sound.h"
BEGIN_BLD_NS BEGIN_BLD_NS

View file

@ -40,7 +40,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "gib.h" #include "gib.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "sectorfx.h" #include "sectorfx.h"
#include "seq.h" #include "seq.h"
#include "sound.h" #include "sound.h"
@ -502,7 +501,6 @@ void GameInterface::app_init()
FireInit(); FireInit();
Printf(PRINT_NONOTIFY, "Initializing weapon animations\n"); Printf(PRINT_NONOTIFY, "Initializing weapon animations\n");
WeaponInit(); WeaponInit();
LoadSaveSetup();
myconnectindex = connecthead = 0; myconnectindex = connecthead = 0;
gNetPlayers = numplayers = 1; gNetPlayers = numplayers = 1;

View file

@ -82,8 +82,6 @@ struct GameInterface : ::GameInterface
void MenuClosed() override; void MenuClosed() override;
bool CanSave() override; bool CanSave() override;
bool StartGame(FNewGameStartup& gs) override; bool StartGame(FNewGameStartup& gs) override;
bool SaveGame() override;
bool LoadGame() override;
void QuitToTitle() override; void QuitToTitle() override;
FString GetCoordString() override; FString GetCoordString() override;
ReservedSpace GetReservedScreenSpace(int viewsize) override; ReservedSpace GetReservedScreenSpace(int viewsize) override;

View file

@ -463,13 +463,8 @@ struct LOCATION {
int ang; int ang;
}; };
struct POINT2D { using POINT2D = vec2_t;
int x, y; using POINT3D = vec3_t;
};
struct POINT3D {
int x, y, z;
};
struct VECTOR2D { struct VECTOR2D {
int dx, dy; int dx, dy;

View file

@ -47,6 +47,9 @@ XSPRITE xsprite[kMaxXSprites];
XSECTOR xsector[kMaxXSectors]; XSECTOR xsector[kMaxXSectors];
XWALL xwall[kMaxXWalls]; XWALL xwall[kMaxXWalls];
XSECTOR xsectorbackup[kMaxXSectors];
XWALL xwallbackup[kMaxXWalls];
SPRITEHIT gSpriteHit[kMaxXSprites]; SPRITEHIT gSpriteHit[kMaxXSprites];
int xvel[kMaxSprites], yvel[kMaxSprites], zvel[kMaxSprites]; int xvel[kMaxSprites], yvel[kMaxSprites], zvel[kMaxSprites];
@ -274,6 +277,20 @@ void InitFreeList(unsigned short *pList, int nCount)
pList[0] = nCount - 1; pList[0] = nCount - 1;
} }
void InitFreeList(unsigned short* pList, int nCount, FixedBitArray<MAXSPRITES>&used)
{
int lastfree = 0;
for (int i = 1; i < nCount; i++)
{
if (!used[i])
{
pList[i] = lastfree;
lastfree = i;
}
}
pList[0] = lastfree;
}
void InsertFree(unsigned short *pList, int nIndex) void InsertFree(unsigned short *pList, int nIndex)
{ {
pList[nIndex] = pList[0]; pList[nIndex] = pList[0];
@ -391,14 +408,13 @@ void PropagateMarkerReferences(void)
} }
} }
bool byte_1A76C6, byte_1A76C7, byte_1A76C8; bool drawtile2048, encrypted;
MAPHEADER2 byte_19AE44; MAPHEADER2 byte_19AE44;
unsigned int dbReadMapCRC(const char *pPath) unsigned int dbReadMapCRC(const char *pPath)
{ {
byte_1A76C7 = 0; encrypted = 0;
byte_1A76C8 = 0;
FString mapname = pPath; FString mapname = pPath;
DefaultExtension(mapname, ".map"); DefaultExtension(mapname, ".map");
@ -422,7 +438,7 @@ unsigned int dbReadMapCRC(const char *pPath)
} }
else if ((ver & 0xff00) == 0x700) else if ((ver & 0xff00) == 0x700)
{ {
byte_1A76C8 = 1; encrypted = 1;
} }
else else
{ {
@ -432,7 +448,7 @@ unsigned int dbReadMapCRC(const char *pPath)
return fr.ReadInt32(); return fr.ReadInt32();
} }
int gMapRev, gSongId, gSkyCount; int gMapRev, gMattId, gSkyCount;
//char byte_19AE44[128]; //char byte_19AE44[128];
const int nXSectorSize = 60; const int nXSectorSize = 60;
const int nXSpriteSize = 56; const int nXSpriteSize = 56;
@ -517,9 +533,9 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
{ {
I_Error("%s: Map file corrupted", mapname.GetChars()); I_Error("%s: Map file corrupted", mapname.GetChars());
} }
byte_1A76C8 = 0; encrypted = 0;
if ((LittleShort(header.version) & 0xff00) == 0x700) { if ((LittleShort(header.version) & 0xff00) == 0x700) {
byte_1A76C8 = 1; encrypted = 1;
#ifdef NOONE_EXTENSIONS #ifdef NOONE_EXTENSIONS
// indicate if the map requires modern features to work properly // indicate if the map requires modern features to work properly
@ -536,7 +552,6 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
fr.Read(&mapHeader,37/* sizeof(mapHeader)*/); fr.Read(&mapHeader,37/* sizeof(mapHeader)*/);
if (mapHeader.mattid != 0 && mapHeader.mattid != 0x7474614d && mapHeader.mattid != 0x4d617474) { if (mapHeader.mattid != 0 && mapHeader.mattid != 0x7474614d && mapHeader.mattid != 0x4d617474) {
dbCrypt((char*)&mapHeader, sizeof(mapHeader), 0x7474614d); dbCrypt((char*)&mapHeader, sizeof(mapHeader), 0x7474614d);
byte_1A76C7 = 1;
} }
mapHeader.x = LittleLong(mapHeader.x); mapHeader.x = LittleLong(mapHeader.x);
@ -558,16 +573,16 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
*pAngle = mapHeader.ang; *pAngle = mapHeader.ang;
*pSector = mapHeader.sect; *pSector = mapHeader.sect;
gVisibility = g_visibility = mapHeader.visibility; gVisibility = g_visibility = mapHeader.visibility;
gSongId = mapHeader.mattid; gMattId = mapHeader.mattid;
if (byte_1A76C8) if (encrypted)
{ {
if (mapHeader.mattid == 0x7474614d || mapHeader.mattid == 0x4d617474) if (mapHeader.mattid == 0x7474614d || mapHeader.mattid == 0x4d617474)
{ {
byte_1A76C6 = 1; drawtile2048 = 1;
} }
else if (!mapHeader.mattid) else if (!mapHeader.mattid)
{ {
byte_1A76C6 = 0; drawtile2048 = 0;
} }
else else
{ {
@ -583,7 +598,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
numsectors = mapHeader.numsectors; numsectors = mapHeader.numsectors;
numwalls = mapHeader.numwalls; numwalls = mapHeader.numwalls;
dbInit(); dbInit();
if (byte_1A76C8) if (encrypted)
{ {
fr.Read(&byte_19AE44, 128); fr.Read(&byte_19AE44, 128);
dbCrypt((char*)&byte_19AE44, 128, numwalls); dbCrypt((char*)&byte_19AE44, 128, numwalls);
@ -598,7 +613,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
} }
gSkyCount = 1<< mapHeader.pskybits; gSkyCount = 1<< mapHeader.pskybits;
fr.Read(tpskyoff, gSkyCount*sizeof(tpskyoff[0])); fr.Read(tpskyoff, gSkyCount*sizeof(tpskyoff[0]));
if (byte_1A76C8) if (encrypted)
{ {
dbCrypt((char*)tpskyoff, gSkyCount*sizeof(tpskyoff[0]), gSkyCount*2); dbCrypt((char*)tpskyoff, gSkyCount*sizeof(tpskyoff[0]), gSkyCount*2);
} }
@ -616,7 +631,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
sectortype *pSector = &sector[i]; sectortype *pSector = &sector[i];
sectortypedisk load; sectortypedisk load;
fr.Read(&load, sizeof(sectortypedisk)); fr.Read(&load, sizeof(sectortypedisk));
if (byte_1A76C8) if (encrypted)
{ {
dbCrypt((char*)&load, sizeof(sectortypedisk), gMapRev*sizeof(sectortypedisk)); dbCrypt((char*)&load, sizeof(sectortypedisk), gMapRev*sizeof(sectortypedisk));
} }
@ -652,7 +667,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
XSECTOR *pXSector = &xsector[nXSector]; XSECTOR *pXSector = &xsector[nXSector];
memset(pXSector, 0, sizeof(XSECTOR)); memset(pXSector, 0, sizeof(XSECTOR));
int nCount; int nCount;
if (!byte_1A76C8) if (!encrypted)
{ {
nCount = nXSectorSize; nCount = nXSectorSize;
} }
@ -750,7 +765,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
walltype *pWall = &wall[i]; walltype *pWall = &wall[i];
walltypedisk load; walltypedisk load;
fr.Read(&load, sizeof(walltypedisk)); fr.Read(&load, sizeof(walltypedisk));
if (byte_1A76C8) if (encrypted)
{ {
dbCrypt((char*)&load, sizeof(walltypedisk), (gMapRev*sizeof(sectortypedisk)) | 0x7474614d); dbCrypt((char*)&load, sizeof(walltypedisk), (gMapRev*sizeof(sectortypedisk)) | 0x7474614d);
} }
@ -779,7 +794,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
XWALL *pXWall = &xwall[nXWall]; XWALL *pXWall = &xwall[nXWall];
memset(pXWall, 0, sizeof(XWALL)); memset(pXWall, 0, sizeof(XWALL));
int nCount; int nCount;
if (!byte_1A76C8) if (!encrypted)
{ {
nCount = nXWallSize; nCount = nXWallSize;
} }
@ -833,7 +848,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
spritetypedisk load; spritetypedisk load;
spritetype *pSprite = &sprite[i]; spritetype *pSprite = &sprite[i];
fr.Read(&load, sizeof(spritetypedisk)); // load into an intermediate buffer so that spritetype is no longer bound by file formats. fr.Read(&load, sizeof(spritetypedisk)); // load into an intermediate buffer so that spritetype is no longer bound by file formats.
if (byte_1A76C8) // What were these people thinking? :( if (encrypted) // What were these people thinking? :(
{ {
dbCrypt((char*)&load, sizeof(spritetypedisk), (gMapRev*sizeof(spritetypedisk)) | 0x7474614d); dbCrypt((char*)&load, sizeof(spritetypedisk), (gMapRev*sizeof(spritetypedisk)) | 0x7474614d);
} }
@ -874,7 +889,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
XSPRITE *pXSprite = &xsprite[nXSprite]; XSPRITE *pXSprite = &xsprite[nXSprite];
memset(pXSprite, 0, sizeof(XSPRITE)); memset(pXSprite, 0, sizeof(XSPRITE));
int nCount; int nCount;
if (!byte_1A76C8) if (!encrypted)
{ {
nCount = nXSpriteSize; nCount = nXSpriteSize;
} }
@ -948,7 +963,7 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
bitReader.skipBits(32); bitReader.skipBits(32);
xsprite[sprite[i].extra].reference = i; xsprite[sprite[i].extra].reference = i;
xsprite[sprite[i].extra].busy = IntToFixed(xsprite[sprite[i].extra].state); xsprite[sprite[i].extra].busy = IntToFixed(xsprite[sprite[i].extra].state);
if (!byte_1A76C8) { if (!encrypted) {
xsprite[sprite[i].extra].lT |= xsprite[sprite[i].extra].lB; xsprite[sprite[i].extra].lT |= xsprite[sprite[i].extra].lB;
} }
@ -978,22 +993,22 @@ void dbLoadMap(const char *pPath, int *pX, int *pY, int *pZ, short *pAngle, shor
if (pCRC) if (pCRC)
*pCRC = nCRC; *pCRC = nCRC;
PropagateMarkerReferences(); PropagateMarkerReferences();
if (byte_1A76C8) if (encrypted)
{ {
if (gSongId == 0x7474614d || gSongId == 0x4d617474) if (gMattId == 0x7474614d || gMattId == 0x4d617474)
{ {
byte_1A76C6 = 1; drawtile2048 = 1;
} }
else if (!gSongId) else if (!gMattId)
{ {
byte_1A76C6 = 0; drawtile2048 = 0;
} }
else else
{ {
I_Error("%s: Corrupted Map file", mapname.GetChars()); I_Error("%s: Corrupted Map file", mapname.GetChars());
} }
} }
else if (gSongId != 0) else if (gMattId != 0)
{ {
I_Error("%s: Corrupted Map file", mapname.GetChars()); I_Error("%s: Corrupted Map file", mapname.GetChars());
} }

View file

@ -298,13 +298,17 @@ struct SPRITEHIT {
extern unsigned short gStatCount[kMaxStatus + 1];; extern unsigned short gStatCount[kMaxStatus + 1];;
extern bool byte_1A76C6, byte_1A76C7, byte_1A76C8; extern bool drawtile2048, encrypted;
extern MAPHEADER2 byte_19AE44; extern MAPHEADER2 byte_19AE44;
extern XSPRITE xsprite[kMaxXSprites]; extern XSPRITE xsprite[kMaxXSprites];
extern XSECTOR xsector[kMaxXSectors]; extern XSECTOR xsector[kMaxXSectors];
extern XWALL xwall[kMaxXWalls]; extern XWALL xwall[kMaxXWalls];
extern XSECTOR xsectorbackup[kMaxXSectors];
extern XWALL xwallbackup[kMaxXWalls];
extern FixedBitArray<MAXSPRITES> activeXSprites;
extern SPRITEHIT gSpriteHit[kMaxXSprites]; extern SPRITEHIT gSpriteHit[kMaxXSprites];
extern char qsector_filler[kMaxSectors]; extern char qsector_filler[kMaxSectors];
@ -312,7 +316,7 @@ extern char qsector_filler[kMaxSectors];
extern int xvel[kMaxSprites], yvel[kMaxSprites], zvel[kMaxSprites]; extern int xvel[kMaxSprites], yvel[kMaxSprites], zvel[kMaxSprites];
extern int gVisibility; extern int gVisibility;
extern int gMapRev, gSongId, gSkyCount; extern int gMapRev, gMattId, gSkyCount;
extern const char *gItemText[]; extern const char *gItemText[];
extern const char *gAmmoText[]; extern const char *gAmmoText[];
extern const char *gWeaponText[]; extern const char *gWeaponText[];
@ -366,6 +370,7 @@ int qchangespritesect(short nSprite, short nSector);
int ChangeSpriteStat(int nSprite, int nStatus); int ChangeSpriteStat(int nSprite, int nStatus);
int qchangespritestat(short nSprite, short nStatus); int qchangespritestat(short nSprite, short nStatus);
void InitFreeList(unsigned short *pList, int nCount); void InitFreeList(unsigned short *pList, int nCount);
void InitFreeList(unsigned short* pList, int nCount, FixedBitArray<MAXSPRITES>& activeXSprites);
void InsertFree(unsigned short *pList, int nIndex); void InsertFree(unsigned short *pList, int nIndex);
unsigned short dbInsertXSprite(int nSprite); unsigned short dbInsertXSprite(int nSprite);
void dbDeleteXSprite(int nXSprite); void dbDeleteXSprite(int nXSprite);

View file

@ -31,7 +31,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "endgame.h" #include "endgame.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "player.h" #include "player.h"
#include "sound.h" #include "sound.h"
#include "view.h" #include "view.h"

View file

@ -33,7 +33,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "endgame.h" #include "endgame.h"
#include "aistate.h" #include "aistate.h"
#include "loadsave.h"
#include "sectorfx.h" #include "sectorfx.h"
#include "choke.h" #include "choke.h"
#include "view.h" #include "view.h"

View file

@ -32,7 +32,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "endgame.h" #include "endgame.h"
#include "inifile.h" #include "inifile.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "messages.h" #include "messages.h"
#include "seq.h" #include "seq.h"
#include "sound.h" #include "sound.h"
@ -45,7 +44,7 @@ BEGIN_BLD_NS
GAMEOPTIONS gGameOptions; GAMEOPTIONS gGameOptions;
GAMEOPTIONS gSingleGameOptions = { GAMEOPTIONS gSingleGameOptions = {
0, 2, 2, 0, 0, 0, 0, 0, 0, 0, 2, 3600, 1800, 1800, 7200 0, 2, 0, 0, 0, 0, 0, 0, 2, 3600, 1800, 1800, 7200
}; };
EPISODEINFO gEpisodeInfo[kMaxEpisodes+1]; EPISODEINFO gEpisodeInfo[kMaxEpisodes+1];

View file

@ -49,8 +49,6 @@ enum EGameFlag
struct GAMEOPTIONS { struct GAMEOPTIONS {
unsigned char nGameType; unsigned char nGameType;
unsigned char nDifficulty; unsigned char nDifficulty;
short nSaveGameSlot;
int picEntry;
char nMonsterSettings; char nMonsterSettings;
int uGameFlags; int uGameFlags;
int uNetGameFlags; int uNetGameFlags;

View file

@ -1,13 +1,12 @@
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
/* /*
Copyright (C) 2010-2019 EDuke32 developers and contributors Copyright (C) 2020 - Christoph Oelckers
Copyright (C) 2019 Nuke.YKT
This file is part of NBlood. This file is part of Raze
NBlood is free software; you can redistribute it and/or Raze is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License version 2 modify it under the terms of the GNU General Public License version 2
as published by the Free Software Foundation. of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful, This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of but WITHOUT ANY WARRANTY; without even the implied warranty of
@ -20,6 +19,7 @@ along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
#include "ns.h" // Must come before everything else! #include "ns.h" // Must come before everything else!
#include <stdio.h> #include <stdio.h>
@ -32,7 +32,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "globals.h" #include "globals.h"
#include "db.h" #include "db.h"
#include "messages.h" #include "messages.h"
#include "loadsave.h"
#include "sectorfx.h" #include "sectorfx.h"
#include "seq.h" #include "seq.h"
#include "sound.h" #include "sound.h"
@ -406,337 +405,233 @@ static AISTATE* allAIStates[] =
&zombieFTeslaRecoil, &zombieFTeslaRecoil,
}; };
void IndexAIState(AISTATE*& state) FSerializer& Serialize(FSerializer& arc, const char* keyname, AISTATE*& w, AISTATE** def)
{ {
int i = 0; int i = 0;
auto savestate = state; if (arc.isWriting())
{
for (auto cstate : allAIStates) for (auto cstate : allAIStates)
{ {
if (state == cstate) if (w == cstate)
{ {
state = (AISTATE*)(intptr_t)i; arc(keyname, i);
return; break;
} }
i++; i++;
} }
state = nullptr;
}
void UnindexAIState(AISTATE*& state)
{
auto index = intptr_t(state);
if (index >= 0 && index < countof(allAIStates))
{
state = allAIStates[index];
} }
else else
{ {
state = nullptr; arc(keyname, i);
} if (i >= 0 && i < countof(allAIStates))
}
unsigned int dword_27AA38 = 0;
unsigned int dword_27AA3C = 0;
unsigned int dword_27AA40 = 0;
FileWriter *LoadSave::hSFile = NULL;
FileReader LoadSave::hLFile;
TDeletingArray<LoadSave*> LoadSave::loadSaves;
void sub_76FD4(void)
{ {
w = allAIStates[i];
} }
else
void LoadSave::Save(void)
{ {
I_Error("Pure virtual function called"); w = nullptr;
}
void LoadSave::Load(void)
{
I_Error("Pure virtual function called");
}
void LoadSave::Read(void *pData, int nSize)
{
dword_27AA38 += nSize;
assert(hLFile.isOpen());
if (hLFile.Read(pData, nSize) != nSize)
I_Error("Error reading save file.");
}
void LoadSave::Write(const void *pData, int nSize)
{
dword_27AA38 += nSize;
dword_27AA3C += nSize;
assert(hSFile != NULL);
if (hSFile->Write(pData, nSize) != (size_t)nSize)
I_Error("File error #%d writing save file.", errno);
}
bool GameInterface::LoadGame()
{
LoadSave::hLFile = ReadSavegameChunk("snapshot.bld");
if (!LoadSave::hLFile.isOpen())
return false;
for (auto rover : LoadSave::loadSaves)
{
rover->Load();
}
LoadSave::hLFile.Close();
FinishSavegameRead();
InitSectorFX();
viewInitializePrediction();
PreloadCache();
if (!gMe->packSlots[1].isActive) // if diving suit is not active, turn off reverb sound effect
sfxSetReverb(0);
ambInit();
for (int i = 0; i < gNetPlayers; i++)
playerSetRace(&gPlayer[i], gPlayer[i].lifeMode);
viewSetErrorMessage("");
Net_ClearFifo();
paused = 0;
#ifdef USE_OPENGL
Polymost_prepare_loadboard();
#endif
#ifdef POLYMER
if (videoGetRenderMode() == REND_POLYMER)
polymer_loadboard();
// this light pointer nulling needs to be outside the videoGetRenderMode check
// because we might be loading the savegame using another renderer but
// change to Polymer later
for (int i=0; i<kMaxSprites; i++)
{
gPolymerLight[i].lightptr = NULL;
gPolymerLight[i].lightId = -1;
}
#endif
Mus_ResumeSaved();
return true;
}
bool GameInterface::SaveGame()
{
LoadSave::hSFile = WriteSavegameChunk("snapshot.bld");
try
{
dword_27AA38 = 0;
dword_27AA40 = 0;
for (auto rover : LoadSave::loadSaves)
{
rover->Save();
if (dword_27AA38 > dword_27AA40)
dword_27AA40 = dword_27AA38;
dword_27AA38 = 0;
} }
} }
catch (CRecoverableError & err) return arc;
{
// Let's not abort for write errors.
Printf(TEXTCOLOR_RED "%s\n", err.what());
return false;
}
LoadSave::hSFile = NULL;
return 1;
} }
class MyLoadSave : public LoadSave FSerializer& Serialize(FSerializer& arc, const char* keyname, XWALL& w, XWALL* def)
{ {
public: if (arc.BeginObject(keyname))
virtual void Load(void); {
virtual void Save(void); arc("flags", w.flags, def->flags)
}; ("busy", w.busy, def->busy)
("reference", w.reference, def->reference)
("data", w.data, def->data)
("txid", w.txID, def->txID)
("rxid", w.rxID, def->rxID)
("busytime", w.busyTime, def->busyTime)
("waittime", w.waitTime, def->waitTime)
("command", w.command, def->command)
("panxvel", w.panXVel, def->panXVel)
("panyvel", w.panYVel, def->panYVel)
("key", w.key, def->key)
("xpanfrac", w.xpanFrac, def->xpanFrac)
("ypanfrac", w.ypanFrac, def->ypanFrac)
.EndObject();
}
return arc;
}
void MyLoadSave::Load(void) FSerializer& Serialize(FSerializer& arc, const char* keyname, XSECTOR& w, XSECTOR* def)
{
if (arc.BeginObject(keyname))
{
arc("flags", w.flags, def->flags)
("busy", w.busy, def->busy)
("reference", w.reference, def->reference)
("data", w.data, def->data)
("txid", w.txID, def->txID)
("rxid", w.rxID, def->rxID)
("offceilz", w.offCeilZ, def->offCeilZ)
("onceilz", w.onCeilZ, def->onCeilZ)
("offloorz", w.offFloorZ, def->offFloorZ)
("onloorz", w.onFloorZ, def->onFloorZ)
("windvel", w.windVel, def->windVel)
("busytimea", w.busyTimeA, def->busyTimeA)
("busytimeb", w.busyTimeB, def->busyTimeB)
("waittimea", w.waitTimeA, def->waitTimeA)
("waittimeb", w.waitTimeB, def->waitTimeB)
("panangle", w.panAngle, def->panAngle)
("marker0", w.marker0, def->marker0)
("marker1", w.marker1, def->marker1)
("windang", w.windAng, def->windAng)
("bobtheta", w.bobTheta, def->bobTheta)
("bobspeed", w.bobSpeed, def->bobSpeed)
("busywavea", w.busyWaveA, def->busyWaveA)
("busywaveb", w.busyWaveB, def->busyWaveB)
("command", w.command, def->command)
("amplitude", w.amplitude, def->amplitude)
("freq", w.freq, def->freq)
("phase", w.phase, def->phase)
("wave", w.wave, def->wave)
("shade", w.shade, def->shade)
("panvel", w.panVel, def->panVel)
("depth", w.Depth, def->Depth)
("key", w.Key, def->Key)
("ceilpal", w.ceilpal, def->ceilpal)
("ceilxpanfrac", w.ceilXPanFrac, def->ceilXPanFrac)
("ceilypanfrac", w.ceilYPanFrac, def->ceilYPanFrac)
("floorxpanfrac", w.floorXPanFrac, def->floorXPanFrac)
("floorypanfrac", w.floorYPanFrac, def->floorYPanFrac)
("floorpal", w.floorpal, def->floorpal)
("damagetype", w.damageType, def->damageType)
("bobzrange", w.bobZRange, def->bobZRange)
.EndObject();
}
return arc;
}
FSerializer& Serialize(FSerializer& arc, const char* keyname, XSPRITE& w, XSPRITE* def)
{
if (arc.BeginObject(keyname))
{
arc("flags", w.flags, def->flags)
("busy", w.busy, def->busy)
("reference", w.reference, def->reference)
("txid", w.txID, def->txID)
("rxid", w.rxID, def->rxID)
("command", w.command, def->command)
("data1", w.data1, def->data1)
("data2", w.data2, def->data2)
("data3", w.data3, def->data3)
("data4", w.data4, def->data4)
("targetX", w.targetX, def->targetX)
("targetY", w.targetY, def->targetY)
("targetZ", w.targetZ, def->targetZ)
("target", w.target, def->target)
("sysdata1", w.sysData1, def->sysData1)
("sysdata2", w.sysData2, def->sysData2)
("scale", w.scale, def->scale)
("physattr", w.physAttr, def->physAttr)
("health", w.health, def->health)
("burnsource", w.burnSource, def->burnSource)
("busytime", w.busyTime, def->busyTime)
("waittime", w.waitTime, def->waitTime)
("goalang", w.goalAng, def->goalAng)
("burntime", w.burnTime, def->burnTime)
("height", w.height, def->height)
("statetimer", w.stateTimer, def->stateTimer)
("respawnpending", w.respawnPending, def->respawnPending)
("dropmsg", w.dropMsg, def->dropMsg)
("key", w.key, def->key)
("lskill", w.lSkill, def->lSkill)
("lockmsg", w.lockMsg, def->lockMsg)
("dodgedir", w.dodgeDir, def->dodgeDir)
.EndObject();
}
return arc;
}
FSerializer& Serialize(FSerializer& arc, const char* keyname, HITINFO& w, HITINFO* def)
{
if (arc.BeginObject(keyname))
{
arc("sect", w.hitsect)
("sprite", w.hitsprite)
("wall", w.hitwall)
("x", w.hitx)
("y", w.hity)
("z", w.hitz)
.EndObject();
}
return arc;
}
FSerializer& Serialize(FSerializer& arc, const char* keyname, GAMEOPTIONS& w, GAMEOPTIONS* def)
{
if (arc.BeginObject(keyname))
{
arc("type", w.nGameType)
("difficulty", w.nDifficulty)
("monster", w.nMonsterSettings)
("flags", w.uGameFlags)
("netflags", w.uNetGameFlags)
("weapons", w.nWeaponSettings)
("items", w.nItemSettings)
("respawn", w.nRespawnSettings)
("team", w.nTeamSettings)
("monsterrespawntime", w.nMonsterRespawnTime)
("itemrespawntime", w.nItemRespawnTime)
("specialrespawntime", w.nSpecialRespawnTime)
("weaponsv10x", w.weaponsV10x)
("friendlyfire", w.bFriendlyFire)
("keepkeys", w.bKeepKeysOnRespawn)
.EndObject();
}
return arc;
}
void SerializeState(FSerializer& arc)
{
if (arc.isReading())
{
cheatReset();
}
if (arc.BeginObject("state"))
{ {
psky_t* pSky = tileSetupSky(DEFAULTPSKY); psky_t* pSky = tileSetupSky(DEFAULTPSKY);
int id;
Read(&id, sizeof(id));
Read(&gGameOptions, sizeof(gGameOptions));
int nNumSprites; arc.Array("sector_filler", qsector_filler, numsectors)
Read(&nNumSprites, sizeof(nNumSprites)); ("visibility", gVisibility)
Read(qsector_filler, sizeof(qsector_filler[0])*numsectors); ("frameclock", gFrameClock)
Read(&pSky->horizfrac, sizeof(pSky->horizfrac)); ("framecount", gFrameCount)
Read(&pSky->yoffs, sizeof(pSky->yoffs)); .Array("basewall", baseWall, numwalls)
Read(&pSky->yscale, sizeof(pSky->yscale)); .SparseArray("basesprite", baseSprite, kMaxSprites, activeSprites)
Read(&gVisibility, sizeof(gVisibility)); .Array("basefloor", baseFloor, numsectors)
Read(pSky->tileofs, sizeof(pSky->tileofs)); .Array("baseceil", baseCeil, numsectors)
Read(&pSky->lognumtiles, sizeof(pSky->lognumtiles)); .Array("velfloor", velFloor, numsectors)
Read(gotpic, sizeof(gotpic)); .Array("velceil", velCeil, numsectors)
Read(gotsector, sizeof(gotsector)); ("hitinfo", gHitInfo)
Read(&gFrameClock, sizeof(gFrameClock)); .Array("statcount", gStatCount, kMaxStatus + 1)
Read(&gFrameCount, sizeof(gFrameCount)); ("xwallsused", XWallsUsed)
Read(&paused, sizeof(paused)); ("xsectorsused", XSectorsUsed)
Read(baseWall, sizeof(baseWall[0])*numwalls); ("fogmode", gFogMode)
Read(baseSprite, sizeof(baseSprite[0])*nNumSprites);
Read(baseFloor, sizeof(baseFloor[0])*numsectors);
Read(baseCeil, sizeof(baseCeil[0])*numsectors);
Read(velFloor, sizeof(velFloor[0])*numsectors);
Read(velCeil, sizeof(velCeil[0])*numsectors);
Read(&gHitInfo, sizeof(gHitInfo));
Read(&byte_1A76C6, sizeof(byte_1A76C6));
Read(&byte_1A76C8, sizeof(byte_1A76C8));
Read(&byte_1A76C7, sizeof(byte_1A76C7));
Read(&byte_19AE44, sizeof(byte_19AE44));
Read(gStatCount, sizeof(gStatCount));
Read(nextXSprite, sizeof(nextXSprite));
Read(&XWallsUsed, sizeof(XWallsUsed));
Read(&XSectorsUsed, sizeof(XSectorsUsed));
memset(xsprite, 0, sizeof(xsprite));
for (int nSprite = 0; nSprite < kMaxSprites; nSprite++)
{
if (sprite[nSprite].statnum < kMaxStatus)
{
int nXSprite = sprite[nSprite].extra;
if (nXSprite > 0)
{
Read(&xsprite[nXSprite], sizeof(XSPRITE));
UnindexAIState(xsprite[nXSprite].aiState);
}
}
}
memset(xwall, 0, sizeof(xwall));
for (int nWall = 0; nWall < numwalls; nWall++)
{
int nXWall = wall[nWall].extra;
if (nXWall > 0)
Read(&xwall[nXWall], sizeof(XWALL));
}
memset(xsector, 0, sizeof(xsector));
for (int nSector = 0; nSector < numsectors; nSector++)
{
int nXSector = sector[nSector].extra;
if (nXSector > 0)
Read(&xsector[nXSector], sizeof(XSECTOR));
}
Read(xvel, nNumSprites*sizeof(xvel[0]));
Read(yvel, nNumSprites*sizeof(yvel[0]));
Read(zvel, nNumSprites*sizeof(zvel[0]));
Read(&gMapRev, sizeof(gMapRev));
Read(&gSongId, sizeof(gSkyCount));
Read(&gFogMode, sizeof(gFogMode));
#ifdef NOONE_EXTENSIONS #ifdef NOONE_EXTENSIONS
Read(&gModernMap, sizeof(gModernMap)); ("modern", gModernMap)
#endif #endif
psky_t *skyInfo = tileSetupSky(DEFAULTPSKY); ("cheating", bPlayerCheated)
Read(skyInfo, sizeof(*skyInfo)); ("nextlevel", gNextLevel)
skyInfo->combinedtile = -1; ("skyhoriz", pSky->horizfrac)
cheatReset(); ("skyy", pSky->yoffs)
Read(&bPlayerCheated, sizeof(bPlayerCheated)); ("scale", pSky->yscale)
Read(&gNextLevel, sizeof(gNextLevel)); .Array("tileofs", pSky->tileofs, countof(pSky->tileofs))
Read(&gGameOptions, sizeof(gGameOptions)); ("numtiles", pSky->lognumtiles)
("gameoptions", gGameOptions)
.Array("xwall", xwall, xwallbackup, XWallsUsed) // todo
.Array("xsector", xsector, xsectorbackup, XSectorsUsed)
.SparseArray("xsprite", xsprite, kMaxXSprites, activeXSprites)
.SparseArray("xvel", xvel, kMaxSprites, activeSprites)
.SparseArray("yvel", yvel, kMaxSprites, activeSprites)
.SparseArray("zvel", zvel, kMaxSprites, activeSprites)
.EndObject();
} }
void MyLoadSave::Save(void)
{
psky_t *pSky = tileSetupSky(0);
int nNumSprites = 0;
int id = 0x5653424e/*'VSBN'*/;
Write(&id, sizeof(id));
for (int nSprite = 0; nSprite < kMaxSprites; nSprite++)
{
if (sprite[nSprite].statnum < kMaxStatus && nSprite > nNumSprites)
nNumSprites = nSprite;
}
//nNumSprites += 2;
nNumSprites++;
Write(&gGameOptions, sizeof(gGameOptions));
Write(&nNumSprites, sizeof(nNumSprites));
Write(qsector_filler, sizeof(qsector_filler[0])*numsectors);
Write(&pSky->horizfrac, sizeof(pSky->horizfrac));
Write(&pSky->yoffs, sizeof(pSky->yoffs));
Write(&pSky->yscale, sizeof(pSky->yscale));
Write(&gVisibility, sizeof(gVisibility));
Write(pSky->tileofs, sizeof(pSky->tileofs));
Write(&pSky->lognumtiles, sizeof(pSky->lognumtiles));
Write(gotpic, sizeof(gotpic));
Write(gotsector, sizeof(gotsector));
Write(&gFrameClock, sizeof(gFrameClock));
Write(&gFrameCount, sizeof(gFrameCount));
Write(&paused, sizeof(paused));
Write(baseWall, sizeof(baseWall[0])*numwalls);
Write(baseSprite, sizeof(baseSprite[0])*nNumSprites);
Write(baseFloor, sizeof(baseFloor[0])*numsectors);
Write(baseCeil, sizeof(baseCeil[0])*numsectors);
Write(velFloor, sizeof(velFloor[0])*numsectors);
Write(velCeil, sizeof(velCeil[0])*numsectors);
Write(&gHitInfo, sizeof(gHitInfo));
Write(&byte_1A76C6, sizeof(byte_1A76C6));
Write(&byte_1A76C8, sizeof(byte_1A76C8));
Write(&byte_1A76C7, sizeof(byte_1A76C7));
Write(&byte_19AE44, sizeof(byte_19AE44));
Write(gStatCount, sizeof(gStatCount));
Write(nextXSprite, sizeof(nextXSprite));
Write(&XWallsUsed, sizeof(XWallsUsed));
Write(&XSectorsUsed, sizeof(XSectorsUsed));
for (int nSprite = 0; nSprite < kMaxSprites; nSprite++)
{
if (sprite[nSprite].statnum < kMaxStatus)
{
int nXSprite = sprite[nSprite].extra;
if (nXSprite > 0)
{
auto saved = xsprite[nXSprite].aiState;
IndexAIState(xsprite[nXSprite].aiState);
Write(&xsprite[nXSprite], sizeof(XSPRITE));
xsprite[nXSprite].aiState = saved;
}
}
}
for (int nWall = 0; nWall < numwalls; nWall++)
{
int nXWall = wall[nWall].extra;
if (nXWall > 0)
Write(&xwall[nXWall], sizeof(XWALL));
}
for (int nSector = 0; nSector < numsectors; nSector++)
{
int nXSector = sector[nSector].extra;
if (nXSector > 0)
Write(&xsector[nXSector], sizeof(XSECTOR));
}
Write(xvel, nNumSprites*sizeof(xvel[0]));
Write(yvel, nNumSprites*sizeof(yvel[0]));
Write(zvel, nNumSprites*sizeof(zvel[0]));
Write(&gMapRev, sizeof(gMapRev));
Write(&gSongId, sizeof(gSkyCount));
Write(&gFogMode, sizeof(gFogMode));
#ifdef NOONE_EXTENSIONS
Write(&gModernMap, sizeof(gModernMap));
#endif
psky_t *skyInfo = tileSetupSky(DEFAULTPSKY);
Write(skyInfo, sizeof(*skyInfo));
Write(&bPlayerCheated, sizeof(bPlayerCheated));
Write(&gNextLevel, sizeof(gNextLevel));
Write(&gGameOptions, sizeof(gGameOptions));
}
void ViewLoadSaveConstruct(void);
#ifdef NOONE_EXTENSIONS
void NNLoadSaveConstruct(void);
#endif
void LoadSaveSetup(void)
{
new MyLoadSave();
ViewLoadSaveConstruct();
#ifdef NOONE_EXTENSIONS
NNLoadSaveConstruct();
#endif
} }
@ -748,6 +643,8 @@ void SerializeActor(FSerializer& arc);
void SerializeAI(FSerializer& arc); void SerializeAI(FSerializer& arc);
void SerializeGameStats(FSerializer& arc); void SerializeGameStats(FSerializer& arc);
void SerializePlayers(FSerializer& arc); void SerializePlayers(FSerializer& arc);
void SerializeView(FSerializer& arc);
void SerializeNNExts(FSerializer& arc);
void GameInterface::SerializeGameState(FSerializer& arc) void GameInterface::SerializeGameState(FSerializer& arc)
{ {
@ -772,6 +669,8 @@ void GameInterface::SerializeGameState(FSerializer& arc)
} }
} }
arc.SerializeMemory("activexsprites", activeXSprites.Storage(), activeXSprites.StorageSize()); arc.SerializeMemory("activexsprites", activeXSprites.Storage(), activeXSprites.StorageSize());
SerializeState(arc);
InitFreeList(nextXSprite, kMaxXSprites, activeXSprites);
SerializeActor(arc); SerializeActor(arc);
SerializeAI(arc); SerializeAI(arc);
SerializePlayers(arc); SerializePlayers(arc);
@ -780,6 +679,27 @@ void GameInterface::SerializeGameState(FSerializer& arc)
SerializeSequences(arc); SerializeSequences(arc);
SerializeWarp(arc); SerializeWarp(arc);
SerializeTriggers(arc); SerializeTriggers(arc);
SerializeView(arc);
#ifdef NOONE_EXTENSIONS
SerializeNNExts(arc);
#endif
if (arc.isReading())
{
InitSectorFX();
viewInitializePrediction();
PreloadCache();
if (!gMe->packSlots[1].isActive) // if diving suit is not active, turn off reverb sound effect
sfxSetReverb(0);
ambInit();
for (int i = 0; i < gNetPlayers; i++)
playerSetRace(&gPlayer[i], gPlayer[i].lifeMode);
viewSetErrorMessage("");
Net_ClearFifo();
paused = 0;
Polymost_prepare_loadboard();
Mus_ResumeSaved();
}
} }

View file

@ -27,23 +27,5 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
struct FSavegameNode; struct FSavegameNode;
BEGIN_BLD_NS BEGIN_BLD_NS
class LoadSave {
public:
static LoadSave head;
static FileWriter *hSFile;
static FileReader hLFile;
static TDeletingArray<LoadSave*> loadSaves;
LoadSave() {
loadSaves.Push(this);
}
virtual ~LoadSave() = default;
virtual void Save(void);
virtual void Load(void);
void Read(void *, int);
void Write(const void *, int);
};
void LoadSaveSetup(void);
extern FixedBitArray<MAXSPRITES> activeXSprites;
END_BLD_NS END_BLD_NS

View file

@ -31,7 +31,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "eventq.h" #include "eventq.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "messages.h" #include "messages.h"
#include "player.h" #include "player.h"
#include "view.h" #include "view.h"

View file

@ -28,7 +28,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "blood.h" #include "blood.h"
#include "db.h" #include "db.h"
#include "gameutil.h" #include "gameutil.h"
#include "loadsave.h"
#include "player.h" #include "player.h"
#include "view.h" #include "view.h"

View file

@ -32,7 +32,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "nnexts.h" #include "nnexts.h"
#ifdef NOONE_EXTENSIONS #ifdef NOONE_EXTENSIONS
#include <random> #include <random>
#include "loadsave.h"
#include "player.h" #include "player.h"
#include "aiunicult.h" #include "aiunicult.h"
#include "triggers.h" #include "triggers.h"
@ -45,6 +44,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "sound.h" #include "sound.h"
#include "seq.h" #include "seq.h"
#include "ai.h" #include "ai.h"
#include "savegamehelp.h"
BEGIN_BLD_NS BEGIN_BLD_NS
@ -5286,43 +5286,83 @@ void callbackGenDudeUpdate(int nSprite) // 24
} }
class NNLoadSave : public LoadSave
{
virtual void Load(void);
virtual void Save(void);
};
void NNLoadSave::Load(void) //---------------------------------------------------------------------------
//
//
//
//---------------------------------------------------------------------------
FSerializer& Serialize(FSerializer& arc, const char* keyname, GENDUDEEXTRA& w, GENDUDEEXTRA* def)
{ {
Read(gSpriteMass, sizeof(gSpriteMass)); if (arc.BeginObject(keyname))
Read(&gProxySpritesCount, sizeof(gProxySpritesCount)); {
Read(gProxySpritesList, sizeof(gProxySpritesList)); arc.Array("initvals", w.initVals, 3)
Read(&gSightSpritesCount, sizeof(gSightSpritesCount)); .Array("availdeaths", w.availDeaths, kDamageMax)
Read(gSightSpritesList, sizeof(gSightSpritesList)); ("movespeed", w.moveSpeed)
Read(&gPhysSpritesCount, sizeof(gPhysSpritesCount)); ("firedist", w.fireDist)
Read(gPhysSpritesList, sizeof(gPhysSpritesList)); ("throwdist", w.throwDist)
Read(&gImpactSpritesCount, sizeof(gImpactSpritesCount)); ("curweapon", w.curWeapon)
Read(gImpactSpritesList, sizeof(gImpactSpritesList)); ("weapontype", w.weaponType)
Read(&gEventRedirectsUsed, sizeof(gEventRedirectsUsed)); ("basedispersion", w.baseDispersion)
("slavecount", w.slaveCount)
("lifeleech", w.nLifeLeech)
.Array("slaves", w.slave, w.slaveCount)
.Array("dmgcontrol", w.dmgControl, kDamageMax)
.Array("updreq", w.updReq, kGenDudePropertyMax)
("flags", w.flags)
.EndObject();
}
return arc;
} }
void NNLoadSave::Save(void) FSerializer& Serialize(FSerializer& arc, const char* keyname, SPRITEMASS& w, SPRITEMASS* def)
{ {
Write(gSpriteMass, sizeof(gSpriteMass)); static SPRITEMASS nul;
Write(&gProxySpritesCount, sizeof(gProxySpritesCount)); if (arc.isReading()) w = {};
Write(gProxySpritesList, sizeof(gProxySpritesList)); if (arc.BeginObject(keyname))
Write(&gSightSpritesCount, sizeof(gSightSpritesCount)); {
Write(gSightSpritesList, sizeof(gSightSpritesList)); arc ("seq", w.seqId, &nul.seqId)
Write(&gPhysSpritesCount, sizeof(gPhysSpritesCount)); ("picnum", w.picnum, &nul.picnum)
Write(gPhysSpritesList, sizeof(gPhysSpritesList)); ("xrepeat", w.xrepeat, &nul.xrepeat)
Write(&gImpactSpritesCount, sizeof(gImpactSpritesCount)); ("yrepeat", w.yrepeat, &nul.yrepeat)
Write(gImpactSpritesList, sizeof(gImpactSpritesList)); ("clipdist", w.clipdist)
Write(&gEventRedirectsUsed, sizeof(gEventRedirectsUsed)); ("mass", w.mass)
("airvel", w.airVel)
("fraction", w.fraction)
.EndObject();
}
return arc;
} }
void NNLoadSaveConstruct(void) void SerializeNNExts(FSerializer& arc)
{ {
new NNLoadSave(); if (arc.BeginObject("nnexts"))
{
// the GenDudeArray only contains valid info for kDudeModernCustom and kDudeModernCustomBurning so only save the relevant entries as these are not small.
bool foundsome = false;
for (int i = 0; i < kMaxSprites; i++)
{
if (activeSprites[i] && (sprite[i].type == kDudeModernCustom || sprite[i].type == kDudeModernCustomBurning))
{
if (!foundsome) arc.BeginArray("gendudeextra");
foundsome = true;
arc(nullptr, gGenDudeExtra[i]);
}
}
if (foundsome) arc.EndArray();
arc.SparseArray("spritemass", gSpriteMass, kMaxSprites, activeXSprites)
("proxyspritescount", gProxySpritesCount)
.Array("proxyspriteslist", gProxySpritesList, gProxySpritesCount)
("sightspritescount", gSightSpritesCount)
.Array("sightspriteslist", gSightSpritesList, gSightSpritesCount)
("physspritescount", gPhysSpritesCount)
.Array("physspriteslist", gPhysSpritesList, gPhysSpritesCount)
("impactspritescount", gImpactSpritesCount)
.Array("impactspriteslist", gImpactSpritesList, gImpactSpritesCount)
("eventredirects", gEventRedirectsUsed)
.EndObject();
}
} }
/////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////

View file

@ -36,7 +36,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "gib.h" #include "gib.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "player.h" #include "player.h"
#include "seq.h" #include "seq.h"
#include "sound.h" #include "sound.h"

View file

@ -33,7 +33,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "endgame.h" #include "endgame.h"
#include "aistate.h" #include "aistate.h"
#include "loadsave.h"
#include "sectorfx.h" #include "sectorfx.h"
#include "choke.h" #include "choke.h"
#include "view.h" #include "view.h"

View file

@ -33,7 +33,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "endgame.h" #include "endgame.h"
#include "aistate.h" #include "aistate.h"
#include "loadsave.h"
#include "sectorfx.h" #include "sectorfx.h"
#include "choke.h" #include "choke.h"
#include "view.h" #include "view.h"

View file

@ -34,7 +34,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "eventq.h" #include "eventq.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "sound.h" #include "sound.h"
#include "seq.h" #include "seq.h"
#include "gameutil.h" #include "gameutil.h"

View file

@ -41,7 +41,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "gib.h" #include "gib.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "player.h" #include "player.h"
#include "seq.h" #include "seq.h"
#include "qav.h" #include "qav.h"

View file

@ -33,7 +33,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "endgame.h" #include "endgame.h"
#include "aistate.h" #include "aistate.h"
#include "loadsave.h"
#include "sectorfx.h" #include "sectorfx.h"
#include "choke.h" #include "choke.h"
#include "view.h" #include "view.h"
@ -481,8 +480,8 @@ void UpdateBlend()
videoTintBlood(nRed, nGreen, nBlue); videoTintBlood(nRed, nGreen, nBlue);
} }
char otherMirrorGotpic[2]; uint8_t otherMirrorGotpic[2];
char bakMirrorGotpic[2]; uint8_t bakMirrorGotpic[2];
// int gVisibility; // int gVisibility;
int deliriumTilt, deliriumTurn, deliriumPitch; int deliriumTilt, deliriumTurn, deliriumPitch;
@ -988,7 +987,7 @@ void viewDrawScreen(bool sceneonly)
gChoke.animateChoke(160, zn, (int)gInterpolate); gChoke.animateChoke(160, zn, (int)gInterpolate);
} }
#if 0 #if 0
if (byte_1A76C6) if (drawtile_2048)
{ {
DrawStatSprite(2048, xdim-15, 20); DrawStatSprite(2048, xdim-15, 20);
} }
@ -1065,36 +1064,17 @@ bool GameInterface::DrawAutomapPlayer(int x, int y, int z, int a)
return true; return true;
} }
void SerializeView(FSerializer& arc)
class ViewLoadSave : public LoadSave {
public:
void Load(void);
void Save(void);
};
void ViewLoadSave::Load(void)
{ {
Read(otherMirrorGotpic, sizeof(otherMirrorGotpic)); if (arc.BeginObject("view"))
Read(bakMirrorGotpic, sizeof(bakMirrorGotpic)); {
Read(&gScreenTilt, sizeof(gScreenTilt)); arc("screentilt", gScreenTilt)
Read(&deliriumTilt, sizeof(deliriumTilt)); ("deliriumtilt", deliriumTilt)
Read(&deliriumTurn, sizeof(deliriumTurn)); ("deliriumturn", deliriumTurn)
Read(&deliriumPitch, sizeof(deliriumPitch)); ("deliriumpitch", deliriumPitch)
.EndObject();
}
} }
void ViewLoadSave::Save(void)
{
Write(otherMirrorGotpic, sizeof(otherMirrorGotpic));
Write(bakMirrorGotpic, sizeof(bakMirrorGotpic));
Write(&gScreenTilt, sizeof(gScreenTilt));
Write(&deliriumTilt, sizeof(deliriumTilt));
Write(&deliriumTurn, sizeof(deliriumTurn));
Write(&deliriumPitch, sizeof(deliriumPitch));
}
void ViewLoadSaveConstruct(void)
{
new ViewLoadSave();
}
END_BLD_NS END_BLD_NS

View file

@ -29,7 +29,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "db.h" #include "db.h"
#include "gameutil.h" #include "gameutil.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "view.h" #include "view.h"
#include "nnexts.h" #include "nnexts.h"
@ -333,33 +332,4 @@ void SerializeWarp(FSerializer& arc)
} }
} }
class WarpLoadSave : public LoadSave
{
public:
virtual void Load();
virtual void Save();
};
void WarpLoadSave::Load()
{
Read(gStartZone, sizeof(gStartZone));
Read(gUpperLink, sizeof(gUpperLink));
Read(gLowerLink, sizeof(gLowerLink));
}
void WarpLoadSave::Save()
{
Write(gStartZone, sizeof(gStartZone));
Write(gUpperLink, sizeof(gUpperLink));
Write(gLowerLink, sizeof(gLowerLink));
}
void WarpLoadSaveConstruct(void)
{
new WarpLoadSave();
}
END_BLD_NS END_BLD_NS

View file

@ -38,7 +38,6 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "gameutil.h" #include "gameutil.h"
#include "globals.h" #include "globals.h"
#include "levels.h" #include "levels.h"
#include "loadsave.h"
#include "player.h" #include "player.h"
#include "qav.h" #include "qav.h"
#include "seq.h" #include "seq.h"

View file

@ -307,7 +307,6 @@ typedef struct {
int16_t tileofs[MAXPSKYTILES]; // for 0 <= j < (1<<lognumtiles): tile offset relative to basetile int16_t tileofs[MAXPSKYTILES]; // for 0 <= j < (1<<lognumtiles): tile offset relative to basetile
int32_t yscale; int32_t yscale;
int combinedtile;
} psky_t; } psky_t;
// Index of map-global (legacy) multi-sky: // Index of map-global (legacy) multi-sky:

View file

@ -243,6 +243,18 @@ void bfirst_search_try(T *const list, uint8_t *const bitmap, T *const eltnumptr,
/* End dependence on compat.o object. */ /* End dependence on compat.o object. */
inline FSerializer& Serialize(FSerializer& arc, const char* key, vec2_t& c, vec2_t* def)
{
if (def && !memcmp(&c, def, sizeof(c))) return arc;
if (arc.BeginObject(key))
{
arc("x", c.x, def? &def->x : nullptr)
("y", c.y, def ? &def->y : nullptr)
.EndObject();
}
return arc;
}
inline FSerializer& Serialize(FSerializer& arc, const char* key, vec3_t& c, vec3_t* def) inline FSerializer& Serialize(FSerializer& arc, const char* key, vec3_t& c, vec3_t* def)
{ {
if (def && !memcmp(&c, def, sizeof(c))) return arc; if (def && !memcmp(&c, def, sizeof(c))) return arc;
@ -256,5 +268,4 @@ inline FSerializer& Serialize(FSerializer& arc, const char* key, vec3_t& c, vec3
return arc; return arc;
} }
#endif // compat_h_ #endif // compat_h_

View file

@ -808,14 +808,12 @@ psky_t * tileSetupSky(int32_t const tilenum)
for (auto& sky : multipskies) for (auto& sky : multipskies)
if (tilenum == sky.tilenum) if (tilenum == sky.tilenum)
{ {
sky.combinedtile = -1; // invalidate the old content
return &sky; return &sky;
} }
multipskies.Reserve(1); multipskies.Reserve(1);
multipskies.Last() = {}; multipskies.Last() = {};
multipskies.Last().tilenum = tilenum; multipskies.Last().tilenum = tilenum;
multipskies.Last().combinedtile = -1;
multipskies.Last().yscale = 65536; multipskies.Last().yscale = 65536;
return &multipskies.Last(); return &multipskies.Last();
} }