Clean up notifications. Merge the timed and untimed text notifications, allow passing a list of players to all notifications, make modification types moddable. Refs #52

This was SVN commit r15394.
This commit is contained in:
sanderd17 2014-06-19 14:37:08 +00:00
parent 6d5039791f
commit 81d1f5f71f
9 changed files with 109 additions and 108 deletions

View File

@ -26,20 +26,25 @@ function getCheatsData()
return cheats;
}
// Notifications
function handleNotifications()
var g_NotificationsTypes =
{
var notification = Engine.GuiInterfaceCall("GetNextNotification");
if (!notification)
return;
if (notification.type === undefined)
notification.type = "text";
// Handle chat notifications specially
if (notification.type == "chat" ||
notification.type == "aichat")
"chat": function(notification, player)
{
var message = {
"type": "message",
"text": notification.message
}
var guid = findGuidForPlayerID(g_PlayerAssignments, player);
if (guid == undefined)
{
message["guid"] = -1;
message["player"] = player;
} else {
message["guid"] = guid;
}
addChatMessage(message);
},
"aichat": function(notification, player)
{
var message = {
"type": "message",
@ -47,33 +52,33 @@ function handleNotifications()
}
if (notification.type == "aichat")
message["translate"] = true;
var guid = findGuidForPlayerID(g_PlayerAssignments, notification.player);
var guid = findGuidForPlayerID(g_PlayerAssignments, player);
if (guid == undefined)
{
message["guid"] = -1;
message["player"] = notification.player;
message["player"] = player;
} else {
message["guid"] = findGuidForPlayerID(g_PlayerAssignments, notification.player);
message["guid"] = guid;
}
addChatMessage(message);
}
else if (notification.type == "defeat")
},
"defeat": function(notification, player)
{
addChatMessage({
"type": "defeat",
"guid": findGuidForPlayerID(g_PlayerAssignments, notification.player),
"player": notification.player
"guid": findGuidForPlayerID(g_PlayerAssignments, player),
"player": player
});
// If the diplomacy panel is open refresh it.
if (isDiplomacyOpen)
openDiplomacy();
}
else if (notification.type == "diplomacy")
},
"diplomacy": function(notification, player)
{
addChatMessage({
"type": "diplomacy",
"player": notification.player,
"player": player,
"player1": notification.player1,
"status": notification.status
});
@ -81,85 +86,76 @@ function handleNotifications()
// If the diplomacy panel is open refresh it.
if (isDiplomacyOpen)
openDiplomacy();
}
else if (notification.type == "quit")
},
"quite": function(notification, player)
{
// Used for AI testing
exit();
}
else if (notification.type == "tribute")
exit(); // TODO this doesn't work anymore
},
"tribute": function(notification, player)
{
addChatMessage({
"type": "tribute",
"player": notification.player,
"player1": notification.player1,
"player": player,
"player1": notification.donator,
"amounts": notification.amounts
});
}
else if (notification.type == "attack")
},
"attack": function(notification, player)
{
if (notification.player == Engine.GetPlayerID())
{
if (Engine.ConfigDB_GetValue("user", "gui.session.attacknotificationmessage") === "true")
{
addChatMessage({
"type": "attack",
"player": notification.player,
"attacker": notification.attacker
});
}
}
}
else if (notification.type == "text")
{
// Only display notifications directed to this player
if (notification.player == Engine.GetPlayerID())
{
notifications.push(notification);
notificationsTimers.push(setTimeout(removeOldNotifications, NOTIFICATION_TIMEOUT));
if (player != Engine.GetPlayerID())
return;
if (Engine.ConfigDB_GetValue("user", "gui.session.attacknotificationmessage") !== "true")
return;
addChatMessage({
"type": "attack",
"player": player,
"attacker": notification.attacker
});
},
};
if (notifications.length > MAX_NUM_NOTIFICATION_LINES)
removeOldNotifications();
else
displayNotifications();
}
}
else
{
warn("notification of unknown type!");
}
}
function removeOldNotifications()
// Notifications
function handleNotifications()
{
clearTimeout(notificationsTimers[0]); // The timer only needs to be cleared when new notifications bump old notifications off
notificationsTimers.shift();
notifications.shift();
displayNotifications();
}
var notification = Engine.GuiInterfaceCall("GetNextNotification");
function displayNotifications()
{
var messages = [];
for each (var n in notifications)
if (!notification)
return;
if (!notification.type)
{
var parameters = n.parameters || {};
if (n.translateParameters)
translateObjectKeys(parameters, n.translateParameters);
var message = n.message;
if (n.translateMessage)
message = translate(message);
messages.push(sprintf(message, parameters));
error("notification without type found.\n"+uneval(notification))
return;
}
Engine.GetGUIObjectByName("notificationText").caption = messages.join("\n");
if (!notification.players)
{
error("notification without players found.\n"+uneval(notification))
return;
}
var action = g_NotificationsTypes[notification.type];
if (!action)
{
error("unknown notification type '" + notification.type + "' found.");
return;
}
for (var player of notification.players)
action(notification, player);
}
function updateTimeNotifications()
{
var notifications = Engine.GuiInterfaceCall("GetTimeNotifications");
var notificationText = "";
var playerID = Engine.GetPlayerID();
for (var n of notifications)
{
if (!n.players)
{
warn("notification has unknown player list. Text:\n"+n.message);
continue
}
if (n.players.indexOf(playerID) == -1)
continue;
var message = n.message;
if (n.translateMessage)
message = translate(message);
@ -169,7 +165,7 @@ function updateTimeNotifications()
parameters.time = timeToString(n.time);
notificationText += sprintf(message, parameters) + "\n";
}
Engine.GetGUIObjectByName("timeNotificationText").caption = notificationText;
Engine.GetGUIObjectByName("notificationText").caption = notificationText;
}
// Returns [username, playercolor] for the given player

