Ticket #1090: loadsave-v4.patch
File loadsave-v4.patch, 18.5 KB (added by , 8 years ago) |
---|
-
binaries/data/mods/public/gui/common/common_styles.xml
304 304 tooltip_style="pgToolTip" 305 305 /> 306 306 307 <style name="MapPlayerList" 308 buffer_zone="8" 309 font="sans-14" 310 scrollbar="true" 311 scrollbar_style="ModernScrollBar" 312 scroll_bottom="false" 313 textcolor="white" 314 text_align="left" 315 text_valign="top" 316 /> 307 317 <!-- 308 318 ========================================== 309 319 CIV ICON -
binaries/data/mods/public/gui/common/functions_utility.js
205 205 } catch (e) { 206 206 } 207 207 } 208 209 /** 210 * Returns a formatted string describing the player assignments. 211 * Including civs, teams, AI settings and player colors 212 * which are given in data (array of objects per player). 213 * 214 * @returns {string} 215 */ 216 function formatPlayerInfo(data) 217 { 218 let playerDescriptions = {}; 219 let playerIdx = 0; 220 for (let playerData of data) 221 { 222 ++playerIdx; 223 let teamIdx = playerData.Team; 224 let showDefeated = playerData.state && playerData.state == "defeated"; 225 let isAI = playerData.AI && playerData.AI != ""; 226 227 // Create human-readable player description 228 229 let translated; 230 if (!isAI && !showDefeated) 231 translated = translateWithContext("replay", "%(playerName)s (%(civ)s)"); 232 else if (!isAI && showDefeated) 233 translated = translateWithContext("replay", "%(playerName)s (%(civ)s, defeated)"); 234 else if (isAI && !showDefeated) 235 translated = translateWithContext("replay", "%(playerName)s (%(civ)s, %(AIdifficulty)s %(AIname)s)"); 236 else 237 translated = translateWithContext("replay", "%(playerName)s (%(civ)s, %(AIdifficulty)s %(AIname)s, defeated)"); 238 239 translated = sprintf(translated, { 240 "playerName": '[color="' + rgbToGuiColor(playerData.Color) + '"]' + escapeText(playerData.Name) + "[/color]", 241 "civ": playerData.Civ, 242 "AIname": isAI ? translateAIName(playerData.AI) : "", 243 "AIdifficulty": isAI ? translateAIDifficulty(playerData.AIDiff) : "" 244 }); 245 246 // Sort player descriptions by team 247 if (!playerDescriptions[teamIdx]) 248 playerDescriptions[teamIdx] = []; 249 playerDescriptions[teamIdx].push(translated); 250 } 251 252 let teams = Object.keys(playerDescriptions); 253 254 // If there are no teams, merge all playersDescriptions 255 if (teams.length == 1) 256 return playerDescriptions[teams[0]].join("\n") + "\n"; 257 258 // If there are teams, merge "Team N:" + playerDescriptions 259 return teams.map(team => { 260 let teamCaption = (team == -1) ? translate("No Team") : sprintf(translate("Team %(team)s"), { "team": +team + 1 }); 261 return '[font="sans-bold-14"]' + teamCaption + "[/font]:\n" + playerDescriptions[team].join("\n"); 262 }).join("\n\n"); 263 } -
binaries/data/mods/public/gui/page_replaymenu.xml
10 10 <include>common/common_sprites.xml</include> 11 11 <include>common/common_styles.xml</include> 12 12 13 <include>replaymenu/styles.xml</include>14 13 <include>replaymenu/replay_menu.xml</include> 15 14 </page> -
binaries/data/mods/public/gui/replaymenu/replay_menu.js
346 346 const metadata = Engine.GetReplayMetadata(replay.directory); 347 347 const spoiler = Engine.GetGUIObjectByName("showSpoiler").checked; 348 348 349 var playerDescriptions = {};350 varplayerIdx = 0;349 let data = []; 350 let playerIdx = 0; 351 351 for (let playerData of replay.attribs.settings.PlayerData) 352 352 { 353 // Get player info354 353 ++playerIdx; 355 let teamIdx = playerData.Team; 356 let playerColor = playerData.Color ? playerData.Color : g_Settings.PlayerDefaults[playerIdx].Color; 357 let playerCiv = !playerData.Civ ? translate("Unknown Civilization") : (g_CivData[playerData.Civ] && g_CivData[playerData.Civ].Name ? translate(g_CivData[playerData.Civ].Name) : playerData.Civ); 358 let showDefeated = spoiler && metadata && metadata.playerStates && metadata.playerStates[playerIdx].state == "defeated"; 359 let isAI = playerData.AI; 360 361 // Create human-readable player description 362 let playerDetails = { 363 "playerName": '[color="' + rgbToGuiColor(playerColor) + '"]' + escapeText(playerData.Name) + "[/color]", 364 "civ": playerCiv, 365 "AIname": isAI ? translateAIName(playerData.AI) : "", 366 "AIdifficulty": isAI ? translateAIDifficulty(playerData.AIDiff) : "" 367 }; 368 369 if (!isAI && !showDefeated) 370 playerDetails = sprintf(translateWithContext("replay", "%(playerName)s (%(civ)s)"), playerDetails); 371 else if (!isAI && showDefeated) 372 playerDetails = sprintf(translateWithContext("replay", "%(playerName)s (%(civ)s, defeated)"), playerDetails); 373 else if (isAI && !showDefeated) 374 playerDetails = sprintf(translateWithContext("replay", "%(playerName)s (%(civ)s, %(AIdifficulty)s %(AIname)s)"), playerDetails); 375 else 376 playerDetails = sprintf(translateWithContext("replay", "%(playerName)s (%(civ)s, %(AIdifficulty)s %(AIname)s, defeated)"), playerDetails); 377 378 // Sort player descriptions by team 379 if (!playerDescriptions[teamIdx]) 380 playerDescriptions[teamIdx] = []; 381 playerDescriptions[teamIdx].push(playerDetails); 354 data.push({ 355 "Team": playerData.Team, 356 "Name": playerData.Name, 357 "Civ": !playerData.Civ ? translate("Unknown Civilization") : 358 (g_CivData[playerData.Civ] && g_CivData[playerData.Civ].Name ? translate(g_CivData[playerData.Civ].Name) : playerData.Civ), 359 "Color": playerData.Color ? playerData.Color : g_Settings.PlayerDefaults[playerIdx].Color, 360 "AI": playerData.AI, 361 "AIDiff": playerData.AIDiff, 362 "Defeated": spoiler && metadata && metadata.playerStates && metadata.playerStates[playerIdx].state == "defeated" 363 }); 382 364 } 383 365 384 var teams = Object.keys(playerDescriptions); 385 386 // If there are no teams, merge all playersDescriptions 387 if (teams.length == 1) 388 return playerDescriptions[teams[0]].join("\n") + "\n"; 389 390 // If there are teams, merge "Team N:" + playerDescriptions 391 return teams.map(team => { 392 let teamCaption = (team == -1) ? translate("No Team") : sprintf(translate("Team %(team)s"), { "team": +team + 1 }); 393 return '[font="sans-bold-14"]' + teamCaption + "[/font]:\n" + playerDescriptions[team].join("\n"); 394 }).join("\n"); 366 return formatPlayerInfo(data); 395 367 } -
binaries/data/mods/public/gui/replaymenu/styles.xml
1 <?xml version="1.0" encoding="utf-8"?>2 3 <styles>4 <style name="MapPlayerList"5 buffer_zone="8"6 font="sans-14"7 scrollbar="true"8 scrollbar_style="ModernScrollBar"9 scroll_bottom="true"10 textcolor="white"11 text_align="left"12 text_valign="top"13 />14 </styles> -
binaries/data/mods/public/gui/savedgames/load.js
8 8 if (!savedGames.length) 9 9 { 10 10 gameSelection.list = [translate("No saved games found")]; 11 gameSelection.selected = 0; 11 gameSelection.selected = -1; 12 selectionChanged(); 12 13 Engine.GetGUIObjectByName("loadGameButton").enabled = false; 13 14 Engine.GetGUIObjectByName("deleteGameButton").enabled = false; 14 15 return; … … 26 27 gameSelection.selected = 0; 27 28 else if (gameSelection.selected >= savedGames.length) // happens when deleting the last saved game 28 29 gameSelection.selected = savedGames.length - 1; 30 else 31 selectionChanged(); 29 32 } 30 33 34 function selectionChanged() 35 { 36 let gameSelection = Engine.GetGUIObjectByName("gameSelection"); 37 let selectionEmpty = gameSelection.selected == -1; 38 Engine.GetGUIObjectByName("invalidGame").hidden = !selectionEmpty; 39 Engine.GetGUIObjectByName("validGame").hidden = selectionEmpty; 40 41 if (selectionEmpty) 42 return; 43 44 let metadata = g_SavedGamesMetadata[gameSelection.selected]; 45 46 Engine.GetGUIObjectByName("savedMapName").caption = translate(metadata.initAttributes.settings.Name); 47 let mapData = getMapDescriptionAndPreview(metadata.initAttributes.mapType, metadata.initAttributes.map); 48 setMapPreviewImage("savedInfoPreview", mapData.preview); 49 50 Engine.GetGUIObjectByName("savedPlayers").caption = metadata.initAttributes.settings.PlayerData.length - 1; 51 Engine.GetGUIObjectByName("savedPlayedTime").caption = timeToString(metadata.gui.timeElapsed ? metadata.gui.timeElapsed : 0); 52 Engine.GetGUIObjectByName("savedMapType").caption = translateMapType(metadata.initAttributes.mapType); 53 Engine.GetGUIObjectByName("savedMapSize").caption = translateMapSize(metadata.initAttributes.settings.Size); 54 Engine.GetGUIObjectByName("savedVictory").caption = translateVictoryCondition(metadata.initAttributes.settings.GameType); 55 56 let caption = sprintf(translate("Mods: %(mods)s"), { "mods": metadata.mods.join(translate(", ")) }); 57 if (!hasSameMods(metadata, Engine.GetEngineInfo())) 58 caption = "[color=\"orange\"]" + caption + "[/color]"; 59 Engine.GetGUIObjectByName("savedMods").caption = caption; 60 61 Engine.GetGUIObjectByName("savedPlayersNames").caption = getPlayerInfoText(metadata); 62 } 63 31 64 function loadGame() 32 65 { 33 66 var gameSelection = Engine.GetGUIObjectByName("gameSelection"); … … 151 184 // Run init again to refresh saved game list 152 185 init(); 153 186 } 187 188 function getPlayerInfoText(metadata) 189 { 190 let data = []; 191 let playerIdx = 0; 192 for (let playerData of metadata.initAttributes.settings.PlayerData) 193 { 194 if (playerData == null || playerData.Name == "gaia") 195 continue; 196 ++playerIdx; 197 data.push({ 198 "Team": playerData.Team, 199 "Name": playerData.Name, 200 "Civ": playerData.Civ, 201 "Color": playerData.Color, 202 "AI": playerData.AI, 203 "AIDiff": playerData.AIDiff, 204 "Defeated": metadata.gui.states && metadata.gui.states[playerIdx] == "defeated" 205 }); 206 } 207 208 return formatPlayerInfo(data); 209 } -
binaries/data/mods/public/gui/savedgames/load.xml
4 4 5 5 <script file="gui/common/functions_global_object.js" /> 6 6 <script file="gui/common/functions_utility.js" /> 7 <script file="gui/common/settings.js" /> 8 9 <script file="gui/common/color.js" /> 10 7 11 <script file="gui/common/functions_utility_loadsave.js" /> 8 12 <script file="gui/savedgames/load.js" /> 9 13 … … 10 14 <!-- Add a translucent black background to fade out the menu page --> 11 15 <object type="image" z="0" sprite="BackgroundTranslucent"/> 12 16 13 <object type="image" style="ModernDialog" size="50%- 300 50%-200 50%+300 50%+200">17 <object type="image" style="ModernDialog" size="50%-400 50%-325 50%+400 50%+325"> 14 18 15 19 <object type="text" style="TitleText" size="50%-128 -18 50%+128 14"> 16 20 <translatableAttribute id="caption">Load Game</translatableAttribute> 17 21 </object> 18 22 19 <object name="gameSelection" 20 style="ModernList" 21 type="list" 22 size="24 24 100%-24 100%-100"> 23 </object> 23 <object type="image" size="0 20 550 100%"> 24 <object name="gameSelection" style="ModernList" type="list" size="24 12 100%-24 100%-90"> 25 <action on="SelectionChange">selectionChanged();</action> 26 </object> 24 27 25 <object type="button" size="0%+25 100%-60 33%+10 100%-32" style="StoneButton" hotkey="cancel">26 <translatableAttribute id="caption">Cancel</translatableAttribute>27 <action on="Press">Engine.PopGuiPage();</action>28 </object>28 <object type="button" size="0%+25 100%-60 33%+10 100%-32" style="StoneButton" hotkey="cancel"> 29 <translatableAttribute id="caption">Cancel</translatableAttribute> 30 <action on="Press">Engine.PopGuiPage();</action> 31 </object> 29 32 30 <object name="deleteGameButton" type="button" size="33%+20 100%-60 66%-15 100%-32" style="StoneButton" hotkey="session.savedgames.delete"> 31 <translatableAttribute id="caption">Delete</translatableAttribute> 32 <action on="Press"> 33 if (!this.enabled) 34 return; 35 if (Engine.HotkeyIsPressed("session.savedgames.noconfirmation")) 36 deleteGameWithoutConfirmation(); 37 else 38 deleteGame(); 39 </action> 33 <object name="deleteGameButton" type="button" size="33%+20 100%-60 66%-15 100%-32" style="StoneButton" hotkey="session.savedgames.delete"> 34 <translatableAttribute id="caption">Delete</translatableAttribute> 35 <action on="Press"> 36 if (!this.enabled) 37 return; 38 if (Engine.HotkeyIsPressed("session.savedgames.noconfirmation")) 39 deleteGameWithoutConfirmation(); 40 else 41 deleteGame(); 42 </action> 43 </object> 44 45 <object name="loadGameButton" type="button" style="StoneButton" size="66%-5 100%-60 100%-25 100%-32"> 46 <translatableAttribute id="caption">Load</translatableAttribute> 47 <action on="Press">loadGame();</action> 48 </object> 49 40 50 </object> 41 51 42 <object name="loadGameButton" type="button" style="StoneButton" size="66%-5 100%-60 100%-25 100%-32"> 43 <translatableAttribute id="caption">Load</translatableAttribute> 44 <action on="Press">loadGame();</action> 52 <object name="validGame" type="image" size="550 20 100%-20 100%"> 53 <object name="savedMapName" size="0 0 100% 20" type="text" style="ModernLabelText" /> 54 <object name="savedInfoPreview" size="0 20 220 240" type="image" sprite="" /> 55 56 <object size="0 250 45% 270" type="text" style="ModernLabelText" text_align="left"> 57 <translatableAttribute id="caption">Players:</translatableAttribute> 58 </object> 59 <object name="savedPlayers" size="45% 250 100%-15 270" type="text" style="ModernLabelText" text_align="left" /> 60 <object size="0 270 45% 290" type="text" style="ModernLabelText" text_align="left"> 61 <translatableAttribute id="caption">Played time:</translatableAttribute> 62 </object> 63 <object name="savedPlayedTime" size="45% 270 100%-15 290" type="text" style="ModernLabelText" text_align="left" /> 64 <object size="0 290 45% 310" type="text" style="ModernLabelText" text_align="left"> 65 <translatableAttribute id="caption">Map Type:</translatableAttribute> 66 </object> 67 <object name="savedMapType" size="45% 290 100%-15 310" type="text" style="ModernLabelText" text_align="left" /> 68 <object size="0 310 45% 330" type="text" style="ModernLabelText" text_align="left"> 69 <translatableAttribute id="caption">Map Size:</translatableAttribute> 70 </object> 71 <object name="savedMapSize" size="45% 310 100%-15 330" type="text" style="ModernLabelText" text_align="left" /> 72 <object size="0 330 45% 350" type="text" style="ModernLabelText" text_align="left"> 73 <translatableAttribute id="caption">Victory:</translatableAttribute> 74 </object> 75 <object name="savedVictory" size="45% 330 100%-15 350" type="text" style="ModernLabelText" text_align="left" /> 76 77 <object size="0 352 100%-15 353" type="image" sprite="ModernWhiteLine" z="25" /> 78 79 <object name="savedMods" size="0 355 100%-15 395" type="text" style="ModernLabelText" text_align="left" /> 80 81 <object size="0 397 100%-15 398" type="image" sprite="ModernWhiteLine" z="25" /> 82 83 <object name="savedPlayersNames" size="0 400 100%-10 100%-32" type="text" style="MapPlayerList" /> 45 84 </object> 46 85 86 <object name="invalidGame" size="550 55 770 155" type="image" sprite="logo" /> 47 87 </object> 48 88 49 89 </objects> -
binaries/data/mods/public/gui/savedgames/save.js
3 3 4 4 function selectDescription() 5 5 { 6 vargameSelection = Engine.GetGUIObjectByName("gameSelection");6 let gameSelection = Engine.GetGUIObjectByName("gameSelection"); 7 7 if (gameSelection.selected == -1) 8 8 return; 9 9 10 vargameID = gameSelection.list_data[gameSelection.selected];10 let gameID = gameSelection.list_data[gameSelection.selected]; 11 11 Engine.GetGUIObjectByName("deleteGameButton").enabled = true; 12 12 Engine.GetGUIObjectByName("saveGameDesc").caption = g_Descriptions[gameID]; 13 13 } … … 14 14 15 15 function init(data) 16 16 { 17 g_SavedGameData = data && data.savedGameData || undefined; 17 g_SavedGameData = data && data.savedGameData || {}; 18 let simulationState = Engine.GuiInterfaceCall("GetSimulationState"); 19 g_SavedGameData.timeElapsed = simulationState.timeElapsed; 20 g_SavedGameData.states = []; 21 for (let player of simulationState.players) 22 g_SavedGameData.states.push(player.state); 18 23 19 vargameSelection = Engine.GetGUIObjectByName("gameSelection");24 let gameSelection = Engine.GetGUIObjectByName("gameSelection"); 20 25 Engine.GetGUIObjectByName("deleteGameButton").enabled = false; 21 26 22 varsavedGames = Engine.GetSavedGames().sort(sortDecreasingDate);27 let savedGames = Engine.GetSavedGames().sort(sortDecreasingDate); 23 28 if (!savedGames.length) 24 29 { 25 30 gameSelection.list = [translate("No saved games found")]; … … 38 43 39 44 function saveGame() 40 45 { 41 vargameSelection = Engine.GetGUIObjectByName("gameSelection");42 vargameLabel = gameSelection.list[gameSelection.selected];43 vargameID = gameSelection.list_data[gameSelection.selected];44 vardesc = Engine.GetGUIObjectByName("saveGameDesc").caption;45 varname = gameID || "savegame";46 let gameSelection = Engine.GetGUIObjectByName("gameSelection"); 47 let gameLabel = gameSelection.list[gameSelection.selected]; 48 let gameID = gameSelection.list_data[gameSelection.selected]; 49 let desc = Engine.GetGUIObjectByName("saveGameDesc").caption; 50 let name = gameID || "savegame"; 46 51 47 52 if (gameSelection.selected == -1) 48 53 { … … 78 83 79 84 function deleteGame() 80 85 { 81 vargameSelection = Engine.GetGUIObjectByName("gameSelection");82 vargameLabel = gameSelection.list[gameSelection.selected];83 vargameID = gameSelection.list_data[gameSelection.selected];86 let gameSelection = Engine.GetGUIObjectByName("gameSelection"); 87 let gameLabel = gameSelection.list[gameSelection.selected]; 88 let gameID = gameSelection.list_data[gameSelection.selected]; 84 89 85 90 // Ask for confirmation 86 91 messageBox(