diff options
4 files changed, 101 insertions, 9 deletions
diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs index ba353c4..b0f2015 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs | |||
@@ -4041,6 +4041,39 @@ namespace OpenSim.Region.Framework.Scenes | |||
4041 | return retmass; | 4041 | return retmass; |
4042 | } | 4042 | } |
4043 | 4043 | ||
4044 | // center of mass of full object | ||
4045 | public Vector3 GetCenterOfMass() | ||
4046 | { | ||
4047 | PhysicsActor pa = RootPart.PhysActor; | ||
4048 | |||
4049 | if(((RootPart.Flags & PrimFlags.Physics) !=0) && pa !=null) | ||
4050 | { | ||
4051 | // physics knows better about center of mass of physical prims | ||
4052 | Vector3 tmp = pa.CenterOfMass; | ||
4053 | return tmp; | ||
4054 | } | ||
4055 | |||
4056 | Vector3 Ptot = Vector3.Zero; | ||
4057 | float totmass = 0f; | ||
4058 | float m; | ||
4059 | |||
4060 | SceneObjectPart[] parts = m_parts.GetArray(); | ||
4061 | for (int i = 0; i < parts.Length; i++) | ||
4062 | { | ||
4063 | m = parts[i].GetMass(); | ||
4064 | Ptot += parts[i].GetPartCenterOfMass() * m; | ||
4065 | totmass += m; | ||
4066 | } | ||
4067 | |||
4068 | if (totmass == 0) | ||
4069 | totmass = 0; | ||
4070 | else | ||
4071 | totmass = 1 / totmass; | ||
4072 | Ptot *= totmass; | ||
4073 | |||
4074 | return Ptot; | ||
4075 | } | ||
4076 | |||
4044 | /// <summary> | 4077 | /// <summary> |
4045 | /// If the object is a sculpt/mesh, retrieve the mesh data for each part and reinsert it into each shape so that | 4078 | /// If the object is a sculpt/mesh, retrieve the mesh data for each part and reinsert it into each shape so that |
4046 | /// the physics engine can use it. | 4079 | /// the physics engine can use it. |
diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs index c9659cb..b198ca7 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs | |||
@@ -1865,7 +1865,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
1865 | { | 1865 | { |
1866 | if ((!isPhantom || isPhysical || _VolumeDetectActive) && !ParentGroup.IsAttachment | 1866 | if ((!isPhantom || isPhysical || _VolumeDetectActive) && !ParentGroup.IsAttachment |
1867 | && !(Shape.PathCurve == (byte)Extrusion.Flexible)) | 1867 | && !(Shape.PathCurve == (byte)Extrusion.Flexible)) |
1868 | AddToPhysics(isPhysical, isPhantom, building, true); | 1868 | AddToPhysics(isPhysical, isPhantom, building, isPhysical); |
1869 | else | 1869 | else |
1870 | PhysActor = null; // just to be sure | 1870 | PhysActor = null; // just to be sure |
1871 | } | 1871 | } |
@@ -2308,7 +2308,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
2308 | */ | 2308 | */ |
2309 | } | 2309 | } |
2310 | 2310 | ||
2311 | public float GetMass() | 2311 | public float GetMass() |
2312 | { | 2312 | { |
2313 | PhysicsActor pa = PhysActor; | 2313 | PhysicsActor pa = PhysActor; |
2314 | 2314 | ||
@@ -2318,6 +2318,40 @@ namespace OpenSim.Region.Framework.Scenes | |||
2318 | return 0; | 2318 | return 0; |
2319 | } | 2319 | } |
2320 | 2320 | ||
2321 | public Vector3 GetCenterOfMass() | ||
2322 | { | ||
2323 | if (ParentGroup.RootPart == this) | ||
2324 | { | ||
2325 | if (ParentGroup.IsDeleted) | ||
2326 | return AbsolutePosition; | ||
2327 | return ParentGroup.GetCenterOfMass(); | ||
2328 | } | ||
2329 | |||
2330 | PhysicsActor pa = PhysActor; | ||
2331 | |||
2332 | if (pa != null) | ||
2333 | { | ||
2334 | Vector3 tmp = pa.CenterOfMass; | ||
2335 | return tmp; | ||
2336 | } | ||
2337 | else | ||
2338 | return AbsolutePosition; | ||
2339 | } | ||
2340 | |||
2341 | public Vector3 GetPartCenterOfMass() | ||
2342 | { | ||
2343 | PhysicsActor pa = PhysActor; | ||
2344 | |||
2345 | if (pa != null) | ||
2346 | { | ||
2347 | Vector3 tmp = pa.CenterOfMass; | ||
2348 | return tmp; | ||
2349 | } | ||
2350 | else | ||
2351 | return AbsolutePosition; | ||
2352 | } | ||
2353 | |||
2354 | |||
2321 | public Vector3 GetForce() | 2355 | public Vector3 GetForce() |
2322 | { | 2356 | { |
2323 | return Force; | 2357 | return Force; |
@@ -4802,7 +4836,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
4802 | { | 4836 | { |
4803 | Velocity = velocity; | 4837 | Velocity = velocity; |
4804 | AngularVelocity = rotationalVelocity; | 4838 | AngularVelocity = rotationalVelocity; |
4805 | pa.Velocity = velocity; | 4839 | // pa.Velocity = velocity; |
4806 | pa.RotationalVelocity = rotationalVelocity; | 4840 | pa.RotationalVelocity = rotationalVelocity; |
4807 | 4841 | ||
4808 | // if not vehicle and root part apply force and torque | 4842 | // if not vehicle and root part apply force and torque |
diff --git a/OpenSim/Region/Physics/UbitOdePlugin/ODEPrim.cs b/OpenSim/Region/Physics/UbitOdePlugin/ODEPrim.cs index 2d587ab..c9a453d 100644 --- a/OpenSim/Region/Physics/UbitOdePlugin/ODEPrim.cs +++ b/OpenSim/Region/Physics/UbitOdePlugin/ODEPrim.cs | |||
@@ -450,7 +450,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
450 | get | 450 | get |
451 | { | 451 | { |
452 | d.Vector3 dtmp; | 452 | d.Vector3 dtmp; |
453 | if (IsPhysical && !childPrim && Body != IntPtr.Zero) | 453 | if (!childPrim && Body != IntPtr.Zero) |
454 | { | 454 | { |
455 | dtmp = d.BodyGetPosition(Body); | 455 | dtmp = d.BodyGetPosition(Body); |
456 | return new Vector3(dtmp.X, dtmp.Y, dtmp.Z); | 456 | return new Vector3(dtmp.X, dtmp.Y, dtmp.Z); |
@@ -465,12 +465,38 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
465 | q.Z = dq.Z; | 465 | q.Z = dq.Z; |
466 | q.W = dq.W; | 466 | q.W = dq.W; |
467 | 467 | ||
468 | Vector3 vtmp = primOOBoffset * q; | 468 | Vector3 Ptot = primOOBoffset * q; |
469 | dtmp = d.GeomGetPosition(prim_geom); | 469 | dtmp = d.GeomGetPosition(prim_geom); |
470 | return new Vector3(dtmp.X + vtmp.X, dtmp.Y + vtmp.Y, dtmp.Z + vtmp.Z); | 470 | Ptot.X += dtmp.X; |
471 | Ptot.Y += dtmp.Y; | ||
472 | Ptot.Z += dtmp.Z; | ||
473 | |||
474 | // if(childPrim) we only know about physical linksets | ||
475 | return Ptot; | ||
476 | /* | ||
477 | float tmass = _mass; | ||
478 | Ptot *= tmass; | ||
479 | |||
480 | float m; | ||
481 | |||
482 | foreach (OdePrim prm in childrenPrim) | ||
483 | { | ||
484 | m = prm._mass; | ||
485 | Ptot += prm.CenterOfMass * m; | ||
486 | tmass += m; | ||
487 | } | ||
488 | |||
489 | if (tmass == 0) | ||
490 | tmass = 0; | ||
491 | else | ||
492 | tmass = 1.0f / tmass; | ||
493 | |||
494 | Ptot *= tmass; | ||
495 | return Ptot; | ||
496 | */ | ||
471 | } | 497 | } |
472 | else | 498 | else |
473 | return Vector3.Zero; | 499 | return _position; |
474 | } | 500 | } |
475 | } | 501 | } |
476 | /* | 502 | /* |
@@ -3490,7 +3516,6 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
3490 | { | 3516 | { |
3491 | d.BodySetPosition(Body, lpos.X, lpos.Y, m_targetHoverHeight); | 3517 | d.BodySetPosition(Body, lpos.X, lpos.Y, m_targetHoverHeight); |
3492 | d.BodySetLinearVel(Body, vel.X, vel.Y, 0); | 3518 | d.BodySetLinearVel(Body, vel.X, vel.Y, 0); |
3493 | return; | ||
3494 | } | 3519 | } |
3495 | else | 3520 | else |
3496 | { | 3521 | { |
diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs index 8e73eb1..6ee1a5d 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/LSL_Api.cs | |||
@@ -5370,7 +5370,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
5370 | public LSL_Vector llGetCenterOfMass() | 5370 | public LSL_Vector llGetCenterOfMass() |
5371 | { | 5371 | { |
5372 | m_host.AddScriptLPS(1); | 5372 | m_host.AddScriptLPS(1); |
5373 | Vector3 center = m_host.GetGeometricCenter(); | 5373 | Vector3 center = m_host.GetCenterOfMass(); |
5374 | return new LSL_Vector(center.X,center.Y,center.Z); | 5374 | return new LSL_Vector(center.X,center.Y,center.Z); |
5375 | } | 5375 | } |
5376 | 5376 | ||