View File

@ -180,9 +180,6 @@
<object name="notificationPanel" type="image" size="50%-300 60 50%+300 120" ghost="true">
<object name="notificationText" size="0 0 100% 100%" type="text" style="notificationPanel" ghost="true"/>
</object>
<object name="timeNotificationPanel" type="image" size="100%-600 60 100%-20 120" ghost="true">
<object name="timeNotificationText" size="0 0 100% 100%" type="text" style="notificationPanel" ghost="true"/>
</object>
<!-- ================================ ================================ -->

View File

@ -78,7 +78,7 @@ AttackDetection.prototype.AttackAlert = function(target, attacker)
this.AddSuppression(event);
Engine.PostMessage(this.entity, MT_AttackDetected, { "player": cmpPlayer.GetPlayerID(), "event": event });
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGuiInterface.PushNotification({"type": "attack", "player": cmpPlayer.GetPlayerID(), "attacker": cmpAttackerOwnership.GetOwner() });
cmpGuiInterface.PushNotification({"type": "attack", "players": [cmpPlayer.GetPlayerID()], "attacker": cmpAttackerOwnership.GetOwner() });
PlaySound("attacked", target);
};

View File

@ -100,7 +100,7 @@ EntityLimits.prototype.AllowedToCreate = function(limitType, category, count)
{
var cmpPlayer = Engine.QueryInterface(this.entity, IID_Player);
var notification = {
"player": cmpPlayer.GetPlayerID(),
"players": [cmpPlayer.GetPlayerID()],
"translateMessage": true,
"translateParameters": ["category"],
"parameters": {"category": category, "limit": this.limit[category]},

View File

@ -847,6 +847,13 @@ GuiInterface.prototype.GetTimeNotifications = function(playerID)
GuiInterface.prototype.PushNotification = function(notification)
{
if (!notification.type || notification.type == "text")
{
if (!notification.duration)
notification.duration = 10000;
this.AddTimeNotification(notification);
return;
}
this.notifications.push(notification);
};

View File

@ -244,7 +244,7 @@ Player.prototype.SubtractResourcesOrNotify = function(amounts)
warn("Localisation: Strings are not localised for more than 4 resources");
var notification = {
"player": this.playerID,
"players": [this.playerID],
"message": msg,
"parameters": parameters,
"translateMessage": true,
@ -641,7 +641,7 @@ Player.prototype.OnPlayerDefeated = function(msg)
cmpRangeManager.SetLosRevealAll(this.playerID, true);
// Send a chat message notifying of the player's defeat.
var notification = {"type": "defeat", "player": this.playerID};
var notification = {"type": "defeat", "players": [this.playerID]};
var cmpGUIInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGUIInterface.PushNotification(notification);
};
@ -698,7 +698,7 @@ Player.prototype.TributeResource = function(player, amounts)
if (cmpTheirStatisticsTracker)
cmpTheirStatisticsTracker.IncreaseTributesReceivedCounter(total);
var notification = {"type": "tribute", "player": player, "player1": this.playerID, "amounts": amounts};
var notification = {"type": "tribute", "players": [player], "donator": this.playerID, "amounts": amounts};
var cmpGUIInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
if (cmpGUIInterface)
cmpGUIInterface.PushNotification(notification);

View File

@ -342,7 +342,7 @@ ProductionQueue.prototype.AddBatch = function(templateName, type, count, metadat
}
else
{
var notification = {"player": cmpPlayer.GetPlayerID(), "message": markForTranslation("The production queue is full."), "translateMessage": true };
var notification = {"players": [cmpPlayer.GetPlayerID()], "message": markForTranslation("The production queue is full."), "translateMessage": true };
var cmpGUIInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGUIInterface.PushNotification(notification);
}

View File

@ -13,7 +13,7 @@ function Cheat(input)
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
if (!cmpPlayer.GetCheatsEnabled())
{
cmpGuiInterface.PushNotification({"type": "chat", "player": input.player, "message": "Cheats are disbaled in this match"});
cmpGuiInterface.PushNotification({"type": "chat", "players": [input.player], "message": "Cheats are disbaled in this match"});
return;
}
@ -61,14 +61,14 @@ function Cheat(input)
case "createunits":
if (!input.selected[0])
{
cmpGuiInterface.PushNotification({"type": "notification", "player": input.player, "message": "You need to select a building that trains units."});
cmpGuiInterface.PushNotification({"type": "notification", "players": [input.player], "message": "You need to select a building that trains units."});
return;
}
var cmpProductionQueue = Engine.QueryInterface(input.selected[0], IID_ProductionQueue);
if (!cmpProductionQueue)
{
cmpGuiInterface.PushNotification({"type": "notification", "player": input.player, "message": "You need to select a building that trains units."});
cmpGuiInterface.PushNotification({"type": "notification", "players": [input.player], "message": "You need to select a building that trains units."});
return;
}
for (var i = 0; i < input.parameter; i++)
@ -115,7 +115,7 @@ function Cheat(input)
// check, if name of technology is given
if (input.parameter.length == 0)
{
cmpGuiInterface.PushNotification({"type": "notification", "player": input.player, "message": "You have to enter the name of a technology or select a building and enter the number of the technology (brainiac number [top|paired].)"});
cmpGuiInterface.PushNotification({"type": "notification", "players": [input.player], "message": "You have to enter the name of a technology or select a building and enter the number of the technology (brainiac number [top|paired].)"});
return;
}
var techname = input.parameter;
@ -144,7 +144,7 @@ function Cheat(input)
var tech = techs[number-1];
if (!tech)
{
cmpGuiInterface.PushNotification({"type": "notification", "player": input.player, "message": "You have already researched this technology."});
cmpGuiInterface.PushNotification({"type": "notification", "players": [input.player], "message": "You have already researched this technology."});
return;
}
// get name of tech
@ -155,7 +155,7 @@ function Cheat(input)
}
else
{
cmpGuiInterface.PushNotification({"type": "notification", "player": input.player, "message": "This building only has " + techs.length + " technologies."});
cmpGuiInterface.PushNotification({"type": "notification", "players": [input.player], "message": "This building only has " + techs.length + " technologies."});
return;
}
}
@ -166,7 +166,7 @@ function Cheat(input)
var template = cmpTechnologyManager.GetTechnologyTemplate(techname);
if (!template)
{
cmpGuiInterface.PushNotification({"type": "notification", "player": input.player, "message": "Technology \"" + techname + "\" does not exist"});
cmpGuiInterface.PushNotification({"type": "notification", "players": [input.player], "message": "Technology \"" + techname + "\" does not exist"});
return;
}

