BulletSim: fix problem where editting a physical linkset caused the
child prim physical positions to get out of sync with the view. More reliably compute the offset of children in a physical linkset.user_profiles
parent
75a05c16c5
commit
5bb85a14d4
|
@ -219,30 +219,31 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
{
|
{
|
||||||
// Gather the child info. It might not be there if the linkset is in transition.
|
// Gather the child info. It might not be there if the linkset is in transition.
|
||||||
BSLinksetCompoundInfo lsi = updated.LinksetInfo as BSLinksetCompoundInfo;
|
BSLinksetCompoundInfo lsi = updated.LinksetInfo as BSLinksetCompoundInfo;
|
||||||
|
if (lsi != null)
|
||||||
|
{
|
||||||
|
// Since the child moved or rotationed, it needs a new relative position within the linkset
|
||||||
|
BSLinksetCompoundInfo newLsi = new BSLinksetCompoundInfo(lsi.Index, LinksetRoot, updated, LinksetRoot.PositionDisplacement);
|
||||||
|
updated.LinksetInfo = newLsi;
|
||||||
|
|
||||||
// The linksetInfo will need to be rebuilt either here or when the linkset is rebuilt
|
// Find the physical instance of the child
|
||||||
if (LinksetRoot.PhysShape.HasPhysicalShape && lsi != null)
|
if (LinksetRoot.PhysShape.HasPhysicalShape && PhysicsScene.PE.IsCompound(LinksetRoot.PhysShape))
|
||||||
{
|
|
||||||
if (PhysicsScene.PE.IsCompound(LinksetRoot.PhysShape))
|
|
||||||
{
|
|
||||||
int numLinksetChildren = PhysicsScene.PE.GetNumberOfCompoundChildren(LinksetRoot.PhysShape);
|
|
||||||
if (lsi.Index < numLinksetChildren)
|
|
||||||
{
|
{
|
||||||
// It is possible that the linkset is still under construction and the child is not yet
|
// It is possible that the linkset is still under construction and the child is not yet
|
||||||
// inserted into the compound shape. A rebuild of the linkset in a pre-step action will
|
// inserted into the compound shape. A rebuild of the linkset in a pre-step action will
|
||||||
// build the whole thing with the new position or rotation.
|
// build the whole thing with the new position or rotation.
|
||||||
// This must be checked for because Bullet references the child array but does no validity
|
// The index must be checked because Bullet references the child array but does no validity
|
||||||
// checking of the child index passed.
|
// checking of the child index passed.
|
||||||
|
int numLinksetChildren = PhysicsScene.PE.GetNumberOfCompoundChildren(LinksetRoot.PhysShape);
|
||||||
|
if (lsi.Index < numLinksetChildren)
|
||||||
|
{
|
||||||
BulletShape linksetChildShape = PhysicsScene.PE.GetChildShapeFromCompoundShapeIndex(LinksetRoot.PhysShape, lsi.Index);
|
BulletShape linksetChildShape = PhysicsScene.PE.GetChildShapeFromCompoundShapeIndex(LinksetRoot.PhysShape, lsi.Index);
|
||||||
if (linksetChildShape.HasPhysicalShape)
|
if (linksetChildShape.HasPhysicalShape)
|
||||||
{
|
{
|
||||||
// Compute the offset from the center-of-gravity
|
// Found the child shape within the compound shape
|
||||||
BSLinksetCompoundInfo newLsi = new BSLinksetCompoundInfo(lsi.Index, LinksetRoot, updated, LinksetRoot.PositionDisplacement);
|
|
||||||
PhysicsScene.PE.UpdateChildTransform(LinksetRoot.PhysShape, lsi.Index,
|
PhysicsScene.PE.UpdateChildTransform(LinksetRoot.PhysShape, lsi.Index,
|
||||||
newLsi.OffsetFromCenterOfMass,
|
newLsi.OffsetFromCenterOfMass,
|
||||||
newLsi.OffsetRot,
|
newLsi.OffsetRot,
|
||||||
true /* shouldRecalculateLocalAabb */);
|
true /* shouldRecalculateLocalAabb */);
|
||||||
updated.LinksetInfo = newLsi;
|
|
||||||
updatedChild = true;
|
updatedChild = true;
|
||||||
DetailLog("{0},BSLinksetCompound.UpdateProperties,changeChildPosRot,whichUpdated={1},newLsi={2}",
|
DetailLog("{0},BSLinksetCompound.UpdateProperties,changeChildPosRot,whichUpdated={1},newLsi={2}",
|
||||||
updated.LocalID, whichUpdated, newLsi);
|
updated.LocalID, whichUpdated, newLsi);
|
||||||
|
@ -262,19 +263,20 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
}
|
}
|
||||||
else // DEBUG DEBUG
|
else // DEBUG DEBUG
|
||||||
{ // DEBUG DEBUG
|
{ // DEBUG DEBUG
|
||||||
DetailLog("{0},BSLinksetCompound.UpdateProperties,couldNotUpdateChild,notCompound", updated.LocalID);
|
DetailLog("{0},BSLinksetCompound.UpdateProperties,couldNotUpdateChild,noBodyOrNotCompound", updated.LocalID);
|
||||||
} // DEBUG DEBUG
|
} // DEBUG DEBUG
|
||||||
}
|
}
|
||||||
else // DEBUG DEBUG
|
else // DEBUG DEBUG
|
||||||
{ // DEBUG DEBUG
|
{ // DEBUG DEBUG
|
||||||
DetailLog("{0},BSLinksetCompound.UpdateProperties,couldNotUpdateChild,rootPhysShape={1},lsi={2}",
|
DetailLog("{0},BSLinksetCompound.UpdateProperties,couldNotUpdateChild,noLinkSetInfo,rootPhysShape={1}",
|
||||||
updated.LocalID, LinksetRoot.PhysShape, lsi == null ? "NULL" : lsi.ToString());
|
updated.LocalID, LinksetRoot.PhysShape);
|
||||||
} // DEBUG DEBUG
|
} // DEBUG DEBUG
|
||||||
|
|
||||||
if (!updatedChild)
|
if (!updatedChild)
|
||||||
{
|
{
|
||||||
// If couldn't do the individual child, the linkset needs a rebuild to incorporate the new child info.
|
// If couldn't do the individual child, the linkset needs a rebuild to incorporate the new child info.
|
||||||
// Note that there are several ways through this code that will not update the child that can
|
// Note: there are several ways through this code that will not update the child if
|
||||||
// occur if the linkset is being rebuilt. In this case, scheduling a rebuild is a NOOP since
|
// the linkset is being rebuilt. In this case, scheduling a rebuild is a NOOP since
|
||||||
// there will already be a rebuild scheduled.
|
// there will already be a rebuild scheduled.
|
||||||
DetailLog("{0},BSLinksetCompound.UpdateProperties,couldNotUpdateChild.schedulingRebuild,whichUpdated={1}",
|
DetailLog("{0},BSLinksetCompound.UpdateProperties,couldNotUpdateChild.schedulingRebuild,whichUpdated={1}",
|
||||||
updated.LocalID, whichUpdated);
|
updated.LocalID, whichUpdated);
|
||||||
|
@ -300,7 +302,8 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
{
|
{
|
||||||
// Because it is a convenient time, recompute child world position and rotation based on
|
// Because it is a convenient time, recompute child world position and rotation based on
|
||||||
// its position in the linkset.
|
// its position in the linkset.
|
||||||
RecomputeChildWorldPosition(child, true);
|
RecomputeChildWorldPosition(child, true /* inTaintTime */);
|
||||||
|
child.LinksetInfo = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Cannot schedule a refresh/rebuild here because this routine is called when
|
// Cannot schedule a refresh/rebuild here because this routine is called when
|
||||||
|
@ -315,6 +318,14 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
// prim. The child prim's location must be recomputed based on the location of the root shape.
|
// prim. The child prim's location must be recomputed based on the location of the root shape.
|
||||||
private void RecomputeChildWorldPosition(BSPhysObject child, bool inTaintTime)
|
private void RecomputeChildWorldPosition(BSPhysObject child, bool inTaintTime)
|
||||||
{
|
{
|
||||||
|
// For the moment (20130201), disable this computation (converting the child physical addr back to
|
||||||
|
// a region address) until we have a good handle on center-of-mass offsets and what the physics
|
||||||
|
// engine moving a child actually means.
|
||||||
|
// The simulator keeps track of where children should be as the linkset moves. Setting
|
||||||
|
// the pos/rot here does not effect that knowledge as there is no good way for the
|
||||||
|
// physics engine to send the simulator an update for a child.
|
||||||
|
|
||||||
|
/*
|
||||||
BSLinksetCompoundInfo lci = child.LinksetInfo as BSLinksetCompoundInfo;
|
BSLinksetCompoundInfo lci = child.LinksetInfo as BSLinksetCompoundInfo;
|
||||||
if (lci != null)
|
if (lci != null)
|
||||||
{
|
{
|
||||||
|
@ -343,6 +354,7 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
// LogHeader, child.LocalID);
|
// LogHeader, child.LocalID);
|
||||||
DetailLog("{0},BSLinksetCompound.recomputeChildWorldPosition,noRelativePositonInfo", child.LocalID);
|
DetailLog("{0},BSLinksetCompound.recomputeChildWorldPosition,noRelativePositonInfo", child.LocalID);
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
}
|
}
|
||||||
|
|
||||||
// ================================================================
|
// ================================================================
|
||||||
|
@ -376,6 +388,7 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
|
|
||||||
// Cause the child's body to be rebuilt and thus restored to normal operation
|
// Cause the child's body to be rebuilt and thus restored to normal operation
|
||||||
RecomputeChildWorldPosition(child, false);
|
RecomputeChildWorldPosition(child, false);
|
||||||
|
child.LinksetInfo = null;
|
||||||
child.ForceBodyShapeRebuild(false);
|
child.ForceBodyShapeRebuild(false);
|
||||||
|
|
||||||
if (!HasAnyChildren)
|
if (!HasAnyChildren)
|
||||||
|
@ -397,7 +410,7 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
// Constraint linksets are rebuilt every time.
|
// Constraint linksets are rebuilt every time.
|
||||||
// Note that this works for rebuilding just the root after a linkset is taken apart.
|
// Note that this works for rebuilding just the root after a linkset is taken apart.
|
||||||
// Called at taint time!!
|
// Called at taint time!!
|
||||||
private bool disableCOM = true; // disable until we get this debugged
|
private bool disableCOM = true; // DEBUG DEBUG: disable until we get this debugged
|
||||||
private void RecomputeLinksetCompound()
|
private void RecomputeLinksetCompound()
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
|
|
|
@ -127,6 +127,7 @@ Physical and phantom will drop through the terrain
|
||||||
|
|
||||||
LINKSETS
|
LINKSETS
|
||||||
======================================================
|
======================================================
|
||||||
|
Child prims do not report collisions
|
||||||
Editing a child of a linkset causes the child to go phantom
|
Editing a child of a linkset causes the child to go phantom
|
||||||
Move a child prim once when it is physical and can never move it again without it going phantom
|
Move a child prim once when it is physical and can never move it again without it going phantom
|
||||||
Offset the center of the linkset to be the geometric center of all the prims
|
Offset the center of the linkset to be the geometric center of all the prims
|
||||||
|
|
Loading…
Reference in New Issue