diff options
Diffstat (limited to '')
-rwxr-xr-x | OpenSim/Region/Physics/BulletSPlugin/BSLinkset.cs | 150 |
1 files changed, 95 insertions, 55 deletions
diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSLinkset.cs b/OpenSim/Region/Physics/BulletSPlugin/BSLinkset.cs index 087b9bb..7e784eb 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSLinkset.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSLinkset.cs | |||
@@ -36,14 +36,17 @@ public class BSLinkset | |||
36 | { | 36 | { |
37 | private static string LogHeader = "[BULLETSIM LINKSET]"; | 37 | private static string LogHeader = "[BULLETSIM LINKSET]"; |
38 | 38 | ||
39 | private BSPrim m_linksetRoot; | 39 | private BSPhysObject m_linksetRoot; |
40 | public BSPrim LinksetRoot { get { return m_linksetRoot; } } | 40 | public BSPhysObject LinksetRoot { get { return m_linksetRoot; } } |
41 | 41 | ||
42 | private BSScene m_physicsScene; | 42 | private BSScene m_physicsScene; |
43 | public BSScene PhysicsScene { get { return m_physicsScene; } } | 43 | public BSScene PhysicsScene { get { return m_physicsScene; } } |
44 | 44 | ||
45 | static int m_nextLinksetID = 1; | ||
46 | public int LinksetID { get; private set; } | ||
47 | |||
45 | // The children under the root in this linkset | 48 | // The children under the root in this linkset |
46 | private List<BSPrim> m_children; | 49 | private List<BSPhysObject> m_children; |
47 | 50 | ||
48 | // We lock the diddling of linkset classes to prevent any badness. | 51 | // We lock the diddling of linkset classes to prevent any badness. |
49 | // This locks the modification of the instances of this class. Changes | 52 | // This locks the modification of the instances of this class. Changes |
@@ -71,19 +74,23 @@ public class BSLinkset | |||
71 | get { return ComputeLinksetGeometricCenter(); } | 74 | get { return ComputeLinksetGeometricCenter(); } |
72 | } | 75 | } |
73 | 76 | ||
74 | public BSLinkset(BSScene scene, BSPrim parent) | 77 | public BSLinkset(BSScene scene, BSPhysObject parent) |
75 | { | 78 | { |
76 | // A simple linkset of one (no children) | 79 | // A simple linkset of one (no children) |
80 | LinksetID = m_nextLinksetID++; | ||
81 | // We create LOTS of linksets. | ||
82 | if (m_nextLinksetID < 0) | ||
83 | m_nextLinksetID = 1; | ||
77 | m_physicsScene = scene; | 84 | m_physicsScene = scene; |
78 | m_linksetRoot = parent; | 85 | m_linksetRoot = parent; |
79 | m_children = new List<BSPrim>(); | 86 | m_children = new List<BSPhysObject>(); |
80 | m_mass = parent.MassRaw; | 87 | m_mass = parent.MassRaw; |
81 | } | 88 | } |
82 | 89 | ||
83 | // Link to a linkset where the child knows the parent. | 90 | // Link to a linkset where the child knows the parent. |
84 | // Parent changing should not happen so do some sanity checking. | 91 | // Parent changing should not happen so do some sanity checking. |
85 | // We return the parent's linkset so the child can track its membership. | 92 | // We return the parent's linkset so the child can track its membership. |
86 | public BSLinkset AddMeToLinkset(BSPrim child) | 93 | public BSLinkset AddMeToLinkset(BSPhysObject child) |
87 | { | 94 | { |
88 | lock (m_linksetActivityLock) | 95 | lock (m_linksetActivityLock) |
89 | { | 96 | { |
@@ -95,7 +102,7 @@ public class BSLinkset | |||
95 | // Remove a child from a linkset. | 102 | // Remove a child from a linkset. |
96 | // Returns a new linkset for the child which is a linkset of one (just the | 103 | // Returns a new linkset for the child which is a linkset of one (just the |
97 | // orphened child). | 104 | // orphened child). |
98 | public BSLinkset RemoveMeFromLinkset(BSPrim child) | 105 | public BSLinkset RemoveMeFromLinkset(BSPhysObject child) |
99 | { | 106 | { |
100 | lock (m_linksetActivityLock) | 107 | lock (m_linksetActivityLock) |
101 | { | 108 | { |
@@ -122,7 +129,7 @@ public class BSLinkset | |||
122 | } | 129 | } |
123 | 130 | ||
124 | // Return 'true' if the passed object is the root object of this linkset | 131 | // Return 'true' if the passed object is the root object of this linkset |
125 | public bool IsRoot(BSPrim requestor) | 132 | public bool IsRoot(BSPhysObject requestor) |
126 | { | 133 | { |
127 | return (requestor.LocalID == m_linksetRoot.LocalID); | 134 | return (requestor.LocalID == m_linksetRoot.LocalID); |
128 | } | 135 | } |
@@ -133,12 +140,12 @@ public class BSLinkset | |||
133 | public bool HasAnyChildren { get { return (m_children.Count > 0); } } | 140 | public bool HasAnyChildren { get { return (m_children.Count > 0); } } |
134 | 141 | ||
135 | // Return 'true' if this child is in this linkset | 142 | // Return 'true' if this child is in this linkset |
136 | public bool HasChild(BSPrim child) | 143 | public bool HasChild(BSPhysObject child) |
137 | { | 144 | { |
138 | bool ret = false; | 145 | bool ret = false; |
139 | lock (m_linksetActivityLock) | 146 | lock (m_linksetActivityLock) |
140 | { | 147 | { |
141 | foreach (BSPrim bp in m_children) | 148 | foreach (BSPhysObject bp in m_children) |
142 | { | 149 | { |
143 | if (child.LocalID == bp.LocalID) | 150 | if (child.LocalID == bp.LocalID) |
144 | { | 151 | { |
@@ -153,7 +160,7 @@ public class BSLinkset | |||
153 | private float ComputeLinksetMass() | 160 | private float ComputeLinksetMass() |
154 | { | 161 | { |
155 | float mass = m_linksetRoot.MassRaw; | 162 | float mass = m_linksetRoot.MassRaw; |
156 | foreach (BSPrim bp in m_children) | 163 | foreach (BSPhysObject bp in m_children) |
157 | { | 164 | { |
158 | mass += bp.MassRaw; | 165 | mass += bp.MassRaw; |
159 | } | 166 | } |
@@ -167,7 +174,7 @@ public class BSLinkset | |||
167 | 174 | ||
168 | lock (m_linksetActivityLock) | 175 | lock (m_linksetActivityLock) |
169 | { | 176 | { |
170 | foreach (BSPrim bp in m_children) | 177 | foreach (BSPhysObject bp in m_children) |
171 | { | 178 | { |
172 | com += bp.Position * bp.MassRaw; | 179 | com += bp.Position * bp.MassRaw; |
173 | totalMass += bp.MassRaw; | 180 | totalMass += bp.MassRaw; |
@@ -185,7 +192,7 @@ public class BSLinkset | |||
185 | 192 | ||
186 | lock (m_linksetActivityLock) | 193 | lock (m_linksetActivityLock) |
187 | { | 194 | { |
188 | foreach (BSPrim bp in m_children) | 195 | foreach (BSPhysObject bp in m_children) |
189 | { | 196 | { |
190 | com += bp.Position * bp.MassRaw; | 197 | com += bp.Position * bp.MassRaw; |
191 | } | 198 | } |
@@ -195,11 +202,33 @@ public class BSLinkset | |||
195 | return com; | 202 | return com; |
196 | } | 203 | } |
197 | 204 | ||
205 | // The object is going dynamic (physical). Do any setup necessary | ||
206 | // for a dynamic linkset. | ||
207 | // Only the state of the passed object can be modified. The rest of the linkset | ||
208 | // has not yet been fully constructed. | ||
209 | // Return 'true' if any properties updated on the passed object. | ||
210 | // Called at taint-time! | ||
211 | public bool MakeDynamic(BSPhysObject child) | ||
212 | { | ||
213 | bool ret = false; | ||
214 | return ret; | ||
215 | } | ||
216 | |||
217 | // The object is going static (non-physical). Do any setup necessary | ||
218 | // for a static linkset. | ||
219 | // Return 'true' if any properties updated on the passed object. | ||
220 | // Called at taint-time! | ||
221 | public bool MakeStatic(BSPhysObject child) | ||
222 | { | ||
223 | // What is done for each object in BSPrim is what we want. | ||
224 | return false; | ||
225 | } | ||
226 | |||
198 | // When physical properties are changed the linkset needs to recalculate | 227 | // When physical properties are changed the linkset needs to recalculate |
199 | // its internal properties. | 228 | // its internal properties. |
200 | public void Refresh(BSPrim requestor) | 229 | public void Refresh(BSPhysObject requestor) |
201 | { | 230 | { |
202 | // If there are no children, there aren't any constraints to recompute | 231 | // If there are no children, there can't be any constraints to recompute |
203 | if (!HasAnyChildren) | 232 | if (!HasAnyChildren) |
204 | return; | 233 | return; |
205 | 234 | ||
@@ -218,15 +247,16 @@ public class BSLinkset | |||
218 | // from a linkset to make sure the constraints know about the new mass and | 247 | // from a linkset to make sure the constraints know about the new mass and |
219 | // geometry. | 248 | // geometry. |
220 | // Must only be called at taint time!! | 249 | // Must only be called at taint time!! |
221 | private bool RecomputeLinksetConstraintVariables() | 250 | private void RecomputeLinksetConstraintVariables() |
222 | { | 251 | { |
223 | float linksetMass = LinksetMass; | 252 | float linksetMass = LinksetMass; |
224 | lock (m_linksetActivityLock) | 253 | lock (m_linksetActivityLock) |
225 | { | 254 | { |
226 | foreach (BSPrim child in m_children) | 255 | bool somethingMissing = false; |
256 | foreach (BSPhysObject child in m_children) | ||
227 | { | 257 | { |
228 | BSConstraint constrain; | 258 | BSConstraint constrain; |
229 | if (m_physicsScene.Constraints.TryGetConstraint(LinksetRoot.Body, child.Body, out constrain)) | 259 | if (m_physicsScene.Constraints.TryGetConstraint(LinksetRoot.BSBody, child.BSBody, out constrain)) |
230 | { | 260 | { |
231 | // DetailLog("{0},BSLinkset.RecomputeLinksetConstraintVariables,taint,child={1},mass={2},A={3},B={4}", | 261 | // DetailLog("{0},BSLinkset.RecomputeLinksetConstraintVariables,taint,child={1},mass={2},A={3},B={4}", |
232 | // LinksetRoot.LocalID, child.LocalID, linksetMass, constrain.Body1.ID, constrain.Body2.ID); | 262 | // LinksetRoot.LocalID, child.LocalID, linksetMass, constrain.Body1.ID, constrain.Body2.ID); |
@@ -234,32 +264,51 @@ public class BSLinkset | |||
234 | } | 264 | } |
235 | else | 265 | else |
236 | { | 266 | { |
237 | // Non-fatal error that can happen when children are being added to the linkset but | 267 | // Non-fatal error that happens when children are being added to the linkset but |
238 | // their constraints have not been created yet. | 268 | // their constraints have not been created yet. |
239 | // Caused by the fact that m_children is built at run time but building constraints | 269 | // Caused by the fact that m_children is built at run time but building constraints |
240 | // happens at taint time. | 270 | // happens at taint time. |
241 | // m_physicsScene.Logger.ErrorFormat("[BULLETSIM LINKSET] RecomputeLinksetConstraintVariables: constraint not found for root={0}, child={1}", | 271 | somethingMissing = true; |
242 | // m_linksetRoot.Body.ID, child.Body.ID); | 272 | break; |
243 | } | 273 | } |
244 | } | 274 | } |
275 | |||
276 | // If the whole linkset is not here, doesn't make sense to recompute linkset wide values | ||
277 | if (!somethingMissing) | ||
278 | { | ||
279 | // If this is a multiple object linkset, set everybody's center of mass to the set's center of mass | ||
280 | OMV.Vector3 centerOfMass = ComputeLinksetCenterOfMass(); | ||
281 | BulletSimAPI.SetCenterOfMassByPosRot2(LinksetRoot.BSBody.Ptr, centerOfMass, OMV.Quaternion.Identity); | ||
282 | foreach (BSPhysObject child in m_children) | ||
283 | { | ||
284 | BulletSimAPI.SetCenterOfMassByPosRot2(child.BSBody.Ptr, centerOfMass, OMV.Quaternion.Identity); | ||
285 | } | ||
286 | /* | ||
287 | // The root prim takes on the weight of the whole linkset | ||
288 | OMV.Vector3 inertia = BulletSimAPI.CalculateLocalInertia2(LinksetRoot.BSShape.Ptr, linksetMass); | ||
289 | BulletSimAPI.SetMassProps2(LinksetRoot.BSBody.Ptr, linksetMass, inertia); | ||
290 | OMV.Vector3 centerOfMass = ComputeLinksetCenterOfMass(); | ||
291 | BulletSimAPI.SetCenterOfMassByPosRot2(LinksetRoot.BSBody.Ptr, centerOfMass, OMV.Quaternion.Identity); | ||
292 | BulletSimAPI.UpdateInertiaTensor2(LinksetRoot.BSBody.Ptr); | ||
293 | */ | ||
294 | } | ||
245 | } | 295 | } |
246 | return false; | 296 | return; |
247 | } | 297 | } |
248 | 298 | ||
249 | // I am the root of a linkset and a new child is being added | 299 | // I am the root of a linkset and a new child is being added |
250 | // Called while LinkActivity is locked. | 300 | // Called while LinkActivity is locked. |
251 | private void AddChildToLinkset(BSPrim child) | 301 | private void AddChildToLinkset(BSPhysObject child) |
252 | { | 302 | { |
253 | if (!HasChild(child)) | 303 | if (!HasChild(child)) |
254 | { | 304 | { |
255 | m_children.Add(child); | 305 | m_children.Add(child); |
256 | 306 | ||
257 | BSPrim rootx = LinksetRoot; // capture the root as of now | 307 | BSPhysObject rootx = LinksetRoot; // capture the root as of now |
258 | BSPrim childx = child; | 308 | BSPhysObject childx = child; |
259 | m_physicsScene.TaintedObject("AddChildToLinkset", delegate() | 309 | m_physicsScene.TaintedObject("AddChildToLinkset", delegate() |
260 | { | 310 | { |
261 | // DebugLog("{0}: AddChildToLinkset: adding child {1} to {2}", LogHeader, child.LocalID, m_linksetRoot.LocalID); | 311 | DetailLog("{0},AddChildToLinkset,taint,child={1}", m_linksetRoot.LocalID, child.LocalID); |
262 | // DetailLog("{0},AddChildToLinkset,taint,child={1}", m_linksetRoot.LocalID, child.LocalID); | ||
263 | PhysicallyLinkAChildToRoot(rootx, childx); // build the physical binding between me and the child | 312 | PhysicallyLinkAChildToRoot(rootx, childx); // build the physical binding between me and the child |
264 | }); | 313 | }); |
265 | } | 314 | } |
@@ -271,7 +320,7 @@ public class BSLinkset | |||
271 | // it's still connected to the linkset. | 320 | // it's still connected to the linkset. |
272 | // Normal OpenSimulator operation will never do this because other SceneObjectPart information | 321 | // Normal OpenSimulator operation will never do this because other SceneObjectPart information |
273 | // has to be updated also (like pointer to prim's parent). | 322 | // has to be updated also (like pointer to prim's parent). |
274 | private void RemoveChildFromOtherLinkset(BSPrim pchild) | 323 | private void RemoveChildFromOtherLinkset(BSPhysObject pchild) |
275 | { | 324 | { |
276 | pchild.Linkset = new BSLinkset(m_physicsScene, pchild); | 325 | pchild.Linkset = new BSLinkset(m_physicsScene, pchild); |
277 | RemoveChildFromLinkset(pchild); | 326 | RemoveChildFromLinkset(pchild); |
@@ -279,21 +328,20 @@ public class BSLinkset | |||
279 | 328 | ||
280 | // I am the root of a linkset and one of my children is being removed. | 329 | // I am the root of a linkset and one of my children is being removed. |
281 | // Safe to call even if the child is not really in my linkset. | 330 | // Safe to call even if the child is not really in my linkset. |
282 | private void RemoveChildFromLinkset(BSPrim child) | 331 | private void RemoveChildFromLinkset(BSPhysObject child) |
283 | { | 332 | { |
284 | if (m_children.Remove(child)) | 333 | if (m_children.Remove(child)) |
285 | { | 334 | { |
286 | BSPrim rootx = LinksetRoot; // capture the root as of now | 335 | BSPhysObject rootx = LinksetRoot; // capture the root as of now |
287 | BSPrim childx = child; | 336 | BSPhysObject childx = child; |
288 | m_physicsScene.TaintedObject("RemoveChildFromLinkset", delegate() | 337 | m_physicsScene.TaintedObject("RemoveChildFromLinkset", delegate() |
289 | { | 338 | { |
290 | // DebugLog("{0}: RemoveChildFromLinkset: Removing constraint to {1}", LogHeader, child.LocalID); | 339 | DetailLog("{0},RemoveChildFromLinkset,taint,child={1}", m_linksetRoot.LocalID, child.LocalID); |
291 | // DetailLog("{0},RemoveChildFromLinkset,taint,child={1}", m_linksetRoot.LocalID, child.LocalID); | ||
292 | 340 | ||
293 | PhysicallyUnlinkAChildFromRoot(rootx, childx); | 341 | PhysicallyUnlinkAChildFromRoot(rootx, childx); |
342 | RecomputeLinksetConstraintVariables(); | ||
294 | }); | 343 | }); |
295 | 344 | ||
296 | RecomputeLinksetConstraintVariables(); | ||
297 | } | 345 | } |
298 | else | 346 | else |
299 | { | 347 | { |
@@ -305,7 +353,7 @@ public class BSLinkset | |||
305 | 353 | ||
306 | // Create a constraint between me (root of linkset) and the passed prim (the child). | 354 | // Create a constraint between me (root of linkset) and the passed prim (the child). |
307 | // Called at taint time! | 355 | // Called at taint time! |
308 | private void PhysicallyLinkAChildToRoot(BSPrim rootPrim, BSPrim childPrim) | 356 | private void PhysicallyLinkAChildToRoot(BSPhysObject rootPrim, BSPhysObject childPrim) |
309 | { | 357 | { |
310 | // Zero motion for children so they don't interpolate | 358 | // Zero motion for children so they don't interpolate |
311 | childPrim.ZeroMotion(); | 359 | childPrim.ZeroMotion(); |
@@ -319,19 +367,18 @@ public class BSLinkset | |||
319 | 367 | ||
320 | // create a constraint that allows no freedom of movement between the two objects | 368 | // create a constraint that allows no freedom of movement between the two objects |
321 | // http://bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=4818 | 369 | // http://bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=4818 |
322 | // DebugLog("{0}: CreateLinkset: Adding a constraint between root prim {1} and child prim {2}", LogHeader, LocalID, childPrim.LocalID); | ||
323 | DetailLog("{0},PhysicallyLinkAChildToRoot,taint,root={1},child={2},rLoc={3},cLoc={4},midLoc={5}", | 370 | DetailLog("{0},PhysicallyLinkAChildToRoot,taint,root={1},child={2},rLoc={3},cLoc={4},midLoc={5}", |
324 | rootPrim.LocalID, rootPrim.LocalID, childPrim.LocalID, rootPrim.Position, childPrim.Position, midPoint); | 371 | rootPrim.LocalID, rootPrim.LocalID, childPrim.LocalID, rootPrim.Position, childPrim.Position, midPoint); |
325 | BS6DofConstraint constrain = new BS6DofConstraint( | 372 | BS6DofConstraint constrain = new BS6DofConstraint( |
326 | m_physicsScene.World, rootPrim.Body, childPrim.Body, | 373 | m_physicsScene.World, rootPrim.BSBody, childPrim.BSBody, |
327 | midPoint, | 374 | midPoint, |
328 | true, | 375 | true, |
329 | true | 376 | true |
330 | ); | 377 | ); |
331 | /* NOTE: attempt to build constraint with full frame computation, etc. | 378 | /* NOTE: below is an attempt to build constraint with full frame computation, etc. |
332 | * Using the midpoint is easier since it lets the Bullet code use the transforms | 379 | * Using the midpoint is easier since it lets the Bullet code use the transforms |
333 | * of the objects. | 380 | * of the objects. |
334 | * Code left here as an example. | 381 | * Code left as a warning to future programmers. |
335 | // ================================================================================== | 382 | // ================================================================================== |
336 | // relative position normalized to the root prim | 383 | // relative position normalized to the root prim |
337 | OMV.Quaternion invThisOrientation = OMV.Quaternion.Inverse(rootPrim.Orientation); | 384 | OMV.Quaternion invThisOrientation = OMV.Quaternion.Inverse(rootPrim.Orientation); |
@@ -343,7 +390,6 @@ public class BSLinkset | |||
343 | 390 | ||
344 | // create a constraint that allows no freedom of movement between the two objects | 391 | // create a constraint that allows no freedom of movement between the two objects |
345 | // http://bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=4818 | 392 | // http://bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=4818 |
346 | // DebugLog("{0}: CreateLinkset: Adding a constraint between root prim {1} and child prim {2}", LogHeader, LocalID, childPrim.LocalID); | ||
347 | DetailLog("{0},PhysicallyLinkAChildToRoot,taint,root={1},child={2}", rootPrim.LocalID, rootPrim.LocalID, childPrim.LocalID); | 393 | DetailLog("{0},PhysicallyLinkAChildToRoot,taint,root={1},child={2}", rootPrim.LocalID, rootPrim.LocalID, childPrim.LocalID); |
348 | BS6DofConstraint constrain = new BS6DofConstraint( | 394 | BS6DofConstraint constrain = new BS6DofConstraint( |
349 | PhysicsScene.World, rootPrim.Body, childPrim.Body, | 395 | PhysicsScene.World, rootPrim.Body, childPrim.Body, |
@@ -374,40 +420,34 @@ public class BSLinkset | |||
374 | PhysicsScene.Params.linkConstraintTransMotorMaxVel, | 420 | PhysicsScene.Params.linkConstraintTransMotorMaxVel, |
375 | PhysicsScene.Params.linkConstraintTransMotorMaxForce); | 421 | PhysicsScene.Params.linkConstraintTransMotorMaxForce); |
376 | constrain.SetCFMAndERP(PhysicsScene.Params.linkConstraintCFM, PhysicsScene.Params.linkConstraintERP); | 422 | constrain.SetCFMAndERP(PhysicsScene.Params.linkConstraintCFM, PhysicsScene.Params.linkConstraintERP); |
423 | if (PhysicsScene.Params.linkConstraintSolverIterations != 0f) | ||
424 | { | ||
425 | constrain.SetSolverIterations(PhysicsScene.Params.linkConstraintSolverIterations); | ||
426 | } | ||
377 | 427 | ||
378 | RecomputeLinksetConstraintVariables(); | 428 | RecomputeLinksetConstraintVariables(); |
379 | } | 429 | } |
380 | 430 | ||
381 | // Remove linkage between myself and a particular child | 431 | // Remove linkage between myself and a particular child |
382 | // Called at taint time! | 432 | // Called at taint time! |
383 | private void PhysicallyUnlinkAChildFromRoot(BSPrim rootPrim, BSPrim childPrim) | 433 | private void PhysicallyUnlinkAChildFromRoot(BSPhysObject rootPrim, BSPhysObject childPrim) |
384 | { | 434 | { |
385 | // DebugLog("{0}: PhysicallyUnlinkAChildFromRoot: RemoveConstraint between root prim {1} and child prim {2}", | ||
386 | // LogHeader, rootPrim.LocalID, childPrim.LocalID); | ||
387 | DetailLog("{0},PhysicallyUnlinkAChildFromRoot,taint,root={1},child={2}", rootPrim.LocalID, rootPrim.LocalID, childPrim.LocalID); | 435 | DetailLog("{0},PhysicallyUnlinkAChildFromRoot,taint,root={1},child={2}", rootPrim.LocalID, rootPrim.LocalID, childPrim.LocalID); |
388 | 436 | ||
389 | // Find the constraint for this link and get rid of it from the overall collection and from my list | 437 | // Find the constraint for this link and get rid of it from the overall collection and from my list |
390 | m_physicsScene.Constraints.RemoveAndDestroyConstraint(rootPrim.Body, childPrim.Body); | 438 | m_physicsScene.Constraints.RemoveAndDestroyConstraint(rootPrim.BSBody, childPrim.BSBody); |
391 | 439 | ||
392 | // Make the child refresh its location | 440 | // Make the child refresh its location |
393 | BulletSimAPI.PushUpdate2(childPrim.Body.Ptr); | 441 | BulletSimAPI.PushUpdate2(childPrim.BSBody.Ptr); |
394 | } | 442 | } |
395 | 443 | ||
396 | // Remove linkage between myself and any possible children I might have | 444 | // Remove linkage between myself and any possible children I might have |
397 | // Called at taint time! | 445 | // Called at taint time! |
398 | private void PhysicallyUnlinkAllChildrenFromRoot(BSPrim rootPrim) | 446 | private void PhysicallyUnlinkAllChildrenFromRoot(BSPhysObject rootPrim) |
399 | { | 447 | { |
400 | // DebugLog("{0}: PhysicallyUnlinkAllChildren:", LogHeader); | ||
401 | DetailLog("{0},PhysicallyUnlinkAllChildren,taint", rootPrim.LocalID); | 448 | DetailLog("{0},PhysicallyUnlinkAllChildren,taint", rootPrim.LocalID); |
402 | 449 | ||
403 | m_physicsScene.Constraints.RemoveAndDestroyConstraint(rootPrim.Body); | 450 | m_physicsScene.Constraints.RemoveAndDestroyConstraint(rootPrim.BSBody); |
404 | } | ||
405 | |||
406 | // Invoke the detailed logger and output something if it's enabled. | ||
407 | private void DebugLog(string msg, params Object[] args) | ||
408 | { | ||
409 | if (m_physicsScene.ShouldDebugLog) | ||
410 | m_physicsScene.Logger.DebugFormat(msg, args); | ||
411 | } | 451 | } |
412 | 452 | ||
413 | // Invoke the detailed logger and output something if it's enabled. | 453 | // Invoke the detailed logger and output something if it's enabled. |