From 4eec2bf5d2a432103a06a4e0a499e3a8c6bcb04b Mon Sep 17 00:00:00 2001 From: historic_bruno Date: Wed, 14 Mar 2012 00:23:28 +0000 Subject: [PATCH] Fixes some bugs related to deleting saved games (in particular, load/delete was broken if the file was deleted externally while the game was running). Adds saved game directory to the hotload watch list. Logs error instead of crashing when saved game is not found. Changes Atlas double-click selection to only pick units from the same player. This was SVN commit r11332. --- .../data/mods/public/gui/savedgames/load.js | 24 +++++++++++++------ source/gui/scripting/ScriptFunctions.cpp | 1 - source/ps/GameSetup/GameSetup.cpp | 2 +- source/ps/SavedGame.cpp | 4 ++++ .../GameInterface/Handlers/ObjectHandlers.cpp | 13 +++++++--- 5 files changed, 32 insertions(+), 12 deletions(-) diff --git a/binaries/data/mods/public/gui/savedgames/load.js b/binaries/data/mods/public/gui/savedgames/load.js index 7fc94dcb14..7b88add85c 100644 --- a/binaries/data/mods/public/gui/savedgames/load.js +++ b/binaries/data/mods/public/gui/savedgames/load.js @@ -26,6 +26,7 @@ function init() if (savedGames.length == 0) { gameSelection.list = [ "No saved games found" ]; + gameSelection.selected = 0; getGUIObjectByName("loadGameButton").enabled = false; getGUIObjectByName("deleteGameButton").enabled = false; return; @@ -47,12 +48,21 @@ function loadGame() var gameID = gameSelection.list_data[gameSelection.selected]; var metadata = Engine.StartSavedGame(gameID); - - Engine.SwitchGuiPage("page_loading.xml", { - "attribs": metadata.initAttributes, - "isNetworked" : false, - "playerAssignments": metadata.gui.playerAssignments - }); + if (!metadata) + { + // Probably the file wasn't found + // Show error and refresh saved game list + error("Could not load saved game '"+gameID+"'"); + init(); + } + else + { + Engine.SwitchGuiPage("page_loading.xml", { + "attribs": metadata.initAttributes, + "isNetworked" : false, + "playerAssignments": metadata.gui.playerAssignments + }); + } } function deleteGame() @@ -71,7 +81,7 @@ function reallyDeleteGame(gameID) { if (!Engine.DeleteSavedGame(gameID)) { - warn("Could not delete saved game '"+gameID+"'"); + error("Could not delete saved game '"+gameID+"'"); } // Run init again to refresh saved game list diff --git a/source/gui/scripting/ScriptFunctions.cpp b/source/gui/scripting/ScriptFunctions.cpp index 9c28e70a01..4fad858096 100644 --- a/source/gui/scripting/ScriptFunctions.cpp +++ b/source/gui/scripting/ScriptFunctions.cpp @@ -213,7 +213,6 @@ CScriptVal StartSavedGame(void* cbdata, std::wstring name) CScriptValRooted metadata; std::string savedState; Status err = SavedGames::Load(name, guiManager->GetScriptInterface(), metadata, savedState); - WARN_IF_ERR(err); if (err < 0) return CScriptVal(); diff --git a/source/ps/GameSetup/GameSetup.cpp b/source/ps/GameSetup/GameSetup.cpp index ea37f1fc54..7bc37366e1 100644 --- a/source/ps/GameSetup/GameSetup.cpp +++ b/source/ps/GameSetup/GameSetup.cpp @@ -454,7 +454,7 @@ static void InitVfs(const CmdLineArgs& args) g_VFS = CreateVfs(cacheSize); g_VFS->Mount(L"screenshots/", paths.Data()/"screenshots"/""); - g_VFS->Mount(L"saves/", paths.Data()/"saves"/""); + g_VFS->Mount(L"saves/", paths.Data()/"saves"/"", VFS_MOUNT_WATCH); const OsPath readonlyConfig = paths.RData()/"config"/""; g_VFS->Mount(L"config/", readonlyConfig); if(readonlyConfig != paths.Config()) diff --git a/source/ps/SavedGame.cpp b/source/ps/SavedGame.cpp index b860617fe1..20bb944e07 100644 --- a/source/ps/SavedGame.cpp +++ b/source/ps/SavedGame.cpp @@ -144,6 +144,10 @@ Status SavedGames::Load(const std::wstring& name, ScriptInterface& scriptInterfa const VfsPath basename(L"saves/" + name); const VfsPath filename = basename.ChangeExtension(L".0adsave"); + // Don't crash just because file isn't found, this can happen if the file is deleted from the OS + if (!VfsFileExists(filename)) + return ERR::FILE_NOT_FOUND; + OsPath realPath; WARN_RETURN_STATUS_IF_ERR(g_VFS->GetRealPath(filename, realPath)); diff --git a/source/tools/atlas/GameInterface/Handlers/ObjectHandlers.cpp b/source/tools/atlas/GameInterface/Handlers/ObjectHandlers.cpp index 01a6e1b18d..456756429e 100644 --- a/source/tools/atlas/GameInterface/Handlers/ObjectHandlers.cpp +++ b/source/tools/atlas/GameInterface/Handlers/ObjectHandlers.cpp @@ -478,10 +478,17 @@ QUERYHANDLER(PickSimilarObjects) { CmpPtr cmpTemplateManager(*g_Game->GetSimulation2(), SYSTEM_ENTITY); ENSURE(cmpTemplateManager); - std::string templateName = cmpTemplateManager->GetCurrentTemplateName((entity_id_t)msg->id); - // Since owner selections are meaningless in Atlas, use INVALID_PLAYER - msg->ids = EntitySelection::PickSimilarEntities(*g_Game->GetSimulation2(), *g_Game->GetView()->GetCamera(), templateName, INVALID_PLAYER, false, true, true); + entity_id_t ent = msg->id; + std::string templateName = cmpTemplateManager->GetCurrentTemplateName(ent); + + // If unit has ownership, only pick units from the same player + player_id_t owner = INVALID_PLAYER; + CmpPtr cmpOwnership(*g_Game->GetSimulation2(), ent); + if (cmpOwnership) + owner = cmpOwnership->GetOwner(); + + msg->ids = EntitySelection::PickSimilarEntities(*g_Game->GetSimulation2(), *g_Game->GetView()->GetCamera(), templateName, owner, false, true, true); }