Surilindur Posted March 19, 2015 Share Posted March 19, 2015 I was wondering if it is possible to define a reference to a base object in an external file, an .ini file, for example, that only contains text. The idea would be to allow the user to define a base object to copy stats and mesh paths from to another object using some OBSE functions. The stats and other things will only be copied once when a savegame is loaded. I have tried something like the following: Create an .ini file with the following line: set ExampleQuest.BaseHelmet to XWhere I have tried to replace the X with both FormIDs (the ones like 00000ABC) and EditorIDs (like HelmetMadeOfCheese). The quest has a script that runs the batch script (the .ini) and it has something like the following in it: ScriptName ExampleQuestScript ref BaseHelmet Begin GameMode If GetGameLoaded RunBatchScript "Data\Example.ini" EndIf Call ExampleFnChangeThings BaseHelmet EndIt now runs the function every time the quest is updated, as I am only testing it. Also, the GetGameLoaded section will be expanded a lot and moved to a different function. Perhaps combined with the stat and other changing function. But at least the idea can be seen... The function looks a bit like that: ScriptName ExampleFnChangeThings ref BaseHelmet Begin Function { BaseHelmet } CopyMaleBipedPath BaseHelmet TargetHelmet EndWhere TargetHelmet is a base record or object... the ones created in the Construction Set. For some reason, I cannot get the 'external' base record definition to work. It works if I set the BaseHelmet in the quest script, for example. Like that: set BaseHelmet to ElvenHelmetI would like to make it possible for the user to define the base objects to copy mesh paths and stats from to a new set of armour without editing the actual plugin. But is it impossible? Link to comment Share on other sites More sharing options...
Legotrash Posted March 24, 2015 Share Posted March 24, 2015 For some reason I think so but the truth is I don't know.I made a quick test but couldn't make it happen. Could you update this thread when/if you'll figure things out? I might need to do something similar in the future. Link to comment Share on other sites More sharing options...
Surilindur Posted March 29, 2015 Author Share Posted March 29, 2015 Yes! I managed to make it work last night. The solution was to use the StringToRef command of Pluggy (the OBSE plugin). Also, this thread here - and especially the first suggestion by QQuix - was helpful. So both OBSE and Pluggy are required for this thing to work. The way I managed to set it up was about this: Create an .ini file with the following in it: ; Print DebugPrint? set QuestName.Debug to 1 ; Define the item (using FormID) set QuestName.FormIDString to sv_Construct "00036343"The item must to be defined using its FormID. That one in the example is glass cuirass, but it does not really matter what the item or something else is. That depends only on what is done with it once it has been successfully turned into a ref. I think. The .ini file can then be 'read' by a quest script, for example. The quest script (attached to a quest with EditorID of 'QuestName') could be something like that: ScriptName QuestNameScript float fQuestDelayTime ; Quest update interval short Debug ; Print DebugPrint? String_var FormIDString ; FormID as OBSE string Long FormIDPluggyThing ; FormID as Pluggy string or something else 'pluggy' Ref ItemRef ; The 'ready-to-use' reference Begin GameMode If ( GetGameLoaded ) If FileExists "Data\NameOfTheINI.ini" RunBatchScript "Data\NameOfTheINI.ini" Else MessageBox "Could not find NameOfTheINI.ini in Data folder!" EndIf If Debug == 0 SetDebugMode 0 Else SetDebugMode 1 EndIf ; Create the Pluggy string thingy set FormIDPluggyThing to CreateString -1 0 1 1 ; Make the OBSE string a Pluggy string so that it can be use by StringToRef SetString FormIDPluggyThing $FormIDString ; Use StringToRef on the Pluggy string thingy to make it a Ref set ItemRef to StringToRef FormIDPluggyThing ; Print the name of the item in the ref to console for debug purposes DebugPrint, "QuestName: ItemRef set to %n", "ItemRef" EndIf EndSo that sets ItemRef to the item defined in the .ini file (with its FormID) once when the game is loaded. That is not exactly the way I used it, but it should be a basic example from which to get the idea and adapt it to whatever purpose you want to use it for. Hopefully that helps a little. Now I can try to finish my little project and release it - if I can get the rest of it to work. :) Link to comment Share on other sites More sharing options...
Legotrash Posted March 30, 2015 Share Posted March 30, 2015 Thanks for the update!Aw, I wish we could avoid the pluggy...Some people have said that it's a bit buggy but maybe I remember wrongly... (or it was but got fixed?) Oh well, better than nothing! I saw your mod released, well done! :)By the way, sorry for the late reply. Link to comment Share on other sites More sharing options...
Surilindur Posted March 31, 2015 Author Share Posted March 31, 2015 You are welcome. And thank you. I hope it would not be too buggy. It has some nice features. But I think it might also be possible define the ref using an OBSE function, although it will likely work in a different way. The thread I linked in the solution contained some kind of an example it by QQuix. Perhaps it could be used instead of the Pluggy function? I have not yet tested it to see if it is more complicated or, who knows, easier to use. Link to comment Share on other sites More sharing options...
forli Posted April 1, 2015 Share Posted April 1, 2015 (edited) QQuix gave you a better function: GetFormFromMod. It allow you to obtain a ref from a string, but it's better than StringToRef. Why? Because StringToRef doesn't check the mod. What you define in the string depends on the load order.If the player change load order, StringToRef doesn't return anymore the ref you want. EXAMPLE: split the string "00036343", into "00" and "036343".The first 2 chars "00" means the reference is in the first mod in the load order (usually "Oblivion.esm" or "Nehrim.esm").The other chars "036343" define the reference.So StringToRef with that string check the reference "036343" in "Oblivion.esm". But what if you want to check a reference in some other mod?You need to find the position in the load order and replace the first 2 digits. If you add, remove or sort your mods you need to repeat this for every string ==> BAD SOLUTION. GetFormFromMod instead check the given mod name, so it doesn't depends on the load order.It will find the mod in the load order automatically when you call it. It works like this (some examples): Let refVar1 := GetFormFromMod "ModWhereTheRefIs.esp", "05A06B" Let refVar2 := GetFormFromMod "AnotherModWhereTheRefIs.esm", $someFormInSomeStringVar Let refVar3 := GetFormFromMod $someModNameInSomeStringVar, "A07C36" Let refVar4 := GetFormFromMod $someModNameInSomeStringVar, $someFormInSomeStringVarSo you don't need Pluggy, you don't need to create a complex code to create and convert the string, you can forget about the load order and it works! Edited April 1, 2015 by forli Link to comment Share on other sites More sharing options...
Legotrash Posted April 1, 2015 Share Posted April 1, 2015 PhilippePetain, in my case, just the OBSE way for it should do the trick. I don't know for your mod but now that forli's here you'll have all the help you need to pick the best for you. :) Thanks forli! This will probably be useful for me too. :) Link to comment Share on other sites More sharing options...
Surilindur Posted April 2, 2015 Author Share Posted April 2, 2015 Thank you, forli. That seems simple. Perhaps I could use it instead of StringToRef. But then the user will need to enter the name of the mod in the .ini file, as well. And that also means more code. Unless I can make it cycle through pairs of mod name strings and FormID strings. Argh. Wasted five hours yesterday trying to refine the Pluggy method. :( Still, I thank you. That method shoul be easier. :) Link to comment Share on other sites More sharing options...
forli Posted April 2, 2015 Share Posted April 2, 2015 Cycling many fields, and even multiple "entries" is simple:Declare all variables you need in a quest (in "yourQuest" declare "ModName" and "FormIDString") and declare an array.Initialize an array before reading the ini.Create a new function (functionRead), which will do something like this: scn functionRead Ref someRefVar Begin Function {} Let someRefVar := GetFormFromMod $yourQuest.ModName, $yourQuest.FormIDString If ( someRefVar ) ;the reference exists ar_Append yourQuest.yourArray, someRefVar EndIf EndCreate a quest (or take a quest you only use to run some global script) and enable "allow repeat stages".In this quest (yourQuest) put a new stage. Assume it's stage 10 but you can use any stage you want.In the stage result script put a single line: "Call functionRead"Now in your ini, fill all fields (in this case: yourQuest.ModName and yourQuest.FormID), followed by "SetStage yourQuest 10"The stage will fire and so the result script, which call the function which get the reference and store it somewhere.You can put fill the fields multiple times, each time followed by "SetStage yourQuest 10". They will be processed one by one, in the given order. Now you have all your references in the array. Link to comment Share on other sites More sharing options...
Surilindur Posted April 3, 2015 Author Share Posted April 3, 2015 Oops. It would seem that I forgot to thank you for the last post, forli. :) That is incredibly simple and incredibly useful. Now I can also update my other mod to use that method. And make it possible to add new faction rank requirements for even mod-added factions (and perhaps also for player's stats and such). Maybe I should have asked about these things months ago... a lot of things might have been easier. Now I can also see if a certain tiny project of mine I had to abandon earlier is possible with this new method. And then I need to see if I can somehow make it work... hmm. Perhaps some day. Thank you. Link to comment Share on other sites More sharing options...
Recommended Posts