FiftyTifty Posted May 8, 2018 Share Posted May 8, 2018 I've made this fairly ambitious mod, that searches 500 units around the player, finds any items that have been dropped, and replaces them with statics. I've got the bulk of the work done, and it works just fine. Only problem is that I can't seem to delete the original items. One or two items are removed, but the rest just stay put. Here's the big ass function: Function ConvertItemsIntoStatics(bool bMakeStatic) bIterating = true int iFormListIndex = 0 ObjectReference[] objrefarrayToDelete Debug.MessageBox("Converting") While iFormListIndex < iNestedFormlistCount FormList formlistSourceCurrent = AAAFyTy_MasterFormList_Source.GetAt(iFormListIndex) as FormList FormList formlistDestCurrent = AAAFyTy_MasterFormList_Dest.GetAt(iFormListIndex) as FormList ObjectReference[] objrefarrayFoundItems if bMakeStatic == true objrefarrayFoundItems = PlayerRef.FindAllReferencesOfType(formlistSourceCurrent, iDistance) Debug.MessageBox("Looking for Items") else objrefarrayFoundItems = PlayerRef.FindAllReferencesOfType(formlistDestCurrent, iDistance) Debug.MessageBox("Looking for Statics") Endif int iFoundItemsCount = objrefarrayFoundItems.Length int iFoundItemIndex = 0 if iFoundItemsCount > 0 Debug.MessageBox("Found Items") While iFoundItemIndex < iFoundItemsCount ObjectReference objrefFoundItem = objrefarrayFoundItems[iFoundItemIndex] as ObjectReference int iBaseObjectIndex float fPosX = objrefFoundItem.GetPositionX() float fPosY = objrefFoundItem.GetPositionY() float fPosZ = objrefFoundItem.GetPositionZ() float fRotX = objrefFoundItem.GetAngleX() float fRotY = objrefFoundItem.GetAngleY() float fRotZ = objrefFoundItem.GetAngleZ() if bMakeStatic == true Debug.MessageBox("Making into static") iBaseObjectIndex = formlistSourceCurrent.Find(objrefFoundItem.GetBaseObject()) ;objrefFoundItem.Disable() ;objrefFoundItem.DeleteWhenAble() objrefarrayToDelete.Add(objrefFoundItem) ObjectReference objrefNewStatic = PlayerRef.PlaceAtMe(formlistDestCurrent.GetAt(iBaseObjectIndex), 1, false, false, false) objrefNewStatic.SetAngle(fRotX, fRotY, fRotZ) objRefNewStatic.SetPosition(fPosX, fPosY, fPosZ) else Debug.MessageBox("Making into items") iBaseObjectIndex = formlistDestCurrent.Find(objrefFoundItem.GetBaseObject()) ;objrefFoundItem.Disable() ;objrefFoundItem.DeleteWhenAble() objrefarrayToDelete.Add(objrefFoundItem) ObjectReference objrefNewItem = PlayerRef.PlaceAtMe(formlistSourceCurrent.GetAt(iBaseObjectIndex), 1, false, false, false) objrefNewItem.SetMotionType(objrefFoundItem.Motion_Keyframed) objrefNewItem.SetAngle(fRotX, fRotY, fRotZ) objrefNewItem.SetPosition(fPosX, fPosY, fPosZ) endif iFoundItemIndex += 1 Debug.MessageBox("Increasing Found Item Index") EndWhile EndIf iFormListIndex += 1 Debug.MessageBox("Increasing Form List Index") EndWhile While objrefarrayToDelete.Length > 0 ObjectReference objrefToDelete = objrefarrayToDelete[objrefarrayToDelete.Length - 1] as ObjectReference objrefarrayToDelete.RemoveLast() objrefToDelete.Disable() objrefToDelete.DeleteWhenAble() EndWhile bIterating = false EndFunction How it works, is that the found items are put into the objrefarrayToDelete array, which is then iterated through at the end of the function after the items have had their static versions placed. But only a couple of items are removed in the delete loop. I assume that I'm f*#@ing something up, as deleting the objects in the main loop causes it to hang, while also only deleting a couple of the items. Any ideas? Link to comment Share on other sites More sharing options...
Evangela Posted May 8, 2018 Share Posted May 8, 2018 Breaking them up into separate functions, would be my first approach to tackling this issue. Link to comment Share on other sites More sharing options...
FiftyTifty Posted May 8, 2018 Author Share Posted May 8, 2018 Breaking them up into separate functions, would be my first approach to tackling this issue. Unfortunately, that didn't work. Made a new function that just deletes what it finds, but only a couple items are deleted as before. Function DeleteItems(bool bDeleteItems) int iFormListIndex = 0 While iFormListIndex < iNestedFormlistCount FormList formlistSourceCurrent = AAAFyTy_MasterFormList_Source.GetAt(iFormListIndex) as FormList FormList formlistDestCurrent = AAAFyTy_MasterFormList_Dest.GetAt(iFormListIndex) as FormList ObjectReference[] objrefarrayFoundItems if bDeleteItems == true objrefarrayFoundItems = PlayerRef.FindAllReferencesOfType(formlistSourceCurrent, iDistance) ;Debug.MessageBox("Looking for Items") else objrefarrayFoundItems = PlayerRef.FindAllReferencesOfType(formlistDestCurrent, iDistance) ;Debug.MessageBox("Looking for Statics") Endif int iFoundItemsCount = objrefarrayFoundItems.Length int iFoundItemIndex = 0 if iFoundItemsCount > 0 While iFoundItemIndex < iFoundItemsCount ObjectReference objrefFoundItem = objrefarrayFoundItems[iFoundItemIndex] as ObjectReference objrefFoundItem.Disable() objrefFoundItem.DeleteWhenAble() iFoundItemIndex += 1 EndWhile Endif iFormListIndex += 1 EndWhile EndFunction Link to comment Share on other sites More sharing options...
SKKmods Posted May 8, 2018 Share Posted May 8, 2018 How many iFoundItemsCount array elements are you getting, anywhere near 128 ? Rather than async .DeleteWhenAble() try the slower but possibly thread safer .Delete() Link to comment Share on other sites More sharing options...
FiftyTifty Posted May 8, 2018 Author Share Posted May 8, 2018 How many iFoundItemsCount array elements are you getting, anywhere near 128 ? Rather than async .DeleteWhenAble() try the slower but possibly thread safer .Delete() In my current tests, there's only around 15 items. DeleteWhenAble nor Delete are called upon all the items. And neither is Disable(), no matter the combination of functions (just Disable(), Disable() and Delete(), Disable() and DeleteWhenAble()). Link to comment Share on other sites More sharing options...
SKKmods Posted May 8, 2018 Share Posted May 8, 2018 (edited) Looking at some working code, the only difference is the ObjectReference to be deleted is defined outside of the logic block at a higher scope: Int iCount = QuestObjectRefs.Length ObjectReference DeleteRef Int iIndex = 0 While iIndex < iCount DeleteRef = QuestObjectRefs[iIndex] DeleteRef.Disable() DeleteRef.Delete() iIndex +=1 EndWhile so you may want to pop the ObjectReference objrefFoundItem declaration before your While block. Update for remembering things: and While loops do not seem to like the count changing so I tend to fix it rather than an elegant sliding count and index. Edited May 8, 2018 by SKK50 Link to comment Share on other sites More sharing options...
FiftyTifty Posted May 9, 2018 Author Share Posted May 9, 2018 Looking at some working code, the only difference is the ObjectReference to be deleted is defined outside of the logic block at a higher scope: Int iCount = QuestObjectRefs.Length ObjectReference DeleteRef Int iIndex = 0 While iIndex < iCount DeleteRef = QuestObjectRefs[iIndex] DeleteRef.Disable() DeleteRef.Delete() iIndex +=1 EndWhile so you may want to pop the ObjectReference objrefFoundItem declaration before your While block. Update for remembering things: and While loops do not seem to like the count changing so I tend to fix it rather than an elegant sliding count and index. Unfortunately, that doesn't work either. I have found a very un-ideal workaround; I can successfully call MoveTo() on the objects inside the array, when I call it inside the main loop. The items aren't deleted, but at least they're removed from the player's cell. Link to comment Share on other sites More sharing options...
Recommended Posts