niston Posted September 19, 2020 Share Posted September 19, 2020 I would like to find out if some resource (say, water) is missing/in short supply across the settlement network.How would I go on about this? I found this in the WorkshopScript, but not sure what exactly to make of it: WorkshopParent.SetResourceData(ratings[WorkshopParent.WorkshopRatingMissingWater].resourceValue, self, missingWater) Looks kinda promising, but I didn't find any documentation about the SetResourceData function, and as far as I can tell it's not defined in WorkshopScript or WorkshopParentScript. Could I iterate over the workshop array and use something like GetResourceData(ratings[WorkshopParent........MissingWater].resourceValue, <objectrefWorkshopToCheck>) to read how much water is missing for each of the workshops? Hmm... Assuming that works, how could I check if the current <objectrefWorkshopToCheck> is indeed connected (by supply line) to the workshop my script is running from? Link to comment Share on other sites More sharing options...
SKKmods Posted September 19, 2020 Share Posted September 19, 2020 The missing workshop ratings are only updated once per game day during the daily update cycle so thay will not account for any build changes since the last run. To get up to date values just shadow the calculation avoiding long winded and bottlnecking calls to WorkshoppParentScript to resolve each actor value. This is what works for me: Int iTotalPopulation = ThisWorkshop.GetValue(pWorkshopRatingPopulation) as Int Int iRobotPopulation = ThisWorkshop.GetValue(pWorkshopRatingPopulationRobots) as Int ;dont need food or water Int iConsumers = iTotalPopulation - iRobotPopulation Int iFoodInWorkshop = ThisWorkshop.GetItemCount(pObjectTypeFood) ;Keyword Int IWaterInWorkshop = ThisWorkshop.GetItemCount(pObjectTypeWater) ;Keyword Int iFoodProduction = ThisWorkshop.GetValue(pFood) as int Int iWaterProduction = ThisWorkshop.GetValue(pWater) as int Int iMissingFood = iConsumers - (iFoodProduction + iFoodInWorkshop) ;flip for negative Int iMissingWater = iConsumers - (iWaterProduction + iWaterInWorkshop) ;flip for negative To check caravan connections you have to use workshop locations: Location MyLocation = (MyWorkshop as WorkshopScript).MyLocation ;Can be different to .GetCurrentLocation Location TargetLocation = (TargetWorkshop as WorkshopScript).MyLocation ;Can be different to .GetCurrentLocation Location[] LinkedLocations = MyLocation.GetAllLinkedLocations(pWorkshopCaravanKeyword) If (LinkedLocations.Find(TargetLocation) > -1) ; Found in linked location network ;do stuff Endif To get missing resources from the network, ya just iterate through all the targets updating the resources without worring about a specific target workshop: Location MyLocation = (MyWorkshop as WorkshopScript).MyLocation ;Can be different to .GetCurrentLocation Location[] LinkedLocations = MyLocation.GetAllLinkedLocations(pWorkshopCaravanKeyword) Int iIndex = 1 While (iIndex < LinkedLocations.Length) Int ThisWorkshopID = (pWorkshopParent as WorkshopParentScript).WorkshopLocations.Find(LinkedLocations[iIndex]) ;quest If (ThisWorkshopID > -1) ; location found WorkshopScript ThisWorkshop = (pWorkshopParent as WorkshopParentScript).GetWorkshop(ThisWorkshopID) If (iMissingFood > 0) ThisWorkshop.RemoveItem(pObjectTypeFood, iMissingFood, true, MyWorkshop) iMissingFood = iConsumers - (iFoodProduction + ThisWorkshop.GetItemCount(pObjectTypeFood)) ;flip for negative EndIf If (iMissingWater > 0) ThisWorkshop.RemoveItem(pObjectTypeFood, iMissingWater, true, MyWorkshop) iMissingWater = iConsumers - (iWaterProduction + ThisWorkshop.GetItemCount(pObjectTypeWater)) ;flip for negative EndIf EndIf iIndex +=1 EndWhile Link to comment Share on other sites More sharing options...
niston Posted September 19, 2020 Author Share Posted September 19, 2020 Smooth! Thanks SKK! One question: Does this work for unloaded workshops? For example, can I do CastleWorkshop.GetValue(pFood) when I'm in Sanctuary? My goal is to determine if the settlement network is lacking a certain resource, and if so, I'm going to release into the settlement network some of that resource from some local storage. In simpler words: Think water tower. If there is enough water around, it shall fill, from the settlement network, up to maxCapacity at up to maxFillRate Purified Water per day. If water is lacking, the tower shall release purified water from it's store into the local workshop, at up to maxSupplyRate per day, until the tower either runs dry or the water shortage is otherwise alleviated. I have this quite powerful, little, self-regulating swiss precision clock event scheduler I can use, so I thought of scheduling two daily checks at say 11:00pm and 11:00am. One, before the daily workshop update, to check for shortages and supply water if needed (and available in storage). The other, after the workshop update, to fill the tower with any excess water that may be around. Tho, on a second thought, I might get away with doing everything in one step at 11:00pm. If I can determine beforehand how much water is going to be missing (or will be in excess) when the next workshop update occurs, which seems possible if stock, population and production are known (can be retrieved using your code) for each workshop. Link to comment Share on other sites More sharing options...
SKKmods Posted September 20, 2020 Share Posted September 20, 2020 Yes totally work unloaded. The reason workshops manage their resource COUNTERS as actor values attached to themselves is that AVs on PERSISTENT objects (Workshops are persistent) can always be remote queried when unloaded. You are of course just querying data fields linked to a database index key (the ObjectReference). Thats how the WorkshopDailyUpdate resource production calculations can work from anywhere. Its also CAUSES the issue of workshop stats being incorrect as the actual non persistent RESOURCE objects need to be loaded when ResetWorkshop triggers to baseline the ActorValue counters on actual physical resource producers. The LinkedReference enumerators like GetWorkshopResourceObjects() and GetActorsLinkedToMe() will only resolve non persistent endpoints if they are loaded so they actually have a database index key (ObjectReference). And you cant force load endpoints (or the cells they live in) if you dont actually know about them in the first place. I did an article on this issue HERE. Link to comment Share on other sites More sharing options...
niston Posted September 20, 2020 Author Share Posted September 20, 2020 Informative article. Has me thinking about a fix for the incorrect stats mess. And I can see that you're a fellow 7 uGrids man. Link to comment Share on other sites More sharing options...
Zorkaz Posted September 20, 2020 Share Posted September 20, 2020 No modding advice here. Just being astounded that the supply system actually works. Link to comment Share on other sites More sharing options...
SKKmods Posted September 20, 2020 Share Posted September 20, 2020 Well monsieur nettoyer, I have killed stuff out to 25 uGrids as a challenge but that needed some serious tuning ... 7 uGrids is what I tend to play at just to ensure the world is live down my scope. Except my hostile workshops are not actually hostile until I get closer. Apparently "a trivial problem to fix" though ! ps No women, no kids, that's the rules. :wink: Link to comment Share on other sites More sharing options...
niston Posted September 20, 2020 Author Share Posted September 20, 2020 Yay! [09/20/2020 - 09:36:30PM] [CRP:WaterTowerScript < (A7035D58)>]: Supply Lines - Found (106) linked locations.... [09/20/2020 - 09:36:30PM] [CRP:WaterTowerScript < (A7035D58)>]: Forecast for Workshop (Index=0, Id=11): 0 Purified Water. [09/20/2020 - 09:36:30PM] [CRP:WaterTowerScript < (A7035D58)>]: Forecast for Workshop (Index=1, Id=93): 0 Purified Water. [09/20/2020 - 09:36:30PM] [CRP:WaterTowerScript < (A7035D58)>]: Forecast for Workshop (Index=2, Id=38): 0 Purified Water. [09/20/2020 - 09:36:30PM] [CRP:WaterTowerScript < (A7035D58)>]: Forecast for Workshop (Index=3, Id=47): -3 Purified Water. [09/20/2020 - 09:36:30PM] [CRP:WaterTowerScript < (A7035D58)>]: Forecast for Workshop (Index=4, Id=60): 0 Purified Water. ...... [09/20/2020 - 09:36:31PM] [CRP:WaterTowerScript < (A7035D58)>]: Forecast for settlement network: 133888 Purified Water. Link to comment Share on other sites More sharing options...
niston Posted September 20, 2020 Author Share Posted September 20, 2020 Re your actor problem: Why not slap the mustpersist keyword on them? Link to comment Share on other sites More sharing options...
SKKmods Posted September 20, 2020 Share Posted September 20, 2020 @niston because it could be any actor in any workshop anywhere = "unknown unknowns". (a) I can only slap a keyword on something I know about. (b) making all settlers persistent to manage is a significant system overhead as I found with my Combat Settlers mod which causes problems trying to share script time-slices with Sim Settlments, Pack Attack, Better locatrional damage, Zombie Walkers and any other highly deployed actor/script intensive applications. The summary being = ********************************************************************************************WARNING: THIS IS IMPORTANTScript sharding grabs an unfair share of papyrus processing time to get the job done. If you have other workshop/actor script intensive solutons like Sim Settlements or PANPC your experience will degrade as the script system will not have enough real time slices for everything. Slow down approaching workshops with all this stuff running. Teleporting to them is really bad, mmmkay ?******************************************************************************************** Link to comment Share on other sites More sharing options...
Recommended Posts