aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs
diff options
context:
space:
mode:
authorRobert Adams2013-01-09 16:27:06 -0800
committerRobert Adams2013-01-11 16:46:53 -0800
commit7e58bbaac6c5ebb5bf0d6a7a875a8316ac264128 (patch)
treebc1f787d149ec52abdc9fe3876d583f5c949d191 /OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs
parentBulletSim: remove double application of buoyancy. Centralize computation of b... (diff)
downloadopensim-SC-7e58bbaac6c5ebb5bf0d6a7a875a8316ac264128.zip
opensim-SC-7e58bbaac6c5ebb5bf0d6a7a875a8316ac264128.tar.gz
opensim-SC-7e58bbaac6c5ebb5bf0d6a7a875a8316ac264128.tar.bz2
opensim-SC-7e58bbaac6c5ebb5bf0d6a7a875a8316ac264128.tar.xz
BulletSim: Redo linear function coding so they can better interact. New algorithm for limitMotorUp that relies on going up when not colliding rather than distance from ground. Add parameter for turning on and off embedded source vehicle debugging.
Diffstat (limited to 'OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs')
-rw-r--r--OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs147
1 files changed, 85 insertions, 62 deletions
diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs b/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs
index 47f2759..2e44ab6 100644
--- a/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs
+++ b/OpenSim/Region/Physics/BulletSPlugin/BSDynamics.cs
@@ -134,6 +134,23 @@ namespace OpenSim.Region.Physics.BulletSPlugin
134 PhysicsScene = myScene; 134 PhysicsScene = myScene;
135 Prim = myPrim; 135 Prim = myPrim;
136 Type = Vehicle.TYPE_NONE; 136 Type = Vehicle.TYPE_NONE;
137 SetupVehicleDebugging();
138 }
139
140 // Stopgap debugging enablement. Allows source level debugging but still checking
141 // in changes by making enablement of debugging flags from INI file.
142 public void SetupVehicleDebugging()
143 {
144 enableAngularVerticalAttraction = true;
145 enableAngularDeflection = true;
146 enableAngularBanking = true;
147 if (BSParam.VehicleDebuggingEnabled != ConfigurationParameters.numericFalse)
148 {
149 enableAngularVerticalAttraction = false;
150 enableAngularDeflection = false;
151 enableAngularBanking = false;
152 VDetailLog("{0},BSDynamics.SetupVehicleDebugging,settingDebugMode");
153 }
137 } 154 }
138 155
139 // Return 'true' if this vehicle is doing vehicle things 156 // Return 'true' if this vehicle is doing vehicle things
@@ -576,8 +593,8 @@ namespace OpenSim.Region.Physics.BulletSPlugin
576 // Vehicles report collision events so we know when it's on the ground 593 // Vehicles report collision events so we know when it's on the ground
577 PhysicsScene.PE.AddToCollisionFlags(Prim.PhysBody, CollisionFlags.BS_VEHICLE_COLLISIONS); 594 PhysicsScene.PE.AddToCollisionFlags(Prim.PhysBody, CollisionFlags.BS_VEHICLE_COLLISIONS);
578 595
579 Vector3 localInertia = PhysicsScene.PE.CalculateLocalInertia(Prim.PhysShape, m_vehicleMass); 596 Prim.Inertia = PhysicsScene.PE.CalculateLocalInertia(Prim.PhysShape, m_vehicleMass);
580 PhysicsScene.PE.SetMassProps(Prim.PhysBody, m_vehicleMass, localInertia); 597 PhysicsScene.PE.SetMassProps(Prim.PhysBody, m_vehicleMass, Prim.Inertia);
581 PhysicsScene.PE.UpdateInertiaTensor(Prim.PhysBody); 598 PhysicsScene.PE.UpdateInertiaTensor(Prim.PhysBody);
582 599
583 // Set the gravity for the vehicle depending on the buoyancy 600 // Set the gravity for the vehicle depending on the buoyancy
@@ -586,7 +603,7 @@ namespace OpenSim.Region.Physics.BulletSPlugin
586 PhysicsScene.PE.SetGravity(Prim.PhysBody, grav); 603 PhysicsScene.PE.SetGravity(Prim.PhysBody, grav);
587 604
588 VDetailLog("{0},BSDynamics.Refresh,mass={1},frict={2},inert={3},aDamp={4},grav={5}", 605 VDetailLog("{0},BSDynamics.Refresh,mass={1},frict={2},inert={3},aDamp={4},grav={5}",
589 Prim.LocalID, m_vehicleMass, friction, localInertia, angularDamping, grav); 606 Prim.LocalID, m_vehicleMass, friction, Prim.Inertia, angularDamping, grav);
590 } 607 }
591 else 608 else
592 { 609 {
@@ -863,69 +880,47 @@ namespace OpenSim.Region.Physics.BulletSPlugin
863 // The movement computed in the linear motor is relative to the vehicle 880 // The movement computed in the linear motor is relative to the vehicle
864 // coordinates. Rotate the movement to world coordinates. 881 // coordinates. Rotate the movement to world coordinates.
865 linearMotorContribution *= VehicleOrientation; 882 linearMotorContribution *= VehicleOrientation;
866 // All the contributions after this are world relative (mostly Z modifications)
867 883
868 Vector3 terrainHeightContribution = ComputeLinearTerrainHeightCorrection(pTimestep); 884 VehicleVelocity = linearMotorContribution;
869 885
870 Vector3 hoverContribution = ComputeLinearHover(pTimestep); 886 ComputeLinearTerrainHeightCorrection(pTimestep);
871 887
872 ComputeLinearBlockingEndPoint(pTimestep); 888 ComputeLinearHover(pTimestep);
873
874 Vector3 limitMotorUpContribution = ComputeLinearMotorUp(pTimestep);
875 889
876 // ================================================================== 890 ComputeLinearBlockingEndPoint(pTimestep);
877 // Select between velocities and forces. Forces will happen over time and
878 // will take into account inertia, collisions, etc. Velocities are
879 // raw updates to the velocity of the vehicle.
880 Vector3 newVelocity = linearMotorContribution
881 + terrainHeightContribution
882 + hoverContribution
883 + limitMotorUpContribution;
884 891
885 Vector3 newForce = Vector3.Zero; 892 ComputeLinearMotorUp(pTimestep);
886 893
887 // If not changing some axis, reduce out velocity 894 // If not changing some axis, reduce out velocity
888 if ((m_flags & (VehicleFlag.NO_X)) != 0) 895 if ((m_flags & (VehicleFlag.NO_X | VehicleFlag.NO_Y | VehicleFlag.NO_Z)) != 0)
889 newVelocity.X = 0; 896 {
890 if ((m_flags & (VehicleFlag.NO_Y)) != 0) 897 Vector3 vel = VehicleVelocity;
891 newVelocity.Y = 0; 898 if ((m_flags & (VehicleFlag.NO_X)) != 0)
892 if ((m_flags & (VehicleFlag.NO_Z)) != 0) 899 vel.X = 0;
893 newVelocity.Z = 0; 900 if ((m_flags & (VehicleFlag.NO_Y)) != 0)
901 vel.Y = 0;
902 if ((m_flags & (VehicleFlag.NO_Z)) != 0)
903 vel.Z = 0;
904 VehicleVelocity = vel;
905 }
894 906
895 // ================================================================== 907 // ==================================================================
896 // Clamp high or low velocities 908 // Clamp high or low velocities
897 float newVelocityLengthSq = newVelocity.LengthSquared(); 909 float newVelocityLengthSq = VehicleVelocity.LengthSquared();
898 if (newVelocityLengthSq > 1000f) 910 if (newVelocityLengthSq > 1000f)
899 { 911 {
900 newVelocity /= newVelocity.Length(); 912 VehicleVelocity /= VehicleVelocity.Length();
901 newVelocity *= 1000f; 913 VehicleVelocity *= 1000f;
902 } 914 }
903 else if (newVelocityLengthSq < 0.001f) 915 else if (newVelocityLengthSq < 0.001f)
904 newVelocity = Vector3.Zero; 916 VehicleVelocity = Vector3.Zero;
905
906 // ==================================================================
907 // Stuff new linear velocity into the vehicle.
908 // Since the velocity is just being set, it is not scaled by pTimeStep. Bullet will do that for us.
909 // Also not scaled by mass since this is a super-physical setting of velocity.
910 VehicleVelocity = newVelocity;
911
912 // Other linear forces are applied as forces.
913 Vector3 totalDownForce = newForce * m_vehicleMass;
914 if (!totalDownForce.ApproxEquals(Vector3.Zero, 0.01f))
915 {
916 VehicleAddForce(totalDownForce);
917 }
918 917
919 VDetailLog("{0}, MoveLinear,done,linContrib={1},terrContrib={2},hoverContrib={3},limitContrib={4},totDown={5},isColl={6},newVel={7}", 918 VDetailLog("{0}, MoveLinear,done,isColl={1},newVel={2}", Prim.LocalID, Prim.IsColliding, VehicleVelocity );
920 Prim.LocalID,
921 linearMotorContribution, terrainHeightContribution, hoverContribution, limitMotorUpContribution,
922 totalDownForce, Prim.IsColliding, newVelocity );
923 919
924 } // end MoveLinear() 920 } // end MoveLinear()
925 921
926 public Vector3 ComputeLinearTerrainHeightCorrection(float pTimestep) 922 public void ComputeLinearTerrainHeightCorrection(float pTimestep)
927 { 923 {
928 Vector3 ret = Vector3.Zero;
929 // If below the terrain, move us above the ground a little. 924 // If below the terrain, move us above the ground a little.
930 // TODO: Consider taking the rotated size of the object or possibly casting a ray. 925 // TODO: Consider taking the rotated size of the object or possibly casting a ray.
931 if (VehiclePosition.Z < GetTerrainHeight(VehiclePosition)) 926 if (VehiclePosition.Z < GetTerrainHeight(VehiclePosition))
@@ -937,13 +932,10 @@ namespace OpenSim.Region.Physics.BulletSPlugin
937 VDetailLog("{0}, MoveLinear,terrainHeight,terrainHeight={1},pos={2}", 932 VDetailLog("{0}, MoveLinear,terrainHeight,terrainHeight={1},pos={2}",
938 Prim.LocalID, GetTerrainHeight(VehiclePosition), VehiclePosition); 933 Prim.LocalID, GetTerrainHeight(VehiclePosition), VehiclePosition);
939 } 934 }
940 return ret;
941 } 935 }
942 936
943 public Vector3 ComputeLinearHover(float pTimestep) 937 public void ComputeLinearHover(float pTimestep)
944 { 938 {
945 Vector3 ret = Vector3.Zero;
946
947 // m_VhoverEfficiency: 0=bouncy, 1=totally damped 939 // m_VhoverEfficiency: 0=bouncy, 1=totally damped
948 // m_VhoverTimescale: time to achieve height 940 // m_VhoverTimescale: time to achieve height
949 if ((m_flags & (VehicleFlag.HOVER_WATER_ONLY | VehicleFlag.HOVER_TERRAIN_ONLY | VehicleFlag.HOVER_GLOBAL_HEIGHT)) != 0) 941 if ((m_flags & (VehicleFlag.HOVER_WATER_ONLY | VehicleFlag.HOVER_TERRAIN_ONLY | VehicleFlag.HOVER_GLOBAL_HEIGHT)) != 0)
@@ -976,6 +968,8 @@ namespace OpenSim.Region.Physics.BulletSPlugin
976 Vector3 pos = VehiclePosition; 968 Vector3 pos = VehiclePosition;
977 pos.Z = m_VhoverTargetHeight; 969 pos.Z = m_VhoverTargetHeight;
978 VehiclePosition = pos; 970 VehiclePosition = pos;
971
972 VDetailLog("{0}, MoveLinear,hover,pos={1},lockHoverHeight", Prim.LocalID, pos);
979 } 973 }
980 } 974 }
981 else 975 else
@@ -985,14 +979,15 @@ namespace OpenSim.Region.Physics.BulletSPlugin
985 float verticalCorrectionVelocity = verticalError / m_VhoverTimescale; 979 float verticalCorrectionVelocity = verticalError / m_VhoverTimescale;
986 980
987 // TODO: implement m_VhoverEfficiency correctly 981 // TODO: implement m_VhoverEfficiency correctly
988 ret = new Vector3(0f, 0f, verticalCorrectionVelocity); 982 VehicleVelocity += new Vector3(0f, 0f, verticalCorrectionVelocity);
983
984 VDetailLog("{0}, MoveLinear,hover,pos={1},eff={2},hoverTS={3},height={4},target={5},err={6},corrVel={7}",
985 Prim.LocalID, VehiclePosition, m_VhoverEfficiency,
986 m_VhoverTimescale, m_VhoverHeight, m_VhoverTargetHeight,
987 verticalError, verticalCorrectionVelocity);
989 } 988 }
990 989
991 VDetailLog("{0}, MoveLinear,hover,pos={1},eff={2},hoverTS={3},height={4},target={5},ret={6}",
992 Prim.LocalID, VehiclePosition, m_VhoverEfficiency, m_VhoverTimescale, m_VhoverHeight, m_VhoverTargetHeight, ret);
993 } 990 }
994
995 return ret;
996 } 991 }
997 992
998 public bool ComputeLinearBlockingEndPoint(float pTimestep) 993 public bool ComputeLinearBlockingEndPoint(float pTimestep)
@@ -1047,30 +1042,58 @@ namespace OpenSim.Region.Physics.BulletSPlugin
1047 // TODO: this code is wrong. Also, what should it do for boats (height from water)? 1042 // TODO: this code is wrong. Also, what should it do for boats (height from water)?
1048 // This is just using the ground and a general collision check. Should really be using 1043 // This is just using the ground and a general collision check. Should really be using
1049 // a downward raycast to find what is below. 1044 // a downward raycast to find what is below.
1050 public Vector3 ComputeLinearMotorUp(float pTimestep) 1045 public void ComputeLinearMotorUp(float pTimestep)
1051 { 1046 {
1052 Vector3 ret = Vector3.Zero; 1047 Vector3 ret = Vector3.Zero;
1053 float distanceAboveGround = 0f;
1054 1048
1055 if ((m_flags & (VehicleFlag.LIMIT_MOTOR_UP)) != 0) 1049 if ((m_flags & (VehicleFlag.LIMIT_MOTOR_UP)) != 0)
1056 { 1050 {
1051 // This code tries to decide if the object is not on the ground and then pushing down
1052 /*
1057 float targetHeight = Type == Vehicle.TYPE_BOAT ? GetWaterLevel(VehiclePosition) : GetTerrainHeight(VehiclePosition); 1053 float targetHeight = Type == Vehicle.TYPE_BOAT ? GetWaterLevel(VehiclePosition) : GetTerrainHeight(VehiclePosition);
1058 distanceAboveGround = VehiclePosition.Z - targetHeight; 1054 distanceAboveGround = VehiclePosition.Z - targetHeight;
1059 // Not colliding if the vehicle is off the ground 1055 // Not colliding if the vehicle is off the ground
1060 if (!Prim.IsColliding) 1056 if (!Prim.IsColliding)
1061 { 1057 {
1062 // downForce = new Vector3(0, 0, -distanceAboveGround / m_bankingTimescale); 1058 // downForce = new Vector3(0, 0, -distanceAboveGround / m_bankingTimescale);
1063 ret = new Vector3(0, 0, -distanceAboveGround); 1059 VehicleVelocity += new Vector3(0, 0, -distanceAboveGround);
1064 } 1060 }
1065 // TODO: this calculation is wrong. From the description at 1061 // TODO: this calculation is wrong. From the description at
1066 // (http://wiki.secondlife.com/wiki/Category:LSL_Vehicle), the downForce 1062 // (http://wiki.secondlife.com/wiki/Category:LSL_Vehicle), the downForce
1067 // has a decay factor. This says this force should 1063 // has a decay factor. This says this force should
1068 // be computed with a motor. 1064 // be computed with a motor.
1069 // TODO: add interaction with banking. 1065 // TODO: add interaction with banking.
1070 } 1066 VDetailLog("{0}, MoveLinear,limitMotorUp,distAbove={1},colliding={2},ret={3}",
1071 VDetailLog("{0}, MoveLinear,limitMotorUp,distAbove={1},colliding={2},ret={3}",
1072 Prim.LocalID, distanceAboveGround, Prim.IsColliding, ret); 1067 Prim.LocalID, distanceAboveGround, Prim.IsColliding, ret);
1073 return ret; 1068 */
1069
1070 // Another approach is to measure if we're going up. If going up and not colliding,
1071 // the vehicle is in the air. Fix that by pushing down.
1072 if (!Prim.IsColliding && VehicleVelocity.Z > 0.1)
1073 {
1074 // Get rid of any of the velocity vector that is pushing us up.
1075 VehicleVelocity += new Vector3(0, 0, -VehicleVelocity.Z);
1076
1077 // If we're pointed up into the air, we should nose down
1078 Vector3 pointingDirection = Vector3.UnitX * VehicleOrientation;
1079 // The rotation around the Y axis is pitch up or down
1080 if (pointingDirection.Y > 0.01f)
1081 {
1082 float angularCorrectionForce = -(float)Math.Asin(pointingDirection.Y);
1083 Vector3 angularCorrectionVector = new Vector3(0f, angularCorrectionForce, 0f);
1084 // Rotate into world coordinates and apply to vehicle
1085 angularCorrectionVector *= VehicleOrientation;
1086 VehicleAddAngularForce(angularCorrectionVector);
1087 VDetailLog("{0}, MoveLinear,limitMotorUp,newVel={1},pntDir={2},corrFrc={3},aCorr={4}",
1088 Prim.LocalID, VehicleVelocity, pointingDirection, angularCorrectionForce, angularCorrectionVector);
1089 }
1090 else
1091 {
1092 VDetailLog("{0}, MoveLinear,limitMotorUp,newVel={1},pntDir={2}",
1093 Prim.LocalID, VehicleVelocity, pointingDirection);
1094 }
1095 }
1096 }
1074 } 1097 }
1075 1098
1076 // ======================================================================= 1099 // =======================================================================