aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs
diff options
context:
space:
mode:
authorRobert.Adams2011-07-22 10:22:21 -0700
committerDan Lake2011-07-22 10:23:40 -0700
commit5ffec1cd648bc8dcc333fc528707c09bb8dce27d (patch)
treea9c6be19df834d4d53eeff7dec267b75d4c7bacb /OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs
parentMerge branch 'master' into bulletsim (diff)
downloadopensim-SC_OLD-5ffec1cd648bc8dcc333fc528707c09bb8dce27d.zip
opensim-SC_OLD-5ffec1cd648bc8dcc333fc528707c09bb8dce27d.tar.gz
opensim-SC_OLD-5ffec1cd648bc8dcc333fc528707c09bb8dce27d.tar.bz2
opensim-SC_OLD-5ffec1cd648bc8dcc333fc528707c09bb8dce27d.tar.xz
Pass collisions and updates in pinned memory (saves marshaling).
Fix folding feet by using collision normals. Add constraint specification.
Diffstat (limited to '')
-rw-r--r--OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs140
1 files changed, 86 insertions, 54 deletions
diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs
index 82a8803..f2ab2d9 100644
--- a/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs
+++ b/OpenSim/Region/Physics/BulletSPlugin/BSPrim.cs
@@ -261,6 +261,7 @@ public sealed class BSPrim : PhysicsActor
261 { 261 {
262 if (_childrenPrims.Contains(child)) 262 if (_childrenPrims.Contains(child))
263 { 263 {
264 BulletSimAPI.RemoveConstraint(_scene.WorldID, child.LocalID, this.LocalID);
264 _childrenPrims.Remove(child); 265 _childrenPrims.Remove(child);
265 child.ParentPrim = null; // the child has lost its parent 266 child.ParentPrim = null; // the child has lost its parent
266 RecreateGeomAndObject(); // rebuild my shape with the child removed 267 RecreateGeomAndObject(); // rebuild my shape with the child removed
@@ -1018,47 +1019,8 @@ public sealed class BSPrim : PhysicsActor
1018 if (IsRootOfLinkset) 1019 if (IsRootOfLinkset)
1019 { 1020 {
1020 // Create a linkset around this object 1021 // Create a linkset around this object
1021 /* 1022 CreateLinksetWithCompoundHull();
1022 * NOTE: the original way of creating a linkset was to create a compound hull in the 1023 // CreateLinksetWithConstraints();
1023 * root which consisted of the hulls of all the children. This didn't work well because
1024 * OpenSimulator needs updates and collisions for all the children and the physics
1025 * engine didn't create events for the children when the root hull was moved.
1026 * This code creates the compound hull.
1027 // If I am the root prim of a linkset, replace my physical shape with all the
1028 // pieces of the children.
1029 // All of the children should have called CreateGeom so they have a hull
1030 // in the physics engine already. Here we pull together all of those hulls
1031 // into one shape.
1032 int totalPrimsInLinkset = _childrenPrims.Count + 1;
1033 // m_log.DebugFormat("{0}: CreateLinkset. Root prim={1}, prims={2}", LogHeader, LocalID, totalPrimsInLinkset);
1034 ShapeData[] shapes = new ShapeData[totalPrimsInLinkset];
1035 FillShapeInfo(out shapes[0]);
1036 int ii = 1;
1037 foreach (BSPrim prim in _childrenPrims)
1038 {
1039 // m_log.DebugFormat("{0}: CreateLinkset: adding prim {1}", LogHeader, prim.LocalID);
1040 prim.FillShapeInfo(out shapes[ii]);
1041 ii++;
1042 }
1043 BulletSimAPI.CreateLinkset(_scene.WorldID, totalPrimsInLinkset, shapes);
1044 */
1045 // Create the linkset by putting constraints between the objects of the set so they cannot move
1046 // relative to each other.
1047 // m_log.DebugFormat("{0}: CreateLinkset. Root prim={1}, prims={2}", LogHeader, LocalID, _childrenPrims.Count+1);
1048
1049 // remove any constraints that might be in place
1050 foreach (BSPrim prim in _childrenPrims)
1051 {
1052 BulletSimAPI.RemoveConstraint(_scene.WorldID, LocalID, prim.LocalID);
1053 }
1054 // create constraints between the root prim and each of the children
1055 foreach (BSPrim prim in _childrenPrims)
1056 {
1057 // this is a constraint that allows no freedom of movement between the two objects
1058 // http://bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=4818
1059 BulletSimAPI.AddConstraint(_scene.WorldID, LocalID, prim.LocalID, OMV.Vector3.Zero, OMV.Vector3.Zero,
1060 OMV.Vector3.Zero, OMV.Vector3.Zero, OMV.Vector3.Zero, OMV.Vector3.Zero);
1061 }
1062 } 1024 }
1063 else 1025 else
1064 { 1026 {
@@ -1070,6 +1032,73 @@ public sealed class BSPrim : PhysicsActor
1070 } 1032 }
1071 } 1033 }
1072 1034
1035 // Create a linkset by creating a compound hull at the root prim that consists of all
1036 // the children.
1037 void CreateLinksetWithCompoundHull()
1038 {
1039 // If I am the root prim of a linkset, replace my physical shape with all the
1040 // pieces of the children.
1041 // All of the children should have called CreateGeom so they have a hull
1042 // in the physics engine already. Here we pull together all of those hulls
1043 // into one shape.
1044 int totalPrimsInLinkset = _childrenPrims.Count + 1;
1045 // m_log.DebugFormat("{0}: CreateLinkset. Root prim={1}, prims={2}", LogHeader, LocalID, totalPrimsInLinkset);
1046 ShapeData[] shapes = new ShapeData[totalPrimsInLinkset];
1047 FillShapeInfo(out shapes[0]);
1048 int ii = 1;
1049 foreach (BSPrim prim in _childrenPrims)
1050 {
1051 // m_log.DebugFormat("{0}: CreateLinkset: adding prim {1}", LogHeader, prim.LocalID);
1052 prim.FillShapeInfo(out shapes[ii]);
1053 ii++;
1054 }
1055 BulletSimAPI.CreateLinkset(_scene.WorldID, totalPrimsInLinkset, shapes);
1056 }
1057
1058 // Create the linkset by putting constraints between the objects of the set so they cannot move
1059 // relative to each other.
1060 void CreateLinksetWithConstraints()
1061 {
1062 // m_log.DebugFormat("{0}: CreateLinkset. Root prim={1}, prims={2}", LogHeader, LocalID, _childrenPrims.Count+1);
1063
1064 // remove any constraints that might be in place
1065 foreach (BSPrim prim in _childrenPrims)
1066 {
1067 // m_log.DebugFormat("{0}: CreateObject: RemoveConstraint between root prim {1} and child prim {2}", LogHeader, LocalID, prim.LocalID);
1068 BulletSimAPI.RemoveConstraint(_scene.WorldID, LocalID, prim.LocalID);
1069 }
1070 // create constraints between the root prim and each of the children
1071 foreach (BSPrim prim in _childrenPrims)
1072 {
1073 // this is a constraint that allows no freedom of movement between the two objects
1074 // http://bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=4818
1075 // m_log.DebugFormat("{0}: CreateObject: AddConstraint between root prim {1} and child prim {2}", LogHeader, LocalID, prim.LocalID);
1076
1077 // relative position normalized to the root prim
1078 OMV.Vector3 childRelativePosition = (prim._position - this._position) * OMV.Quaternion.Inverse(this._orientation);
1079 // OMV.Quaternion relativeRotation = OMV.Quaternion.Identity;
1080
1081 // rotation is pointing up the vector between the object centers
1082 OMV.Quaternion relativeRotation = OMV.Quaternion.CreateFromAxisAngle(childRelativePosition, 0f);
1083
1084 /* // the logic for relative rotation from http://bulletphysics.org/Bullet/phpBB3/viewtopic.php?t=6391
1085 OMV.Vector3 rrn = childRelativePosition;
1086 rrn.Normalize();
1087 rrn /= rrn.X;
1088 OMV.Matrix4 rotmat = new OMV.Matrix4(rrn.X, rrn.Y, rrn.Z, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1);
1089 OMV.Quaternion relativeRotation = OMV.Quaternion.CreateFromRotationMatrix(rotmat);
1090 */
1091
1092 BulletSimAPI.AddConstraint(_scene.WorldID, LocalID, prim.LocalID,
1093 childRelativePosition / 2,
1094 relativeRotation,
1095 -childRelativePosition / 2,
1096 relativeRotation,
1097 OMV.Vector3.Zero, OMV.Vector3.Zero,
1098 OMV.Vector3.Zero, OMV.Vector3.Zero);
1099 }
1100 }
1101
1073 // Copy prim's info into the BulletSim shape description structure 1102 // Copy prim's info into the BulletSim shape description structure
1074 public void FillShapeInfo(out ShapeData shape) 1103 public void FillShapeInfo(out ShapeData shape)
1075 { 1104 {
@@ -1118,50 +1147,53 @@ public sealed class BSPrim : PhysicsActor
1118 // The physics engine says that properties have updated. Update same and inform 1147 // The physics engine says that properties have updated. Update same and inform
1119 // the world that things have changed. 1148 // the world that things have changed.
1120 // TODO: do we really need to check for changed? Maybe just copy values and call RequestPhysicsterseUpdate() 1149 // TODO: do we really need to check for changed? Maybe just copy values and call RequestPhysicsterseUpdate()
1121 private int UpPropPosition = 1 << 0; 1150 enum UpdatedProperties {
1122 private int UpPropRotation = 1 << 1; 1151 Position = 1 << 0,
1123 private int UpPropVelocity = 1 << 2; 1152 Rotation = 1 << 1,
1124 private int UpPropAcceleration = 1 << 3; 1153 Velocity = 1 << 2,
1125 private int UpPropAngularVel = 1 << 4; 1154 Acceleration = 1 << 3,
1155 AngularVel = 1 << 4
1156 }
1126 1157
1127 public void UpdateProperties(EntityProperties entprop) 1158 public void UpdateProperties(EntityProperties entprop)
1128 { 1159 {
1129 int changed = 0; 1160 UpdatedProperties changed = 0;
1130 // assign to the local variables so the normal set action does not happen 1161 // assign to the local variables so the normal set action does not happen
1131 if (_position != entprop.Position) 1162 if (_position != entprop.Position)
1132 { 1163 {
1133 _position = entprop.Position; 1164 _position = entprop.Position;
1134 // m_log.DebugFormat("{0}: UpdateProperties: position = {1}", LogHeader, _position); 1165 // m_log.DebugFormat("{0}: UpdateProperties: position = {1}", LogHeader, _position);
1135 changed |= UpPropPosition; 1166 changed |= UpdatedProperties.Position;
1136 } 1167 }
1137 if (_orientation != entprop.Rotation) 1168 if (_orientation != entprop.Rotation)
1138 { 1169 {
1139 _orientation = entprop.Rotation; 1170 _orientation = entprop.Rotation;
1140 // m_log.DebugFormat("{0}: UpdateProperties: rotation = {1}", LogHeader, _orientation); 1171 // m_log.DebugFormat("{0}: UpdateProperties: rotation = {1}", LogHeader, _orientation);
1141 changed |= UpPropRotation; 1172 changed |= UpdatedProperties.Rotation;
1142 } 1173 }
1143 if (_velocity != entprop.Velocity) 1174 if (_velocity != entprop.Velocity)
1144 { 1175 {
1145 _velocity = entprop.Velocity; 1176 _velocity = entprop.Velocity;
1146 // m_log.DebugFormat("{0}: UpdateProperties: velocity = {1}", LogHeader, _velocity); 1177 // m_log.DebugFormat("{0}: UpdateProperties: velocity = {1}", LogHeader, _velocity);
1147 changed |= UpPropVelocity; 1178 changed |= UpdatedProperties.Velocity;
1148 } 1179 }
1149 if (_acceleration != entprop.Acceleration) 1180 if (_acceleration != entprop.Acceleration)
1150 { 1181 {
1151 _acceleration = entprop.Acceleration; 1182 _acceleration = entprop.Acceleration;
1152 // m_log.DebugFormat("{0}: UpdateProperties: acceleration = {1}", LogHeader, _acceleration); 1183 // m_log.DebugFormat("{0}: UpdateProperties: acceleration = {1}", LogHeader, _acceleration);
1153 changed |= UpPropAcceleration; 1184 changed |= UpdatedProperties.Acceleration;
1154 } 1185 }
1155 if (_rotationalVelocity != entprop.AngularVelocity) 1186 if (_rotationalVelocity != entprop.AngularVelocity)
1156 { 1187 {
1157 _rotationalVelocity = entprop.AngularVelocity; 1188 _rotationalVelocity = entprop.AngularVelocity;
1158 // m_log.DebugFormat("{0}: UpdateProperties: rotationalVelocity = {1}", LogHeader, _rotationalVelocity); 1189 // m_log.DebugFormat("{0}: UpdateProperties: rotationalVelocity = {1}", LogHeader, _rotationalVelocity);
1159 changed |= UpPropAngularVel; 1190 changed |= UpdatedProperties.AngularVel;
1160 } 1191 }
1161 if (changed != 0) 1192 if (changed != 0)
1162 { 1193 {
1163 // m_log.DebugFormat("{0}: UpdateProperties: id={1}, c={2}, pos={3}, rot={4}", LogHeader, LocalID, changed, _position, _orientation); 1194 // m_log.DebugFormat("{0}: UpdateProperties: id={1}, c={2}, pos={3}, rot={4}", LogHeader, LocalID, changed, _position, _orientation);
1164 base.RequestPhysicsterseUpdate(); 1195 if (this._parentPrim == null)
1196 base.RequestPhysicsterseUpdate();
1165 } 1197 }
1166 } 1198 }
1167 1199
@@ -1178,7 +1210,7 @@ public sealed class BSPrim : PhysicsActor
1178 1210
1179 if (_subscribedEventsMs == 0) return; // nothing in the object is waiting for collision events 1211 if (_subscribedEventsMs == 0) return; // nothing in the object is waiting for collision events
1180 // throttle the collisions to the number of milliseconds specified in the subscription 1212 // throttle the collisions to the number of milliseconds specified in the subscription
1181 int nowTime = Util.EnvironmentTickCount(); 1213 int nowTime = _scene.SimulationNowTime;
1182 if (nowTime < (_lastCollisionTime + _subscribedEventsMs)) return; 1214 if (nowTime < (_lastCollisionTime + _subscribedEventsMs)) return;
1183 _lastCollisionTime = nowTime; 1215 _lastCollisionTime = nowTime;
1184 1216