From 67407b234a9948a433cdddbfb45a86a5a5902139 Mon Sep 17 00:00:00 2001 From: Afforess Date: Tue, 3 Nov 2015 23:21:47 -0500 Subject: [PATCH 1/3] Require remote sensor to supply the mod_name when created Remove remote sensors associated with removed mods --- control.lua | 6 +++-- evoGUI.lua | 47 +++++++++++++++++++++++++++++---- locale/en/locale.cfg | 1 + remote.lua | 21 +++++++++++---- value_sensors/remote_sensor.lua | 31 +++++++++++++++++++++- 5 files changed, 93 insertions(+), 13 deletions(-) diff --git a/control.lua b/control.lua index b015c73..98b66c4 100644 --- a/control.lua +++ b/control.lua @@ -37,14 +37,16 @@ end script.on_init(evogui.mod_init) script.on_configuration_changed(evogui.mod_update) - +script.on_load(function() + local status, err = pcall(RemoteSensor.initialize) + if err then evogui.log({"err_generic", "on_load", err}) end +end) script.on_event(defines.events.on_player_created, function(event) local status, err = pcall(evogui.new_player, event) if err then evogui.log({"err_generic", "on_player_created", err}) end end) - script.on_event(defines.events.on_tick, function(event) local status, err = pcall(evogui.update_gui, event) if err then evogui.log({"err_generic", "on_tick", err}) end diff --git a/evoGUI.lua b/evoGUI.lua index 7df027f..d1782a3 100644 --- a/evoGUI.lua +++ b/evoGUI.lua @@ -23,12 +23,49 @@ function evogui.mod_init() end end - function evogui.mod_update(data) - if data.mod_changes["{{MOD_NAME}}"] then - -- TODO: If a more major migration ever needs doing, do that here. - -- Otherwise, just falling back to mod_init should work fine. - evogui.mod_init() + if data.mod_changes then + if data.mod_changes["{{MOD_NAME}}"] then + -- TODO: If a more major migration ever needs doing, do that here. + -- Otherwise, just falling back to mod_init should work fine. + evogui.mod_init() + end + + evogui.validate_sensors(data.mod_changes) + end +end + +-- Iterate through all value_sensors, if any are associated with a mod_name that +-- has been removed, remove the sensor from the list of value_sensors. +function evogui.validate_sensors(mod_changes) + local valid_sensors = {} + for sensor in evogui.value_sensors do + if sensor.mod_name and mod_changes[sensor.mod_name] then + -- mod upgrade, keep sensor + if mod_changes[sensor.mod_name].new_version ~= nil then + valid_sensors[#valid_sensors + 1] = sensor + else + -- mod removed, remove sensor from ui + evogui.hide_sensor(sensor) + end + else + valid_sensors[#valid_sensors + 1] = sensor + end + end + evogui.value_sensors = valid_sensors +end + +function evogui.hide_sensor(sensor) + for player_name, data in pairs(global.evogui) do + if data.always_visible then + data.always_visible[sensor["name"]] = false + end + end + for _, player in pairs(game.players) do + local player_settings = global.evogui[player.name] + + local sensor_flow = player.gui.top.evoGUI.sensor_flow + evogui.update_av(player, sensor_flow.always_visible) end end diff --git a/locale/en/locale.cfg b/locale/en/locale.cfg index a0c9a34..a609aae 100644 --- a/locale/en/locale.cfg +++ b/locale/en/locale.cfg @@ -79,6 +79,7 @@ err_needplayername=[EvoGUI] Need a player name! err_nosuchplayer=[EvoGUI] No such player: __1__! err_noplayerdata=[EvoGUI] No player data for __1__! +err_nomodname=[EvoGUI] Missing the mod name of the sensor! err_nosensorname=[EvoGUI] Missing a sensor name! err_nosensortext=[EvoGUI] Missing sensor text for __1__! err_nosensorcaption=[EvoGUI] Missing caption text for __1__! diff --git a/remote.lua b/remote.lua index c8968e5..ecf10f9 100644 --- a/remote.lua +++ b/remote.lua @@ -33,12 +33,18 @@ end -- -- Creates a sensor managed by a remote interface (another mod or script) +-- mod_name: Name of the mod registering the sensor. Sensor will be removed if the mod is removed from the game. -- sensor_name: internal name of the sensor. Should be unique. -- sensor_text: Text to display in the active gui -- sensor_caption: Sensor setting name in the EvoGUI settings panel -- sensor_color: Font color of the text to display in the active gui, optional, may be nil -- example: remote.call("EvoGUI", "create_remote_sensor", "mymod_my_sensor_name", "Text: Lorem Ipsum", "[My Mod] Lorem Ipsum Text") -local function create_remote_sensor(sensor_name, sensor_text, sensor_caption, sensor_color) +local function create_remote_sensor(mod_name, sensor_name, sensor_text, sensor_caption, sensor_color) + if not mod_name then + evogui.log({"err_nomodname"}) + return + end + if not sensor_name then evogui.log({"err_nosensorname"}) return @@ -53,8 +59,13 @@ local function create_remote_sensor(sensor_name, sensor_text, sensor_caption, se evogui.log({"err_nosensorcaption", sensor_name}) return end - - RemoteSensor.new(sensor_name, sensor_text, sensor_caption, sensor_color) + + local sensor = RemoteSensor.get_by_name(sensor_name) + if not sensor then + RemoteSensor.new(mod_name, sensor_name, sensor_text, sensor_caption, sensor_color) + else + -- should anything happen here? + end end -- @@ -93,8 +104,8 @@ interface = { if err then evogui.log({"err_generic", "interface.rebuild", err}) end end, - create_remote_sensor = function(sensor_name, sensor_text, sensor_caption, sensor_color) - local status, err = pcall(create_remote_sensor, sensor_name, sensor_text, sensor_caption, sensor_color) + create_remote_sensor = function(mod_name, sensor_name, sensor_text, sensor_caption, sensor_color) + local status, err = pcall(create_remote_sensor, mod_name, sensor_name, sensor_text, sensor_caption, sensor_color) if err then evogui.log({"err_generic", "remote.create_remote_sensor", err}) end end, diff --git a/value_sensors/remote_sensor.lua b/value_sensors/remote_sensor.lua index b23bdb0..1c4dba2 100644 --- a/value_sensors/remote_sensor.lua +++ b/value_sensors/remote_sensor.lua @@ -1,8 +1,10 @@ require "template" RemoteSensor = {} -function RemoteSensor.new(name, line, caption, color) +function RemoteSensor.new(mod_name, name, line, caption, color) local sensor = ValueSensor.new("remote_sensor_" .. name) + + sensor["mod_name"] = mod_name sensor["line"] = line sensor["display_name"] = caption sensor["color"] = color @@ -16,10 +18,37 @@ function RemoteSensor.new(name, line, caption, color) end ValueSensor.register(sensor) + if not global.remote_sensors then + global.remote_sensors = {} + end + + -- store sensor data for global serialization + local sensor_data = { + mod_name = sensor.mod_name, + name = name, + line = sensor.line, + display_name = sensor.display_name, + color = sensor.color + } + global.remote_sensors[name] = sensor_data + print("Added Global Remote Sensors: " .. serpent.dump(global.remote_sensors)) end function RemoteSensor.get_by_name(name) return ValueSensor.get_by_name("remote_sensor_" .. name) end +function RemoteSensor.initialize() + print("Initializing Global Remote Sensors: " .. serpent.dump(global.remote_sensors)) + -- Initialize any remote sensors that were previously saved + if global.remote_sensors then + print("Global Remote Sensors: " .. serpent.dump(global.remote_sensors)) + for _, sensor in pairs(global.remote_sensors) do + if not RemoteSensor.get_by_name(sensor.name) then + RemoteSensor.new(sensor.mod_name, sensor.name, sensor.line, sensor.display_name, sensor.color) + end + end + end +end + return RemoteSensor From 12bd9869dc4b264012bdcf4dd986c072df157987 Mon Sep 17 00:00:00 2001 From: Afforess Date: Tue, 3 Nov 2015 23:29:12 -0500 Subject: [PATCH 2/3] Remove two print statements. --- value_sensors/remote_sensor.lua | 2 -- 1 file changed, 2 deletions(-) diff --git a/value_sensors/remote_sensor.lua b/value_sensors/remote_sensor.lua index 1c4dba2..89edb29 100644 --- a/value_sensors/remote_sensor.lua +++ b/value_sensors/remote_sensor.lua @@ -31,7 +31,6 @@ function RemoteSensor.new(mod_name, name, line, caption, color) color = sensor.color } global.remote_sensors[name] = sensor_data - print("Added Global Remote Sensors: " .. serpent.dump(global.remote_sensors)) end function RemoteSensor.get_by_name(name) @@ -39,7 +38,6 @@ function RemoteSensor.get_by_name(name) end function RemoteSensor.initialize() - print("Initializing Global Remote Sensors: " .. serpent.dump(global.remote_sensors)) -- Initialize any remote sensors that were previously saved if global.remote_sensors then print("Global Remote Sensors: " .. serpent.dump(global.remote_sensors)) From fe4d33ce82c288f3a41bf8e906f34316fe5a0d6b Mon Sep 17 00:00:00 2001 From: Afforess Date: Wed, 4 Nov 2015 21:37:06 -0500 Subject: [PATCH 3/3] Simplify removal of sensors from value_sensors table. Change create_remote_sensors function to use a table parameter Prefix caption / display_name with mod_name in brackets. Print error if game object is not available --- control.lua | 8 ++++-- evoGUI.lua | 15 ++++------ locale/en/locale.cfg | 5 ++-- remote.lua | 51 +++++++++++++++------------------ value_sensors/remote_sensor.lua | 30 +++++++------------ 5 files changed, 48 insertions(+), 61 deletions(-) diff --git a/control.lua b/control.lua index 98b66c4..cc59110 100644 --- a/control.lua +++ b/control.lua @@ -4,8 +4,12 @@ require "evoGUI" if not evogui then evogui = {} end function evogui.log(message) - for i, p in ipairs(game.players) do - p.print(message) + if game then + for i, p in ipairs(game.players) do + p.print(message) + end + else + error(serpent.dump(message, {compact = false, nocode = true, indent = ' '})) end end diff --git a/evoGUI.lua b/evoGUI.lua index d1782a3..59606dc 100644 --- a/evoGUI.lua +++ b/evoGUI.lua @@ -38,21 +38,16 @@ end -- Iterate through all value_sensors, if any are associated with a mod_name that -- has been removed, remove the sensor from the list of value_sensors. function evogui.validate_sensors(mod_changes) - local valid_sensors = {} - for sensor in evogui.value_sensors do + for i = #evogui.value_sensors, 1, -1 do + local sensor = evogui.value_sensors[i] if sensor.mod_name and mod_changes[sensor.mod_name] then - -- mod upgrade, keep sensor - if mod_changes[sensor.mod_name].new_version ~= nil then - valid_sensors[#valid_sensors + 1] = sensor - else - -- mod removed, remove sensor from ui + -- mod removed, remove sensor from ui + if mod_changes[sensor.mod_name].new_version == nil then evogui.hide_sensor(sensor) + table.remove(evogui.value_sensors, i) end - else - valid_sensors[#valid_sensors + 1] = sensor end end - evogui.value_sensors = valid_sensors end function evogui.hide_sensor(sensor) diff --git a/locale/en/locale.cfg b/locale/en/locale.cfg index a609aae..12f4337 100644 --- a/locale/en/locale.cfg +++ b/locale/en/locale.cfg @@ -79,8 +79,9 @@ err_needplayername=[EvoGUI] Need a player name! err_nosuchplayer=[EvoGUI] No such player: __1__! err_noplayerdata=[EvoGUI] No player data for __1__! -err_nomodname=[EvoGUI] Missing the mod name of the sensor! err_nosensorname=[EvoGUI] Missing a sensor name! +err_no_sensor_data=[EvoGUI] Missing remote sensor data! +err_sensor_missing_field=[EvoGUI] Remote sensor __1__ is missing a required field __2__! err_nosensortext=[EvoGUI] Missing sensor text for __1__! err_nosensorcaption=[EvoGUI] Missing caption text for __1__! -err_nosensorfound=[EvoGUI] No sensor was previously created matching the name __1__! Create a sensor first. +err_nosensorfound=[EvoGUI] No sensor matching the name __1__! Create a sensor first. diff --git a/remote.lua b/remote.lua index ecf10f9..c30270c 100644 --- a/remote.lua +++ b/remote.lua @@ -33,38 +33,33 @@ end -- -- Creates a sensor managed by a remote interface (another mod or script) --- mod_name: Name of the mod registering the sensor. Sensor will be removed if the mod is removed from the game. --- sensor_name: internal name of the sensor. Should be unique. --- sensor_text: Text to display in the active gui --- sensor_caption: Sensor setting name in the EvoGUI settings panel --- sensor_color: Font color of the text to display in the active gui, optional, may be nil --- example: remote.call("EvoGUI", "create_remote_sensor", "mymod_my_sensor_name", "Text: Lorem Ipsum", "[My Mod] Lorem Ipsum Text") -local function create_remote_sensor(mod_name, sensor_name, sensor_text, sensor_caption, sensor_color) - if not mod_name then - evogui.log({"err_nomodname"}) - return - end - - if not sensor_name then - evogui.log({"err_nosensorname"}) +-- sensor_data: a table with the following fields, +-- mod_name: Name of the mod registering the sensor. Sensor will be removed if the mod is removed from the game. +-- name: internal name of the sensor. Should be unique. +-- text: Text to display in the active gui +-- caption: Sensor setting name in the EvoGUI settings panel +-- color: Font color of the text to display in the active gui, optional, may be nil +-- +-- example: remote.call("EvoGUI", "create_remote_sensor", { "mod_name" = "my_mod", +-- "name" = "my_mod_my_sensor_name", +-- "text" = "Text: Lorem Ipsum", +-- "caption" = "[My Mod] Lorem Ipsum Text" }) +local function create_remote_sensor(sensor_data) + if not sensor_data then + evogui.log({"err_no_sensor_data"}) return end - if not sensor_text then - evogui.log({"err_nosensortext", sensor_name}) - return + for _, field in pairs({ "mod_name", "name", "text", "caption" }) do + if not sensor_data[field] then + evogui.log({"err_sensor_missing_field", serpent.dump(sensor_data, {compact = false, nocode = true, indent = ' '}), field}) + return + end end - if not sensor_caption then - evogui.log({"err_nosensorcaption", sensor_name}) - return - end - - local sensor = RemoteSensor.get_by_name(sensor_name) + local sensor = RemoteSensor.get_by_name(sensor_data.name) if not sensor then - RemoteSensor.new(mod_name, sensor_name, sensor_text, sensor_caption, sensor_color) - else - -- should anything happen here? + RemoteSensor.new(sensor_data) end end @@ -104,8 +99,8 @@ interface = { if err then evogui.log({"err_generic", "interface.rebuild", err}) end end, - create_remote_sensor = function(mod_name, sensor_name, sensor_text, sensor_caption, sensor_color) - local status, err = pcall(create_remote_sensor, mod_name, sensor_name, sensor_text, sensor_caption, sensor_color) + create_remote_sensor = function(sensor_data) + local status, err = pcall(create_remote_sensor, sensor_data) if err then evogui.log({"err_generic", "remote.create_remote_sensor", err}) end end, diff --git a/value_sensors/remote_sensor.lua b/value_sensors/remote_sensor.lua index 89edb29..f266808 100644 --- a/value_sensors/remote_sensor.lua +++ b/value_sensors/remote_sensor.lua @@ -1,13 +1,13 @@ require "template" RemoteSensor = {} -function RemoteSensor.new(mod_name, name, line, caption, color) - local sensor = ValueSensor.new("remote_sensor_" .. name) +function RemoteSensor.new(sensor_data) + local sensor = ValueSensor.new("remote_sensor_" .. sensor_data.name) - sensor["mod_name"] = mod_name - sensor["line"] = line - sensor["display_name"] = caption - sensor["color"] = color + sensor["mod_name"] = sensor_data.mod_name + sensor["line"] = sensor_data.text + sensor["display_name"] = "[" .. sensor_data.mod_name .. "]" .. sensor_data.caption + sensor["color"] = sensor_data.color function sensor:set_line(text) self.line = text @@ -21,16 +21,9 @@ function RemoteSensor.new(mod_name, name, line, caption, color) if not global.remote_sensors then global.remote_sensors = {} end - + -- store sensor data for global serialization - local sensor_data = { - mod_name = sensor.mod_name, - name = name, - line = sensor.line, - display_name = sensor.display_name, - color = sensor.color - } - global.remote_sensors[name] = sensor_data + global.remote_sensors[sensor_data.name] = sensor_data end function RemoteSensor.get_by_name(name) @@ -40,10 +33,9 @@ end function RemoteSensor.initialize() -- Initialize any remote sensors that were previously saved if global.remote_sensors then - print("Global Remote Sensors: " .. serpent.dump(global.remote_sensors)) - for _, sensor in pairs(global.remote_sensors) do - if not RemoteSensor.get_by_name(sensor.name) then - RemoteSensor.new(sensor.mod_name, sensor.name, sensor.line, sensor.display_name, sensor.color) + for _, sensor_data in pairs(global.remote_sensors) do + if not RemoteSensor.get_by_name(sensor_data.name) then + RemoteSensor.new(sensor_data) end end end