mirror of
https://github.com/dhewm/dhewm3.git
synced 2025-02-17 01:31:47 +00:00
Use more than one QuickSave file, #392
Now the game cycles between QuickSave, QuickSave2, QuickSave3, ... (up to com_numQuicksaves files, 4 by default, up to 99), always replacing the oldest. Quick-loading always loads the newest quicksave, but all quicksaves can be loaded via the load game menu.
This commit is contained in:
parent
277dbf89f1
commit
10dea591a8
2 changed files with 107 additions and 6 deletions
|
@ -58,6 +58,9 @@ idCVar idSessionLocal::com_aviDemoTics( "com_aviDemoTics", "2", CVAR_SYSTEM | CV
|
|||
idCVar idSessionLocal::com_wipeSeconds( "com_wipeSeconds", "1", CVAR_SYSTEM, "" );
|
||||
idCVar idSessionLocal::com_guid( "com_guid", "", CVAR_SYSTEM | CVAR_ARCHIVE | CVAR_ROM, "" );
|
||||
|
||||
idCVar idSessionLocal::com_numQuicksaves( "com_numQuicksaves", "4", CVAR_SYSTEM|CVAR_ARCHIVE|CVAR_INTEGER,
|
||||
"number of quicksaves to keep before overwriting the oldest", 1, 99 );
|
||||
|
||||
idSessionLocal sessLocal;
|
||||
idSession *session = &sessLocal;
|
||||
|
||||
|
@ -1753,8 +1756,7 @@ LoadGame_f
|
|||
void LoadGame_f( const idCmdArgs &args ) {
|
||||
console->Close();
|
||||
if ( args.Argc() < 2 || idStr::Icmp(args.Argv(1), "quick" ) == 0 ) {
|
||||
idStr saveName = common->GetLanguageDict()->GetString( "#str_07178" );
|
||||
sessLocal.LoadGame( saveName );
|
||||
sessLocal.QuickLoad();
|
||||
} else {
|
||||
sessLocal.LoadGame( args.Argv(1) );
|
||||
}
|
||||
|
@ -1767,10 +1769,7 @@ SaveGame_f
|
|||
*/
|
||||
void SaveGame_f( const idCmdArgs &args ) {
|
||||
if ( args.Argc() < 2 || idStr::Icmp( args.Argv(1), "quick" ) == 0 ) {
|
||||
idStr saveName = common->GetLanguageDict()->GetString( "#str_07178" );
|
||||
if ( sessLocal.SaveGame( saveName ) ) {
|
||||
common->Printf( "%s\n", saveName.c_str() );
|
||||
}
|
||||
sessLocal.QuickSave();
|
||||
} else {
|
||||
if ( sessLocal.SaveGame( args.Argv(1) ) ) {
|
||||
common->Printf( "Saved %s\n", args.Argv(1) );
|
||||
|
@ -2161,6 +2160,104 @@ bool idSessionLocal::LoadGame( const char *saveName ) {
|
|||
#endif
|
||||
}
|
||||
|
||||
bool idSessionLocal::QuickSave()
|
||||
{
|
||||
idStr saveName = common->GetLanguageDict()->GetString( "#str_07178" );
|
||||
|
||||
idStr saveFilePathBase = saveName;
|
||||
ScrubSaveGameFileName( saveFilePathBase );
|
||||
saveFilePathBase = "savegames/" + saveFilePathBase;
|
||||
|
||||
const char* game = cvarSystem->GetCVarString( "fs_game" );
|
||||
if ( game != NULL && game[0] == '\0' ) {
|
||||
game = NULL;
|
||||
}
|
||||
|
||||
const int maxNum = com_numQuicksaves.GetInteger();
|
||||
int indexToUse = 1;
|
||||
ID_TIME_T oldestTime = 0;
|
||||
for( int i = 1; i <= maxNum; ++i ) {
|
||||
idStr saveFilePath = saveFilePathBase;
|
||||
if ( i > 1 ) {
|
||||
// the first one is just called "QuickSave" without a number, like before.
|
||||
// the others are called "QuickSave2" "QuickSave3" etc
|
||||
saveFilePath += i;
|
||||
}
|
||||
saveFilePath.SetFileExtension( ".save" );
|
||||
|
||||
idFile *f = fileSystem->OpenFileRead( saveFilePath, true, game );
|
||||
if ( f == NULL ) {
|
||||
// this savegame doesn't exist yet => we can use this index for the name
|
||||
indexToUse = i;
|
||||
break;
|
||||
} else {
|
||||
ID_TIME_T ts = f->Timestamp();
|
||||
assert( ts != 0 );
|
||||
if ( ts < oldestTime || oldestTime == 0 ) {
|
||||
// this is the oldest quicksave we found so far => a candidate to be overwritten
|
||||
indexToUse = i;
|
||||
oldestTime = ts;
|
||||
}
|
||||
delete f;
|
||||
}
|
||||
}
|
||||
|
||||
if ( indexToUse > 1 ) {
|
||||
saveName += indexToUse;
|
||||
}
|
||||
|
||||
if ( SaveGame( saveName ) ) {
|
||||
common->Printf( "%s\n", saveName.c_str() );
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool idSessionLocal::QuickLoad()
|
||||
{
|
||||
idStr saveName = common->GetLanguageDict()->GetString( "#str_07178" );
|
||||
|
||||
idStr saveFilePathBase = saveName;
|
||||
ScrubSaveGameFileName( saveFilePathBase );
|
||||
saveFilePathBase = "savegames/" + saveFilePathBase;
|
||||
|
||||
const char* game = cvarSystem->GetCVarString( "fs_game" );
|
||||
if ( game != NULL && game[0] == '\0' ) {
|
||||
game = NULL;
|
||||
}
|
||||
|
||||
// find the newest QuickSave (or QuickSave2, QuickSave3, ...)
|
||||
const int maxNum = com_numQuicksaves.GetInteger();
|
||||
int indexToUse = 1;
|
||||
ID_TIME_T newestTime = 0;
|
||||
for( int i = 1; i <= maxNum; ++i ) {
|
||||
idStr saveFilePath = saveFilePathBase;
|
||||
if ( i > 1 ) {
|
||||
// the first one is just called "QuickSave" without a number, like before.
|
||||
// the others are called "QuickSave2" "QuickSave3" etc
|
||||
saveFilePath += i;
|
||||
}
|
||||
saveFilePath.SetFileExtension( ".save" );
|
||||
|
||||
idFile *f = fileSystem->OpenFileRead( saveFilePath, true, game );
|
||||
if ( f != NULL ) {
|
||||
ID_TIME_T ts = f->Timestamp();
|
||||
assert( ts != 0 );
|
||||
if ( ts > newestTime ) {
|
||||
indexToUse = i;
|
||||
newestTime = ts;
|
||||
}
|
||||
delete f;
|
||||
}
|
||||
}
|
||||
|
||||
if ( indexToUse > 1 ) {
|
||||
saveName += indexToUse;
|
||||
}
|
||||
|
||||
return sessLocal.LoadGame( saveName );
|
||||
}
|
||||
|
||||
/*
|
||||
===============
|
||||
idSessionLocal::ProcessEvent
|
||||
|
|
|
@ -166,6 +166,9 @@ public:
|
|||
// DG: added saveFileName so we can set a sensible filename for autosaves (see comment in MoveToNewMap())
|
||||
bool SaveGame(const char *saveName, bool autosave = false, const char* saveFileName = NULL);
|
||||
|
||||
bool QuickSave();
|
||||
bool QuickLoad();
|
||||
|
||||
const char *GetAuthMsg( void );
|
||||
|
||||
//=====================================
|
||||
|
@ -182,6 +185,7 @@ public:
|
|||
static idCVar com_aviDemoTics;
|
||||
static idCVar com_wipeSeconds;
|
||||
static idCVar com_guid;
|
||||
static idCVar com_numQuicksaves;
|
||||
|
||||
static idCVar gui_configServerRate;
|
||||
|
||||
|
|
Loading…
Reference in a new issue