Zackreaver Posted March 25, 2015 Share Posted March 25, 2015 So in combination with my characters ability to predict hound attacks, I want to have him also capable of predicting the attack of Deerclops and brethren. However, the basehassler.lua doesn't have a public function I can use to get the _timetoattack that I would need. I know there's still a way I can get this information cleanly without having to edit basehassler, but I can't put my finger on what I need to do. I usually test script in Console before I add it to scripts, but I'm not sure how I could check here. At an rate, I'm essentially trying to get access to the private member variables of basehassler to use in a giant prediction perk for my character. Link to comment Share on other sites More sharing options...
ryouryou Posted March 25, 2015 Share Posted March 25, 2015 I thought that they did hear the Deerclops coming, emoting something like "That sounds big." Is that not currently happening in RoG test? Or am I even remembering it right that it happened at all?OH WELL, if it doesn't happen, it certainly should be able to. Link to comment Share on other sites More sharing options...
applebottom Posted March 25, 2015 Share Posted March 25, 2015 I thought that they did hear the Deerclops coming, emoting something like "That sounds big." It does. And I remember Wigfrid saying "A worthy foe approaches" with the Dragonfly too. So there should be something for the other giants. Maybe one of the pro modders can come here and give some help.... Link to comment Share on other sites More sharing options...
rezecib Posted March 25, 2015 Share Posted March 25, 2015 @Zackreaver, There's no good way to do it. It's one of a number of components that are currently pretty unmoddable, like weather and clock. We'll just have to wait for PeterA to do a pass on them to make them mod-friendly. Link to comment Share on other sites More sharing options...
DarkXero Posted March 26, 2015 Share Posted March 26, 2015 If you really, really, REALLY, REALLY, AND SUPER REALLY.And really, really, I say really.Want to use that. AddComponentPostInit("basehassler", function(self) local old = self.OnUpdate local _counter = 120 function self:OnUpdate(dt) old(self, dt) _counter = _counter - dt if _counter < 0 then dont, seriously = GLOBAL.debug.getupvalue(old, 1) for k, v in pairs(GLOBAL.AllPlayers) do if seriously then v:PushEvent("plsno", {timeleft = seriously}) end end _counter = 120 end endend)AddPlayerPostInit(function(inst) inst:ListenForEvent("plsno", function(inst, data) local daysleft = data.timeleft / 480 inst.components.talker:Say("Please, dont do this, but Clops comes in "..daysleft.." days") end)end) Here I give an example. An abomination. When the dormant state stops, the timetoattack clock will tick and basehassler will update.When timetoattack reaches 0, the deerclops growls will start. Use with caution. Link to comment Share on other sites More sharing options...
rezecib Posted March 26, 2015 Share Posted March 26, 2015 Use with caution. Thus spake Prometheus... Dose function and event names, doe. 10/10 Link to comment Share on other sites More sharing options...
Developer bizziboi Posted March 26, 2015 Developer Share Posted March 26, 2015 Yep, debug.getupvalue will get you to a local. As @DarkXero stated, It's inadvisable - its very likely to break and would be highly incompatible with other mods if they chose to override things that are properly exposed. Link to comment Share on other sites More sharing options...
Zackreaver Posted March 26, 2015 Author Share Posted March 26, 2015 (edited) @DarkXero, Well that's fine, it's not really high priority and I could gladly wait for it to become more moddable, I mostly want to figure out what resource and methods I have available. But I have once particular question. Are you trying to portray some kind of message to me? As if I'm about to open a pandora's box? Either way, I can't help but laugh when looking at the names of things. Yep, debug.getupvalue will get you to a local. As @DarkXero stated, It's inadvisable - its very likely to break and would be highly incompatible with other mods if they chose to override things that are properly exposed. Mostly interested in the learning experience here, are you saying that I shouldn't CHANGE any of the local values here? or is it just dangerous to DO ANYTHING with the local values here? Because I essentially only want VIEW the information without making adjustments. I'll tear something apart all the way to binary if I have too, I want to know as much as I can with the tools I'm using. Especially so I can know WHY something would prove problematic. Edit: I think I managed to figure out the issue's that would come up (Albeit I opened pandora's box and destroyed an entire dimension, nothing major obviously), I'll probably just end up waiting until it becomes more moddable, such as when it gets a function similar to hounded:GetTimeToAttack() which simply hands me the variable I'm looking for, as opposed to a method that's almost as unsafe as directly changing basehassler.lua itself. Edit 2: My curiousity has peaked, what exactly is GLOBAL.debug.getupvalue doing? Because through my test code I have a theory, so let me know if I got this right. I decided based off of your example to make a different change.AddComponentPostInit("basehassler", function(self) local old = self.GetDebugString function self:GetDebugString(debugstr) if debugstr == "test1" then return GLOBAL.debug.getupvalue(old, 1) end if debugstr == "test2" then return GLOBAL.debug.getupvalue(old, 2) end if debugstr == "test3" then return GLOBAL.debug.getupvalue(old, 3) end if debugstr == "test4" then return GLOBAL.debug.getupvalue(old, 4) end if debugstr == "test5" then return GLOBAL.debug.getupvalue(old, 5) end if debugstr == "test6" then return GLOBAL.debug.getupvalue(old, 6) end if debugstr == "test7" then return GLOBAL.debug.getupvalue(old, 7) end return old() --This didn't work, oh well no ones using it. endend)Using this I could test out your example in console by doingPrint(TheWorld.components.basehassler:GetDebugString("test1")And I would get _timetoattack 1589.959435... blah blah the number I need I could also do test 2-4, with those I got_warning_activehassler_storedhasslerThen test5 came up nil. SO to make sense of things I looked at the function self:GetDebugString() that I made changes toI noticed that the local variables that got used in that function, were used in the order 1. _timetoattack2. _warning3. _activehassler4. _storedhassler So I theorize that GLOBAL.debug.getupvalue(old, #) gives me the #th variable that was used in that function, I went back to OnUpdate and noticed that the first variable that ever gets used is_timetoattack Which I bet that if I were to have changed GLOBAL.debug.getupvalue(old, 1) to GLOBAL.debug.getupvalue(old, 2) in your example DarkXero, I would get _activehassler instead since that is the second used variable in that function, with 3 being _warning and etc...Am I on the right track teach? So basically your warnings are basically trying to inform me that if I use code utilizing this method, if these functions ever get changed and move the order of their variables around, then my code will break immediately. Which makes absolute sense in this whole regard of how debug.getupvalue() appears to work. Now theories aside, what is debug.getupvalue doing? and furthermore, what type of variable is my print() showing me? and lastly, what am I capable of doing with what I'm getting? Edit 3: Also as a side question, the old basehassler:GetDebugString() normally returns a string after giving it no arguements so I wanted to see if I could make GetDebugString do what it normally does if I don't put in a string, but it gives me an error saying self is nil. What did I do wrong at the end there, how could I fix it? Again, learning experience so I can understand how to use AddComponentPostInit better. Edit 4: This thing where we store the old function before we replace it with a new one that references the old one so that it still functions like the old one on top of the new one. Is there a name for it? A terminology? Cause calling it a "That thing where we store the old function before we replace it with a new one that references the old one so that it still functions like the old one while also doing what we want in the new one but done in a way so that other mods don't conflict because they can all do this exact thing infinitely because the new one then BECOMES the old one which then newer ones do the same thing treating this one like the old one but it's actually a modified version of the old one which might have also been modded by other ones as well" is a bit of a mouthful. If it doesn't have a name, then I shall abbreviate it to Ttwwstofbwriwanotrtoostisfltoowadwwwitnobdiawstomdcbtcadtetibtnotbtoowtnodtstttoltoobiaamvotoowmhabmbooaw for short. Edit 5: Wait did I post this in general discussion? I thought I posted this in Mods and Tools? What is this madness? Edited March 26, 2015 by Zackreaver Link to comment Share on other sites More sharing options...
DarkXero Posted March 26, 2015 Share Posted March 26, 2015 You can combat the movement of upvalues inside a function.debug = GLOBAL.debuglocal t = debug.getinfo(func)local name, value = 0, 0for i = 1, t.nups, 1 do name, value = debug.getupvalue(func, i) if name == "_timetoattack" then break end value = nilendif value == nil then -- nothing foundelse -- _timetoattack upvalueendBut you shouldn't be combatting a function: debugging is for what the name says, debugging. Upvalues: http://www.lua.org/pil/27.3.3.html Lua 5.1 library (debug): http://www.lua.org/manual/5.1/manual.html#5.9This is the one for Klei. You can print this one if in modmain you do:for k, v in pairs(GLOBAL.debug) do print(k, v)end Lua versions here: http://www.lua.org/versions.html And:-- Your old didn't work because you havefunction self:GetDebugString()-- that equates intofunction self.GetDebugString(self)-- so, the correct way isreturn old(self) Link to comment Share on other sites More sharing options...
Zackreaver Posted March 26, 2015 Author Share Posted March 26, 2015 (edited) @DarkXero,let me just say that I envy your ability to break everything down so nice and tidy. As you can clearly see I have a major issue with trying to keep things short and sweet. But you shouldn't be combatting a function: debugging is for what the name says, debugging.I get what your saying, I don't intend to have my code running with a paper mache foundation. I'll just use whatever I can with caution comments to erase sections that go out of date and correct it later when better code becomes available. But if I can manage to get something working and little damage is caused to everything else, then I'll do it for as long as it's possible. Edit: Okay I finally have it all figured out, the funny thing is I'm not even gonna use this code yet anyway since it's for a separate item I'm gonna make down the line so by the time I actually finish it hassler might get an update. However, the knowledge of things I'm capable of doing is always the most valuable thing here. I feel I understand LUA a little bit better everytime you two come to help me. Edited March 26, 2015 by Zackreaver 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