diff options
Diffstat (limited to 'OpenSim/Region/Physics/OdePlugin/OdePlugin.cs')
-rw-r--r-- | OpenSim/Region/Physics/OdePlugin/OdePlugin.cs | 38 |
1 files changed, 36 insertions, 2 deletions
diff --git a/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs b/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs index 397ba6d..ae46feb 100644 --- a/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs +++ b/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs | |||
@@ -26,6 +26,7 @@ | |||
26 | * | 26 | * |
27 | */ | 27 | */ |
28 | using System; | 28 | using System; |
29 | using System.Threading; | ||
29 | using System.Collections.Generic; | 30 | using System.Collections.Generic; |
30 | using Axiom.Math; | 31 | using Axiom.Math; |
31 | using Ode.NET; | 32 | using Ode.NET; |
@@ -83,7 +84,6 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
83 | private List<OdePrim> _prims = new List<OdePrim>(); | 84 | private List<OdePrim> _prims = new List<OdePrim>(); |
84 | private static d.ContactGeom[] contacts = new d.ContactGeom[30]; | 85 | private static d.ContactGeom[] contacts = new d.ContactGeom[30]; |
85 | private static d.Contact contact; | 86 | private static d.Contact contact; |
86 | |||
87 | public OdeScene() | 87 | public OdeScene() |
88 | { | 88 | { |
89 | contact.surface.mode |= d.ContactFlags.Approx1 | d.ContactFlags.SoftCFM | d.ContactFlags.SoftERP; | 89 | contact.surface.mode |= d.ContactFlags.Approx1 | d.ContactFlags.SoftCFM | d.ContactFlags.SoftERP; |
@@ -92,24 +92,35 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
92 | contact.surface.soft_erp = 0.005f; | 92 | contact.surface.soft_erp = 0.005f; |
93 | contact.surface.soft_cfm = 0.00003f; | 93 | contact.surface.soft_cfm = 0.00003f; |
94 | 94 | ||
95 | Monitor.Enter(typeof(OdeScene)); | ||
95 | world = d.WorldCreate(); | 96 | world = d.WorldCreate(); |
96 | space = d.HashSpaceCreate(IntPtr.Zero); | 97 | space = d.HashSpaceCreate(IntPtr.Zero); |
97 | contactgroup = d.JointGroupCreate(0); | 98 | contactgroup = d.JointGroupCreate(0); |
98 | d.WorldSetGravity(world, 0.0f, 0.0f, -10.0f); | 99 | d.WorldSetGravity(world, 0.0f, 0.0f, -10.0f); |
99 | d.WorldSetAutoDisableFlag(world, false); | 100 | d.WorldSetAutoDisableFlag(world, false); |
100 | d.WorldSetContactSurfaceLayer(world, 0.001f); | 101 | d.WorldSetContactSurfaceLayer(world, 0.001f); |
102 | Monitor.Exit(typeof(OdeScene)); | ||
103 | |||
101 | this._heightmap = new double[65536]; | 104 | this._heightmap = new double[65536]; |
102 | } | 105 | } |
103 | 106 | ||
104 | // This function blatantly ripped off from BoxStack.cs | 107 | // This function blatantly ripped off from BoxStack.cs |
105 | static private void near(IntPtr space, IntPtr g1, IntPtr g2) | 108 | static private void near(IntPtr space, IntPtr g1, IntPtr g2) |
106 | { | 109 | { |
110 | // no lock here! It's invoked from within Simulate(), which is thread-locked | ||
107 | IntPtr b1 = d.GeomGetBody(g1); | 111 | IntPtr b1 = d.GeomGetBody(g1); |
108 | IntPtr b2 = d.GeomGetBody(g2); | 112 | IntPtr b2 = d.GeomGetBody(g2); |
109 | if (b1 != IntPtr.Zero && b2 != IntPtr.Zero && d.AreConnectedExcluding(b1, b2, d.JointType.Contact)) | 113 | if (b1 != IntPtr.Zero && b2 != IntPtr.Zero && d.AreConnectedExcluding(b1, b2, d.JointType.Contact)) |
110 | return; | 114 | return; |
111 | 115 | ||
112 | int count = d.Collide(g1, g2, 500, contacts, d.ContactGeom.SizeOf); | 116 | int count = d.Collide(g1, g2, 500, contacts, d.ContactGeom.SizeOf); |
117 | if (count>0) | ||
118 | { | ||
119 | if (b2 != IntPtr.Zero) | ||
120 | { | ||
121 | Console.WriteLine("+++++ collision twixt: " + b1 + " & " + b2); | ||
122 | } | ||
123 | } | ||
113 | for (int i = 0; i < count; ++i) | 124 | for (int i = 0; i < count; ++i) |
114 | { | 125 | { |
115 | contact.geom = contacts[i]; | 126 | contact.geom = contacts[i]; |
@@ -137,6 +148,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
137 | 148 | ||
138 | public override PhysicsActor AddPrim(PhysicsVector position, PhysicsVector size, Quaternion rotation) | 149 | public override PhysicsActor AddPrim(PhysicsVector position, PhysicsVector size, Quaternion rotation) |
139 | { | 150 | { |
151 | Console.WriteLine("+++++++++++++++++++++++++++++++++AddPrim pos: " + position + " size: " + size + " quat: " + rotation); | ||
140 | PhysicsVector pos = new PhysicsVector(); | 152 | PhysicsVector pos = new PhysicsVector(); |
141 | pos.X = position.X; | 153 | pos.X = position.X; |
142 | pos.Y = position.Y; | 154 | pos.Y = position.Y; |
@@ -157,6 +169,11 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
157 | 169 | ||
158 | public override void Simulate(float timeStep) | 170 | public override void Simulate(float timeStep) |
159 | { | 171 | { |
172 | Monitor.Enter(typeof(OdeScene)); | ||
173 | foreach (OdePrim p in _prims) | ||
174 | { | ||
175 | // Console.WriteLine("+++ prim: " + p.Position); | ||
176 | } | ||
160 | foreach (OdeCharacter actor in _characters) | 177 | foreach (OdeCharacter actor in _characters) |
161 | { | 178 | { |
162 | actor.Move(timeStep); | 179 | actor.Move(timeStep); |
@@ -172,6 +189,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
172 | { | 189 | { |
173 | actor.UpdatePosition(); | 190 | actor.UpdatePosition(); |
174 | } | 191 | } |
192 | Monitor.Exit(typeof(OdeScene)); | ||
175 | } | 193 | } |
176 | 194 | ||
177 | public override void GetResults() | 195 | public override void GetResults() |
@@ -198,6 +216,8 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
198 | this._heightmap[i] = (double)heightMap[x * 256 + y]; | 216 | this._heightmap[i] = (double)heightMap[x * 256 + y]; |
199 | } | 217 | } |
200 | IntPtr HeightmapData = d.GeomHeightfieldDataCreate(); | 218 | IntPtr HeightmapData = d.GeomHeightfieldDataCreate(); |
219 | |||
220 | Monitor.Enter(typeof(OdeScene)); | ||
201 | d.GeomHeightfieldDataBuildDouble(HeightmapData, _heightmap, 0, 256, 256, 256, 256, 1.0f, 0.0f, 2.0f, 0); | 221 | d.GeomHeightfieldDataBuildDouble(HeightmapData, _heightmap, 0, 256, 256, 256, 256, 1.0f, 0.0f, 2.0f, 0); |
202 | d.GeomHeightfieldDataSetBounds(HeightmapData, 256, 256); | 222 | d.GeomHeightfieldDataSetBounds(HeightmapData, 256, 256); |
203 | LandGeom = d.CreateHeightfield(space, HeightmapData, 1); | 223 | LandGeom = d.CreateHeightfield(space, HeightmapData, 1); |
@@ -215,7 +235,8 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
215 | 235 | ||
216 | d.RFromAxisAndAngle(out R, v3.x, v3.y, v3.z, angle); | 236 | d.RFromAxisAndAngle(out R, v3.x, v3.y, v3.z, angle); |
217 | d.GeomSetRotation(LandGeom, ref R); | 237 | d.GeomSetRotation(LandGeom, ref R); |
218 | d.GeomSetPosition(LandGeom, 128, 128, 0); | 238 | d.GeomSetPosition(LandGeom, 128, 128, 0); |
239 | Monitor.Exit(typeof(OdeScene)); | ||
219 | } | 240 | } |
220 | 241 | ||
221 | public override void DeleteTerrain() | 242 | public override void DeleteTerrain() |
@@ -240,12 +261,14 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
240 | _velocity = new PhysicsVector(); | 261 | _velocity = new PhysicsVector(); |
241 | _position = pos; | 262 | _position = pos; |
242 | _acceleration = new PhysicsVector(); | 263 | _acceleration = new PhysicsVector(); |
264 | Monitor.Enter(typeof(OdeScene)); | ||
243 | d.MassSetCapsule(out capsule_mass, 50.0f, 3, 0.5f, 2f); | 265 | d.MassSetCapsule(out capsule_mass, 50.0f, 3, 0.5f, 2f); |
244 | capsule_geom = d.CreateSphere(OdeScene.space, 1.0f); /// not a typo! Spheres roll, capsules tumble | 266 | capsule_geom = d.CreateSphere(OdeScene.space, 1.0f); /// not a typo! Spheres roll, capsules tumble |
245 | this.BoundingCapsule = d.BodyCreate(OdeScene.world); | 267 | this.BoundingCapsule = d.BodyCreate(OdeScene.world); |
246 | d.BodySetMass(BoundingCapsule, ref capsule_mass); | 268 | d.BodySetMass(BoundingCapsule, ref capsule_mass); |
247 | d.BodySetPosition(BoundingCapsule, pos.X, pos.Y, pos.Z); | 269 | d.BodySetPosition(BoundingCapsule, pos.X, pos.Y, pos.Z); |
248 | d.GeomSetBody(capsule_geom, BoundingCapsule); | 270 | d.GeomSetBody(capsule_geom, BoundingCapsule); |
271 | Monitor.Exit(typeof(OdeScene)); | ||
249 | } | 272 | } |
250 | 273 | ||
251 | public override bool Flying | 274 | public override bool Flying |
@@ -345,6 +368,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
345 | 368 | ||
346 | public void Move(float timeStep) | 369 | public void Move(float timeStep) |
347 | { | 370 | { |
371 | // no lock; for now it's only called from within Simulate() | ||
348 | PhysicsVector vec = new PhysicsVector(); | 372 | PhysicsVector vec = new PhysicsVector(); |
349 | d.Vector3 vel = d.BodyGetLinearVel(BoundingCapsule); | 373 | d.Vector3 vel = d.BodyGetLinearVel(BoundingCapsule); |
350 | vec.X = (vel.X - this._velocity.X) * -75000.0f; | 374 | vec.X = (vel.X - this._velocity.X) * -75000.0f; |
@@ -358,6 +382,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
358 | 382 | ||
359 | public void UpdatePosition() | 383 | public void UpdatePosition() |
360 | { | 384 | { |
385 | // no lock; called from Simulate() -- if you call this from elsewhere, gotta lock or do Monitor.Enter/Exit! | ||
361 | d.Vector3 vec = d.BodyGetPosition(BoundingCapsule); | 386 | d.Vector3 vec = d.BodyGetPosition(BoundingCapsule); |
362 | this._position.X = vec.X; | 387 | this._position.X = vec.X; |
363 | this._position.Y = vec.Y; | 388 | this._position.Y = vec.Y; |
@@ -382,6 +407,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
382 | _acceleration = new PhysicsVector(); | 407 | _acceleration = new PhysicsVector(); |
383 | _orientation = rotation; | 408 | _orientation = rotation; |
384 | prim_geom = d.CreateBox(OdeScene.space, _size.X, _size.Y, _size.Z); | 409 | prim_geom = d.CreateBox(OdeScene.space, _size.X, _size.Y, _size.Z); |
410 | Monitor.Enter(typeof(OdeScene)); | ||
385 | d.GeomSetPosition(prim_geom, _position.X, _position.Y, _position.Z); | 411 | d.GeomSetPosition(prim_geom, _position.X, _position.Y, _position.Z); |
386 | d.Quaternion myrot = new d.Quaternion(); | 412 | d.Quaternion myrot = new d.Quaternion(); |
387 | myrot.W = rotation.w; | 413 | myrot.W = rotation.w; |
@@ -389,6 +415,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
389 | myrot.Y = rotation.y; | 415 | myrot.Y = rotation.y; |
390 | myrot.Z = rotation.z; | 416 | myrot.Z = rotation.z; |
391 | d.GeomSetQuaternion(prim_geom, ref myrot); | 417 | d.GeomSetQuaternion(prim_geom, ref myrot); |
418 | Monitor.Exit(typeof(OdeScene)); | ||
392 | } | 419 | } |
393 | 420 | ||
394 | public override bool Flying | 421 | public override bool Flying |
@@ -410,8 +437,12 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
410 | } | 437 | } |
411 | set | 438 | set |
412 | { | 439 | { |
440 | Console.WriteLine("+++++++++++++++++++++++++++++++++++++++++++ setting pos: " + value); | ||
413 | _position = value; | 441 | _position = value; |
442 | Monitor.Enter(typeof(OdeScene)); | ||
414 | d.GeomSetPosition(prim_geom, _position.X, _position.Y, _position.Z); | 443 | d.GeomSetPosition(prim_geom, _position.X, _position.Y, _position.Z); |
444 | Monitor.Exit(typeof(OdeScene)); | ||
445 | |||
415 | } | 446 | } |
416 | } | 447 | } |
417 | 448 | ||
@@ -423,6 +454,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
423 | } | 454 | } |
424 | set | 455 | set |
425 | { | 456 | { |
457 | Console.WriteLine("+++++++++++++++++++++++++++++++++++++++++++ setting size: " + value); | ||
426 | _size = value; | 458 | _size = value; |
427 | } | 459 | } |
428 | } | 460 | } |
@@ -459,12 +491,14 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
459 | set | 491 | set |
460 | { | 492 | { |
461 | _orientation = value; | 493 | _orientation = value; |
494 | Monitor.Enter(typeof(OdeScene)); | ||
462 | d.Quaternion myrot = new d.Quaternion(); | 495 | d.Quaternion myrot = new d.Quaternion(); |
463 | myrot.W = _orientation.w; | 496 | myrot.W = _orientation.w; |
464 | myrot.X = _orientation.x; | 497 | myrot.X = _orientation.x; |
465 | myrot.Y = _orientation.y; | 498 | myrot.Y = _orientation.y; |
466 | myrot.Z = _orientation.z; | 499 | myrot.Z = _orientation.z; |
467 | d.GeomSetQuaternion(prim_geom, ref myrot); | 500 | d.GeomSetQuaternion(prim_geom, ref myrot); |
501 | Monitor.Exit(typeof(OdeScene)); | ||
468 | } | 502 | } |
469 | } | 503 | } |
470 | 504 | ||