Index: binaries/data/mods/public/gui/aiconfig/aiconfig.js
===================================================================
--- binaries/data/mods/public/gui/aiconfig/aiconfig.js (revision 18192)
+++ binaries/data/mods/public/gui/aiconfig/aiconfig.js (working copy)
@@ -16,20 +16,20 @@
let aiSelection = Engine.GetGUIObjectByName("aiSelection");
aiSelection.list = g_AIDescriptions.map(ai => ai.data.name);
aiSelection.selected = g_AIDescriptions.findIndex(ai => ai.id == settings.id);
- aiSelection.hidden = !settings.isController;
+ aiSelection.hidden = !settings.canBeChanged;
let aiSelectionText = Engine.GetGUIObjectByName("aiSelectionText");
aiSelectionText.caption = aiSelection.list[aiSelection.selected];
- aiSelectionText.hidden = settings.isController;
+ aiSelectionText.hidden = settings.canBeChanged;
let aiDiff = Engine.GetGUIObjectByName("aiDifficulty");
aiDiff.list = prepareForDropdown(g_Settings.AIDifficulties).Title;
aiDiff.selected = settings.difficulty;
- aiDiff.hidden = !settings.isController;
+ aiDiff.hidden = !settings.canBeChanged;
let aiDiffText = Engine.GetGUIObjectByName("aiDifficultyText");
aiDiffText.caption = aiDiff.list[aiDiff.selected];
- aiDiffText.hidden = settings.isController;
+ aiDiffText.hidden = settings.canBeChanged;
}
function selectAI(idx)
Index: binaries/data/mods/public/gui/common/settings.js
===================================================================
--- binaries/data/mods/public/gui/common/settings.js (revision 18192)
+++ binaries/data/mods/public/gui/common/settings.js (working copy)
@@ -37,6 +37,7 @@
"MapTypes": loadMapTypes(),
"MapSizes": loadSettingValuesFile("map_sizes.json"),
"PlayerDefaults": loadPlayerDefaults(),
+ "GuestSettings": loadSettingValuesFile("guest_settings.json"),
"PopulationCapacities": loadPopulationCapacities(),
"StartingResources": loadSettingValuesFile("starting_resources.json"),
"VictoryConditions": loadVictoryConditions()
Index: binaries/data/mods/public/gui/gamesetup/gamesetup.js
===================================================================
--- binaries/data/mods/public/gui/gamesetup/gamesetup.js (revision 18192)
+++ binaries/data/mods/public/gui/gamesetup/gamesetup.js (working copy)
@@ -5,6 +5,7 @@
const g_GameSpeeds = prepareForDropdown(g_Settings && g_Settings.GameSpeeds.filter(speed => !speed.ReplayOnly));
const g_MapSizes = prepareForDropdown(g_Settings && g_Settings.MapSizes);
const g_MapTypes = prepareForDropdown(g_Settings && g_Settings.MapTypes);
+const g_GuestSettings = prepareForDropdown(g_Settings && g_Settings.GuestSettings);
const g_PopulationCapacities = prepareForDropdown(g_Settings && g_Settings.PopulationCapacities);
const g_StartingResources = prepareForDropdown(g_Settings && g_Settings.StartingResources);
const g_VictoryConditions = prepareForDropdown(g_Settings && g_Settings.VictoryConditions);
@@ -270,6 +271,7 @@
initCivNameList();
initMapTypes();
initMapFilters();
+ initDropdowns();
if (g_IsController)
{
@@ -277,17 +279,6 @@
g_GameAttributes.matchID = Engine.GetMatchID();
g_GameAttributes.settings.CheatsEnabled = !g_IsNetworked;
g_GameAttributes.settings.RatingEnabled = Engine.IsRankedGame() || undefined;
-
- initMapNameList();
- initNumberOfPlayers();
- initGameSpeed();
- initPopulationCaps();
- initStartingResources();
- initCeasefire();
- initWonderDurations();
- initVictoryConditions();
- initMapSizes();
- initRadioButtons();
}
else
hideControls();
@@ -309,6 +300,21 @@
}
}
+function initDropdowns()
+{
+ initMapNameList();
+ initNumberOfPlayers();
+ initGameSpeed();
+ initGuestSettings();
+ initPopulationCaps();
+ initStartingResources();
+ initCeasefire();
+ initWonderDurations();
+ initVictoryConditions();
+ initMapSizes();
+ initRadioButtons();
+}
+
function initMapTypes()
{
let mapTypes = Engine.GetGUIObjectByName("mapType");
@@ -318,8 +324,7 @@
if (this.selected != -1)
selectMapType(this.list_data[this.selected]);
};
- if (g_IsController)
- mapTypes.selected = g_MapTypes.Default;
+ mapTypes.selected = g_MapTypes.Default;
}
function initMapFilters()
@@ -331,8 +336,7 @@
if (this.selected != -1)
selectMapFilter(this.list_data[this.selected]);
};
- if (g_IsController)
- mapFilters.selected = 0;
+ mapFilters.selected = 0;
g_GameAttributes.mapFilter = "default";
}
@@ -349,6 +353,7 @@
"optionPopulationCap",
"optionStartingResources",
"optionCeasefire",
+ "optionGuestSettings",
"optionRevealMap",
"optionExploreMap",
"optionDisableTreasures",
@@ -398,8 +403,6 @@
function initGameSpeed()
{
let gameSpeed = Engine.GetGUIObjectByName("gameSpeed");
- gameSpeed.hidden = false;
- Engine.GetGUIObjectByName("gameSpeedText").hidden = true;
gameSpeed.list = g_GameSpeeds.Title;
gameSpeed.list_data = g_GameSpeeds.Speed;
gameSpeed.onSelectionChange = function() {
@@ -453,6 +456,21 @@
};
}
+function initGuestSettings()
+{
+ let guestSettings = Engine.GetGUIObjectByName("guestSettings");
+ guestSettings.list = g_GuestSettings.Title;
+ guestSettings.list_data = g_GuestSettings.Data;
+ guestSettings.onSelectionChange = function() {
+ if (this.selected != -1)
+ g_GameAttributes.GuestSettings = g_GuestSettings.Data[this.selected];
+
+ updateGameAttributes();
+ };
+ if (guestSettings.selected == -1)
+ guestSettings.selected = g_GuestSettings.Default;
+}
+
function initVictoryConditions()
{
let victoryConditions = Engine.GetGUIObjectByName("victoryCondition");
@@ -533,9 +551,8 @@
function hideControls()
{
for (let ctrl of ["mapType", "mapFilter", "mapSelection", "victoryCondition", "gameSpeed", "numPlayers"])
- hideControl(ctrl, ctrl + "Text");
+ hideControl(ctrl, ctrl + "Text", canPlayerChange(ctrl));
- // TODO: Shouldn't players be able to choose their own assignment?
for (let i = 0; i < g_MaxPlayers; ++i)
{
Engine.GetGUIObjectByName("playerAssignment["+i+"]").hidden = true;
@@ -573,6 +590,32 @@
}
/**
+ * Returns if the player is allowed to change this setting
+ */
+function canPlayerChange(setting)
+{
+ if (g_GameAttributes.mapType == "scenario" &&
+ ["victoryCondition", "wonderDuration", "populationCap",
+ "startingResources", "ceasefire", "revealMap", "exploreMap",
+ "disableTreasures", "lockTeams", "playerCiv", "playerTeam", "playerColor"].indexOf(setting) >= 0)
+ return false;
+
+ if (g_GameAttributes.mapType != "random" && setting == "numPlayers")
+ return false;
+
+ if (g_IsController)
+ return true;
+
+ if (setting == "guestSettings")
+ return false;
+
+ if (g_GuestSettings.Data.indexOf(setting) == -1)
+ return g_GameAttributes.GuestSettings == "all";
+
+ return g_GuestSettings.Data.indexOf(g_GameAttributes.GuestSettings) >= g_GuestSettings.Data.indexOf(setting);
+}
+
+/**
* Hide and set some elements depending on whether we play single- or multiplayer.
*/
function initMultiplayerSettings()
@@ -579,6 +622,7 @@
{
Engine.GetGUIObjectByName("chatPanel").hidden = !g_IsNetworked;
Engine.GetGUIObjectByName("optionCheats").hidden = !g_IsNetworked;
+ Engine.GetGUIObjectByName("optionGuestSettings").hidden = !g_IsNetworked;
Engine.GetGUIObjectByName("optionRating").hidden = !Engine.HasXmppClient();
Engine.GetGUIObjectByName("enableCheats").enabled = !Engine.IsRankedGame();
@@ -695,7 +739,7 @@
}
/**
- * Called whenever the host changed any setting.
+ * Called whenever someone changed any setting.
* @param {Object} message
*/
function handleGamesetupMessage(message)
@@ -1046,7 +1090,7 @@
function selectNumPlayers(num)
{
// Avoid recursion
- if (g_IsInGuiUpdate || !g_IsController || g_GameAttributes.mapType != "random")
+ if (g_IsInGuiUpdate || !canPlayerChange("numPlayers") || g_GameAttributes.mapType != "random")
return;
// Unassign players from nonexistent slots
@@ -1110,7 +1154,7 @@
function selectMapType(type)
{
// Avoid recursion
- if (g_IsInGuiUpdate || !g_IsController)
+ if (g_IsInGuiUpdate)
return;
if (!g_MapPath[type])
@@ -1140,7 +1184,7 @@
function selectMapFilter(id)
{
// Avoid recursion
- if (g_IsInGuiUpdate || !g_IsController)
+ if (g_IsInGuiUpdate)
return;
g_GameAttributes.mapFilter = id;
@@ -1153,7 +1197,7 @@
function selectMap(name)
{
// Avoid recursion
- if (g_IsInGuiUpdate || !g_IsController || !name)
+ if (g_IsInGuiUpdate || !name)
return;
// Reset some map specific properties which are not necessarily redefined on each map
@@ -1285,7 +1329,7 @@
if (g_IsNetworked)
{
- Engine.SetNetworkGameAttributes(g_GameAttributes);
+ Engine.NetworkChangeSettings(g_GameAttributes);
Engine.StartNetworkGame();
}
else
@@ -1324,6 +1368,7 @@
let mapFilterIdx = g_MapFilters.findIndex(mapFilter => mapFilter.id == (g_GameAttributes.mapFilter || "default"));
let mapTypeIdx = g_GameAttributes.mapType !== undefined ? g_MapTypes.Name.indexOf(g_GameAttributes.mapType) : g_MapTypes.Default;
let gameSpeedIdx = g_GameAttributes.gameSpeed !== undefined ? g_GameSpeeds.Speed.indexOf(g_GameAttributes.gameSpeed) : g_GameSpeeds.Default;
+ let guestSettingsIdx = g_GameAttributes.GuestSettings !== undefined ? g_GuestSettings.Data.indexOf(g_GameAttributes.GuestSettings) : g_GuestSettings.Default;
// These dropdowns might set the default (as they ignore g_IsInGuiUpdate)
let mapSizeIdx = mapSettings.Size !== undefined ? g_MapSizes.Tiles.indexOf(mapSettings.Size) : g_MapSizes.Default;
@@ -1334,37 +1379,35 @@
let ceasefireIdx = mapSettings.Ceasefire !== undefined ? g_Ceasefire.Duration.indexOf(mapSettings.Ceasefire) : g_Ceasefire.Default;
let numPlayers = mapSettings.PlayerData ? mapSettings.PlayerData.length : g_MaxPlayers;
- if (g_IsController)
- {
- Engine.GetGUIObjectByName("mapType").selected = mapTypeIdx;
- Engine.GetGUIObjectByName("mapFilter").selected = mapFilterIdx;
- Engine.GetGUIObjectByName("mapSelection").selected = Engine.GetGUIObjectByName("mapSelection").list_data.indexOf(mapName);
- Engine.GetGUIObjectByName("mapSize").selected = mapSizeIdx;
- Engine.GetGUIObjectByName("numPlayers").selected = numPlayers - 1;
- Engine.GetGUIObjectByName("victoryCondition").selected = victoryIdx;
- Engine.GetGUIObjectByName("wonderDuration").selected = wonderDurationIdx;
- Engine.GetGUIObjectByName("populationCap").selected = popIdx;
- Engine.GetGUIObjectByName("gameSpeed").selected = gameSpeedIdx;
- Engine.GetGUIObjectByName("ceasefire").selected = ceasefireIdx;
- Engine.GetGUIObjectByName("startingResources").selected = startingResIdx;
- }
- else
- {
- Engine.GetGUIObjectByName("mapTypeText").caption = g_MapTypes.Title[mapTypeIdx];
- Engine.GetGUIObjectByName("mapFilterText").caption = g_MapFilters[mapFilterIdx].name;
- Engine.GetGUIObjectByName("mapSelectionText").caption = mapName == "random" ? g_RandomMap : translate(getMapDisplayName(mapName));
- initMapNameList();
- }
+ Engine.GetGUIObjectByName("mapType").selected = mapTypeIdx;
+ Engine.GetGUIObjectByName("mapFilter").selected = mapFilterIdx;
+ Engine.GetGUIObjectByName("mapSelection").selected = Engine.GetGUIObjectByName("mapSelection").list_data.indexOf(mapName);
+ Engine.GetGUIObjectByName("mapSize").selected = mapSizeIdx;
+ Engine.GetGUIObjectByName("numPlayers").selected = numPlayers - 1;
+ Engine.GetGUIObjectByName("victoryCondition").selected = victoryIdx;
+ Engine.GetGUIObjectByName("wonderDuration").selected = wonderDurationIdx;
+ Engine.GetGUIObjectByName("populationCap").selected = popIdx;
+ Engine.GetGUIObjectByName("gameSpeed").selected = gameSpeedIdx;
+ Engine.GetGUIObjectByName("ceasefire").selected = ceasefireIdx;
+ Engine.GetGUIObjectByName("startingResources").selected = startingResIdx;
+ Engine.GetGUIObjectByName("guestSettings").selected = guestSettingsIdx;
+
+ initMapNameList();
+
// Can be visible to both host and clients
Engine.GetGUIObjectByName("mapSizeText").caption = g_GameAttributes.mapType == "random" ? g_MapSizes.LongName[mapSizeIdx] : translate("Default");
Engine.GetGUIObjectByName("numPlayersText").caption = numPlayers;
Engine.GetGUIObjectByName("victoryConditionText").caption = g_VictoryConditions.Title[victoryIdx];
Engine.GetGUIObjectByName("wonderDurationText").caption = g_WonderDurations.Title[wonderDurationIdx];
+ Engine.GetGUIObjectByName("guestSettingsText").caption = g_GuestSettings.Title[guestSettingsIdx];
Engine.GetGUIObjectByName("populationCapText").caption = g_PopulationCapacities.Title[popIdx];
Engine.GetGUIObjectByName("startingResourcesText").caption = g_StartingResources.Title[startingResIdx];
Engine.GetGUIObjectByName("ceasefireText").caption = g_Ceasefire.Title[ceasefireIdx];
Engine.GetGUIObjectByName("gameSpeedText").caption = g_GameSpeeds.Title[gameSpeedIdx];
+ Engine.GetGUIObjectByName("mapTypeText").caption = g_MapTypes.Title[mapTypeIdx];
+ Engine.GetGUIObjectByName("mapFilterText").caption = g_MapFilters[mapFilterIdx].name;
+ Engine.GetGUIObjectByName("mapSelectionText").caption = mapName == "random" ? g_RandomMap : translate(getMapDisplayName(mapName));
setGUIBoolean("enableCheats", "enableCheatsText", !!mapSettings.CheatsEnabled);
setGUIBoolean("disableTreasures", "disableTreasuresText", !!mapSettings.DisableTreasures);
@@ -1387,15 +1430,16 @@
Engine.GetGUIObjectByName("mapSizeDesc").hidden = !isRandom;
Engine.GetGUIObjectByName("mapSize").hidden = !isRandom || !g_IsController;
Engine.GetGUIObjectByName("mapSizeText").hidden = !isRandom || g_IsController;
- hideControl("numPlayers", "numPlayersText", isRandom && g_IsController);
- let notScenario = g_GameAttributes.mapType != "scenario" && g_IsController ;
-
for (let ctrl of ["victoryCondition", "wonderDuration", "populationCap",
"startingResources", "ceasefire", "revealMap",
- "exploreMap", "disableTreasures", "lockTeams"])
- hideControl(ctrl, ctrl + "Text", notScenario);
+ "exploreMap", "disableTreasures", "lockTeams",
+ "gameSpeed", "guestSettings", "enableCheats",
+ "mapSelection", "numPlayers", "mapType", "mapFilter"])
+ hideControl(ctrl, ctrl + "Text", canPlayerChange(ctrl));
+ let notScenario = g_GameAttributes.mapType != "scenario" && g_IsController ;
+
setMapDescription();
for (let i = 0; i < g_MaxPlayers; ++i)
@@ -1431,17 +1475,16 @@
pCiv.selected = civ ? pCiv.list_data.indexOf(civ) : 0;
pTeam.selected = team !== undefined && team >= 0 ? team+1 : 0;
- hideControl("playerAssignment["+i+"]", "playerAssignmentText["+i+"]", g_IsController);
- hideControl("playerCiv["+i+"]", "playerCivText["+i+"]", notScenario);
- hideControl("playerTeam["+i+"]", "playerTeamText["+i+"]", notScenario);
+ hideControl("playerAssignment["+i+"]", "playerAssignmentText["+i+"]", canPlayerChange("playerAssignment"));
+ hideControl("playerCiv["+i+"]", "playerCivText["+i+"]", canPlayerChange("playerCiv"));
+ hideControl("playerTeam["+i+"]", "playerTeamText["+i+"]", canPlayerChange("playerTeam"));
// Allow host to chose player colors on non-scenario maps
let pColorPicker = Engine.GetGUIObjectByName("playerColorPicker["+i+"]");
let pColorPickerHeading = Engine.GetGUIObjectByName("playerColorHeading");
- let canChangeColors = g_IsController && g_GameAttributes.mapType != "scenario";
- pColorPicker.hidden = !canChangeColors;
- pColorPickerHeading.hidden = !canChangeColors;
- if (canChangeColors)
+ pColorPicker.hidden = !canPlayerChange("playerColor");
+ pColorPickerHeading.hidden = !canPlayerChange("playerColor");
+ if (canPlayerChange("playerColor"))
pColorPicker.selected = g_PlayerColors.findIndex(col => sameColor(col, color));
}
@@ -1508,12 +1551,12 @@
*/
function updateGameAttributes()
{
- if (g_IsInGuiUpdate || !g_IsController)
+ if (g_IsInGuiUpdate)
return;
if (g_IsNetworked)
{
- Engine.SetNetworkGameAttributes(g_GameAttributes);
+ Engine.NetworkChangeSettings(g_GameAttributes);
if (g_LoadingState >= 2)
sendRegisterGameStanza();
}
@@ -1527,7 +1570,7 @@
Engine.PushGuiPage("page_aiconfig.xml", {
"callback": "AIConfigCallback",
- "isController": g_IsController,
+ "canBeChanged": canPlayerChange("playerConfig"),
"playerSlot": playerSlot,
"id": g_GameAttributes.settings.PlayerData[playerSlot].AI,
"difficulty": g_GameAttributes.settings.PlayerData[playerSlot].AIDiff
@@ -1541,7 +1584,7 @@
{
g_LastViewedAIPlayer = -1;
- if (!ai.save || !g_IsController)
+ if (!ai.save)
return;
g_GameAttributes.settings.PlayerData[ai.playerSlot].AI = ai.id;
@@ -1548,7 +1591,7 @@
g_GameAttributes.settings.PlayerData[ai.playerSlot].AIDiff = ai.difficulty;
if (g_IsNetworked)
- Engine.SetNetworkGameAttributes(g_GameAttributes);
+ Engine.NetworkChangeSettings(g_GameAttributes);
else
updatePlayerList();
}
@@ -1644,7 +1687,7 @@
{
g_GameAttributes.settings.PlayerData[playerSlot].AI = "";
if (g_IsNetworked)
- Engine.SetNetworkGameAttributes(g_GameAttributes);
+ Engine.NetworkChangeSettings(g_GameAttributes);
}
let assignBox = Engine.GetGUIObjectByName("playerAssignment["+i+"]");
@@ -1655,37 +1698,36 @@
assignBox.selected = selection;
assignBoxText.caption = hostNameList[selection];
- if (g_IsController)
- assignBox.onselectionchange = function() {
- if (g_IsInGuiUpdate)
- return;
+ assignBox.onSelectionChange = function() {
+ if (g_IsInGuiUpdate)
+ return;
- let guid = hostGuidList[this.selected];
- if (!guid)
- {
- if (g_IsNetworked)
- // Unassign any host from this player slot
- Engine.AssignNetworkPlayer(playerID, "");
- // Remove AI from this player slot
- g_GameAttributes.settings.PlayerData[playerSlot].AI = "";
- }
- else if (guid.substr(0, 3) == "ai:")
- {
- if (g_IsNetworked)
- // Unassign any host from this player slot
- Engine.AssignNetworkPlayer(playerID, "");
- // Set the AI for this player slot
- g_GameAttributes.settings.PlayerData[playerSlot].AI = guid.substr(3);
- }
- else
- swapPlayers(guid, playerSlot);
+ let guid = hostGuidList[this.selected];
+ if (!guid)
+ {
+ if (g_IsNetworked)
+ // Unassign any host from this player slot
+ Engine.AssignNetworkPlayer(playerID, "");
+ // Remove AI from this player slot
+ g_GameAttributes.settings.PlayerData[playerSlot].AI = "";
+ }
+ else if (guid.substr(0, 3) == "ai:")
+ {
+ if (g_IsNetworked)
+ // Unassign any host from this player slot
+ Engine.AssignNetworkPlayer(playerID, "");
+ // Set the AI for this player slot
+ g_GameAttributes.settings.PlayerData[playerSlot].AI = guid.substr(3);
+ }
+ else
+ swapPlayers(guid, playerSlot);
- if (g_IsNetworked)
- Engine.SetNetworkGameAttributes(g_GameAttributes);
- else
- updatePlayerList();
- updateReadyUI();
- };
+ if (g_IsNetworked)
+ Engine.NetworkChangeSettings(g_GameAttributes);
+ else
+ updatePlayerList();
+ updateReadyUI();
+ };
}
g_IsInGuiUpdate = false;
Index: binaries/data/mods/public/gui/gamesetup/gamesetup.xml
===================================================================
--- binaries/data/mods/public/gui/gamesetup/gamesetup.xml (revision 18192)
+++ binaries/data/mods/public/gui/gamesetup/gamesetup.xml (working copy)
@@ -80,7 +80,7 @@
-
+
+
+
Revealed Map:
Index: source/gui/scripting/ScriptFunctions.cpp
===================================================================
--- source/gui/scripting/ScriptFunctions.cpp (revision 18192)
+++ source/gui/scripting/ScriptFunctions.cpp (working copy)
@@ -332,9 +332,9 @@
LOGERROR("Failed to save game");
}
-void SetNetworkGameAttributes(ScriptInterface::CxPrivate* pCxPrivate, JS::HandleValue attribs1)
+void NetworkChangeSettings(ScriptInterface::CxPrivate* pCxPrivate, JS::HandleValue attribs1)
{
- ENSURE(g_NetServer);
+ ENSURE(g_NetClient);
//TODO: This is a workaround because we need to pass a MutableHandle to a JSAPI functions somewhere
// (with no obvious reason).
JSContext* cx = pCxPrivate->pScriptInterface->GetContext();
@@ -341,7 +341,7 @@
JSAutoRequest rq(cx);
JS::RootedValue attribs(cx, attribs1);
- g_NetServer->UpdateGameAttributes(&attribs, *(pCxPrivate->pScriptInterface));
+ g_NetClient->SendChangeSettingsMessage(&attribs, *(pCxPrivate->pScriptInterface));
}
void StartNetworkHost(ScriptInterface::CxPrivate* pCxPrivate, const std::wstring& playerName)
@@ -427,9 +427,9 @@
void AssignNetworkPlayer(ScriptInterface::CxPrivate* UNUSED(pCxPrivate), int playerID, const std::string& guid)
{
- ENSURE(g_NetServer);
+ ENSURE(g_NetClient);
- g_NetServer->AssignPlayer(playerID, guid);
+ g_NetClient->SendAssignPlayerMessage(playerID, guid);
}
void SetNetworkPlayerStatus(ScriptInterface::CxPrivate* UNUSED(pCxPrivate), const std::string& guid, int ready)
@@ -1048,7 +1048,7 @@
scriptInterface.RegisterFunction("GetPlayerGUID");
scriptInterface.RegisterFunction("KickPlayer");
scriptInterface.RegisterFunction("PollNetworkClient");
- scriptInterface.RegisterFunction("SetNetworkGameAttributes");
+ scriptInterface.RegisterFunction("NetworkChangeSettings");
scriptInterface.RegisterFunction("AssignNetworkPlayer");
scriptInterface.RegisterFunction("SetNetworkPlayerStatus");
scriptInterface.RegisterFunction("ClearAllPlayerReady");
Index: source/network/NetClient.cpp
===================================================================
--- source/network/NetClient.cpp (revision 18192)
+++ source/network/NetClient.cpp (working copy)
@@ -321,6 +321,24 @@
SetCurrState(NCS_UNCONNECTED);
}
+void CNetClient::SendChangeSettingsMessage(JS::MutableHandleValue attrs, ScriptInterface& scriptInterface)
+{
+ // Pass the attributes as JSON, since that's the easiest safe
+ // cross-thread way of passing script data
+ std::string attrsJSON = scriptInterface.StringifyJSON(attrs, false);
+ CChangeSettingsMessage changeSetting;
+ changeSetting.m_Settings = attrsJSON;
+ SendMessage(&changeSetting);
+}
+
+void CNetClient::SendAssignPlayerMessage(const int playerID, const std::string guid)
+{
+ CAssignPlayerMessage assignPlayer;
+ assignPlayer.m_PlayerID = playerID;
+ assignPlayer.m_GUIDToAssign = guid;
+ SendMessage(&assignPlayer);
+}
+
void CNetClient::SendChatMessage(const std::wstring& text)
{
CChatMessage chat;
Index: source/network/NetClient.h
===================================================================
--- source/network/NetClient.h (revision 18192)
+++ source/network/NetClient.h (working copy)
@@ -187,6 +187,10 @@
*/
void LoadFinished();
+ void SendChangeSettingsMessage(JS::MutableHandleValue attrs, ScriptInterface& scriptInterface);
+
+ void SendAssignPlayerMessage(const int playerID, const std::string guid);
+
void SendChatMessage(const std::wstring& text);
void SendReadyMessage(const int status);
Index: source/network/NetMessage.cpp
===================================================================
--- source/network/NetMessage.cpp (revision 18192)
+++ source/network/NetMessage.cpp (working copy)
@@ -199,6 +199,13 @@
pNewMessage = new CSimulationMessage(scriptInterface);
break;
+ case NMT_CHANGE_SETTINGS:
+ pNewMessage = new CChangeSettingsMessage;
+ break;
+ case NMT_ASSIGN_PLAYER:
+ pNewMessage = new CAssignPlayerMessage;
+ break;
+
default:
LOGERROR("CNetMessageFactory::CreateMessage(): Unknown message type '%d' received", header.GetType());
break;
Index: source/network/NetMessages.h
===================================================================
--- source/network/NetMessages.h (revision 18192)
+++ source/network/NetMessages.h (working copy)
@@ -28,7 +28,7 @@
#define PS_PROTOCOL_MAGIC 0x5073013f // 'P', 's', 0x01, '?'
#define PS_PROTOCOL_MAGIC_RESPONSE 0x50630121 // 'P', 'c', 0x01, '!'
-#define PS_PROTOCOL_VERSION 0x01010012 // Arbitrary protocol
+#define PS_PROTOCOL_VERSION 0x01010013 // Arbitrary protocol
#define PS_DEFAULT_PORT 0x5073 // 'P', 's'
// Defines the list of message types. The order of the list must not change.
@@ -37,15 +37,15 @@
// positive values.
enum NetMessageType
{
- NMT_CONNECT_COMPLETE = -256, // Connection is complete
+ NMT_CONNECT_COMPLETE = -256,
NMT_CONNECTION_LOST,
- NMT_INVALID = 0, // Invalid message
- NMT_SERVER_HANDSHAKE, // Handshake stage
+ NMT_INVALID = 0,
+ NMT_SERVER_HANDSHAKE,
NMT_CLIENT_HANDSHAKE,
NMT_SERVER_HANDSHAKE_RESPONSE,
- NMT_AUTHENTICATE, // Authentication stage
+ NMT_AUTHENTICATE,
NMT_AUTHENTICATE_RESULT,
- NMT_CHAT, // Common chat message
+ NMT_CHAT,
NMT_READY,
NMT_GAME_SETUP,
NMT_PLAYER_ASSIGNMENT,
@@ -66,10 +66,12 @@
NMT_LOADED_GAME,
NMT_GAME_START,
NMT_END_COMMAND_BATCH,
- NMT_SYNC_CHECK, // OOS-detection hash checking
- NMT_SYNC_ERROR, // OOS-detection error
+ NMT_SYNC_CHECK,
+ NMT_SYNC_ERROR,
NMT_SIMULATION_COMMAND,
- NMT_LAST // Last message in the list
+ NMT_CHANGE_SETTINGS,
+ NMT_ASSIGN_PLAYER,
+ NMT_LAST // Last message in the list
};
// Authentication result codes
@@ -208,6 +210,16 @@
NMT_END_ARRAY()
END_NMT_CLASS()
+START_NMT_CLASS_(ChangeSettings, NMT_CHANGE_SETTINGS)
+ NMT_FIELD(CStr, m_GUID)
+ NMT_FIELD(CStr, m_Settings)
+END_NMT_CLASS()
+
+START_NMT_CLASS_(AssignPlayer, NMT_ASSIGN_PLAYER)
+ NMT_FIELD_INT(m_PlayerID, i8, 1)
+ NMT_FIELD(CStr, m_GUIDToAssign)
+END_NMT_CLASS()
+
END_NMTS()
#else
Index: source/network/NetServer.cpp
===================================================================
--- source/network/NetServer.cpp (revision 18192)
+++ source/network/NetServer.cpp (working copy)
@@ -649,6 +649,8 @@
session->AddTransition(NSS_PREGAME, (uint)NMT_CONNECTION_LOST, NSS_UNCONNECTED, (void*)&OnDisconnect, context);
session->AddTransition(NSS_PREGAME, (uint)NMT_CHAT, NSS_PREGAME, (void*)&OnChat, context);
session->AddTransition(NSS_PREGAME, (uint)NMT_READY, NSS_PREGAME, (void*)&OnReady, context);
+ session->AddTransition(NSS_PREGAME, (uint)NMT_CHANGE_SETTINGS, NSS_PREGAME, (void*)&OnChangeSettings, context);
+ session->AddTransition(NSS_PREGAME, (uint)NMT_ASSIGN_PLAYER, NSS_PREGAME, (void*)&OnAssignPlayer, context);
session->AddTransition(NSS_PREGAME, (uint)NMT_LOADED_GAME, NSS_INGAME, (void*)&OnLoadedGame, context);
session->AddTransition(NSS_JOIN_SYNCING, (uint)NMT_CONNECTION_LOST, NSS_UNCONNECTED, (void*)&OnDisconnect, context);
@@ -1106,6 +1108,28 @@
return true;
}
+bool CNetServerWorker::OnChangeSettings(void* context, CFsmEvent* event)
+{
+ ENSURE(event->GetType() == (uint)NMT_CHANGE_SETTINGS);
+ CNetServerSession* session = (CNetServerSession*)context;
+ CNetServerWorker& server = session->GetServer();
+
+ CChangeSettingsMessage* message = (CChangeSettingsMessage*)event->GetParamRef();
+ server.m_GameAttributesQueue.push_back(message->m_Settings);
+ return true;
+}
+
+bool CNetServerWorker::OnAssignPlayer(void* context, CFsmEvent* event)
+{
+ ENSURE(event->GetType() == (uint)NMT_ASSIGN_PLAYER);
+ CNetServerSession* session = (CNetServerSession*)context;
+ CNetServerWorker& server = session->GetServer();
+
+ CAssignPlayerMessage* message = (CAssignPlayerMessage*)event->GetParamRef();
+ server.m_AssignPlayerQueue.emplace_back(message->m_PlayerID, message->m_GUIDToAssign);
+ return true;
+}
+
bool CNetServerWorker::OnLoadedGame(void* context, CFsmEvent* event)
{
ENSURE(event->GetType() == (uint)NMT_LOADED_GAME);
Index: source/network/NetServer.h
===================================================================
--- source/network/NetServer.h (revision 18192)
+++ source/network/NetServer.h (working copy)
@@ -270,6 +270,8 @@
static bool OnInGame(void* context, CFsmEvent* event);
static bool OnChat(void* context, CFsmEvent* event);
static bool OnReady(void* context, CFsmEvent* event);
+ static bool OnChangeSettings(void* context, CFsmEvent* event);
+ static bool OnAssignPlayer(void* context, CFsmEvent* event);
static bool OnLoadedGame(void* context, CFsmEvent* event);
static bool OnJoinSyncingLoadedGame(void* context, CFsmEvent* event);
static bool OnRejoined(void* context, CFsmEvent* event);