View File

@ -45,13 +45,13 @@ var commands = {
"chat": function(player, cmd, data)
{
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGuiInterface.PushNotification({"type": cmd.type, "player": player, "message": cmd.message});
cmpGuiInterface.PushNotification({"type": cmd.type, "players": [player], "message": cmd.message});
},
"aichat": function(player, cmd, data)
{
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGuiInterface.PushNotification({"type": cmd.type, "player": player, "message": cmd.message});
cmpGuiInterface.PushNotification({"type": cmd.type, "players": [player], "message": cmd.message});
},
"cheat": function(player, cmd, data)
@ -62,6 +62,7 @@ var commands = {
"quit": function(player, cmd, data)
{
// Let the AI exit the game for testing purposes
// TODO broken, does this need a fix?
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGuiInterface.PushNotification({"type": "quit"});
},
@ -83,7 +84,7 @@ var commands = {
warn("Invalid command: Could not set "+player+" diplomacy status of player "+cmd.player+" to "+cmd.to);
}
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGuiInterface.PushNotification({"type": "diplomacy", "player": player, "player1": cmd.player, "status": cmd.to});
cmpGuiInterface.PushNotification({"type": "diplomacy", "players": [player], "player1": cmd.player, "status": cmd.to});
},
"tribute": function(player, cmd, data)
@ -526,7 +527,7 @@ var commands = {
{
// No need to do checks here since this is a cheat anyway
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGuiInterface.PushNotification({"type": "chat", "player": player, "message": "(Cheat - promoted units)"});
cmpGuiInterface.PushNotification({"type": "chat", "players": [player], "message": "(Cheat - promoted units)"});
for each (var ent in cmd.entities)
{
@ -645,7 +646,7 @@ var commands = {
function notifyUnloadFailure(player, garrisonHolder)
{
var cmpPlayer = QueryPlayerIDInterface(player, IID_Player);
var notification = {"player": cmpPlayer.GetPlayerID(), "message": "Unable to ungarrison unit(s)" };
var notification = {"players": [cmpPlayer.GetPlayerID()], "message": "Unable to ungarrison unit(s)" };
var cmpGUIInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGUIInterface.PushNotification(notification);
}
@ -656,7 +657,7 @@ function notifyUnloadFailure(player, garrisonHolder)
function notifyBackToWorkFailure(player)
{
var cmpPlayer = QueryPlayerIDInterface(player, IID_Player);
var notification = {"player": cmpPlayer.GetPlayerID(), "message": "Some unit(s) can't go back to work" };
var notification = {"players": [cmpPlayer.GetPlayerID()], "message": "Some unit(s) can't go back to work" };
var cmpGUIInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGUIInterface.PushNotification(notification);
}
@ -667,7 +668,7 @@ function notifyBackToWorkFailure(player)
function notifyAlertFailure(player)
{
var cmpPlayer = QueryPlayerIDInterface(player, IID_Player);
var notification = {"player": cmpPlayer.GetPlayerID(), "message": "You can't raise the alert to a higher level !" };
var notification = {"players": [cmpPlayer.GetPlayerID()], "message": "You can't raise the alert to a higher level !" };
var cmpGUIInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGUIInterface.PushNotification(notification);
}
@ -873,7 +874,7 @@ function TryConstructBuilding(player, cmpPlayer, controlAllUnits, cmd)
}
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
ret.player = player;
ret.players = [player];
cmpGuiInterface.PushNotification(ret);
// Remove the foundation because the construction was aborted
@ -912,7 +913,7 @@ function TryConstructBuilding(player, cmpPlayer, controlAllUnits, cmd)
}
var cmpGuiInterface = Engine.QueryInterface(SYSTEM_ENTITY, IID_GuiInterface);
cmpGuiInterface.PushNotification({ "player": player, "message": "Building's technology requirements are not met." });
cmpGuiInterface.PushNotification({ "players": [player], "message": "Building's technology requirements are not met." });
// Remove the foundation because the construction was aborted
cmpPosition.MoveOutOfWorld();