debugman18 Posted October 30, 2015 Share Posted October 30, 2015 (edited) Hoping a dev or an enlightened modder could make my life easier. I have this code:local function doextend()local basic_AddPrefabPostInit = assert( modenv.AddPrefabPostInit )local late_AddPrefabPostInit = nil local function AddPrefabPostInit(prefab, fn) if TheMod:IsRunning() then return basic_AddPrefabPostInit(prefab, fn) else if late_AddPrefabPostInit == nil then late_AddPrefabPostInit = assert( MakeLateAddPrefabPostInit() ) end return late_AddPrefabPostInit(prefab, fn) endend TheMod:EmbedHook("PrefabPostInit", AddPrefabPostInit)end which is part of Wicker made by simplex. The problem is that in DST, when creating the world, it isn't able to do anything with AddPrefabPostInit. Without exploring this in great detail, it seems somewhere along the line, post inits were broken during worldgen (or something). The issue shines here the most:TheMod:AddPrefabPostInit("world", function() logic_implication(IsDedicated(), IsServer(), "dedicated -> server") logic_equivalence(IsServer(), not IsClient(), "server <-> not client")end)If anybody has at least an explanation, or could steer me towards solving this problem, you'd make my life significantly easier (and push U&A one step closer towards DST compatibility!) It's preferable to crawling over every inch of relevant DST code. Edited October 30, 2015 by debugman18 Link to comment Share on other sites More sharing options...
Kzisor Posted October 30, 2015 Share Posted October 30, 2015 (edited) The list of available code in the world generation of DST has changed significantly. You should use modmain when you wanting to modify instances of items. World generation is specifically for world generation. For more information look at modutil.lua. Regards,Kzisor/Ysovuka Edited October 30, 2015 by Kzisor Link to comment Share on other sites More sharing options...
debugman18 Posted October 30, 2015 Author Share Posted October 30, 2015 (edited) The list of available code in the world generation of DST has changed significantly. You should use modmain when you wanting to modify instances of items. World generation is specifically for world generation. For more information look at modutil.lua. Regards,Kzisor/Ysovuka It's way more complicated than just using modmain instead of what's being done now. I mean, have you seen the code for Up and Away? You're basically suggesting I remove Wicker from Up and Away (which would require an incredible [read: improbable] amount of refactoring, to put it lightly) or refactor a sizable chunk of Wicker (which is just as awful, considering I had no part in its inception and creation.) Here's the entire code for assumptions.lua, just a piece of the puzzle that is Wicker: local Lambda = wickerrequire "paradigms.functional"local Logic = wickerrequire "lib.logic" local function NewLogicAssertion(operation, operation_name) local op_name = tostring(operation_name) return function(a, b, desc) if not operation(a, b) then return error("Assumption about "..tostring(desc).." logical "..op_name.." failed. ("..tostring(a)..", "..tostring(b)..")", 2) end endend local logic_equivalence = NewLogicAssertion(Logic.IfAndOnlyIf, "equivalence")local logic_implication = NewLogicAssertion(Logic.Implies, "implication") logic_equivalence(IsServer(), IsMasterSimulation(), "server <-> master simulation") -- This doesn't hold in the main menu.TheMod:AddPrefabPostInit("world", function() logic_implication(IsDedicated(), IsServer(), "dedicated -> server") logic_equivalence(IsServer(), not IsClient(), "server <-> not client")end) Edited October 30, 2015 by debugman18 Link to comment Share on other sites More sharing options...
Woodlegs Posted October 30, 2015 Share Posted October 30, 2015 PeterA He knows all, he sees all... O_O Link to comment Share on other sites More sharing options...
Kzisor Posted October 30, 2015 Share Posted October 30, 2015 @debugman18, I completely understand, it's the main reason I don't put my mods up on both games. Each game requires a separate code base written specifically for the engine they're running on. Link to comment Share on other sites More sharing options...
DarkXero Posted October 30, 2015 Share Posted October 30, 2015 Put this in modworldgenmainif postinitfns.PrefabPostInit == nil then postinitfns.PrefabPostInit = {}endHackPrefabPostInit = function(prefab, fn) if postinitfns.PrefabPostInit[prefab] == nil then postinitfns.PrefabPostInit[prefab] = {} end table.insert(postinitfns.PrefabPostInit[prefab], fn)endlocal AddPrefabPostInit = AddPrefabPostInit or HackPrefabPostInitAddPrefabPostInit("world", function(inst) inst.yourmom = "ishappy"end)and now it "just werks". Link to comment Share on other sites More sharing options...
debugman18 Posted October 30, 2015 Author Share Posted October 30, 2015 (edited) Put this in modworldgenmainif postinitfns.PrefabPostInit == nil then postinitfns.PrefabPostInit = {}endHackPrefabPostInit = function(prefab, fn) if postinitfns.PrefabPostInit[prefab] == nil then postinitfns.PrefabPostInit[prefab] = {} end table.insert(postinitfns.PrefabPostInit[prefab], fn)endlocal AddPrefabPostInit = AddPrefabPostInit or HackPrefabPostInitAddPrefabPostInit("world", function(inst) inst.yourmom = "ishappy"end)and now it "just werks". It's far from "just werking" but I see what you did there. With a little bit of tinkering I may be able to utilize it. Thanks for your help! Edited October 30, 2015 by debugman18 Link to comment Share on other sites More sharing options...
Developer PeterA Posted October 30, 2015 Developer Share Posted October 30, 2015 A change went in earlier this year to remove some functions from the mod environment during world gen that shouldn't be called, such as AddAction. For compatibility between code bases, I'd recommend doing something similar to what @DarkXero is suggesting (minus the yourmom references ). Link to comment Share on other sites More sharing options...
debugman18 Posted October 30, 2015 Author Share Posted October 30, 2015 (edited) A change went in earlier this year to remove some functions from the mod environment during world gen that shouldn't be called, such as AddAction. For compatibility between code bases, I'd recommend doing something similar to what @DarkXero is suggesting (minus the yourmom references ). I'm pretty rusty. Any ideas as to how I would go about running something like his code within the assumptions.lua file (it's a "module" type file within wicker)? I'm not sure doing modenv stuff in modworldgenmain and calling that from there would work. Or would it? I'm on lunch, so I don't have time right now to bang my head against it. Edit: If anybody awesome wants to explore the issue further, here's my log: [00:00:12]: Mod: UpAndAway (Up and Away (dev)) Error loading mod![string "../mods/UpAndAway/wicker/kernel_extensions/..."]:20: attempt to call method 'AddPrefabPostInit' (a nil value)LUA ERROR stack traceback: ../mods/UpAndAway/wicker/kernel_extensions/dst_abstraction/assumptions.lua(20,1) in function 'fn' ../mods/UpAndAway/wicker/init/kernel_components/loaders.lua(109,1) in function 'fn' ../mods/UpAndAway/lib/use.lua(109,1) in function 'basic_import' ../mods/UpAndAway/wicker/init/kernel_components/basic_importers.lua(35,1) in function 'prefixed_import' ../mods/UpAndAway/wicker/init/kernel_components/basic_importers.lua(80,1) in function 'pkgrequire' ../mods/UpAndAway/wicker/kernel_extensions/dst_abstraction.lua(27,1) in function 'fn' ../mods/UpAndAway/wicker/init/kernel_components/loaders.lua(109,1) in function 'fn' ../mods/UpAndAway/lib/use.lua(109,1) in function 'basic_import' ../mods/UpAndAway/wicker/init/kernel_components/basic_importers.lua(35,1) in function 'prefixed_import' ../mods/UpAndAway/wicker/init/kernel_components/basic_importers.lua(80,1) in function 'pkgrequire' ../mods/UpAndAway/wicker/kernel_extensions.lua(153,1) in function 'doextend'... ../mods/UpAndAway/wicker/init.lua(234,1) in function 'process_mod_environment' ../mods/UpAndAway/wicker/init.lua(257,1) =(tail call) ? ../mods/UpAndAway/lib/use.lua(109,1) in function 'use' ../mods/UpAndAway/modworldgenmain.lua(15,1) in main chunk =[C] in function 'xpcall' scripts/util.lua(560,1) in function 'RunInEnvironment' scripts/mods.lua(416,1) in function 'InitializeModMain' scripts/mods.lua(393,1) in function 'LoadMods' scripts/worldgen_main.lua(73,1) in main chunk Edited October 30, 2015 by debugman18 Link to comment Share on other sites More sharing options...
Kzisor Posted October 31, 2015 Share Posted October 31, 2015 @debugman18, this will make it not crash on world gen.local Lambda = wickerrequire "paradigms.functional"local Logic = wickerrequire "lib.logic"local function NewLogicAssertion(operation, operation_name) local op_name = tostring(operation_name) return function(a, b, desc) if not operation(a, b) then return error("Assumption about "..tostring(desc).." logical "..op_name.." failed. ("..tostring(a)..", "..tostring(b)..")", 2) end endendlocal logic_equivalence = NewLogicAssertion(Logic.IfAndOnlyIf, "equivalence")local logic_implication = NewLogicAssertion(Logic.Implies, "implication")logic_equivalence(IsServer(), IsMasterSimulation(), "server <-> master simulation")-- This doesn't hold in the main menu.-- This is currently crashing on worldgen. -debugif not ModManager.worldgen then TheMod:AddPrefabPostInit("world", function() logic_implication(IsDedicated(), IsServer(), "dedicated -> server") logic_equivalence(IsServer(), not IsClient(), "server <-> not client") end)end Link to comment Share on other sites More sharing options...
debugman18 Posted October 31, 2015 Author Share Posted October 31, 2015 @debugman18, this will make it not crash on world gen.local Lambda = wickerrequire "paradigms.functional"local Logic = wickerrequire "lib.logic"local function NewLogicAssertion(operation, operation_name) local op_name = tostring(operation_name) return function(a, b, desc) if not operation(a, b) then return error("Assumption about "..tostring(desc).." logical "..op_name.." failed. ("..tostring(a)..", "..tostring(b)..")", 2) end endendlocal logic_equivalence = NewLogicAssertion(Logic.IfAndOnlyIf, "equivalence")local logic_implication = NewLogicAssertion(Logic.Implies, "implication")logic_equivalence(IsServer(), IsMasterSimulation(), "server <-> master simulation")-- This doesn't hold in the main menu.-- This is currently crashing on worldgen. -debugif not ModManager.worldgen then TheMod:AddPrefabPostInit("world", function() logic_implication(IsDedicated(), IsServer(), "dedicated -> server") logic_equivalence(IsServer(), not IsClient(), "server <-> not client") end)end Appreciate the help, but I'm getting this issue:[00:00:16]: Mod: UpAndAway (Up and Away (dev)) Error loading mod![string "../mods/UpAndAway/wicker/api_extensions.lua"]:66: assertion failed!LUA ERROR stack traceback: =[C] in function 'assert' ../mods/UpAndAway/wicker/api_extensions.lua(66,1) in function 'doextend' ../mods/UpAndAway/wicker/api_extensions.lua(84,1) in function 'api_extender' ../mods/UpAndAway/wicker/init.lua(186,1) in function 'extend_self' ../mods/UpAndAway/wicker/init.lua(234,1) in function 'process_mod_environment' ../mods/UpAndAway/wicker/init.lua(257,1) =(tail call) ? ../mods/UpAndAway/lib/use.lua(109,1) in function 'use' ../mods/UpAndAway/modworldgenmain.lua(15,1) in main chunk =[C] in function 'xpcall' scripts/util.lua(560,1) in function 'RunInEnvironment' scripts/mods.lua(416,1) in function 'InitializeModMain' scripts/mods.lua(393,1) in function 'LoadMods' scripts/worldgen_main.lua(73,1) in main chunk Basically, Wicker is insisting that AddPrefabPostInit exists at any given time. Normally it extends that function of the API, but whatever was changed with worldgen and the modenv broke it. I'm going to follow the log and see *why* it's insisting, but I doubt it's because of whimsy. Link to comment Share on other sites More sharing options...
Kzisor Posted October 31, 2015 Share Posted October 31, 2015 @debugman18, you will need to modify wicker whenever DST is the game engine to not rely on AddPrefabPostInit during world generation. Link to comment Share on other sites More sharing options...
DarkXero Posted October 31, 2015 Share Posted October 31, 2015 if postinitfns.PrefabPostInit == nil then postinitfns.PrefabPostInit = {}endHackPrefabPostInit = function(prefab, fn) if postinitfns.PrefabPostInit[prefab] == nil then postinitfns.PrefabPostInit[prefab] = {} end table.insert(postinitfns.PrefabPostInit[prefab], fn)endGLOBAL.getfenv(1).AddPrefabPostInit = AddPrefabPostInit or HackPrefabPostInitAddPrefabPostInit("world", function(inst) inst.test = "test"end)Inject it back into the mod env? Try this. Link to comment Share on other sites More sharing options...
debugman18 Posted October 31, 2015 Author Share Posted October 31, 2015 (edited) if postinitfns.PrefabPostInit == nil then postinitfns.PrefabPostInit = {}endHackPrefabPostInit = function(prefab, fn) if postinitfns.PrefabPostInit[prefab] == nil then postinitfns.PrefabPostInit[prefab] = {} end table.insert(postinitfns.PrefabPostInit[prefab], fn)endGLOBAL.getfenv(1).AddPrefabPostInit = AddPrefabPostInit or HackPrefabPostInitAddPrefabPostInit("world", function(inst) inst.test = "test"end)Inject it back into the mod env? Try this. How should I be calling the mod environment from assumptions.lua? That's the file which uses AddPrefabPostInit. That aside, though, it seems there are much deeper issues here. Wicker apparently initializes during worldgen, for reasons I've yet to determine, and doing it any other way breaks balance tuning. (We use tunings file and call them through a CFG module type thing.) And thanks again. Hopefully a solution can be found, because the idea of either refactoring Wicker or removing it altogether is really discouraging to me. Edited October 31, 2015 by debugman18 Link to comment Share on other sites More sharing options...
DarkXero Posted October 31, 2015 Share Posted October 31, 2015 How should I be calling the mod environment from assumptions.lua? If you doGLOBAL.getfenv(1).AddPrefabPostInit = AddPrefabPostInit or HackPrefabPostInitthen when assumptions.lua imports the mod environment it imports the function. If it doesn't import it, then the AddPrefabPostInit nil error should have happened before all of this, right? You can doGLOBAL.getfenv(1).AddPrefabPostInit = AddPrefabPostInit or HackPrefabPostInitGLOBAL._UNA = {}GLOBAL._UNA.AddPrefabPostInit = AddPrefabPostInitand then access globally AddPrefabPostInit via _UNA.AddPrefabPostInit (_UNA so you don't have the PostInit function as a global by itself, you can put other mod functions there too). Link to comment Share on other sites More sharing options...
debugman18 Posted October 31, 2015 Author Share Posted October 31, 2015 (edited) If you doGLOBAL.getfenv(1).AddPrefabPostInit = AddPrefabPostInit or HackPrefabPostInitthen when assumptions.lua imports the mod environment it imports the function. If it doesn't import it, then the AddPrefabPostInit nil error should have happened before all of this, right? You can doGLOBAL.getfenv(1).AddPrefabPostInit = AddPrefabPostInit or HackPrefabPostInitGLOBAL._UNA = {}GLOBAL._UNA.AddPrefabPostInit = AddPrefabPostInitand then access globally AddPrefabPostInit via _UNA.AddPrefabPostInit (_UNA so you don't have the PostInit function as a global by itself, you can put other mod functions there too). Well, things are so broke. [string "../mods/UpAndAway/wicker/kernel_extensions/..."]:19: variable '_UNA' is not declared It's also relevant that Wicker initializes during worldgen, in modworldgenmain:TheMod = use 'start_wicker'Edit: Hang on, I think there are some typo shenanigans going on... Edit 2: Nope, no typo shenanigans. It's just not running your code. Modmain, modworldgenmain, neither is running it. What in the world... Edit 3: Okay, it was Wicker shenanigans. That bit is solved. Alas, it reveals significant other issues. More on that soon. Thanks! Edited October 31, 2015 by debugman18 Link to comment Share on other sites More sharing options...
debugman18 Posted October 31, 2015 Author Share Posted October 31, 2015 (edited) Alright, so there's a new problem. I'll try and tackle it. It's very similar to the other problem, so...[string "../mods/UpAndAway/code/map/levels/upandaway..."]:99: attempt to call method 'GetCurrentMode' (a nil value)Okay, so apparently that function was removed in DST. I wonder if the caves testing branch reimplemented it? Edit: So many things are broken. So many things to fix. So many things I can actually test now! Edited October 31, 2015 by debugman18 Link to comment Share on other sites More sharing options...
DarkXero Posted November 1, 2015 Share Posted November 1, 2015 There aren't modes now, it's all servers with presets.You can pretty much replace all the GetCurrentMode with "survival". But I imagine the survival, adventures and caves distinction was beanstalk related. Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now