aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Physics/OdePlugin/ODECharacter.cs
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--OpenSim/Region/Physics/OdePlugin/ODECharacter.cs147
1 files changed, 57 insertions, 90 deletions
diff --git a/OpenSim/Region/Physics/OdePlugin/ODECharacter.cs b/OpenSim/Region/Physics/OdePlugin/ODECharacter.cs
index 4cc8c59..92927e4 100644
--- a/OpenSim/Region/Physics/OdePlugin/ODECharacter.cs
+++ b/OpenSim/Region/Physics/OdePlugin/ODECharacter.cs
@@ -39,7 +39,6 @@ namespace OpenSim.Region.Physics.OdePlugin
39 /// <summary> 39 /// <summary>
40 /// Various properties that ODE uses for AMotors but isn't exposed in ODE.NET so we must define them ourselves. 40 /// Various properties that ODE uses for AMotors but isn't exposed in ODE.NET so we must define them ourselves.
41 /// </summary> 41 /// </summary>
42
43 public enum dParam : int 42 public enum dParam : int
44 { 43 {
45 LowStop = 0, 44 LowStop = 0,
@@ -64,6 +63,7 @@ namespace OpenSim.Region.Physics.OdePlugin
64 StopERP3 = 7 + 512, 63 StopERP3 = 7 + 512,
65 StopCFM3 = 8 + 512 64 StopCFM3 = 8 + 512
66 } 65 }
66
67 public class OdeCharacter : PhysicsActor 67 public class OdeCharacter : PhysicsActor
68 { 68 {
69 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 69 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
@@ -107,9 +107,12 @@ namespace OpenSim.Region.Physics.OdePlugin
107 public bool m_tainted_isPhysical = false; // set when the physical status is tainted (false=not existing in physics engine, true=existing) 107 public bool m_tainted_isPhysical = false; // set when the physical status is tainted (false=not existing in physics engine, true=existing)
108 public float MinimumGroundFlightOffset = 3f; 108 public float MinimumGroundFlightOffset = 3f;
109 109
110 private float m_tainted_CAPSULE_LENGTH; // set when the capsule length changes. 110 private float m_tainted_CAPSULE_LENGTH; // set when the capsule length changes.
111 private float m_tiltMagnitudeWhenProjectedOnXYPlane = 0.1131371f; // used to introduce a fixed tilt because a straight-up capsule falls through terrain, probably a bug in terrain collider
112 111
112 /// <summary>
113 /// Used to introduce a fixed tilt because a straight-up capsule falls through terrain, probably a bug in terrain collider
114 /// </summary>
115 private float m_tiltMagnitudeWhenProjectedOnXYPlane = 0.1131371f;
113 116
114 private float m_buoyancy = 0f; 117 private float m_buoyancy = 0f;
115 118
@@ -891,12 +894,14 @@ namespace OpenSim.Region.Physics.OdePlugin
891 { 894 {
892 } 895 }
893 896
894
895 /// <summary> 897 /// <summary>
896 /// Called from Simulate 898 /// Called from Simulate
897 /// This is the avatar's movement control + PID Controller 899 /// This is the avatar's movement control + PID Controller
898 /// </summary> 900 /// </summary>
899 /// <param name="timeStep"></param> 901 /// <param name="timeStep"></param>
902 /// <param name="defects">
903 /// If there is something wrong with the character (e.g. its position is non-finite)
904 /// then it is added to this list. The ODE structures associated with it are also destroyed.</param>
900 public void Move(float timeStep, List<OdeCharacter> defects) 905 public void Move(float timeStep, List<OdeCharacter> defects)
901 { 906 {
902 // no lock; for now it's only called from within Simulate() 907 // no lock; for now it's only called from within Simulate()
@@ -918,36 +923,12 @@ namespace OpenSim.Region.Physics.OdePlugin
918 923
919 if (!localPos.IsFinite()) 924 if (!localPos.IsFinite())
920 { 925 {
921
922 m_log.Warn("[PHYSICS]: Avatar Position is non-finite!"); 926 m_log.Warn("[PHYSICS]: Avatar Position is non-finite!");
927
923 defects.Add(this); 928 defects.Add(this);
924 // _parent_scene.RemoveCharacter(this); 929 // _parent_scene.RemoveCharacter(this);
925 930
926 // destroy avatar capsule and related ODE data 931 DestroyOdeStructures();
927 if (Amotor != IntPtr.Zero)
928 {
929 // Kill the Amotor
930 d.JointDestroy(Amotor);
931 Amotor = IntPtr.Zero;
932 }
933
934 //kill the Geometry
935 _parent_scene.waitForSpaceUnlock(_parent_scene.space);
936
937 if (Body != IntPtr.Zero)
938 {
939 //kill the body
940 d.BodyDestroy(Body);
941
942 Body = IntPtr.Zero;
943 }
944
945 if (Shell != IntPtr.Zero)
946 {
947 d.GeomDestroy(Shell);
948 _parent_scene.geom_name_map.Remove(Shell);
949 Shell = IntPtr.Zero;
950 }
951 932
952 return; 933 return;
953 } 934 }
@@ -975,6 +956,7 @@ namespace OpenSim.Region.Physics.OdePlugin
975 _zeroFlag = true; 956 _zeroFlag = true;
976 _zeroPosition = d.BodyGetPosition(Body); 957 _zeroPosition = d.BodyGetPosition(Body);
977 } 958 }
959
978 if (m_pidControllerActive) 960 if (m_pidControllerActive)
979 { 961 {
980 // We only want to deactivate the PID Controller if we think we want to have our surrogate 962 // We only want to deactivate the PID Controller if we think we want to have our surrogate
@@ -1005,14 +987,14 @@ namespace OpenSim.Region.Physics.OdePlugin
1005 else if (m_iscolliding && flying) 987 else if (m_iscolliding && flying)
1006 { 988 {
1007 // We're flying and colliding with something 989 // We're flying and colliding with something
1008 vec.X = ((_target_velocity.X/movementdivisor) - vel.X)*(PID_D / 16); 990 vec.X = ((_target_velocity.X / movementdivisor) - vel.X) * (PID_D / 16);
1009 vec.Y = ((_target_velocity.Y/movementdivisor) - vel.Y)*(PID_D / 16); 991 vec.Y = ((_target_velocity.Y / movementdivisor) - vel.Y) * (PID_D / 16);
1010 } 992 }
1011 else if (!m_iscolliding && flying) 993 else if (!m_iscolliding && flying)
1012 { 994 {
1013 // we're in mid air suspended 995 // we're in mid air suspended
1014 vec.X = ((_target_velocity.X / movementdivisor) - vel.X) * (PID_D/6); 996 vec.X = ((_target_velocity.X / movementdivisor) - vel.X) * (PID_D / 6);
1015 vec.Y = ((_target_velocity.Y / movementdivisor) - vel.Y) * (PID_D/6); 997 vec.Y = ((_target_velocity.Y / movementdivisor) - vel.Y) * (PID_D / 6);
1016 } 998 }
1017 999
1018 if (m_iscolliding && !flying && _target_velocity.Z > 0.0f) 1000 if (m_iscolliding && !flying && _target_velocity.Z > 0.0f)
@@ -1023,11 +1005,11 @@ namespace OpenSim.Region.Physics.OdePlugin
1023 vec.Z = (_target_velocity.Z - vel.Z)*PID_D + (_zeroPosition.Z - pos.Z)*PID_P; 1005 vec.Z = (_target_velocity.Z - vel.Z)*PID_D + (_zeroPosition.Z - pos.Z)*PID_P;
1024 if (_target_velocity.X > 0) 1006 if (_target_velocity.X > 0)
1025 { 1007 {
1026 vec.X = ((_target_velocity.X - vel.X)/1.2f)*PID_D; 1008 vec.X = ((_target_velocity.X - vel.X) / 1.2f) * PID_D;
1027 } 1009 }
1028 if (_target_velocity.Y > 0) 1010 if (_target_velocity.Y > 0)
1029 { 1011 {
1030 vec.Y = ((_target_velocity.Y - vel.Y)/1.2f)*PID_D; 1012 vec.Y = ((_target_velocity.Y - vel.Y) / 1.2f) * PID_D;
1031 } 1013 }
1032 } 1014 }
1033 else if (!m_iscolliding && !flying) 1015 else if (!m_iscolliding && !flying)
@@ -1051,9 +1033,10 @@ namespace OpenSim.Region.Physics.OdePlugin
1051 vec.Z = (_target_velocity.Z - vel.Z) * (PID_D); 1033 vec.Z = (_target_velocity.Z - vel.Z) * (PID_D);
1052 } 1034 }
1053 } 1035 }
1036
1054 if (flying) 1037 if (flying)
1055 { 1038 {
1056 vec.Z += ((-1 * _parent_scene.gravityz)*m_mass); 1039 vec.Z += ((-1 * _parent_scene.gravityz) * m_mass);
1057 1040
1058 //Added for auto fly height. Kitto Flora 1041 //Added for auto fly height. Kitto Flora
1059 //d.Vector3 pos = d.BodyGetPosition(Body); 1042 //d.Vector3 pos = d.BodyGetPosition(Body);
@@ -1065,13 +1048,13 @@ namespace OpenSim.Region.Physics.OdePlugin
1065 } 1048 }
1066 // end add Kitto Flora 1049 // end add Kitto Flora
1067 } 1050 }
1051
1068 if (vec.IsFinite()) 1052 if (vec.IsFinite())
1069 { 1053 {
1070 doForce(vec); 1054 doForce(vec);
1055
1071 if (!_zeroFlag) 1056 if (!_zeroFlag)
1072 { 1057 AlignAvatarTiltWithCurrentDirectionOfMovement(vec);
1073 AlignAvatarTiltWithCurrentDirectionOfMovement(vec);
1074 }
1075 } 1058 }
1076 else 1059 else
1077 { 1060 {
@@ -1079,30 +1062,8 @@ namespace OpenSim.Region.Physics.OdePlugin
1079 m_log.Warn("[PHYSICS]: Avatar Position is non-finite!"); 1062 m_log.Warn("[PHYSICS]: Avatar Position is non-finite!");
1080 defects.Add(this); 1063 defects.Add(this);
1081 // _parent_scene.RemoveCharacter(this); 1064 // _parent_scene.RemoveCharacter(this);
1082 // destroy avatar capsule and related ODE data
1083 if (Amotor != IntPtr.Zero)
1084 {
1085 // Kill the Amotor
1086 d.JointDestroy(Amotor);
1087 Amotor = IntPtr.Zero;
1088 }
1089 //kill the Geometry
1090 _parent_scene.waitForSpaceUnlock(_parent_scene.space);
1091 1065
1092 if (Body != IntPtr.Zero) 1066 DestroyOdeStructures();
1093 {
1094 //kill the body
1095 d.BodyDestroy(Body);
1096
1097 Body = IntPtr.Zero;
1098 }
1099
1100 if (Shell != IntPtr.Zero)
1101 {
1102 d.GeomDestroy(Shell);
1103 _parent_scene.geom_name_map.Remove(Shell);
1104 Shell = IntPtr.Zero;
1105 }
1106 } 1067 }
1107 } 1068 }
1108 1069
@@ -1125,7 +1086,6 @@ namespace OpenSim.Region.Physics.OdePlugin
1125 base.RaiseOutOfBounds(_position); // Tells ScenePresence that there's a problem! 1086 base.RaiseOutOfBounds(_position); // Tells ScenePresence that there's a problem!
1126 m_log.WarnFormat("[ODEPLUGIN]: Avatar Null reference for Avatar {0}, physical actor {1}", m_name, m_uuid); 1087 m_log.WarnFormat("[ODEPLUGIN]: Avatar Null reference for Avatar {0}, physical actor {1}", m_name, m_uuid);
1127 } 1088 }
1128
1129 1089
1130 // kluge to keep things in bounds. ODE lets dead avatars drift away (they should be removed!) 1090 // kluge to keep things in bounds. ODE lets dead avatars drift away (they should be removed!)
1131 if (vec.X < 0.0f) vec.X = 0.0f; 1091 if (vec.X < 0.0f) vec.X = 0.0f;
@@ -1204,6 +1164,38 @@ namespace OpenSim.Region.Physics.OdePlugin
1204 _parent_scene.AddPhysicsActorTaint(this); 1164 _parent_scene.AddPhysicsActorTaint(this);
1205 } 1165 }
1206 1166
1167 /// <summary>
1168 /// Used internally to destroy the ODE structures associated with this character.
1169 /// </summary>
1170 public void DestroyOdeStructures()
1171 {
1172 // destroy avatar capsule and related ODE data
1173 if (Amotor != IntPtr.Zero)
1174 {
1175 // Kill the Amotor
1176 d.JointDestroy(Amotor);
1177 Amotor = IntPtr.Zero;
1178 }
1179
1180 //kill the Geometry
1181 _parent_scene.waitForSpaceUnlock(_parent_scene.space);
1182
1183 if (Body != IntPtr.Zero)
1184 {
1185 //kill the body
1186 d.BodyDestroy(Body);
1187
1188 Body = IntPtr.Zero;
1189 }
1190
1191 if (Shell != IntPtr.Zero)
1192 {
1193 d.GeomDestroy(Shell);
1194 _parent_scene.geom_name_map.Remove(Shell);
1195 Shell = IntPtr.Zero;
1196 }
1197 }
1198
1207 public override void CrossingFailure() 1199 public override void CrossingFailure()
1208 { 1200 {
1209 } 1201 }
@@ -1273,7 +1265,6 @@ namespace OpenSim.Region.Physics.OdePlugin
1273 1265
1274 public void ProcessTaints(float timestep) 1266 public void ProcessTaints(float timestep)
1275 { 1267 {
1276
1277 if (m_tainted_isPhysical != m_isPhysical) 1268 if (m_tainted_isPhysical != m_isPhysical)
1278 { 1269 {
1279 if (m_tainted_isPhysical) 1270 if (m_tainted_isPhysical)
@@ -1295,31 +1286,7 @@ namespace OpenSim.Region.Physics.OdePlugin
1295 else 1286 else
1296 { 1287 {
1297 _parent_scene.RemoveCharacter(this); 1288 _parent_scene.RemoveCharacter(this);
1298 // destroy avatar capsule and related ODE data 1289 DestroyOdeStructures();
1299 if (Amotor != IntPtr.Zero)
1300 {
1301 // Kill the Amotor
1302 d.JointDestroy(Amotor);
1303 Amotor = IntPtr.Zero;
1304 }
1305 //kill the Geometry
1306 _parent_scene.waitForSpaceUnlock(_parent_scene.space);
1307
1308 if (Body != IntPtr.Zero)
1309 {
1310 //kill the body
1311 d.BodyDestroy(Body);
1312
1313 Body = IntPtr.Zero;
1314 }
1315
1316 if (Shell != IntPtr.Zero)
1317 {
1318 d.GeomDestroy(Shell);
1319 _parent_scene.geom_name_map.Remove(Shell);
1320 Shell = IntPtr.Zero;
1321 }
1322
1323 } 1290 }
1324 1291
1325 m_isPhysical = m_tainted_isPhysical; 1292 m_isPhysical = m_tainted_isPhysical;