Index: binaries/data/config/default.cfg =================================================================== --- binaries/data/config/default.cfg +++ binaries/data/config/default.cfg @@ -360,6 +360,7 @@ attackrange = true ; Display attack range overlays of selected defensive structures aurasrange = true ; Display aura range overlays of selected units and structures healrange = true ; Display heal range overlays of selected units +sortrespoptooltip = 0 ; Sorting players in the resources and population tooltip by value (0 - no sort, -1 - ascending, 1 - descending) [gui.session.minimap] blinkduration = 1.7 ; The blink duration while pinging Index: binaries/data/mods/public/gui/options/options.json =================================================================== --- binaries/data/mods/public/gui/options/options.json +++ binaries/data/mods/public/gui/options/options.json @@ -127,6 +127,17 @@ "label": "Heal Range Visualization", "tooltip": "Display the healing range of selected units (can also be toggled in-game with the hotkey).", "config": "gui.session.healrange" + }, + { + "type": "dropdown", + "label": "Sort resources and population tooltip", + "tooltip": "Dynamically sort players in resources and population tooltip by value.", + "config": "gui.session.sortrespoptooltip", + "list": [ + { "value": 0, "label": "Unordered" }, + { "value": -1, "label": "Ascending" }, + { "value": 1, "label": "Descending" } + ] } ] }, Index: binaries/data/mods/public/gui/session/session.js =================================================================== --- binaries/data/mods/public/gui/session/session.js +++ binaries/data/mods/public/gui/session/session.js @@ -1116,34 +1116,70 @@ debug.caption = text.replace(/\[/g, "\\["); } -function getAllyStatTooltip(resource) +/** + * Build ally player stat tooltip. + * @param {string} resource - Resource code. + * @param {object} playersState - Stats from viewable players. + * @param {integer} order - 0 no order, -1 descending, 1 ascending order + * @returns {string} Tooltip string. + */ +function getAllyStatTooltip(resource, playersState, order) { - let playersState = GetSimState().players; - let ret = ""; + let tooltip = []; for (let player in playersState) - if (player != 0 && - player != g_ViewedPlayer && - g_Players[player].state != "defeated" && - (g_IsObserver || - playersState[g_ViewedPlayer].hasSharedLos && - g_Players[player].isMutualAlly[g_ViewedPlayer])) - ret += "\n" + sprintf(translate("%(playername)s: %(statValue)s"), { - "playername": colorizePlayernameHelper("■", player) + " " + g_Players[player].name, - "statValue": resource == "pop" ? - sprintf(translate("%(popCount)s/%(popLimit)s/%(popMax)s"), playersState[player]) : - Math.round(playersState[player].resourceCounts[resource]) - }); + tooltip.push({ + "playername": colorizePlayernameHelper("■", player) + " " + g_Players[player].name, + "statValue": resource == "pop" ? + sprintf(translate("%(popCount)s/%(popLimit)s/%(popMax)s"), playersState[player]) : + Math.round(playersState[player].resourceCounts[resource]), + "orderValue": resource == "pop" ? playersState[player].popCount : + Math.round(playersState[player].resourceCounts[resource]) + }); + if (order) + tooltip.sort((a, b) => order * (b.orderValue - a.orderValue)); + return "\n" + tooltip.map(stat => sprintf(translate("%(playername)s: %(statValue)s"), stat)).join("\n"); +} - return ret; +/** + * Get or set user config setting. + * @param {string} name - Setting name. + * @param {string} value - Set value. + * @returns {string} If value not setted, return setting value. + */ +function configDb(name, value) +{ + if (value === undefined) + return Engine.ConfigDB_GetValue("user", name); + Engine.ConfigDB_CreateValue("user", name, value); + Engine.ConfigDB_WriteValueToFile("user", name, value, "config/user.cfg"); } function updatePlayerDisplay() { - let playerState = GetSimState().players[g_ViewedPlayer]; + let playersState = GetSimState().players; + let playerState = playersState[g_ViewedPlayer]; + let viewablePlayerStates = {}; + Object.keys(playersState).forEach(player => { + if (player != 0 && + player != g_ViewedPlayer && + g_Players[player].state != "defeated" && + (g_IsObserver || + playerState.hasSharedLos && + g_Players[player].isMutualAlly[g_ViewedPlayer])) + viewablePlayerStates[player] = playersState[player]; + }); if (!playerState) return; + let orderTooltip = configDb("gui.session.sortrespoptooltip"); + let orderHotkeyTooltip = viewablePlayerStates.length <= 1 ? "" : + "\n" + sprintf(translate("%(order)s: %(hotkey)s cycle order."), { + "hotkey": coloredText("\\[Click]", g_HotkeyColor), + "order": orderTooltip == 0 ? translate("Unordered") : orderTooltip == 1 ? translate("Descending") : translate("Ascending") + }); + let changeOrder = () => configDb("gui.session.sortrespoptooltip", orderTooltip == 0 ? 1 : orderTooltip == 1 ? -1 : 0); + let resCodes = g_ResourceData.GetCodes(); for (let r = 0; r < resCodes.length; ++r) { @@ -1154,23 +1190,26 @@ let res = resCodes[r]; let tooltip = '[font="' + g_ResourceTitleFont + '"]' + - resourceNameFirstWord(res) + '[/font]'; + resourceNameFirstWord(res) + '[/font]' + orderHotkeyTooltip; let descr = g_ResourceData.GetResource(res).description; if (descr) tooltip += "\n" + translate(descr); - tooltip += getAllyStatTooltip(res); + tooltip += getAllyStatTooltip(res, viewablePlayerStates, orderTooltip); resourceObj.tooltip = tooltip; + resourceObj.onPress = changeOrder; Engine.GetGUIObjectByName("resource[" + r + "]_count").caption = Math.floor(playerState.resourceCounts[res]); } Engine.GetGUIObjectByName("resourcePop").caption = sprintf(translate("%(popCount)s/%(popLimit)s"), playerState); - Engine.GetGUIObjectByName("population").tooltip = translate("Population (current / limit)") + "\n" + + Engine.GetGUIObjectByName("population").onPress = changeOrder; + Engine.GetGUIObjectByName("population").tooltip = translate("Population (current / limit)") + + orderHotkeyTooltip + "\n" + sprintf(translate("Maximum population: %(popCap)s"), { "popCap": playerState.popMax }) + - getAllyStatTooltip("pop"); + getAllyStatTooltip("pop", viewablePlayerStates, orderTooltip); g_IsTrainingBlocked = playerState.trainingBlocked; } Index: binaries/data/mods/public/gui/session/top_panel/resource_population.xml =================================================================== --- binaries/data/mods/public/gui/session/top_panel/resource_population.xml +++ binaries/data/mods/public/gui/session/top_panel/resource_population.xml @@ -1,6 +1,6 @@ - + Index: binaries/data/mods/public/gui/session/top_panel/resources.xml =================================================================== --- binaries/data/mods/public/gui/session/top_panel/resources.xml +++ binaries/data/mods/public/gui/session/top_panel/resources.xml @@ -2,7 +2,7 @@ - +