In my mod description, I mention a C++ patch that is applied to fix a Bethesda-side bug. The technical details of this patch probably aren't important to most users, but I'd like to document them for those who really want to know exactly what they're putting into their game.
While working on this mod, I discovered a nasty bug: if you SetMotionType(4) on certain references, they become impossible to move stably; their coordinates will change, but their 3D models will remain in exactly the same spot. (Whiterun and Riften interior doors are both examples of objects that break in this manner.) Even worse: there is no way to detect that this has happened.
Further investigation turned up a few factors of interest. While I don't know all of the factors that cause references to break, I do know that all affected references (that I've found) use 3D models whose motion types are 4 by default, and whose nodes include a NiControllerManager. I also experimentally verified that these references have motion type 4 before SetMotionType is called, so nothing should actually change. However, when SetMotionType runs on a reference, Skyrim blindly sets the HAVOK_MOVE changeFlag. (ChangeFlags are bits used to signal to Skyrim that something about an object has changed, and that this change needs to be written into the savegame.) The mere presence of that changeFlag on these references was enough to break them.
Our entire problem falls under the scenario of redundantly running SetMotionType(4) and then setting a flag that doesn't need to be set, to track a "change" that didn't actually change anything. Thus, a workaround: patch SetMotionType so that we don't set the Havok changeFlag for these specific redundant operations. Everything behaves more or less the same, minus the brokenness.
Bear in mind that this doesn't fix any references that have already broken; it only prevents future references from breaking. To handle things retroactively, I also added Papyrus APIs to check for the presence of a NiControllerManager on a reference's loaded 3D, and to forcibly clear any changeFlag. When you select an object with Cobb Positioner, we check if the object has a NiControllerManager and if its Havok changeFlag is set; if so, we forcibly clear the Havok changeFlag off of anything you select (which we can do because we'll be setting motion type 4 anyway -- it doesn't matter what Havok data was present beforehand).
Thus, this patch should prevent all other mods from breaking references in this manner, but doesn't offer them any recourse for fixing objects that are already broken. I would've liked to fix the problem at the source, but I couldn't find where it was actually occurring. A workaround was the best I could do.
EDIT 05/20/2017: Turns out, it wasn't the NiControllerManager; it was flag 8 in the bhkCollisionObjects. I don't know whether that flag causes problems for objects that don't default to motion-type 4, so for now, I haven't changed the SetMotionType patch; I've just changed things so that we forcibly clear the HAVOK_MOVE changeFlag if the reference has a bhkCollisionObject with the problematic flag. This does mean that if an object has the bad flag and is movable by default, we may still run into problems with it; but I haven't seen any such problems in the wild.
MotionType/Move Patch
-
Total views2.5k