diff --git a/binaries/data/mods/public/gui/session_new/messages.js b/binaries/data/mods/public/gui/session_new/messages.js
index 4449905b73..c4f46ab31c 100644
--- a/binaries/data/mods/public/gui/session_new/messages.js
+++ b/binaries/data/mods/public/gui/session_new/messages.js
@@ -4,6 +4,39 @@ const MAX_NUM_CHAT_LINES = 20;
var chatMessages = [];
var chatTimers = [];
+// Notification Data
+const NOTIFICATION_TIMEOUT = 10000;
+const MAX_NUM_NOTIFICATION_LINES = 3;
+var notifications = [];
+var notificationsTimers = [];
+
+// Notifications
+function handleNotifications()
+{
+ var notification = Engine.GuiInterfaceCall("PopNotification");
+ var timerExpiredFunction = function () { removeOldNotifications(); }
+
+ if (notification)
+ {
+ notifications.push(notification);
+ notificationsTimers.push(setTimeout(timerExpiredFunction, NOTIFICATION_TIMEOUT));
+
+ if (notifications.length <= MAX_NUM_NOTIFICATION_LINES)
+ getGUIObjectByName("notificationText").caption = notifications.join("\n");
+ else
+ removeOldNotifications();
+ }
+}
+
+function removeOldNotifications()
+{
+ clearTimeout(notificationsTimers[0]); // The timer only needs to be cleared when new notifications bump old notifications off
+ notificationsTimers.shift();
+ notifications.shift();
+ getGUIObjectByName("notificationText").caption = notifications.join("\n");
+}
+
+//Messages
function handleNetMessage(message)
{
log("Net message: "+uneval(message));
@@ -84,7 +117,7 @@ function addChatMessage(msg)
switch (msg.type)
{
case "disconnect":
- formatted = '<[font=\"serif-stroke-14\"][color="' + playerColor + '"]' + msg.username + '[/color][/font]> has left';
+ formatted = "<[color=\"" + playerColor + "\"]" + msg.username + "[/color]> has left";
break;
case "message":
@@ -102,7 +135,7 @@ function addChatMessage(msg)
chatMessages.push(formatted);
chatTimers.push(setTimeout(timerExpiredFunction, CHAT_TIMEOUT));
- if (chatMessages.length < MAX_NUM_CHAT_LINES)
+ if (chatMessages.length <= MAX_NUM_CHAT_LINES)
getGUIObjectByName("chatText").caption = chatMessages.join("\n");
else
removeOldChatMessages();
@@ -124,9 +157,3 @@ function getColorByPlayerName(playerName)
return "255 255 255";
}
-
-function clearChatInput()
-{
- getGUIObjectByName("chatInput").caption = "";
-}
-
diff --git a/binaries/data/mods/public/gui/session_new/session.js b/binaries/data/mods/public/gui/session_new/session.js
index a616c21c2f..2570e4412f 100644
--- a/binaries/data/mods/public/gui/session_new/session.js
+++ b/binaries/data/mods/public/gui/session_new/session.js
@@ -23,7 +23,6 @@ var g_IsNetworked = false;
// Cache the basic player data (name, civ, color)
var g_Players = [];
-
var g_PlayerAssignments = {};
// Cache dev-mode settings that are frequently or widely used
@@ -110,6 +109,10 @@ function onSimulationUpdate()
if (!simState)
return;
+
+ handleNotifications();
+
+
updateDebug(simState);
updatePlayerDisplay(simState);
updateSelectionDetails();
diff --git a/binaries/data/mods/public/gui/session_new/session.xml b/binaries/data/mods/public/gui/session_new/session.xml
index e0d9e79665..6e5ebc63ae 100644
--- a/binaries/data/mods/public/gui/session_new/session.xml
+++ b/binaries/data/mods/public/gui/session_new/session.xml
@@ -131,6 +131,13 @@
togglePause();
+
+
+
+
+
diff --git a/binaries/data/mods/public/gui/session_new/styles.xml b/binaries/data/mods/public/gui/session_new/styles.xml
index 6fbecd8570..c889910567 100644
--- a/binaries/data/mods/public/gui/session_new/styles.xml
+++ b/binaries/data/mods/public/gui/session_new/styles.xml
@@ -154,5 +154,14 @@
text_align="left"
text_valign="top"
/>
+
+
diff --git a/binaries/data/mods/public/simulation/components/GuiInterface.js b/binaries/data/mods/public/simulation/components/GuiInterface.js
index e1e0c67900..5d732c45fa 100644
--- a/binaries/data/mods/public/simulation/components/GuiInterface.js
+++ b/binaries/data/mods/public/simulation/components/GuiInterface.js
@@ -1,4 +1,7 @@
-function GuiInterface() {}
+function GuiInterface()
+{
+ this.notifications = [];
+}
GuiInterface.prototype.Schema =
"";
@@ -14,6 +17,21 @@ GuiInterface.prototype.Init = function()
this.rallyPoints = undefined;
};
+GuiInterface.prototype.PushNotification = function(notification)
+{
+ this.notifications.push(notification);
+};
+
+GuiInterface.prototype.PopNotification = function()
+{
+ //warn(uneval(this.notifications));
+
+ if (this.notifications.length)
+ return this.notifications.pop();
+ else
+ return "";
+};
+
GuiInterface.prototype.GetSimulationState = function(player)
{
var ret = {
@@ -367,6 +385,7 @@ GuiInterface.prototype.SetRangeDebugOverlay = function(player, enabled)
// trusted and indicates the player associated with the current client; no data should
// be returned unless this player is meant to be able to see it.)
var exposedFunctions = {
+ "PopNotification": 1,
"GetSimulationState": 1,
"GetEntityState": 1,
"GetTemplateData": 1,
diff --git a/binaries/data/mods/public/simulation/components/Player.js b/binaries/data/mods/public/simulation/components/Player.js
index 050a3283f2..bb49fafab7 100644
--- a/binaries/data/mods/public/simulation/components/Player.js
+++ b/binaries/data/mods/public/simulation/components/Player.js
@@ -82,14 +82,29 @@ Player.prototype.AddResources = function(amounts)
Player.prototype.TrySubtractResources = function(amounts)
{
- // Check we can afford it all
+ // Check if we can afford it all
+ var amountsNeeded = {};
for (var type in amounts)
if (amounts[type] > this.resourceCount[type])
- return false;
-
- // Subtract the resources
- for (var type in amounts)
- this.resourceCount[type] -= amounts[type];
+ amountsNeeded[type] = amounts[type] - this.resourceCount[type];
+
+ var formattedAmountsNeeded = [];
+ for (var type in amountsNeeded)
+ formattedAmountsNeeded.push(type + ": " + amountsNeeded[type]);
+
+ // If we don't have enough resources, send a notification to the player
+ if (formattedAmountsNeeded.length)
+ {
+ var cmpGUIInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
+ cmpGUIInterface.PushNotification("Resources needed: " + formattedAmountsNeeded.join(", "));
+ return false;
+ }
+ else
+ {
+ // Subtract the resources
+ for (var type in amounts)
+ his.resourceCount[type] -= amounts[type];
+ }
return true;
};
diff --git a/binaries/data/mods/public/simulation/components/TrainingQueue.js b/binaries/data/mods/public/simulation/components/TrainingQueue.js
index 2c8f51b990..5dab096147 100644
--- a/binaries/data/mods/public/simulation/components/TrainingQueue.js
+++ b/binaries/data/mods/public/simulation/components/TrainingQueue.js
@@ -81,7 +81,7 @@ TrainingQueue.prototype.AddBatch = function(player, templateName, count)
if (!cmpPlayer.TrySubtractResources(costs))
{
- // TODO: report error to player (they ran out of resources)
+ // TrySubtractResources should report error to player (they ran out of resources)
return;
}