BulletSim: search the mesh and hull lists to find shapes if type is not known. This makes sure the correct accounting is done for the particular shape.
parent
498ea76e63
commit
894bb4893b
|
@ -134,7 +134,7 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
}
|
}
|
||||||
|
|
||||||
// Routine called when rebuilding the body of some member of the linkset.
|
// Routine called when rebuilding the body of some member of the linkset.
|
||||||
// Since we don't keep in-physical world relationships, do nothing unless it's a child changing.
|
// Since we don't keep in world relationships, do nothing unless it's a child changing.
|
||||||
// Returns 'true' of something was actually removed and would need restoring
|
// Returns 'true' of something was actually removed and would need restoring
|
||||||
// Called at taint-time!!
|
// Called at taint-time!!
|
||||||
public override bool RemoveBodyDependencies(BSPrim child)
|
public override bool RemoveBodyDependencies(BSPrim child)
|
||||||
|
@ -221,10 +221,12 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
DetailLog("{0},BSLinksetCompound.RecomputeLinksetCompound,start,rBody={1},rShape={2},numChildren={3}",
|
DetailLog("{0},BSLinksetCompound.RecomputeLinksetCompound,start,rBody={1},rShape={2},numChildren={3}",
|
||||||
LinksetRoot.LocalID, LinksetRoot.PhysBody, LinksetRoot.PhysShape, NumberOfChildren);
|
LinksetRoot.LocalID, LinksetRoot.PhysBody, LinksetRoot.PhysShape, NumberOfChildren);
|
||||||
|
|
||||||
|
// Add a shape for each of the other children in the linkset
|
||||||
ForEachMember(delegate(BSPhysObject cPrim)
|
ForEachMember(delegate(BSPhysObject cPrim)
|
||||||
{
|
{
|
||||||
if (!IsRoot(cPrim))
|
if (!IsRoot(cPrim))
|
||||||
{
|
{
|
||||||
|
// Each child position and rotation is given relative to the root.
|
||||||
OMV.Quaternion invRootOrientation = OMV.Quaternion.Inverse(LinksetRoot.RawOrientation);
|
OMV.Quaternion invRootOrientation = OMV.Quaternion.Inverse(LinksetRoot.RawOrientation);
|
||||||
OMV.Vector3 displacementPos = (cPrim.RawPosition - LinksetRoot.RawPosition) * invRootOrientation;
|
OMV.Vector3 displacementPos = (cPrim.RawPosition - LinksetRoot.RawPosition) * invRootOrientation;
|
||||||
OMV.Quaternion displacementRot = cPrim.RawOrientation * invRootOrientation;
|
OMV.Quaternion displacementRot = cPrim.RawOrientation * invRootOrientation;
|
||||||
|
@ -245,7 +247,7 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// For the shared shapes (meshes and hulls) just use the shape in the child
|
// For the shared shapes (meshes and hulls), just use the shape in the child.
|
||||||
if (PhysicsScene.Shapes.ReferenceShape(cPrim.PhysShape))
|
if (PhysicsScene.Shapes.ReferenceShape(cPrim.PhysShape))
|
||||||
{
|
{
|
||||||
PhysicsScene.Logger.ErrorFormat("{0} Rebuilt sharable shape when building linkset! Region={1}, primID={2}, shape={3}",
|
PhysicsScene.Logger.ErrorFormat("{0} Rebuilt sharable shape when building linkset! Region={1}, primID={2}, shape={3}",
|
||||||
|
@ -254,10 +256,10 @@ public sealed class BSLinksetCompound : BSLinkset
|
||||||
BulletSimAPI.AddChildShapeToCompoundShape2(LinksetRoot.PhysShape.ptr, cPrim.PhysShape.ptr, displacementPos, displacementRot);
|
BulletSimAPI.AddChildShapeToCompoundShape2(LinksetRoot.PhysShape.ptr, cPrim.PhysShape.ptr, displacementPos, displacementRot);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false;
|
return false; // 'false' says to move onto the next child in the list
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// With all of the linkset packed into the root prim, it has the mass of everyone.
|
||||||
float linksetMass = LinksetMass;
|
float linksetMass = LinksetMass;
|
||||||
LinksetRoot.UpdatePhysicalMassProperties(linksetMass);
|
LinksetRoot.UpdatePhysicalMassProperties(linksetMass);
|
||||||
|
|
||||||
|
|
|
@ -294,7 +294,7 @@ public sealed class BSLinksetConstraints : BSLinkset
|
||||||
float linksetMass = LinksetMass;
|
float linksetMass = LinksetMass;
|
||||||
LinksetRoot.UpdatePhysicalMassProperties(linksetMass);
|
LinksetRoot.UpdatePhysicalMassProperties(linksetMass);
|
||||||
|
|
||||||
// DEBUG: see of inter-linkset collisions are causing problems
|
// DEBUG: see of inter-linkset collisions are causing problems
|
||||||
// BulletSimAPI.SetCollisionFilterMask2(LinksetRoot.BSBody.ptr,
|
// BulletSimAPI.SetCollisionFilterMask2(LinksetRoot.BSBody.ptr,
|
||||||
// (uint)CollisionFilterGroups.LinksetFilter, (uint)CollisionFilterGroups.LinksetMask);
|
// (uint)CollisionFilterGroups.LinksetFilter, (uint)CollisionFilterGroups.LinksetMask);
|
||||||
DetailLog("{0},BSLinksetConstraint.RecomputeLinksetConstraints,set,rBody={1},linksetMass={2}",
|
DetailLog("{0},BSLinksetConstraint.RecomputeLinksetConstraints,set,rBody={1},linksetMass={2}",
|
||||||
|
|
|
@ -1472,7 +1472,7 @@ public sealed class BSScene : PhysicsScene, IPhysicsParameters
|
||||||
public void DetailLog(string msg, params Object[] args)
|
public void DetailLog(string msg, params Object[] args)
|
||||||
{
|
{
|
||||||
PhysicsLogging.Write(msg, args);
|
PhysicsLogging.Write(msg, args);
|
||||||
// Add the Flush() if debugging crashes to get all the messages written out.
|
// Add the Flush() if debugging crashes. Gets all the messages written out.
|
||||||
PhysicsLogging.Flush();
|
PhysicsLogging.Flush();
|
||||||
}
|
}
|
||||||
// Used to fill in the LocalID when there isn't one. It's the correct number of characters.
|
// Used to fill in the LocalID when there isn't one. It's the correct number of characters.
|
||||||
|
|
|
@ -48,6 +48,7 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
public IntPtr ptr;
|
public IntPtr ptr;
|
||||||
public int referenceCount;
|
public int referenceCount;
|
||||||
public DateTime lastReferenced;
|
public DateTime lastReferenced;
|
||||||
|
public UInt64 shapeKey;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Description of a hull.
|
// Description of a hull.
|
||||||
|
@ -57,6 +58,7 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
public IntPtr ptr;
|
public IntPtr ptr;
|
||||||
public int referenceCount;
|
public int referenceCount;
|
||||||
public DateTime lastReferenced;
|
public DateTime lastReferenced;
|
||||||
|
public UInt64 shapeKey;
|
||||||
}
|
}
|
||||||
|
|
||||||
// The sharable set of meshes and hulls. Indexed by their shape hash.
|
// The sharable set of meshes and hulls. Indexed by their shape hash.
|
||||||
|
@ -116,7 +118,7 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Track another user of a body
|
// Track another user of a body.
|
||||||
// We presume the caller has allocated the body.
|
// We presume the caller has allocated the body.
|
||||||
// Bodies only have one user so the body is just put into the world if not already there.
|
// Bodies only have one user so the body is just put into the world if not already there.
|
||||||
public void ReferenceBody(BulletBody body, bool inTaintTime)
|
public void ReferenceBody(BulletBody body, bool inTaintTime)
|
||||||
|
@ -146,13 +148,16 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
{
|
{
|
||||||
PhysicsScene.TaintedObject(inTaintTime, "BSShapeCollection.DereferenceBody", delegate()
|
PhysicsScene.TaintedObject(inTaintTime, "BSShapeCollection.DereferenceBody", delegate()
|
||||||
{
|
{
|
||||||
DetailLog("{0},BSShapeCollection.DereferenceBody,DestroyingBody. ptr={1}, inTaintTime={2}",
|
DetailLog("{0},BSShapeCollection.DereferenceBody,DestroyingBody,body={1},inTaintTime={2}",
|
||||||
body.ID, body.ptr.ToString("X"), inTaintTime);
|
body.ID, body, inTaintTime);
|
||||||
// If the caller needs to know the old body is going away, pass the event up.
|
// If the caller needs to know the old body is going away, pass the event up.
|
||||||
if (bodyCallback != null) bodyCallback(body);
|
if (bodyCallback != null) bodyCallback(body);
|
||||||
|
|
||||||
// It may have already been removed from the world in which case the next is a NOOP.
|
if (BulletSimAPI.IsInWorld2(body.ptr))
|
||||||
BulletSimAPI.RemoveObjectFromWorld2(PhysicsScene.World.ptr, body.ptr);
|
{
|
||||||
|
BulletSimAPI.RemoveObjectFromWorld2(PhysicsScene.World.ptr, body.ptr);
|
||||||
|
DetailLog("{0},BSShapeCollection.DereferenceBody,removingFromWorld. Body={1}", body.ID, body);
|
||||||
|
}
|
||||||
|
|
||||||
// Zero any reference to the shape so it is not freed when the body is deleted.
|
// Zero any reference to the shape so it is not freed when the body is deleted.
|
||||||
BulletSimAPI.SetCollisionShape2(PhysicsScene.World.ptr, body.ptr, IntPtr.Zero);
|
BulletSimAPI.SetCollisionShape2(PhysicsScene.World.ptr, body.ptr, IntPtr.Zero);
|
||||||
|
@ -185,6 +190,7 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
{
|
{
|
||||||
// This is a new reference to a mesh
|
// This is a new reference to a mesh
|
||||||
meshDesc.ptr = shape.ptr;
|
meshDesc.ptr = shape.ptr;
|
||||||
|
meshDesc.shapeKey = shape.shapeKey;
|
||||||
// We keep a reference to the underlying IMesh data so a hull can be built
|
// We keep a reference to the underlying IMesh data so a hull can be built
|
||||||
meshDesc.referenceCount = 1;
|
meshDesc.referenceCount = 1;
|
||||||
DetailLog("{0},BSShapeCollection.ReferenceShape,newMesh,key={1},cnt={2}",
|
DetailLog("{0},BSShapeCollection.ReferenceShape,newMesh,key={1},cnt={2}",
|
||||||
|
@ -207,6 +213,7 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
{
|
{
|
||||||
// This is a new reference to a hull
|
// This is a new reference to a hull
|
||||||
hullDesc.ptr = shape.ptr;
|
hullDesc.ptr = shape.ptr;
|
||||||
|
hullDesc.shapeKey = shape.shapeKey;
|
||||||
hullDesc.referenceCount = 1;
|
hullDesc.referenceCount = 1;
|
||||||
DetailLog("{0},BSShapeCollection.ReferenceShape,newHull,key={1},cnt={2}",
|
DetailLog("{0},BSShapeCollection.ReferenceShape,newHull,key={1},cnt={2}",
|
||||||
BSScene.DetailLogZero, shape.shapeKey.ToString("X"), hullDesc.referenceCount);
|
BSScene.DetailLogZero, shape.shapeKey.ToString("X"), hullDesc.referenceCount);
|
||||||
|
@ -306,7 +313,7 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
|
|
||||||
// Remove a reference to a compound shape.
|
// Remove a reference to a compound shape.
|
||||||
// Taking a compound shape apart is a little tricky because if you just delete the
|
// Taking a compound shape apart is a little tricky because if you just delete the
|
||||||
// physical object, it will free all the underlying children. We can't do that because
|
// physical shape, it will free all the underlying children. We can't do that because
|
||||||
// they could be shared. So, this removes each of the children from the compound and
|
// they could be shared. So, this removes each of the children from the compound and
|
||||||
// dereferences them separately before destroying the compound collision object itself.
|
// dereferences them separately before destroying the compound collision object itself.
|
||||||
// Called at taint-time.
|
// Called at taint-time.
|
||||||
|
@ -335,22 +342,53 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
|
|
||||||
// Sometimes we have a pointer to a collision shape but don't know what type it is.
|
// Sometimes we have a pointer to a collision shape but don't know what type it is.
|
||||||
// Figure out type and call the correct dereference routine.
|
// Figure out type and call the correct dereference routine.
|
||||||
// This is coming from a compound shape that we created so we know it is either native or mesh.
|
|
||||||
// Called at taint-time.
|
// Called at taint-time.
|
||||||
private void DereferenceAnonCollisionShape(IntPtr cShape)
|
private void DereferenceAnonCollisionShape(IntPtr cShape)
|
||||||
{
|
{
|
||||||
BulletShape shapeInfo = new BulletShape(cShape, ShapeData.PhysicsShapeType.SHAPE_MESH);
|
MeshDesc meshDesc;
|
||||||
if (BulletSimAPI.IsCompound2(cShape))
|
HullDesc hullDesc;
|
||||||
shapeInfo.type = ShapeData.PhysicsShapeType.SHAPE_COMPOUND;
|
|
||||||
|
|
||||||
if (BulletSimAPI.IsNativeShape2(cShape))
|
BulletShape shapeInfo = new BulletShape(cShape);
|
||||||
|
if (TryGetMeshByPtr(cShape, out meshDesc))
|
||||||
{
|
{
|
||||||
shapeInfo.isNativeShape = true;
|
shapeInfo.type = ShapeData.PhysicsShapeType.SHAPE_MESH;
|
||||||
shapeInfo.type = ShapeData.PhysicsShapeType.SHAPE_BOX; // (technically, type doesn't matter)
|
shapeInfo.shapeKey = meshDesc.shapeKey;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (TryGetHullByPtr(cShape, out hullDesc))
|
||||||
|
{
|
||||||
|
shapeInfo.type = ShapeData.PhysicsShapeType.SHAPE_HULL;
|
||||||
|
shapeInfo.shapeKey = hullDesc.shapeKey;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (BulletSimAPI.IsCompound2(cShape))
|
||||||
|
{
|
||||||
|
shapeInfo.type = ShapeData.PhysicsShapeType.SHAPE_COMPOUND;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (BulletSimAPI.IsNativeShape2(cShape))
|
||||||
|
{
|
||||||
|
shapeInfo.isNativeShape = true;
|
||||||
|
shapeInfo.type = ShapeData.PhysicsShapeType.SHAPE_BOX; // (technically, type doesn't matter)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
DetailLog("{0},BSShapeCollection.DereferenceAnonCollisionShape,shape={1}", BSScene.DetailLogZero, shapeInfo);
|
DetailLog("{0},BSShapeCollection.DereferenceAnonCollisionShape,shape={1}", BSScene.DetailLogZero, shapeInfo);
|
||||||
|
|
||||||
DereferenceShape(shapeInfo, true, null);
|
if (shapeInfo.type != ShapeData.PhysicsShapeType.SHAPE_UNKNOWN)
|
||||||
|
{
|
||||||
|
DereferenceShape(shapeInfo, true, null);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
PhysicsScene.Logger.ErrorFormat("{0} Could not decypher shape type. Region={1}, addr={2}",
|
||||||
|
LogHeader, PhysicsScene.RegionName, cShape.ToString("X"));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create the geometry information in Bullet for later use.
|
// Create the geometry information in Bullet for later use.
|
||||||
|
@ -913,6 +951,42 @@ public sealed class BSShapeCollection : IDisposable
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private bool TryGetMeshByPtr(IntPtr addr, out MeshDesc outDesc)
|
||||||
|
{
|
||||||
|
bool ret = false;
|
||||||
|
MeshDesc foundDesc = new MeshDesc();
|
||||||
|
foreach (MeshDesc md in Meshes.Values)
|
||||||
|
{
|
||||||
|
if (md.ptr == addr)
|
||||||
|
{
|
||||||
|
foundDesc = md;
|
||||||
|
ret = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
outDesc = foundDesc;
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
private bool TryGetHullByPtr(IntPtr addr, out HullDesc outDesc)
|
||||||
|
{
|
||||||
|
bool ret = false;
|
||||||
|
HullDesc foundDesc = new HullDesc();
|
||||||
|
foreach (HullDesc hd in Hulls.Values)
|
||||||
|
{
|
||||||
|
if (hd.ptr == addr)
|
||||||
|
{
|
||||||
|
foundDesc = hd;
|
||||||
|
ret = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
outDesc = foundDesc;
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
private void DetailLog(string msg, params Object[] args)
|
private void DetailLog(string msg, params Object[] args)
|
||||||
{
|
{
|
||||||
if (PhysicsScene.PhysicsLogging.Enabled)
|
if (PhysicsScene.PhysicsLogging.Enabled)
|
||||||
|
|
Loading…
Reference in New Issue