From ebb63b55aab98da6d44e82fc0ecfd5d22f245172 Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Thu, 7 Feb 2013 11:53:49 -0800 Subject: [PATCH 1/3] BulletSim: add user setting of friction, density and restitution. --- .../Physics/BulletSPlugin/BSCharacter.cs | 5 +- .../Physics/BulletSPlugin/BSPhysObject.cs | 17 +++- .../Region/Physics/BulletSPlugin/BSPrim.cs | 99 +++++++++++++++---- 3 files changed, 94 insertions(+), 27 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSCharacter.cs b/OpenSim/Region/Physics/BulletSPlugin/BSCharacter.cs index 192bcb5f3a..d694a6a5e7 100644 --- a/OpenSim/Region/Physics/BulletSPlugin/BSCharacter.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSCharacter.cs @@ -749,9 +749,10 @@ public sealed class BSCharacter : BSPhysObject _buoyancy = value; DetailLog("{0},BSCharacter.setForceBuoyancy,taint,buoy={1}", LocalID, _buoyancy); // Buoyancy is faked by changing the gravity applied to the object - float grav = PhysicsScene.Params.gravity * (1f - _buoyancy); + float grav = BSParam.Gravity * (1f - _buoyancy); + Gravity = new OMV.Vector3(0f, 0f, grav); if (PhysBody.HasPhysicalBody) - PhysicsScene.PE.SetGravity(PhysBody, new OMV.Vector3(0f, 0f, grav)); + PhysicsScene.PE.SetGravity(PhysBody, Gravity); } } diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs b/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs index ec25aa927e..0b35f3a31f 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs @@ -78,6 +78,10 @@ public abstract class BSPhysObject : PhysicsActor Name = name; // PhysicsActor also has the name of the object. Someday consolidate. TypeName = typeName; + // Initialize variables kept in base. + GravityModifier = 1.0f; + Gravity = new OMV.Vector3(0f, 0f, BSParam.Gravity); + // We don't have any physical representation yet. PhysBody = new BulletBody(localID); PhysShape = new BulletShape(); @@ -88,8 +92,8 @@ public abstract class BSPhysObject : PhysicsActor LastAssetBuildFailed = false; - // Default material type - Material = MaterialAttributes.Material.Wood; + // Default material type. Also sets Friction, Restitution and Density. + SetMaterial((int)MaterialAttributes.Material.Wood); CollisionCollection = new CollisionEventUpdate(); CollisionsLastTick = CollisionCollection; @@ -122,6 +126,8 @@ public abstract class BSPhysObject : PhysicsActor // 'inWorld' true if the object has already been added to the dynamic world. public abstract void UpdatePhysicalMassProperties(float mass, bool inWorld); + // The gravity being applied to the object. A function of default grav, GravityModifier and Buoyancy. + public virtual OMV.Vector3 Gravity { get; set; } // The last value calculated for the prim's inertia public OMV.Vector3 Inertia { get; set; } @@ -164,15 +170,16 @@ public abstract class BSPhysObject : PhysicsActor public override void SetMaterial(int material) { Material = (MaterialAttributes.Material)material; + MaterialAttributes matAttrib = BSMaterials.GetAttributes(Material, false); + Friction = matAttrib.friction; + Restitution = matAttrib.restitution; + Density = matAttrib.density; } // Stop all physical motion. public abstract void ZeroMotion(bool inTaintTime); public abstract void ZeroAngularMotion(bool inTaintTime); - // Step the vehicle simulation for this object. A NOOP if the vehicle was not configured. - public virtual void StepVehicle(float timeStep) { } - // Update the physical location and motion of the object. Called with data from Bullet. public abstract void UpdateProperties(EntityProperties entprop); diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs index 54bf063add..a86932a10b 100644 --- a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs @@ -55,7 +55,6 @@ public sealed class BSPrim : BSPhysObject private OMV.Vector3 _position; private float _mass; // the mass of this object - private float _density; private OMV.Vector3 _force; private OMV.Vector3 _velocity; private OMV.Vector3 _torque; @@ -64,8 +63,6 @@ public sealed class BSPrim : BSPhysObject private int _physicsActorType; private bool _isPhysical; private bool _flying; - private float _friction; - private float _restitution; private bool _setAlwaysRun; private bool _throttleUpdates; private bool _floatOnWater; @@ -101,12 +98,6 @@ public sealed class BSPrim : BSPhysObject _isPhysical = pisPhysical; _isVolumeDetect = false; - // Someday set default attributes based on the material but, for now, we don't know the prim material yet. - // MaterialAttributes primMat = BSMaterials.GetAttributes(Material, pisPhysical); - _density = PhysicsScene.Params.defaultDensity; - _friction = PhysicsScene.Params.defaultFriction; - _restitution = PhysicsScene.Params.defaultRestitution; - VehicleController = new BSDynamics(PhysicsScene, this); // add vehicleness _mass = CalculateMass(); @@ -457,11 +448,6 @@ public sealed class BSPrim : BSPhysObject { AddObjectToPhysicalWorld(); } - - // Must set gravity after it has been added to the world because, for unknown reasons, - // adding the object resets the object's gravity to world gravity - PhysicsScene.PE.SetGravity(PhysBody, grav); - } } } @@ -469,7 +455,7 @@ public sealed class BSPrim : BSPhysObject // Return what gravity should be set to this very moment public OMV.Vector3 ComputeGravity(float buoyancy) { - OMV.Vector3 ret = PhysicsScene.DefaultGravity; + OMV.Vector3 ret = PhysicsScene.DefaultGravity * GravityModifier; if (!IsStatic) ret *= (1f - buoyancy); @@ -596,6 +582,74 @@ public sealed class BSPrim : BSPhysObject } return; } + public override void SetMaterial(int material) + { + base.SetMaterial(material); + PhysicsScene.TaintedObject("BSPrim.SetMaterial", delegate() + { + UpdatePhysicalParameters(); + }); + } + public override float Friction + { + get { return base.Friction; } + set + { + if (base.Friction != value) + { + base.Friction = value; + PhysicsScene.TaintedObject("BSPrim.setFriction", delegate() + { + UpdatePhysicalParameters(); + }); + } + } + } + public override float Restitution + { + get { return base.Restitution; } + set + { + if (base.Restitution != value) + { + base.Restitution = value; + PhysicsScene.TaintedObject("BSPrim.setRestitution", delegate() + { + UpdatePhysicalParameters(); + }); + } + } + } + public override float Density + { + get { return base.Density; } + set + { + if (base.Density != value) + { + base.Density = value; + PhysicsScene.TaintedObject("BSPrim.setDensity", delegate() + { + UpdatePhysicalParameters(); + }); + } + } + } + public override float GravityModifier + { + get { return base.GravityModifier; } + set + { + if (base.GravityModifier != value) + { + base.GravityModifier = value; + PhysicsScene.TaintedObject("BSPrim.setGravityModifier", delegate() + { + UpdatePhysicalParameters(); + }); + } + } + } public override OMV.Vector3 RawVelocity { get { return _velocity; } @@ -810,8 +864,8 @@ public sealed class BSPrim : BSPhysObject // Set various physical properties so other object interact properly MaterialAttributes matAttrib = BSMaterials.GetAttributes(Material, false); - PhysicsScene.PE.SetFriction(PhysBody, matAttrib.friction); - PhysicsScene.PE.SetRestitution(PhysBody, matAttrib.restitution); + PhysicsScene.PE.SetFriction(PhysBody, Friction); + PhysicsScene.PE.SetRestitution(PhysBody, Restitution); // Mass is zero which disables a bunch of physics stuff in Bullet UpdatePhysicalMassProperties(0f, false); @@ -840,8 +894,8 @@ public sealed class BSPrim : BSPhysObject // Set various physical properties so other object interact properly MaterialAttributes matAttrib = BSMaterials.GetAttributes(Material, true); - PhysicsScene.PE.SetFriction(PhysBody, matAttrib.friction); - PhysicsScene.PE.SetRestitution(PhysBody, matAttrib.restitution); + PhysicsScene.PE.SetFriction(PhysBody, Friction); + PhysicsScene.PE.SetRestitution(PhysBody, Restitution); // per http://www.bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=3382 // Since this can be called multiple times, only zero forces when becoming physical @@ -940,6 +994,11 @@ public sealed class BSPrim : BSPhysObject if (PhysBody.HasPhysicalBody) { PhysicsScene.PE.AddObjectToWorld(PhysicsScene.World, PhysBody); + + // Must set gravity after it has been added to the world because, for unknown reasons, + // adding the object resets the object's gravity to world gravity + OMV.Vector3 grav = ComputeGravity(Buoyancy); + PhysicsScene.PE.SetGravity(PhysBody, grav); } else { @@ -1581,7 +1640,7 @@ public sealed class BSPrim : BSPhysObject profileEnd = 1.0f - (float)BaseShape.ProfileEnd * 2.0e-5f; volume *= (profileEnd - profileBegin); - returnMass = _density * volume; + returnMass = Density * volume; /* Comment out code that computes the mass of the linkset. That is done in the Linkset class. if (IsRootOfLinkset) From b545e131846f38cc96757d5c4456c1ee8e7abe75 Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Thu, 7 Feb 2013 14:44:12 -0800 Subject: [PATCH 2/3] BulletSim: fix exceptions caused by setting physical properties before the prim body is initialized. --- OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs index a86932a10b..38adb72d63 100644 --- a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs @@ -587,7 +587,8 @@ public sealed class BSPrim : BSPhysObject base.SetMaterial(material); PhysicsScene.TaintedObject("BSPrim.SetMaterial", delegate() { - UpdatePhysicalParameters(); + if (PhysBody.HasPhysicalBody) + UpdatePhysicalParameters(); }); } public override float Friction @@ -600,7 +601,8 @@ public sealed class BSPrim : BSPhysObject base.Friction = value; PhysicsScene.TaintedObject("BSPrim.setFriction", delegate() { - UpdatePhysicalParameters(); + if (PhysBody.HasPhysicalBody) + UpdatePhysicalParameters(); }); } } @@ -615,7 +617,8 @@ public sealed class BSPrim : BSPhysObject base.Restitution = value; PhysicsScene.TaintedObject("BSPrim.setRestitution", delegate() { - UpdatePhysicalParameters(); + if (PhysBody.HasPhysicalBody) + UpdatePhysicalParameters(); }); } } @@ -630,7 +633,8 @@ public sealed class BSPrim : BSPhysObject base.Density = value; PhysicsScene.TaintedObject("BSPrim.setDensity", delegate() { - UpdatePhysicalParameters(); + if (PhysBody.HasPhysicalBody) + UpdatePhysicalParameters(); }); } } @@ -645,7 +649,8 @@ public sealed class BSPrim : BSPhysObject base.GravityModifier = value; PhysicsScene.TaintedObject("BSPrim.setGravityModifier", delegate() { - UpdatePhysicalParameters(); + if (PhysBody.HasPhysicalBody) + UpdatePhysicalParameters(); }); } } From 913965256fecd4e25e06fe374fa5d8b8712a3b15 Mon Sep 17 00:00:00 2001 From: Robert Adams Date: Thu, 7 Feb 2013 17:05:40 -0800 Subject: [PATCH 3/3] BulletSim: Adapt BulletSim to the newer physical properties. Viewer dialog setting of friction, restitution, ... working. --- .../Physics/BulletSPlugin/BSPhysObject.cs | 4 +- .../Region/Physics/BulletSPlugin/BSPrim.cs | 54 +++++++++---------- 2 files changed, 28 insertions(+), 30 deletions(-) diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs b/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs index 0b35f3a31f..0d8bb0304c 100755 --- a/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSPhysObject.cs @@ -79,7 +79,7 @@ public abstract class BSPhysObject : PhysicsActor TypeName = typeName; // Initialize variables kept in base. - GravityModifier = 1.0f; + GravModifier = 1.0f; Gravity = new OMV.Vector3(0f, 0f, BSParam.Gravity); // We don't have any physical representation yet. @@ -170,6 +170,8 @@ public abstract class BSPhysObject : PhysicsActor public override void SetMaterial(int material) { Material = (MaterialAttributes.Material)material; + + // Setting the material sets the material attributes also. MaterialAttributes matAttrib = BSMaterials.GetAttributes(Material, false); Friction = matAttrib.friction; Restitution = matAttrib.restitution; diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs index 38adb72d63..85c2627f1c 100644 --- a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs +++ b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs @@ -423,8 +423,6 @@ public sealed class BSPrim : BSPhysObject } else { - OMV.Vector3 grav = ComputeGravity(Buoyancy); - if (inWorld) { // Changing interesting properties doesn't change proxy and collision cache @@ -434,15 +432,15 @@ public sealed class BSPrim : BSPhysObject } // The computation of mass props requires gravity to be set on the object. - PhysicsScene.PE.SetGravity(PhysBody, grav); + Gravity = ComputeGravity(Buoyancy); + PhysicsScene.PE.SetGravity(PhysBody, Gravity); Inertia = PhysicsScene.PE.CalculateLocalInertia(PhysShape, physMass); PhysicsScene.PE.SetMassProps(PhysBody, physMass, Inertia); PhysicsScene.PE.UpdateInertiaTensor(PhysBody); - // center of mass is at the zero of the object - // DEBUG DEBUG PhysicsScene.PE.SetCenterOfMassByPosRot(PhysBody, ForcePosition, ForceOrientation); - DetailLog("{0},BSPrim.UpdateMassProperties,mass={1},localInertia={2},grav={3},inWorld={4}", LocalID, physMass, Inertia, grav, inWorld); + DetailLog("{0},BSPrim.UpdateMassProperties,mass={1},localInertia={2},grav={3},inWorld={4}", + LocalID, physMass, Inertia, Gravity, inWorld); if (inWorld) { @@ -455,10 +453,13 @@ public sealed class BSPrim : BSPhysObject // Return what gravity should be set to this very moment public OMV.Vector3 ComputeGravity(float buoyancy) { - OMV.Vector3 ret = PhysicsScene.DefaultGravity * GravityModifier; + OMV.Vector3 ret = PhysicsScene.DefaultGravity; if (!IsStatic) + { ret *= (1f - buoyancy); + ret *= GravModifier; + } return ret; } @@ -587,8 +588,7 @@ public sealed class BSPrim : BSPhysObject base.SetMaterial(material); PhysicsScene.TaintedObject("BSPrim.SetMaterial", delegate() { - if (PhysBody.HasPhysicalBody) - UpdatePhysicalParameters(); + UpdatePhysicalParameters(); }); } public override float Friction @@ -601,8 +601,7 @@ public sealed class BSPrim : BSPhysObject base.Friction = value; PhysicsScene.TaintedObject("BSPrim.setFriction", delegate() { - if (PhysBody.HasPhysicalBody) - UpdatePhysicalParameters(); + UpdatePhysicalParameters(); }); } } @@ -617,8 +616,7 @@ public sealed class BSPrim : BSPhysObject base.Restitution = value; PhysicsScene.TaintedObject("BSPrim.setRestitution", delegate() { - if (PhysBody.HasPhysicalBody) - UpdatePhysicalParameters(); + UpdatePhysicalParameters(); }); } } @@ -633,24 +631,22 @@ public sealed class BSPrim : BSPhysObject base.Density = value; PhysicsScene.TaintedObject("BSPrim.setDensity", delegate() { - if (PhysBody.HasPhysicalBody) - UpdatePhysicalParameters(); + UpdatePhysicalParameters(); }); } } } - public override float GravityModifier + public override float GravModifier { - get { return base.GravityModifier; } + get { return base.GravModifier; } set { - if (base.GravityModifier != value) + if (base.GravModifier != value) { - base.GravityModifier = value; + base.GravModifier = value; PhysicsScene.TaintedObject("BSPrim.setGravityModifier", delegate() { - if (PhysBody.HasPhysicalBody) - UpdatePhysicalParameters(); + UpdatePhysicalParameters(); }); } } @@ -820,7 +816,12 @@ public sealed class BSPrim : BSPhysObject // collisionEvents: whether this object returns collision events public void UpdatePhysicalParameters() { - // DetailLog("{0},BSPrim.UpdatePhysicalParameters,entry,body={1},shape={2}", LocalID, BSBody, BSShape); + if (!PhysBody.HasPhysicalBody) + { + // This would only happen if updates are called for during initialization when the body is not set up yet. + DetailLog("{0},BSPrim.UpdatePhysicalParameters,taint,calledWithNoPhysBody", LocalID); + return; + } // Mangling all the physical properties requires the object not be in the physical world. // This is a NOOP if the object is not in the world (BulletSim and Bullet ignore objects not found). @@ -898,9 +899,9 @@ public sealed class BSPrim : BSPhysObject CurrentCollisionFlags = PhysicsScene.PE.RemoveFromCollisionFlags(PhysBody, CollisionFlags.CF_STATIC_OBJECT); // Set various physical properties so other object interact properly - MaterialAttributes matAttrib = BSMaterials.GetAttributes(Material, true); PhysicsScene.PE.SetFriction(PhysBody, Friction); PhysicsScene.PE.SetRestitution(PhysBody, Restitution); + // DetailLog("{0},BSPrim.MakeDynamic,frict={1},rest={2}", LocalID, Friction, Restitution); // per http://www.bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=3382 // Since this can be called multiple times, only zero forces when becoming physical @@ -999,16 +1000,11 @@ public sealed class BSPrim : BSPhysObject if (PhysBody.HasPhysicalBody) { PhysicsScene.PE.AddObjectToWorld(PhysicsScene.World, PhysBody); - - // Must set gravity after it has been added to the world because, for unknown reasons, - // adding the object resets the object's gravity to world gravity - OMV.Vector3 grav = ComputeGravity(Buoyancy); - PhysicsScene.PE.SetGravity(PhysBody, grav); } else { m_log.ErrorFormat("{0} Attempt to add physical object without body. id={1}", LogHeader, LocalID); - DetailLog("{0},BSPrim.UpdatePhysicalParameters,addObjectWithoutBody,cType={1}", LocalID, PhysBody.collisionType); + DetailLog("{0},BSPrim.AddObjectToPhysicalWorld,addObjectWithoutBody,cType={1}", LocalID, PhysBody.collisionType); } }