diff options
Diffstat (limited to 'OpenSim/Region/Physics/BulletSPlugin/BSLinksetConstraints.cs')
-rwxr-xr-x | OpenSim/Region/Physics/BulletSPlugin/BSLinksetConstraints.cs | 82 |
1 files changed, 61 insertions, 21 deletions
diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSLinksetConstraints.cs b/OpenSim/Region/Physics/BulletSPlugin/BSLinksetConstraints.cs index a06a44d..f17d698 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSLinksetConstraints.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSLinksetConstraints.cs | |||
@@ -48,12 +48,22 @@ public sealed class BSLinksetConstraints : BSLinkset | |||
48 | { | 48 | { |
49 | base.Refresh(requestor); | 49 | base.Refresh(requestor); |
50 | 50 | ||
51 | if (HasAnyChildren && IsRoot(requestor)) | 51 | } |
52 | |||
53 | private void ScheduleRebuild(BSPrimLinkable requestor) | ||
54 | { | ||
55 | DetailLog("{0},BSLinksetConstraint.ScheduleRebuild,,rebuilding={1},hasChildren={2},actuallyScheduling={3}", | ||
56 | requestor.LocalID, Rebuilding, HasAnyChildren, (!Rebuilding && HasAnyChildren)); | ||
57 | |||
58 | // When rebuilding, it is possible to set properties that would normally require a rebuild. | ||
59 | // If already rebuilding, don't request another rebuild. | ||
60 | // If a linkset with just a root prim (simple non-linked prim) don't bother rebuilding. | ||
61 | if (!Rebuilding && HasAnyChildren) | ||
52 | { | 62 | { |
53 | // Queue to happen after all the other taint processing | 63 | // Queue to happen after all the other taint processing |
54 | m_physicsScene.PostTaintObject("BSLinksetContraints.Refresh", requestor.LocalID, delegate() | 64 | m_physicsScene.PostTaintObject("BSLinksetContraints.Refresh", requestor.LocalID, delegate() |
55 | { | 65 | { |
56 | if (HasAnyChildren && IsRoot(requestor)) | 66 | if (HasAnyChildren) |
57 | RecomputeLinksetConstraints(); | 67 | RecomputeLinksetConstraints(); |
58 | }); | 68 | }); |
59 | } | 69 | } |
@@ -67,8 +77,14 @@ public sealed class BSLinksetConstraints : BSLinkset | |||
67 | // Called at taint-time! | 77 | // Called at taint-time! |
68 | public override bool MakeDynamic(BSPrimLinkable child) | 78 | public override bool MakeDynamic(BSPrimLinkable child) |
69 | { | 79 | { |
70 | // What is done for each object in BSPrim is what we want. | 80 | bool ret = false; |
71 | return false; | 81 | DetailLog("{0},BSLinksetConstraints.MakeDynamic,call,IsRoot={1}", child.LocalID, IsRoot(child)); |
82 | if (IsRoot(child)) | ||
83 | { | ||
84 | // The root is going dynamic. Rebuild the linkset so parts and mass get computed properly. | ||
85 | ScheduleRebuild(LinksetRoot); | ||
86 | } | ||
87 | return ret; | ||
72 | } | 88 | } |
73 | 89 | ||
74 | // The object is going static (non-physical). Do any setup necessary for a static linkset. | 90 | // The object is going static (non-physical). Do any setup necessary for a static linkset. |
@@ -78,8 +94,16 @@ public sealed class BSLinksetConstraints : BSLinkset | |||
78 | // Called at taint-time! | 94 | // Called at taint-time! |
79 | public override bool MakeStatic(BSPrimLinkable child) | 95 | public override bool MakeStatic(BSPrimLinkable child) |
80 | { | 96 | { |
81 | // What is done for each object in BSPrim is what we want. | 97 | bool ret = false; |
82 | return false; | 98 | |
99 | DetailLog("{0},BSLinksetConstraint.MakeStatic,call,IsRoot={1}", child.LocalID, IsRoot(child)); | ||
100 | child.ClearDisplacement(); | ||
101 | if (IsRoot(child)) | ||
102 | { | ||
103 | // Schedule a rebuild to verify that the root shape is set to the real shape. | ||
104 | ScheduleRebuild(LinksetRoot); | ||
105 | } | ||
106 | return ret; | ||
83 | } | 107 | } |
84 | 108 | ||
85 | // Called at taint-time!! | 109 | // Called at taint-time!! |
@@ -105,7 +129,7 @@ public sealed class BSLinksetConstraints : BSLinkset | |||
105 | // Just undo all the constraints for this linkset. Rebuild at the end of the step. | 129 | // Just undo all the constraints for this linkset. Rebuild at the end of the step. |
106 | ret = PhysicallyUnlinkAllChildrenFromRoot(LinksetRoot); | 130 | ret = PhysicallyUnlinkAllChildrenFromRoot(LinksetRoot); |
107 | // Cause the constraints, et al to be rebuilt before the next simulation step. | 131 | // Cause the constraints, et al to be rebuilt before the next simulation step. |
108 | Refresh(LinksetRoot); | 132 | ScheduleRebuild(LinksetRoot); |
109 | } | 133 | } |
110 | return ret; | 134 | return ret; |
111 | } | 135 | } |
@@ -123,7 +147,7 @@ public sealed class BSLinksetConstraints : BSLinkset | |||
123 | DetailLog("{0},BSLinksetConstraints.AddChildToLinkset,call,child={1}", LinksetRoot.LocalID, child.LocalID); | 147 | DetailLog("{0},BSLinksetConstraints.AddChildToLinkset,call,child={1}", LinksetRoot.LocalID, child.LocalID); |
124 | 148 | ||
125 | // Cause constraints and assorted properties to be recomputed before the next simulation step. | 149 | // Cause constraints and assorted properties to be recomputed before the next simulation step. |
126 | Refresh(LinksetRoot); | 150 | ScheduleRebuild(LinksetRoot); |
127 | } | 151 | } |
128 | return; | 152 | return; |
129 | } | 153 | } |
@@ -147,7 +171,7 @@ public sealed class BSLinksetConstraints : BSLinkset | |||
147 | PhysicallyUnlinkAChildFromRoot(rootx, childx); | 171 | PhysicallyUnlinkAChildFromRoot(rootx, childx); |
148 | }); | 172 | }); |
149 | // See that the linkset parameters are recomputed at the end of the taint time. | 173 | // See that the linkset parameters are recomputed at the end of the taint time. |
150 | Refresh(LinksetRoot); | 174 | ScheduleRebuild(LinksetRoot); |
151 | } | 175 | } |
152 | else | 176 | else |
153 | { | 177 | { |
@@ -165,6 +189,7 @@ public sealed class BSLinksetConstraints : BSLinkset | |||
165 | Refresh(rootPrim); | 189 | Refresh(rootPrim); |
166 | } | 190 | } |
167 | 191 | ||
192 | // Create a static constraint between the two passed objects | ||
168 | private BSConstraint BuildConstraint(BSPrimLinkable rootPrim, BSPrimLinkable childPrim) | 193 | private BSConstraint BuildConstraint(BSPrimLinkable rootPrim, BSPrimLinkable childPrim) |
169 | { | 194 | { |
170 | // Zero motion for children so they don't interpolate | 195 | // Zero motion for children so they don't interpolate |
@@ -281,24 +306,39 @@ public sealed class BSLinksetConstraints : BSLinkset | |||
281 | DetailLog("{0},BSLinksetConstraint.RecomputeLinksetConstraints,set,rBody={1},linksetMass={2}", | 306 | DetailLog("{0},BSLinksetConstraint.RecomputeLinksetConstraints,set,rBody={1},linksetMass={2}", |
282 | LinksetRoot.LocalID, LinksetRoot.PhysBody.AddrString, linksetMass); | 307 | LinksetRoot.LocalID, LinksetRoot.PhysBody.AddrString, linksetMass); |
283 | 308 | ||
284 | foreach (BSPrimLinkable child in m_children) | 309 | try |
285 | { | 310 | { |
286 | // A child in the linkset physically shows the mass of the whole linkset. | 311 | Rebuilding = true; |
287 | // This allows Bullet to apply enough force on the child to move the whole linkset. | ||
288 | // (Also do the mass stuff before recomputing the constraint so mass is not zero.) | ||
289 | child.UpdatePhysicalMassProperties(linksetMass, true); | ||
290 | 312 | ||
291 | BSConstraint constrain; | 313 | // There is no reason to build all this physical stuff for a non-physical linkset. |
292 | if (!m_physicsScene.Constraints.TryGetConstraint(LinksetRoot.PhysBody, child.PhysBody, out constrain)) | 314 | if (!LinksetRoot.IsPhysicallyActive) |
293 | { | 315 | { |
294 | // If constraint doesn't exist yet, create it. | 316 | DetailLog("{0},BSLinksetConstraint.RecomputeLinksetCompound,notPhysical", LinksetRoot.LocalID); |
295 | constrain = BuildConstraint(LinksetRoot, child); | 317 | return; // Note the 'finally' clause at the botton which will get executed. |
296 | } | 318 | } |
297 | constrain.RecomputeConstraintVariables(linksetMass); | ||
298 | 319 | ||
299 | // PhysicsScene.PE.DumpConstraint(PhysicsScene.World, constrain.Constraint); // DEBUG DEBUG | 320 | foreach (BSPrimLinkable child in m_children) |
300 | } | 321 | { |
322 | // A child in the linkset physically shows the mass of the whole linkset. | ||
323 | // This allows Bullet to apply enough force on the child to move the whole linkset. | ||
324 | // (Also do the mass stuff before recomputing the constraint so mass is not zero.) | ||
325 | child.UpdatePhysicalMassProperties(linksetMass, true); | ||
326 | |||
327 | BSConstraint constrain; | ||
328 | if (!m_physicsScene.Constraints.TryGetConstraint(LinksetRoot.PhysBody, child.PhysBody, out constrain)) | ||
329 | { | ||
330 | // If constraint doesn't exist yet, create it. | ||
331 | constrain = BuildConstraint(LinksetRoot, child); | ||
332 | } | ||
333 | constrain.RecomputeConstraintVariables(linksetMass); | ||
301 | 334 | ||
335 | // PhysicsScene.PE.DumpConstraint(PhysicsScene.World, constrain.Constraint); // DEBUG DEBUG | ||
336 | } | ||
337 | } | ||
338 | finally | ||
339 | { | ||
340 | Rebuilding = false; | ||
341 | } | ||
302 | } | 342 | } |
303 | } | 343 | } |
304 | } | 344 | } |