From f5b437dd9cef971e098d497dd7600c3d46f1f52e Mon Sep 17 00:00:00 2001 From: obligaron Date: Thu, 15 Jul 2021 23:40:40 +0200 Subject: [PATCH] Use save number to load/save games (instead of hero name) --- Source/DiabloUI/diabloui.h | 5 +++-- Source/DiabloUI/selgame.cpp | 2 +- Source/DiabloUI/selhero.cpp | 13 +++++++------ Source/mainmenu.cpp | 8 ++++---- Source/mainmenu.h | 2 +- Source/multi.cpp | 2 +- Source/pfile.cpp | 32 ++++++++++---------------------- Source/pfile.h | 2 +- 8 files changed, 28 insertions(+), 38 deletions(-) diff --git a/Source/DiabloUI/diabloui.h b/Source/DiabloUI/diabloui.h index 37d176f1d..7e8ff999e 100644 --- a/Source/DiabloUI/diabloui.h +++ b/Source/DiabloUI/diabloui.h @@ -53,6 +53,7 @@ struct _uidefaultstats { }; struct _uiheroinfo { + uint32_t saveNumber; char name[16]; uint8_t level; HeroClass heroclass; @@ -97,8 +98,8 @@ void UiTitleDialog(); void UiSetSpawned(bool bSpawned); void UiInitialize(); bool UiValidPlayerName(const char *name); /* check */ -void UiSelHeroMultDialog(bool (*fninfo)(bool (*fninfofunc)(_uiheroinfo *)), bool (*fncreate)(_uiheroinfo *), bool (*fnremove)(_uiheroinfo *), void (*fnstats)(unsigned int, _uidefaultstats *), _selhero_selections *dlgresult, char (*name)[16]); -void UiSelHeroSingDialog(bool (*fninfo)(bool (*fninfofunc)(_uiheroinfo *)), bool (*fncreate)(_uiheroinfo *), bool (*fnremove)(_uiheroinfo *), void (*fnstats)(unsigned int, _uidefaultstats *), _selhero_selections *dlgresult, char (*name)[16], _difficulty *difficulty); +void UiSelHeroMultDialog(bool (*fninfo)(bool (*fninfofunc)(_uiheroinfo *)), bool (*fncreate)(_uiheroinfo *), bool (*fnremove)(_uiheroinfo *), void (*fnstats)(unsigned int, _uidefaultstats *), _selhero_selections *dlgresult, uint32_t *saveNumber); +void UiSelHeroSingDialog(bool (*fninfo)(bool (*fninfofunc)(_uiheroinfo *)), bool (*fncreate)(_uiheroinfo *), bool (*fnremove)(_uiheroinfo *), void (*fnstats)(unsigned int, _uidefaultstats *), _selhero_selections *dlgresult, uint32_t *saveNumber, _difficulty *difficulty); bool UiCreditsDialog(); bool UiSupportDialog(); bool UiMainMenuDialog(const char *name, _mainmenu_selections *pdwResult, void (*fnSound)(const char *file), int attractTimeOut); diff --git a/Source/DiabloUI/selgame.cpp b/Source/DiabloUI/selgame.cpp index ab6ed100f..8ef309ecc 100644 --- a/Source/DiabloUI/selgame.cpp +++ b/Source/DiabloUI/selgame.cpp @@ -120,7 +120,7 @@ void selgame_GameSelection_Focus(int value) */ bool UpdateHeroLevel(_uiheroinfo *pInfo) { - if (strcasecmp(pInfo->name, gszHero) == 0) + if (pInfo->saveNumber == gSaveNumber) heroLevel = pInfo->level; return true; diff --git a/Source/DiabloUI/selhero.cpp b/Source/DiabloUI/selhero.cpp index 886d0674c..b3f9e475d 100644 --- a/Source/DiabloUI/selhero.cpp +++ b/Source/DiabloUI/selhero.cpp @@ -186,6 +186,7 @@ void SelheroListSelect(int value) UiInitList(vecSelHeroDlgItems.size(), SelheroClassSelectorFocus, SelheroClassSelectorSelect, SelheroClassSelectorEsc, vecSelDlgItems); memset(&selhero_heroInfo.name, 0, sizeof(selhero_heroInfo.name)); + selhero_heroInfo.saveNumber = MAX_CHARACTERS; title = selhero_isMultiPlayer ? _("New Multi Player Hero") : _("New Single Player Hero"); return; } @@ -550,7 +551,7 @@ static void UiSelHeroDialog( void (*fnstats)(unsigned int, _uidefaultstats *), bool (*fnremove)(_uiheroinfo *), _selhero_selections *dlgresult, - char (*name)[16]) + uint32_t *saveNumber) { do { gfnHeroInfo = fninfo; @@ -592,7 +593,7 @@ static void UiSelHeroDialog( } while (selhero_navigateYesNo); *dlgresult = selhero_result; - strncpy(*name, selhero_heroInfo.name, sizeof(*name)); + *saveNumber = selhero_heroInfo.saveNumber; } void UiSelHeroSingDialog( @@ -601,11 +602,11 @@ void UiSelHeroSingDialog( bool (*fnremove)(_uiheroinfo *), void (*fnstats)(unsigned int, _uidefaultstats *), _selhero_selections *dlgresult, - char (*name)[16], + uint32_t *saveNumber, _difficulty *difficulty) { selhero_isMultiPlayer = false; - UiSelHeroDialog(fninfo, fncreate, fnstats, fnremove, dlgresult, name); + UiSelHeroDialog(fninfo, fncreate, fnstats, fnremove, dlgresult, saveNumber); *difficulty = nDifficulty; } @@ -615,10 +616,10 @@ void UiSelHeroMultDialog( bool (*fnremove)(_uiheroinfo *), void (*fnstats)(unsigned int, _uidefaultstats *), _selhero_selections *dlgresult, - char (*name)[16]) + uint32_t *saveNumber) { selhero_isMultiPlayer = true; - UiSelHeroDialog(fninfo, fncreate, fnstats, fnremove, dlgresult, name); + UiSelHeroDialog(fninfo, fncreate, fnstats, fnremove, dlgresult, saveNumber); } } // namespace devilution diff --git a/Source/mainmenu.cpp b/Source/mainmenu.cpp index f9a895f32..3ca61e827 100644 --- a/Source/mainmenu.cpp +++ b/Source/mainmenu.cpp @@ -14,7 +14,7 @@ namespace devilution { -char gszHero[16]; +uint32_t gSaveNumber; namespace { @@ -88,7 +88,7 @@ bool mainmenu_select_hero_dialog(GameData *gameData) pfile_delete_save, pfile_ui_set_class_stats, &dlgresult, - &gszHero, + &gSaveNumber, &gameData->nDifficulty); gbLoadGame = (dlgresult == SELHERO_CONTINUE); @@ -99,14 +99,14 @@ bool mainmenu_select_hero_dialog(GameData *gameData) pfile_delete_save, pfile_ui_set_class_stats, &dlgresult, - &gszHero); + &gSaveNumber); } if (dlgresult == SELHERO_PREVIOUS) { SErrSetLastError(1223); return false; } - pfile_read_player_from_save(gszHero, MyPlayerId); + pfile_read_player_from_save(gSaveNumber, MyPlayerId); return true; } diff --git a/Source/mainmenu.h b/Source/mainmenu.h index db7411b95..1a657b98d 100644 --- a/Source/mainmenu.h +++ b/Source/mainmenu.h @@ -9,7 +9,7 @@ namespace devilution { -extern char gszHero[16]; +extern uint32_t gSaveNumber; bool mainmenu_select_hero_dialog(GameData *gameData); void mainmenu_loop(); diff --git a/Source/multi.cpp b/Source/multi.cpp index eb70d82f6..85426e14c 100644 --- a/Source/multi.cpp +++ b/Source/multi.cpp @@ -454,7 +454,7 @@ bool InitMulti(GameData *gameData) MyPlayerId = playerId; gbIsMultiplayer = true; - pfile_read_player_from_save(gszHero, MyPlayerId); + pfile_read_player_from_save(gSaveNumber, MyPlayerId); return true; } diff --git a/Source/pfile.cpp b/Source/pfile.cpp index 153086d99..cba8550b9 100644 --- a/Source/pfile.cpp +++ b/Source/pfile.cpp @@ -113,18 +113,6 @@ void RenameTempToPerm() assert(!GetPermSaveNames(dwIndex, szPerm)); } -uint32_t GetSaveNumberFromName(const char *name) -{ - uint32_t i; - - for (i = 0; i < MAX_CHARACTERS; i++) { - if (strcasecmp(hero_names[i], name) == 0) - break; - } - - return i; -} - std::unique_ptr ReadArchive(HANDLE archive, const char *pszName, size_t *pdwLen = nullptr) { HANDLE file; @@ -203,7 +191,6 @@ void CloseArchive(HANDLE *hsArchive) void Game2UiPlayer(const PlayerStruct &player, _uiheroinfo *heroinfo, bool bHasSaveFile) { - memset(heroinfo, 0, sizeof(*heroinfo)); strncpy(heroinfo->name, player._pName, sizeof(heroinfo->name) - 1); heroinfo->name[sizeof(heroinfo->name) - 1] = '\0'; heroinfo->level = player._pLevel; @@ -266,7 +253,7 @@ const char *pfile_get_password() } PFileScopedArchiveWriter::PFileScopedArchiveWriter(bool clearTables) - : save_num_(GetSaveNumberFromName(Players[MyPlayerId]._pName)) + : save_num_(gSaveNumber) , clear_tables_(clearTables) { if (!OpenArchive(save_num_)) @@ -304,6 +291,7 @@ bool pfile_ui_set_hero_infos(bool (*uiAddHeroInfo)(_uiheroinfo *)) PkPlayerStruct pkplr; if (ReadHero(archive, &pkplr)) { _uiheroinfo uihero; + uihero.saveNumber = i; strcpy(hero_names[i], pkplr.pName); bool hasSaveGame = ArchiveContainsGame(archive); if (hasSaveGame) @@ -338,7 +326,7 @@ bool pfile_ui_save_create(_uiheroinfo *heroinfo) { PkPlayerStruct pkplr; - uint32_t saveNum = GetSaveNumberFromName(heroinfo->name); + uint32_t saveNum = heroinfo->saveNumber; if (saveNum >= MAX_CHARACTERS) { for (saveNum = 0; saveNum < MAX_CHARACTERS; saveNum++) { if (hero_names[saveNum][0] == '\0') @@ -349,6 +337,7 @@ bool pfile_ui_save_create(_uiheroinfo *heroinfo) } if (!OpenArchive(saveNum)) return false; + heroinfo->saveNumber = saveNum; mpqapi_remove_hash_entries(GetFileName); strncpy(hero_names[saveNum], heroinfo->name, PLR_NAME_LEN); hero_names[saveNum][PLR_NAME_LEN - 1] = '\0'; @@ -371,7 +360,7 @@ bool pfile_ui_save_create(_uiheroinfo *heroinfo) bool pfile_delete_save(_uiheroinfo *heroInfo) { - uint32_t saveNum = GetSaveNumberFromName(heroInfo->name); + uint32_t saveNum = heroInfo->saveNumber; if (saveNum < MAX_CHARACTERS) { hero_names[saveNum][0] = '\0'; RemoveFile(GetSavePath(saveNum).c_str()); @@ -379,12 +368,11 @@ bool pfile_delete_save(_uiheroinfo *heroInfo) return true; } -void pfile_read_player_from_save(char name[16], int playerId) +void pfile_read_player_from_save(uint32_t saveNum, int playerId) { HANDLE archive; PkPlayerStruct pkplr; - uint32_t saveNum = GetSaveNumberFromName(name); archive = OpenSaveArchive(saveNum); if (archive == nullptr) app_fatal("%s", _("Unable to open archive")); @@ -410,7 +398,7 @@ bool LevelFileExists() GetPermLevelNames(szName); - uint32_t saveNum = GetSaveNumberFromName(Players[MyPlayerId]._pName); + uint32_t saveNum = gSaveNumber; if (!OpenArchive(saveNum)) app_fatal("%s", _("Unable to read to save file archive")); @@ -429,7 +417,7 @@ void GetTempLevelNames(char *szTemp) void GetPermLevelNames(char *szPerm) { - uint32_t saveNum = GetSaveNumberFromName(Players[MyPlayerId]._pName); + uint32_t saveNum = gSaveNumber; GetTempLevelNames(szPerm); if (!OpenArchive(saveNum)) app_fatal("%s", _("Unable to read to save file archive")); @@ -449,7 +437,7 @@ void pfile_remove_temp_files() if (gbIsMultiplayer) return; - uint32_t saveNum = GetSaveNumberFromName(Players[MyPlayerId]._pName); + uint32_t saveNum = gSaveNumber; if (!OpenArchive(saveNum)) app_fatal("%s", _("Unable to write to save file archive")); mpqapi_remove_hash_entries(GetTempSaveNames); @@ -460,7 +448,7 @@ std::unique_ptr pfile_read(const char *pszName, size_t *pdwLen) { HANDLE archive; - uint32_t saveNum = GetSaveNumberFromName(Players[MyPlayerId]._pName); + uint32_t saveNum = gSaveNumber; archive = OpenSaveArchive(saveNum); if (archive == nullptr) return nullptr; diff --git a/Source/pfile.h b/Source/pfile.h index 8bfe2da8c..1fa4f0ff6 100644 --- a/Source/pfile.h +++ b/Source/pfile.h @@ -33,7 +33,7 @@ bool pfile_ui_set_hero_infos(bool (*uiAddHeroInfo)(_uiheroinfo *)); void pfile_ui_set_class_stats(unsigned int playerClass, _uidefaultstats *classStats); bool pfile_ui_save_create(_uiheroinfo *heroinfo); bool pfile_delete_save(_uiheroinfo *heroInfo); -void pfile_read_player_from_save(char name[16], int playerId); +void pfile_read_player_from_save(uint32_t saveNum, int playerId); bool LevelFileExists(); void GetTempLevelNames(char *szTemp); void GetPermLevelNames(char *szPerm);