Page 1 of 1
How do I figure out what "type" factorio object is?
Posted: Wed May 31, 2017 3:18 am
by credomane
I need to know if a table passed to a function of mine is a LuaPlayer, LuaGui, LuiGuiElement, or some other Factorio "object".
Simply checking for elements that don't exist works for any other table in lua but the ones representing Factorio "objects" FORCE an error even if I use pcall in an attempt to trap the error!
For example
Code: Select all
--assume tbl is a LuaPlayer object
if not tbl.childen then
--This is not a LuaGui or LuaGuiElement
if tbl.gui then
--This is a LuaPlayer; return the Player's LuaGui
return tbl.gui
else
--Not a LuaPlayer either. What is this thing?
return nil
end
else
--This is a LuaGui or LuaGuiElement; no correction needed
return tbl
end
Instead of reaching the "This is a LuaPlayer" branch Factorio throws the error "LuaPlayer does not contain the key children".
A normal table doesn't throw this error and has unset keys "set" to nil as expected.
I expected
reading unset keys on a factorio object to return nil just like any other Lua table while attempting to
set a non-existent key on a factorio object to throw the "LuaPlayer does not contain the key children".
Is there any way to work around this problem with Factorio objects? It is really putting a damper on my plans.

Re: How do I figure out what "type" factorio object is?
Posted: Wed May 31, 2017 3:59 am
by Rseding91
Pass the type with the object. You know at every call site what each object type is so just pass that along.
Re: How do I figure out what "type" factorio object is?
Posted: Wed May 31, 2017 4:16 am
by credomane
I'm working on a GUI lib for my addons that I plan to eventually turn into PR against stdlib.
I found a super hacky way around it by abusing the new help function on every factorio object that I just discovered. Now that I have a "properly" working proof-of-concept I really want this function in the modding api! Filing a request shortly.
Code: Select all
function table_contains(tbl, query)
return string.contains(tbl.help(), query) --provided by stdlib
end
-- Is this a LuaGui or LuaGuiElement?
if not table_contains(element, "LuaGui") then
--Were we given a LuaPlayer directly?
if not table_contains(element, "LuaPlayer") then
--Abort, abort, abort! What is this thing!?
return nil
end
--Use the player's root gui element
element = element.gui
end
return element
Re: How do I figure out what "type" factorio object is?
Posted: Wed May 31, 2017 4:22 am
by Rseding91
credomane wrote:I'm working on a GUI lib for my addons that I plan to eventually turn into PR against stdlib.
I found a super hacky way around it by abusing the new help function on every factorio object that I just discovered. Now that I have a "properly" working proof-of-concept I really want this function in the modding api! Filing a request shortly.
Code: Select all
function table_contains(tbl, query)
return string.contains(tbl.help(), query) --provided by stdlib
end
-- Is this a LuaGui or LuaGuiElement?
if not table_contains(element, "LuaGui") then
--Were we given a LuaPlayer directly?
if not table_contains(element, "LuaPlayer") then
--Abort, abort, abort! What is this thing!?
return nil
end
--Use the player's root gui element
element = element.gui
end
return element
That's going to be *incredibly* slow performance wise. Don't do that...
Re: How do I figure out what "type" factorio object is?
Posted: Wed May 31, 2017 4:29 am
by credomane
Rseding91 wrote:That's going to be *incredibly* slow performance wise. Don't do that...
I know but it was the only way to make my function "smart" in the desired fashion.
Hopefully the Modding API Request I'm working on will make sense why I did it the way I did.
Re: How do I figure out what "type" factorio object is?
Posted: Wed May 31, 2017 6:15 am
by credomane
And I just caught my mistake with pcall that I spent literally hours pacing the house trying to figure out. Forgot the anonymous "wrapper" function. No wonder the error was "escaping" pcall. The error was actually thrown before pcall even got called. Doh! Now I can finally go to bed and actually sleep.
This doesn't work so well and lead to my horrid hack:
Code: Select all
pcall(contains(element, "children"))
The correctly working snippet:
Code: Select all
--Workaround for Factorio throwing errors when accessing non-existent properties on Factorio Objects.
function contains(tbl, query)
if tbl[query] ~= nil then
return true
end
return nil
end
-- Is this a LuaGui or LuaGuiElement?
if not pcall(function() contains(element, "children") end) then
--Were we given a LuaPlayer directly?
if not pcall(function() contains(element, "gui") end) then
--Abort, abort, abort! What is this thing!?
return nil
end
--Use the player's root gui element
element = element.gui
end
Re: How do I figure out what "type" factorio object is?
Posted: Wed May 31, 2017 6:22 am
by Rseding91
Again, why can't you just pass the type of the object into the function you're using?