diff options
Diffstat (limited to 'OpenSim/Region/Framework/Scenes/SceneObjectPart.cs')
-rw-r--r-- | OpenSim/Region/Framework/Scenes/SceneObjectPart.cs | 1105 |
1 files changed, 781 insertions, 324 deletions
diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs index 439b718..cfa3cd4 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs | |||
@@ -62,7 +62,8 @@ namespace OpenSim.Region.Framework.Scenes | |||
62 | TELEPORT = 512, | 62 | TELEPORT = 512, |
63 | REGION_RESTART = 1024, | 63 | REGION_RESTART = 1024, |
64 | MEDIA = 2048, | 64 | MEDIA = 2048, |
65 | ANIMATION = 16384 | 65 | ANIMATION = 16384, |
66 | POSITION = 32768 | ||
66 | } | 67 | } |
67 | 68 | ||
68 | // I don't really know where to put this except here. | 69 | // I don't really know where to put this except here. |
@@ -184,6 +185,15 @@ namespace OpenSim.Region.Framework.Scenes | |||
184 | 185 | ||
185 | public UUID FromFolderID; | 186 | public UUID FromFolderID; |
186 | 187 | ||
188 | // The following two are to hold the attachment data | ||
189 | // while an object is inworld | ||
190 | [XmlIgnore] | ||
191 | public byte AttachPoint = 0; | ||
192 | |||
193 | [XmlIgnore] | ||
194 | public Vector3 AttachOffset = Vector3.Zero; | ||
195 | |||
196 | [XmlIgnore] | ||
187 | public int STATUS_ROTATE_X; | 197 | public int STATUS_ROTATE_X; |
188 | 198 | ||
189 | public int STATUS_ROTATE_Y; | 199 | public int STATUS_ROTATE_Y; |
@@ -210,8 +220,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
210 | 220 | ||
211 | public Vector3 RotationAxis = Vector3.One; | 221 | public Vector3 RotationAxis = Vector3.One; |
212 | 222 | ||
213 | public bool VolumeDetectActive; // XmlIgnore set to avoid problems with persistance until I come to care for this | 223 | public bool VolumeDetectActive; |
214 | // Certainly this must be a persistant setting finally | ||
215 | 224 | ||
216 | public bool IsWaitingForFirstSpinUpdatePacket; | 225 | public bool IsWaitingForFirstSpinUpdatePacket; |
217 | 226 | ||
@@ -251,10 +260,10 @@ namespace OpenSim.Region.Framework.Scenes | |||
251 | private Quaternion m_sitTargetOrientation = Quaternion.Identity; | 260 | private Quaternion m_sitTargetOrientation = Quaternion.Identity; |
252 | private Vector3 m_sitTargetPosition; | 261 | private Vector3 m_sitTargetPosition; |
253 | private string m_sitAnimation = "SIT"; | 262 | private string m_sitAnimation = "SIT"; |
263 | private bool m_occupied; // KF if any av is sitting on this prim | ||
254 | private string m_text = String.Empty; | 264 | private string m_text = String.Empty; |
255 | private string m_touchName = String.Empty; | 265 | private string m_touchName = String.Empty; |
256 | private readonly Stack<UndoState> m_undo = new Stack<UndoState>(5); | 266 | private UndoRedoState m_UndoRedo = null; |
257 | private readonly Stack<UndoState> m_redo = new Stack<UndoState>(5); | ||
258 | 267 | ||
259 | private bool m_passTouches; | 268 | private bool m_passTouches; |
260 | 269 | ||
@@ -283,7 +292,16 @@ namespace OpenSim.Region.Framework.Scenes | |||
283 | protected Vector3 m_lastAcceleration; | 292 | protected Vector3 m_lastAcceleration; |
284 | protected Vector3 m_lastAngularVelocity; | 293 | protected Vector3 m_lastAngularVelocity; |
285 | protected int m_lastTerseSent; | 294 | protected int m_lastTerseSent; |
286 | 295 | protected float m_buoyancy = 0.0f; | |
296 | protected Vector3 m_force; | ||
297 | protected Vector3 m_torque; | ||
298 | |||
299 | protected byte m_physicsShapeType = (byte)PhysShapeType.prim; | ||
300 | protected float m_density = 1000.0f; // in kg/m^3 | ||
301 | protected float m_gravitymod = 1.0f; | ||
302 | protected float m_friction = 0.6f; // wood | ||
303 | protected float m_bounce = 0.5f; // wood | ||
304 | |||
287 | /// <summary> | 305 | /// <summary> |
288 | /// Stores media texture data | 306 | /// Stores media texture data |
289 | /// </summary> | 307 | /// </summary> |
@@ -299,6 +317,17 @@ namespace OpenSim.Region.Framework.Scenes | |||
299 | private UUID m_collisionSound; | 317 | private UUID m_collisionSound; |
300 | private float m_collisionSoundVolume; | 318 | private float m_collisionSoundVolume; |
301 | 319 | ||
320 | |||
321 | private SOPVehicle m_vehicle = null; | ||
322 | |||
323 | private KeyframeMotion m_keyframeMotion = null; | ||
324 | |||
325 | public KeyframeMotion KeyframeMotion | ||
326 | { | ||
327 | get; set; | ||
328 | } | ||
329 | |||
330 | |||
302 | #endregion Fields | 331 | #endregion Fields |
303 | 332 | ||
304 | // ~SceneObjectPart() | 333 | // ~SceneObjectPart() |
@@ -341,7 +370,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
341 | UUID ownerID, PrimitiveBaseShape shape, Vector3 groupPosition, | 370 | UUID ownerID, PrimitiveBaseShape shape, Vector3 groupPosition, |
342 | Quaternion rotationOffset, Vector3 offsetPosition) : this() | 371 | Quaternion rotationOffset, Vector3 offsetPosition) : this() |
343 | { | 372 | { |
344 | m_name = "Primitive"; | 373 | m_name = "Object"; |
345 | 374 | ||
346 | CreationDate = (int)Utils.DateTimeToUnixTime(Rezzed); | 375 | CreationDate = (int)Utils.DateTimeToUnixTime(Rezzed); |
347 | LastOwnerID = CreatorID = OwnerID = ownerID; | 376 | LastOwnerID = CreatorID = OwnerID = ownerID; |
@@ -381,7 +410,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
381 | private uint _ownerMask = (uint)PermissionMask.All; | 410 | private uint _ownerMask = (uint)PermissionMask.All; |
382 | private uint _groupMask = (uint)PermissionMask.None; | 411 | private uint _groupMask = (uint)PermissionMask.None; |
383 | private uint _everyoneMask = (uint)PermissionMask.None; | 412 | private uint _everyoneMask = (uint)PermissionMask.None; |
384 | private uint _nextOwnerMask = (uint)PermissionMask.All; | 413 | private uint _nextOwnerMask = (uint)(PermissionMask.Move | PermissionMask.Modify | PermissionMask.Transfer); |
385 | private PrimFlags _flags = PrimFlags.None; | 414 | private PrimFlags _flags = PrimFlags.None; |
386 | private DateTime m_expires; | 415 | private DateTime m_expires; |
387 | private DateTime m_rezzed; | 416 | private DateTime m_rezzed; |
@@ -475,12 +504,16 @@ namespace OpenSim.Region.Framework.Scenes | |||
475 | } | 504 | } |
476 | 505 | ||
477 | /// <value> | 506 | /// <value> |
478 | /// Access should be via Inventory directly - this property temporarily remains for xml serialization purposes | 507 | /// Get the inventory list |
479 | /// </value> | 508 | /// </value> |
480 | public TaskInventoryDictionary TaskInventory | 509 | public TaskInventoryDictionary TaskInventory |
481 | { | 510 | { |
482 | get { return m_inventory.Items; } | 511 | get { |
483 | set { m_inventory.Items = value; } | 512 | return m_inventory.Items; |
513 | } | ||
514 | set { | ||
515 | m_inventory.Items = value; | ||
516 | } | ||
484 | } | 517 | } |
485 | 518 | ||
486 | /// <summary> | 519 | /// <summary> |
@@ -529,19 +562,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
529 | } | 562 | } |
530 | } | 563 | } |
531 | 564 | ||
532 | public byte Material | ||
533 | { | ||
534 | get { return (byte) m_material; } | ||
535 | set | ||
536 | { | ||
537 | m_material = (Material)value; | ||
538 | if (PhysActor != null) | ||
539 | { | ||
540 | PhysActor.SetMaterial((int)value); | ||
541 | } | ||
542 | } | ||
543 | } | ||
544 | |||
545 | public bool PassTouches | 565 | public bool PassTouches |
546 | { | 566 | { |
547 | get { return m_passTouches; } | 567 | get { return m_passTouches; } |
@@ -624,14 +644,12 @@ namespace OpenSim.Region.Framework.Scenes | |||
624 | set { m_LoopSoundSlavePrims = value; } | 644 | set { m_LoopSoundSlavePrims = value; } |
625 | } | 645 | } |
626 | 646 | ||
627 | |||
628 | public Byte[] TextureAnimation | 647 | public Byte[] TextureAnimation |
629 | { | 648 | { |
630 | get { return m_TextureAnimation; } | 649 | get { return m_TextureAnimation; } |
631 | set { m_TextureAnimation = value; } | 650 | set { m_TextureAnimation = value; } |
632 | } | 651 | } |
633 | 652 | ||
634 | |||
635 | public Byte[] ParticleSystem | 653 | public Byte[] ParticleSystem |
636 | { | 654 | { |
637 | get { return m_particleSystem; } | 655 | get { return m_particleSystem; } |
@@ -668,9 +686,11 @@ namespace OpenSim.Region.Framework.Scenes | |||
668 | { | 686 | { |
669 | // If this is a linkset, we don't want the physics engine mucking up our group position here. | 687 | // If this is a linkset, we don't want the physics engine mucking up our group position here. |
670 | PhysicsActor actor = PhysActor; | 688 | PhysicsActor actor = PhysActor; |
671 | if (actor != null && ParentID == 0) | 689 | if (ParentID == 0) |
672 | { | 690 | { |
673 | m_groupPosition = actor.Position; | 691 | if (actor != null) |
692 | m_groupPosition = actor.Position; | ||
693 | return m_groupPosition; | ||
674 | } | 694 | } |
675 | 695 | ||
676 | if (ParentGroup.IsAttachment) | 696 | if (ParentGroup.IsAttachment) |
@@ -680,12 +700,14 @@ namespace OpenSim.Region.Framework.Scenes | |||
680 | return sp.AbsolutePosition; | 700 | return sp.AbsolutePosition; |
681 | } | 701 | } |
682 | 702 | ||
703 | // use root prim's group position. Physics may have updated it | ||
704 | if (ParentGroup.RootPart != this) | ||
705 | m_groupPosition = ParentGroup.RootPart.GroupPosition; | ||
683 | return m_groupPosition; | 706 | return m_groupPosition; |
684 | } | 707 | } |
685 | set | 708 | set |
686 | { | 709 | { |
687 | m_groupPosition = value; | 710 | m_groupPosition = value; |
688 | |||
689 | PhysicsActor actor = PhysActor; | 711 | PhysicsActor actor = PhysActor; |
690 | if (actor != null) | 712 | if (actor != null) |
691 | { | 713 | { |
@@ -711,16 +733,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
711 | m_log.Error("[SCENEOBJECTPART]: GROUP POSITION. " + e.Message); | 733 | m_log.Error("[SCENEOBJECTPART]: GROUP POSITION. " + e.Message); |
712 | } | 734 | } |
713 | } | 735 | } |
714 | |||
715 | // TODO if we decide to do sitting in a more SL compatible way (multiple avatars per prim), this has to be fixed, too | ||
716 | if (SitTargetAvatar != UUID.Zero) | ||
717 | { | ||
718 | ScenePresence avatar; | ||
719 | if (ParentGroup.Scene.TryGetScenePresence(SitTargetAvatar, out avatar)) | ||
720 | { | ||
721 | avatar.ParentPosition = GetWorldPosition(); | ||
722 | } | ||
723 | } | ||
724 | } | 736 | } |
725 | } | 737 | } |
726 | 738 | ||
@@ -729,7 +741,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
729 | get { return m_offsetPosition; } | 741 | get { return m_offsetPosition; } |
730 | set | 742 | set |
731 | { | 743 | { |
732 | // StoreUndoState(); | 744 | Vector3 oldpos = m_offsetPosition; |
733 | m_offsetPosition = value; | 745 | m_offsetPosition = value; |
734 | 746 | ||
735 | if (ParentGroup != null && !ParentGroup.IsDeleted) | 747 | if (ParentGroup != null && !ParentGroup.IsDeleted) |
@@ -744,7 +756,22 @@ namespace OpenSim.Region.Framework.Scenes | |||
744 | if (ParentGroup.Scene != null) | 756 | if (ParentGroup.Scene != null) |
745 | ParentGroup.Scene.PhysicsScene.AddPhysicsActorTaint(actor); | 757 | ParentGroup.Scene.PhysicsScene.AddPhysicsActorTaint(actor); |
746 | } | 758 | } |
759 | |||
760 | if (!m_parentGroup.m_dupeInProgress) | ||
761 | { | ||
762 | List<ScenePresence> avs = ParentGroup.GetLinkedAvatars(); | ||
763 | foreach (ScenePresence av in avs) | ||
764 | { | ||
765 | if (av.ParentID == m_localId) | ||
766 | { | ||
767 | Vector3 offset = (m_offsetPosition - oldpos); | ||
768 | av.AbsolutePosition += offset; | ||
769 | av.SendAvatarDataToAllAgents(); | ||
770 | } | ||
771 | } | ||
772 | } | ||
747 | } | 773 | } |
774 | TriggerScriptChangedEvent(Changed.POSITION); | ||
748 | } | 775 | } |
749 | } | 776 | } |
750 | 777 | ||
@@ -793,7 +820,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
793 | 820 | ||
794 | set | 821 | set |
795 | { | 822 | { |
796 | StoreUndoState(); | 823 | // StoreUndoState(); |
797 | m_rotationOffset = value; | 824 | m_rotationOffset = value; |
798 | 825 | ||
799 | PhysicsActor actor = PhysActor; | 826 | PhysicsActor actor = PhysActor; |
@@ -881,7 +908,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
881 | get | 908 | get |
882 | { | 909 | { |
883 | PhysicsActor actor = PhysActor; | 910 | PhysicsActor actor = PhysActor; |
884 | if ((actor != null) && actor.IsPhysical) | 911 | if ((actor != null) && actor.IsPhysical && ParentGroup.RootPart == this) |
885 | { | 912 | { |
886 | m_angularVelocity = actor.RotationalVelocity; | 913 | m_angularVelocity = actor.RotationalVelocity; |
887 | } | 914 | } |
@@ -893,7 +920,16 @@ namespace OpenSim.Region.Framework.Scenes | |||
893 | /// <summary></summary> | 920 | /// <summary></summary> |
894 | public Vector3 Acceleration | 921 | public Vector3 Acceleration |
895 | { | 922 | { |
896 | get { return m_acceleration; } | 923 | get |
924 | { | ||
925 | PhysicsActor actor = PhysActor; | ||
926 | if (actor != null) | ||
927 | { | ||
928 | m_acceleration = actor.Acceleration; | ||
929 | } | ||
930 | return m_acceleration; | ||
931 | } | ||
932 | |||
897 | set { m_acceleration = value; } | 933 | set { m_acceleration = value; } |
898 | } | 934 | } |
899 | 935 | ||
@@ -950,7 +986,10 @@ namespace OpenSim.Region.Framework.Scenes | |||
950 | public PrimitiveBaseShape Shape | 986 | public PrimitiveBaseShape Shape |
951 | { | 987 | { |
952 | get { return m_shape; } | 988 | get { return m_shape; } |
953 | set { m_shape = value;} | 989 | set |
990 | { | ||
991 | m_shape = value; | ||
992 | } | ||
954 | } | 993 | } |
955 | 994 | ||
956 | /// <summary> | 995 | /// <summary> |
@@ -963,7 +1002,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
963 | { | 1002 | { |
964 | if (m_shape != null) | 1003 | if (m_shape != null) |
965 | { | 1004 | { |
966 | StoreUndoState(); | ||
967 | 1005 | ||
968 | m_shape.Scale = value; | 1006 | m_shape.Scale = value; |
969 | 1007 | ||
@@ -990,6 +1028,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
990 | } | 1028 | } |
991 | 1029 | ||
992 | public UpdateRequired UpdateFlag { get; set; } | 1030 | public UpdateRequired UpdateFlag { get; set; } |
1031 | public bool UpdatePhysRequired { get; set; } | ||
993 | 1032 | ||
994 | /// <summary> | 1033 | /// <summary> |
995 | /// Used for media on a prim. | 1034 | /// Used for media on a prim. |
@@ -1030,10 +1069,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
1030 | { | 1069 | { |
1031 | get | 1070 | get |
1032 | { | 1071 | { |
1033 | if (ParentGroup.IsAttachment) | 1072 | return GroupPosition + (m_offsetPosition * ParentGroup.RootPart.RotationOffset); |
1034 | return GroupPosition; | ||
1035 | |||
1036 | return m_offsetPosition + m_groupPosition; | ||
1037 | } | 1073 | } |
1038 | } | 1074 | } |
1039 | 1075 | ||
@@ -1203,6 +1239,13 @@ namespace OpenSim.Region.Framework.Scenes | |||
1203 | _flags = value; | 1239 | _flags = value; |
1204 | } | 1240 | } |
1205 | } | 1241 | } |
1242 | |||
1243 | [XmlIgnore] | ||
1244 | public bool IsOccupied // KF If an av is sittingon this prim | ||
1245 | { | ||
1246 | get { return m_occupied; } | ||
1247 | set { m_occupied = value; } | ||
1248 | } | ||
1206 | 1249 | ||
1207 | /// <summary> | 1250 | /// <summary> |
1208 | /// ID of the avatar that is sat on us. If there is no such avatar then is UUID.Zero | 1251 | /// ID of the avatar that is sat on us. If there is no such avatar then is UUID.Zero |
@@ -1262,6 +1305,316 @@ namespace OpenSim.Region.Framework.Scenes | |||
1262 | set { m_collisionSoundVolume = value; } | 1305 | set { m_collisionSoundVolume = value; } |
1263 | } | 1306 | } |
1264 | 1307 | ||
1308 | public float Buoyancy | ||
1309 | { | ||
1310 | get | ||
1311 | { | ||
1312 | if (ParentGroup.RootPart == this) | ||
1313 | return m_buoyancy; | ||
1314 | |||
1315 | return ParentGroup.RootPart.Buoyancy; | ||
1316 | } | ||
1317 | set | ||
1318 | { | ||
1319 | if (ParentGroup != null && ParentGroup.RootPart != null && ParentGroup.RootPart != this) | ||
1320 | { | ||
1321 | ParentGroup.RootPart.Buoyancy = value; | ||
1322 | return; | ||
1323 | } | ||
1324 | m_buoyancy = value; | ||
1325 | if (PhysActor != null) | ||
1326 | PhysActor.Buoyancy = value; | ||
1327 | } | ||
1328 | } | ||
1329 | |||
1330 | public Vector3 Force | ||
1331 | { | ||
1332 | get | ||
1333 | { | ||
1334 | if (ParentGroup.RootPart == this) | ||
1335 | return m_force; | ||
1336 | |||
1337 | return ParentGroup.RootPart.Force; | ||
1338 | } | ||
1339 | |||
1340 | set | ||
1341 | { | ||
1342 | if (ParentGroup != null && ParentGroup.RootPart != null && ParentGroup.RootPart != this) | ||
1343 | { | ||
1344 | ParentGroup.RootPart.Force = value; | ||
1345 | return; | ||
1346 | } | ||
1347 | m_force = value; | ||
1348 | if (PhysActor != null) | ||
1349 | PhysActor.Force = value; | ||
1350 | } | ||
1351 | } | ||
1352 | |||
1353 | public Vector3 Torque | ||
1354 | { | ||
1355 | get | ||
1356 | { | ||
1357 | if (ParentGroup.RootPart == this) | ||
1358 | return m_torque; | ||
1359 | |||
1360 | return ParentGroup.RootPart.Torque; | ||
1361 | } | ||
1362 | |||
1363 | set | ||
1364 | { | ||
1365 | if (ParentGroup != null && ParentGroup.RootPart != null && ParentGroup.RootPart != this) | ||
1366 | { | ||
1367 | ParentGroup.RootPart.Torque = value; | ||
1368 | return; | ||
1369 | } | ||
1370 | m_torque = value; | ||
1371 | if (PhysActor != null) | ||
1372 | PhysActor.Torque = value; | ||
1373 | } | ||
1374 | } | ||
1375 | |||
1376 | public byte Material | ||
1377 | { | ||
1378 | get { return (byte)m_material; } | ||
1379 | set | ||
1380 | { | ||
1381 | if (value >= 0 && value <= (byte)SOPMaterialData.MaxMaterial) | ||
1382 | { | ||
1383 | bool update = false; | ||
1384 | |||
1385 | if (m_material != (Material)value) | ||
1386 | { | ||
1387 | update = true; | ||
1388 | m_material = (Material)value; | ||
1389 | } | ||
1390 | |||
1391 | if (m_friction != SOPMaterialData.friction(m_material)) | ||
1392 | { | ||
1393 | update = true; | ||
1394 | m_friction = SOPMaterialData.friction(m_material); | ||
1395 | } | ||
1396 | |||
1397 | if (m_bounce != SOPMaterialData.bounce(m_material)) | ||
1398 | { | ||
1399 | update = true; | ||
1400 | m_bounce = SOPMaterialData.bounce(m_material); | ||
1401 | } | ||
1402 | |||
1403 | if (update) | ||
1404 | { | ||
1405 | if (PhysActor != null) | ||
1406 | { | ||
1407 | PhysActor.SetMaterial((int)value); | ||
1408 | } | ||
1409 | if(ParentGroup != null) | ||
1410 | ParentGroup.HasGroupChanged = true; | ||
1411 | ScheduleFullUpdateIfNone(); | ||
1412 | UpdatePhysRequired = true; | ||
1413 | } | ||
1414 | } | ||
1415 | } | ||
1416 | } | ||
1417 | |||
1418 | // not a propriety to move to methods place later | ||
1419 | private bool HasMesh() | ||
1420 | { | ||
1421 | if (Shape != null && (Shape.SculptType == (byte)SculptType.Mesh)) | ||
1422 | return true; | ||
1423 | return false; | ||
1424 | } | ||
1425 | |||
1426 | // not a propriety to move to methods place later | ||
1427 | public byte DefaultPhysicsShapeType() | ||
1428 | { | ||
1429 | byte type; | ||
1430 | |||
1431 | if (Shape != null && (Shape.SculptType == (byte)SculptType.Mesh)) | ||
1432 | type = (byte)PhysShapeType.convex; | ||
1433 | else | ||
1434 | type = (byte)PhysShapeType.prim; | ||
1435 | |||
1436 | return type; | ||
1437 | } | ||
1438 | |||
1439 | [XmlIgnore] | ||
1440 | public bool UsesComplexCost | ||
1441 | { | ||
1442 | get | ||
1443 | { | ||
1444 | byte pst = PhysicsShapeType; | ||
1445 | if(pst == (byte) PhysShapeType.none || pst == (byte) PhysShapeType.convex || HasMesh()) | ||
1446 | return true; | ||
1447 | return false; | ||
1448 | } | ||
1449 | } | ||
1450 | |||
1451 | [XmlIgnore] | ||
1452 | public float PhysicsCost | ||
1453 | { | ||
1454 | get | ||
1455 | { | ||
1456 | if(PhysicsShapeType == (byte)PhysShapeType.none) | ||
1457 | return 0; | ||
1458 | |||
1459 | float cost = 0.1f; | ||
1460 | if (PhysActor != null) | ||
1461 | // cost += PhysActor.Cost; | ||
1462 | |||
1463 | if ((Flags & PrimFlags.Physics) != 0) | ||
1464 | cost *= (1.0f + 0.01333f * Scale.LengthSquared()); // 0.01333 == 0.04/3 | ||
1465 | return cost; | ||
1466 | } | ||
1467 | } | ||
1468 | |||
1469 | [XmlIgnore] | ||
1470 | public float StreamingCost | ||
1471 | { | ||
1472 | get | ||
1473 | { | ||
1474 | |||
1475 | |||
1476 | return 0.1f; | ||
1477 | } | ||
1478 | } | ||
1479 | |||
1480 | [XmlIgnore] | ||
1481 | public float SimulationCost | ||
1482 | { | ||
1483 | get | ||
1484 | { | ||
1485 | // ignoring scripts. Don't like considering them for this | ||
1486 | if((Flags & PrimFlags.Physics) != 0) | ||
1487 | return 1.0f; | ||
1488 | |||
1489 | return 0.5f; | ||
1490 | } | ||
1491 | } | ||
1492 | |||
1493 | public byte PhysicsShapeType | ||
1494 | { | ||
1495 | get { return m_physicsShapeType; } | ||
1496 | set | ||
1497 | { | ||
1498 | byte oldv = m_physicsShapeType; | ||
1499 | |||
1500 | if (value >= 0 && value <= (byte)PhysShapeType.convex) | ||
1501 | { | ||
1502 | if (value == (byte)PhysShapeType.none && ParentGroup != null && ParentGroup.RootPart == this) | ||
1503 | m_physicsShapeType = DefaultPhysicsShapeType(); | ||
1504 | else | ||
1505 | m_physicsShapeType = value; | ||
1506 | } | ||
1507 | else | ||
1508 | m_physicsShapeType = DefaultPhysicsShapeType(); | ||
1509 | |||
1510 | if (m_physicsShapeType != oldv && ParentGroup != null) | ||
1511 | { | ||
1512 | if (m_physicsShapeType == (byte)PhysShapeType.none) | ||
1513 | { | ||
1514 | if (PhysActor != null) | ||
1515 | { | ||
1516 | Velocity = new Vector3(0, 0, 0); | ||
1517 | Acceleration = new Vector3(0, 0, 0); | ||
1518 | if (ParentGroup.RootPart == this) | ||
1519 | AngularVelocity = new Vector3(0, 0, 0); | ||
1520 | ParentGroup.Scene.RemovePhysicalPrim(1); | ||
1521 | RemoveFromPhysics(); | ||
1522 | } | ||
1523 | } | ||
1524 | else if (PhysActor == null) | ||
1525 | ApplyPhysics((uint)Flags, VolumeDetectActive, false); | ||
1526 | else | ||
1527 | { | ||
1528 | PhysActor.PhysicsShapeType = m_physicsShapeType; | ||
1529 | if (Shape.SculptEntry) | ||
1530 | CheckSculptAndLoad(); | ||
1531 | } | ||
1532 | |||
1533 | if (ParentGroup != null) | ||
1534 | ParentGroup.HasGroupChanged = true; | ||
1535 | } | ||
1536 | |||
1537 | if (m_physicsShapeType != value) | ||
1538 | { | ||
1539 | UpdatePhysRequired = true; | ||
1540 | } | ||
1541 | } | ||
1542 | } | ||
1543 | |||
1544 | public float Density // in kg/m^3 | ||
1545 | { | ||
1546 | get { return m_density; } | ||
1547 | set | ||
1548 | { | ||
1549 | if (value >=1 && value <= 22587.0) | ||
1550 | { | ||
1551 | m_density = value; | ||
1552 | UpdatePhysRequired = true; | ||
1553 | } | ||
1554 | |||
1555 | ScheduleFullUpdateIfNone(); | ||
1556 | |||
1557 | if (ParentGroup != null) | ||
1558 | ParentGroup.HasGroupChanged = true; | ||
1559 | } | ||
1560 | } | ||
1561 | |||
1562 | public float GravityModifier | ||
1563 | { | ||
1564 | get { return m_gravitymod; } | ||
1565 | set | ||
1566 | { | ||
1567 | if( value >= -1 && value <=28.0f) | ||
1568 | { | ||
1569 | m_gravitymod = value; | ||
1570 | UpdatePhysRequired = true; | ||
1571 | } | ||
1572 | |||
1573 | ScheduleFullUpdateIfNone(); | ||
1574 | |||
1575 | if (ParentGroup != null) | ||
1576 | ParentGroup.HasGroupChanged = true; | ||
1577 | |||
1578 | } | ||
1579 | } | ||
1580 | |||
1581 | public float Friction | ||
1582 | { | ||
1583 | get { return m_friction; } | ||
1584 | set | ||
1585 | { | ||
1586 | if (value >= 0 && value <= 255.0f) | ||
1587 | { | ||
1588 | m_friction = value; | ||
1589 | UpdatePhysRequired = true; | ||
1590 | } | ||
1591 | |||
1592 | ScheduleFullUpdateIfNone(); | ||
1593 | |||
1594 | if (ParentGroup != null) | ||
1595 | ParentGroup.HasGroupChanged = true; | ||
1596 | } | ||
1597 | } | ||
1598 | |||
1599 | public float Bounciness | ||
1600 | { | ||
1601 | get { return m_bounce; } | ||
1602 | set | ||
1603 | { | ||
1604 | if (value >= 0 && value <= 1.0f) | ||
1605 | { | ||
1606 | m_bounce = value; | ||
1607 | UpdatePhysRequired = true; | ||
1608 | } | ||
1609 | |||
1610 | ScheduleFullUpdateIfNone(); | ||
1611 | |||
1612 | if (ParentGroup != null) | ||
1613 | ParentGroup.HasGroupChanged = true; | ||
1614 | } | ||
1615 | } | ||
1616 | |||
1617 | |||
1265 | #endregion Public Properties with only Get | 1618 | #endregion Public Properties with only Get |
1266 | 1619 | ||
1267 | private uint ApplyMask(uint val, bool set, uint mask) | 1620 | private uint ApplyMask(uint val, bool set, uint mask) |
@@ -1437,20 +1790,24 @@ namespace OpenSim.Region.Framework.Scenes | |||
1437 | /// </summary> | 1790 | /// </summary> |
1438 | /// <param name="impulsei">Vector force</param> | 1791 | /// <param name="impulsei">Vector force</param> |
1439 | /// <param name="localGlobalTF">true for the local frame, false for the global frame</param> | 1792 | /// <param name="localGlobalTF">true for the local frame, false for the global frame</param> |
1440 | public void SetAngularImpulse(Vector3 impulsei, bool localGlobalTF) | 1793 | |
1794 | // this is actualy Set Torque.. keeping naming so not to edit lslapi also | ||
1795 | public void SetAngularImpulse(Vector3 torquei, bool localGlobalTF) | ||
1441 | { | 1796 | { |
1442 | Vector3 impulse = impulsei; | 1797 | Vector3 torque = torquei; |
1443 | 1798 | ||
1444 | if (localGlobalTF) | 1799 | if (localGlobalTF) |
1445 | { | 1800 | { |
1801 | /* | ||
1446 | Quaternion grot = GetWorldRotation(); | 1802 | Quaternion grot = GetWorldRotation(); |
1447 | Quaternion AXgrot = grot; | 1803 | Quaternion AXgrot = grot; |
1448 | Vector3 AXimpulsei = impulsei; | 1804 | Vector3 AXimpulsei = impulsei; |
1449 | Vector3 newimpulse = AXimpulsei * AXgrot; | 1805 | Vector3 newimpulse = AXimpulsei * AXgrot; |
1450 | impulse = newimpulse; | 1806 | */ |
1807 | torque *= GetWorldRotation(); | ||
1451 | } | 1808 | } |
1452 | 1809 | ||
1453 | ParentGroup.setAngularImpulse(impulse); | 1810 | Torque = torque; |
1454 | } | 1811 | } |
1455 | 1812 | ||
1456 | /// <summary> | 1813 | /// <summary> |
@@ -1458,18 +1815,19 @@ namespace OpenSim.Region.Framework.Scenes | |||
1458 | /// </summary> | 1815 | /// </summary> |
1459 | /// <param name="rootObjectFlags"></param> | 1816 | /// <param name="rootObjectFlags"></param> |
1460 | /// <param name="VolumeDetectActive"></param> | 1817 | /// <param name="VolumeDetectActive"></param> |
1461 | public void ApplyPhysics(uint rootObjectFlags, bool VolumeDetectActive) | 1818 | |
1819 | public void ApplyPhysics(uint rootObjectFlags, bool VolumeDetectActive, bool building) | ||
1462 | { | 1820 | { |
1463 | if (!ParentGroup.Scene.CollidablePrims) | 1821 | if (!ParentGroup.Scene.CollidablePrims) |
1464 | return; | 1822 | return; |
1465 | 1823 | ||
1466 | // m_log.DebugFormat( | 1824 | if (PhysicsShapeType == (byte)PhysShapeType.none) |
1467 | // "[SCENE OBJECT PART]: Applying physics to {0} {1}, m_physicalPrim {2}", | 1825 | return; |
1468 | // Name, LocalId, UUID, m_physicalPrim); | ||
1469 | 1826 | ||
1470 | bool isPhysical = (rootObjectFlags & (uint) PrimFlags.Physics) != 0; | 1827 | bool isPhysical = (rootObjectFlags & (uint) PrimFlags.Physics) != 0; |
1471 | bool isPhantom = (rootObjectFlags & (uint) PrimFlags.Phantom) != 0; | 1828 | bool isPhantom = (rootObjectFlags & (uint) PrimFlags.Phantom) != 0; |
1472 | 1829 | ||
1830 | |||
1473 | if (IsJoint()) | 1831 | if (IsJoint()) |
1474 | { | 1832 | { |
1475 | DoPhysicsPropertyUpdate(isPhysical, true); | 1833 | DoPhysicsPropertyUpdate(isPhysical, true); |
@@ -1477,16 +1835,19 @@ namespace OpenSim.Region.Framework.Scenes | |||
1477 | else | 1835 | else |
1478 | { | 1836 | { |
1479 | // Special case for VolumeDetection: If VolumeDetection is set, the phantom flag is locally ignored | 1837 | // Special case for VolumeDetection: If VolumeDetection is set, the phantom flag is locally ignored |
1480 | if (VolumeDetectActive) | 1838 | // if (VolumeDetectActive) |
1481 | isPhantom = false; | 1839 | // isPhantom = false; |
1482 | 1840 | ||
1483 | // Added clarification.. since A rigid body is an object that you can kick around, etc. | 1841 | // Added clarification.. since A rigid body is an object that you can kick around, etc. |
1484 | bool RigidBody = isPhysical && !isPhantom; | 1842 | // bool RigidBody = isPhysical && !isPhantom; |
1485 | 1843 | ||
1486 | // The only time the physics scene shouldn't know about the prim is if it's phantom or an attachment, which is phantom by definition | 1844 | // The only time the physics scene shouldn't know about the prim is if it's phantom or an attachment, which is phantom by definition |
1487 | // or flexible | 1845 | // or flexible |
1488 | if (!isPhantom && !ParentGroup.IsAttachment && !(Shape.PathCurve == (byte)Extrusion.Flexible)) | 1846 | // if (!isPhantom && !ParentGroup.IsAttachment && !(Shape.PathCurve == (byte)Extrusion.Flexible)) |
1847 | if ((!isPhantom || isPhysical || VolumeDetectActive) && !ParentGroup.IsAttachment && !(Shape.PathCurve == (byte)Extrusion.Flexible)) | ||
1489 | { | 1848 | { |
1849 | Vector3 velocity = Velocity; | ||
1850 | Vector3 rotationalVelocity = AngularVelocity; | ||
1490 | try | 1851 | try |
1491 | { | 1852 | { |
1492 | PhysActor = ParentGroup.Scene.PhysicsScene.AddPrimShape( | 1853 | PhysActor = ParentGroup.Scene.PhysicsScene.AddPrimShape( |
@@ -1494,8 +1855,10 @@ namespace OpenSim.Region.Framework.Scenes | |||
1494 | Shape, | 1855 | Shape, |
1495 | AbsolutePosition, | 1856 | AbsolutePosition, |
1496 | Scale, | 1857 | Scale, |
1497 | RotationOffset, | 1858 | GetWorldRotation(), |
1498 | RigidBody, | 1859 | isPhysical, |
1860 | isPhantom, | ||
1861 | PhysicsShapeType, | ||
1499 | m_localId); | 1862 | m_localId); |
1500 | } | 1863 | } |
1501 | catch | 1864 | catch |
@@ -1509,8 +1872,30 @@ namespace OpenSim.Region.Framework.Scenes | |||
1509 | { | 1872 | { |
1510 | PhysActor.SOPName = this.Name; // save object into the PhysActor so ODE internals know the joint/body info | 1873 | PhysActor.SOPName = this.Name; // save object into the PhysActor so ODE internals know the joint/body info |
1511 | PhysActor.SetMaterial(Material); | 1874 | PhysActor.SetMaterial(Material); |
1512 | DoPhysicsPropertyUpdate(RigidBody, true); | 1875 | |
1513 | PhysActor.SetVolumeDetect(VolumeDetectActive ? 1 : 0); | 1876 | // if root part apply vehicle |
1877 | if (m_vehicle != null && LocalId == ParentGroup.RootPart.LocalId) | ||
1878 | m_vehicle.SetVehicle(PhysActor); | ||
1879 | |||
1880 | DoPhysicsPropertyUpdate(isPhysical, true); | ||
1881 | if(VolumeDetectActive) // change if not the default only | ||
1882 | PhysActor.SetVolumeDetect(1); | ||
1883 | |||
1884 | if (!building) | ||
1885 | PhysActor.Building = false; | ||
1886 | |||
1887 | Velocity = velocity; | ||
1888 | AngularVelocity = rotationalVelocity; | ||
1889 | PhysActor.Velocity = velocity; | ||
1890 | PhysActor.RotationalVelocity = rotationalVelocity; | ||
1891 | |||
1892 | // if not vehicle and root part apply force and torque | ||
1893 | if ((m_vehicle == null || m_vehicle.Type == Vehicle.TYPE_NONE) | ||
1894 | && LocalId == ParentGroup.RootPart.LocalId) | ||
1895 | { | ||
1896 | PhysActor.Force = Force; | ||
1897 | PhysActor.Torque = Torque; | ||
1898 | } | ||
1514 | } | 1899 | } |
1515 | } | 1900 | } |
1516 | } | 1901 | } |
@@ -1564,6 +1949,11 @@ namespace OpenSim.Region.Framework.Scenes | |||
1564 | dupe.Category = Category; | 1949 | dupe.Category = Category; |
1565 | dupe.m_rezzed = m_rezzed; | 1950 | dupe.m_rezzed = m_rezzed; |
1566 | 1951 | ||
1952 | dupe.m_UndoRedo = null; | ||
1953 | |||
1954 | dupe.IgnoreUndoUpdate = false; | ||
1955 | dupe.Undoing = false; | ||
1956 | |||
1567 | dupe.m_inventory = new SceneObjectPartInventory(dupe); | 1957 | dupe.m_inventory = new SceneObjectPartInventory(dupe); |
1568 | dupe.m_inventory.Items = (TaskInventoryDictionary)m_inventory.Items.Clone(); | 1958 | dupe.m_inventory.Items = (TaskInventoryDictionary)m_inventory.Items.Clone(); |
1569 | 1959 | ||
@@ -1579,6 +1969,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
1579 | 1969 | ||
1580 | // Move afterwards ResetIDs as it clears the localID | 1970 | // Move afterwards ResetIDs as it clears the localID |
1581 | dupe.LocalId = localID; | 1971 | dupe.LocalId = localID; |
1972 | |||
1582 | // This may be wrong... it might have to be applied in SceneObjectGroup to the object that's being duplicated. | 1973 | // This may be wrong... it might have to be applied in SceneObjectGroup to the object that's being duplicated. |
1583 | dupe.LastOwnerID = OwnerID; | 1974 | dupe.LastOwnerID = OwnerID; |
1584 | 1975 | ||
@@ -1598,6 +1989,9 @@ namespace OpenSim.Region.Framework.Scenes | |||
1598 | dupe.DoPhysicsPropertyUpdate(UsePhysics, true); | 1989 | dupe.DoPhysicsPropertyUpdate(UsePhysics, true); |
1599 | } | 1990 | } |
1600 | 1991 | ||
1992 | if (dupe.PhysActor != null) | ||
1993 | dupe.PhysActor.LocalID = localID; | ||
1994 | |||
1601 | ParentGroup.Scene.EventManager.TriggerOnSceneObjectPartCopy(dupe, this, userExposed); | 1995 | ParentGroup.Scene.EventManager.TriggerOnSceneObjectPartCopy(dupe, this, userExposed); |
1602 | 1996 | ||
1603 | // m_log.DebugFormat("[SCENE OBJECT PART]: Clone of {0} {1} finished", Name, UUID); | 1997 | // m_log.DebugFormat("[SCENE OBJECT PART]: Clone of {0} {1} finished", Name, UUID); |
@@ -1735,63 +2129,63 @@ namespace OpenSim.Region.Framework.Scenes | |||
1735 | { | 2129 | { |
1736 | if (UsePhysics != PhysActor.IsPhysical || isNew) | 2130 | if (UsePhysics != PhysActor.IsPhysical || isNew) |
1737 | { | 2131 | { |
1738 | if (PhysActor.IsPhysical) // implies UsePhysics==false for this block | 2132 | if (PhysActor.IsPhysical) |
1739 | { | 2133 | { |
1740 | if (!isNew) | 2134 | if (!isNew) // implies UsePhysics==false for this block |
2135 | { | ||
1741 | ParentGroup.Scene.RemovePhysicalPrim(1); | 2136 | ParentGroup.Scene.RemovePhysicalPrim(1); |
1742 | 2137 | ||
1743 | PhysActor.OnRequestTerseUpdate -= PhysicsRequestingTerseUpdate; | 2138 | Velocity = new Vector3(0, 0, 0); |
1744 | PhysActor.OnOutOfBounds -= PhysicsOutOfBounds; | 2139 | Acceleration = new Vector3(0, 0, 0); |
1745 | PhysActor.delink(); | 2140 | if (ParentGroup.RootPart == this) |
2141 | AngularVelocity = new Vector3(0, 0, 0); | ||
1746 | 2142 | ||
1747 | if (ParentGroup.Scene.PhysicsScene.SupportsNINJAJoints && (!isNew)) | 2143 | if (PhysActor.Phantom) |
1748 | { | 2144 | { |
1749 | // destroy all joints connected to this now deactivated body | 2145 | RemoveFromPhysics(); |
1750 | ParentGroup.Scene.PhysicsScene.RemoveAllJointsConnectedToActorThreadLocked(PhysActor); | 2146 | return; |
1751 | } | 2147 | } |
1752 | 2148 | ||
1753 | // stop client-side interpolation of all joint proxy objects that have just been deleted | 2149 | PhysActor.IsPhysical = UsePhysics; |
1754 | // this is done because RemoveAllJointsConnectedToActor invokes the OnJointDeactivated callback, | 2150 | PhysActor.OnRequestTerseUpdate -= PhysicsRequestingTerseUpdate; |
1755 | // which stops client-side interpolation of deactivated joint proxy objects. | 2151 | PhysActor.OnOutOfBounds -= PhysicsOutOfBounds; |
2152 | PhysActor.delink(); | ||
2153 | if (ParentGroup.Scene.PhysicsScene.SupportsNINJAJoints) | ||
2154 | { | ||
2155 | // destroy all joints connected to this now deactivated body | ||
2156 | ParentGroup.Scene.PhysicsScene.RemoveAllJointsConnectedToActorThreadLocked(PhysActor); | ||
2157 | } | ||
2158 | } | ||
1756 | } | 2159 | } |
1757 | 2160 | ||
1758 | if (!UsePhysics && !isNew) | 2161 | if (PhysActor.IsPhysical != UsePhysics) |
1759 | { | 2162 | PhysActor.IsPhysical = UsePhysics; |
1760 | // reset velocity to 0 on physics switch-off. Without that, the client thinks the | ||
1761 | // prim still has velocity and continues to interpolate its position along the old | ||
1762 | // velocity-vector. | ||
1763 | Velocity = new Vector3(0, 0, 0); | ||
1764 | Acceleration = new Vector3(0, 0, 0); | ||
1765 | AngularVelocity = new Vector3(0, 0, 0); | ||
1766 | //RotationalVelocity = new Vector3(0, 0, 0); | ||
1767 | } | ||
1768 | 2163 | ||
1769 | PhysActor.IsPhysical = UsePhysics; | 2164 | if (UsePhysics) |
2165 | { | ||
2166 | if (ParentGroup.RootPart.KeyframeMotion != null) | ||
2167 | ParentGroup.RootPart.KeyframeMotion.Stop(); | ||
2168 | ParentGroup.RootPart.KeyframeMotion = null; | ||
2169 | ParentGroup.Scene.AddPhysicalPrim(1); | ||
1770 | 2170 | ||
1771 | // If we're not what we're supposed to be in the physics scene, recreate ourselves. | 2171 | PhysActor.OnRequestTerseUpdate += PhysicsRequestingTerseUpdate; |
1772 | //m_parentGroup.Scene.PhysicsScene.RemovePrim(PhysActor); | 2172 | PhysActor.OnOutOfBounds += PhysicsOutOfBounds; |
1773 | /// that's not wholesome. Had to make Scene public | ||
1774 | //PhysActor = null; | ||
1775 | 2173 | ||
1776 | if ((Flags & PrimFlags.Phantom) == 0) | 2174 | if (ParentID != 0 && ParentID != LocalId) |
1777 | { | ||
1778 | if (UsePhysics) | ||
1779 | { | 2175 | { |
1780 | ParentGroup.Scene.AddPhysicalPrim(1); | 2176 | if (ParentGroup.RootPart.PhysActor != null) |
1781 | |||
1782 | PhysActor.OnRequestTerseUpdate += PhysicsRequestingTerseUpdate; | ||
1783 | PhysActor.OnOutOfBounds += PhysicsOutOfBounds; | ||
1784 | if (ParentID != 0 && ParentID != LocalId) | ||
1785 | { | 2177 | { |
1786 | if (ParentGroup.RootPart.PhysActor != null) | 2178 | PhysActor.link(ParentGroup.RootPart.PhysActor); |
1787 | { | ||
1788 | PhysActor.link(ParentGroup.RootPart.PhysActor); | ||
1789 | } | ||
1790 | } | 2179 | } |
1791 | } | 2180 | } |
1792 | } | 2181 | } |
1793 | } | 2182 | } |
1794 | 2183 | ||
2184 | bool phan = ((Flags & PrimFlags.Phantom) != 0); | ||
2185 | if (PhysActor.Phantom != phan) | ||
2186 | PhysActor.Phantom = phan; | ||
2187 | |||
2188 | |||
1795 | // If this part is a sculpt then delay the physics update until we've asynchronously loaded the | 2189 | // If this part is a sculpt then delay the physics update until we've asynchronously loaded the |
1796 | // mesh data. | 2190 | // mesh data. |
1797 | if (Shape.SculptEntry) | 2191 | if (Shape.SculptEntry) |
@@ -1924,10 +2318,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
1924 | 2318 | ||
1925 | public Vector3 GetForce() | 2319 | public Vector3 GetForce() |
1926 | { | 2320 | { |
1927 | if (PhysActor != null) | 2321 | return Force; |
1928 | return PhysActor.Force; | ||
1929 | else | ||
1930 | return Vector3.Zero; | ||
1931 | } | 2322 | } |
1932 | 2323 | ||
1933 | /// <summary> | 2324 | /// <summary> |
@@ -2561,9 +2952,9 @@ namespace OpenSim.Region.Framework.Scenes | |||
2561 | Vector3 newpos = new Vector3(PhysActor.Position.GetBytes(), 0); | 2952 | Vector3 newpos = new Vector3(PhysActor.Position.GetBytes(), 0); |
2562 | 2953 | ||
2563 | if (ParentGroup.Scene.TestBorderCross(newpos, Cardinals.N) | 2954 | if (ParentGroup.Scene.TestBorderCross(newpos, Cardinals.N) |
2564 | | ParentGroup.Scene.TestBorderCross(newpos, Cardinals.S) | 2955 | || ParentGroup.Scene.TestBorderCross(newpos, Cardinals.S) |
2565 | | ParentGroup.Scene.TestBorderCross(newpos, Cardinals.E) | 2956 | || ParentGroup.Scene.TestBorderCross(newpos, Cardinals.E) |
2566 | | ParentGroup.Scene.TestBorderCross(newpos, Cardinals.W)) | 2957 | || ParentGroup.Scene.TestBorderCross(newpos, Cardinals.W)) |
2567 | { | 2958 | { |
2568 | ParentGroup.AbsolutePosition = newpos; | 2959 | ParentGroup.AbsolutePosition = newpos; |
2569 | return; | 2960 | return; |
@@ -2584,17 +2975,18 @@ namespace OpenSim.Region.Framework.Scenes | |||
2584 | //Trys to fetch sound id from prim's inventory. | 2975 | //Trys to fetch sound id from prim's inventory. |
2585 | //Prim's inventory doesn't support non script items yet | 2976 | //Prim's inventory doesn't support non script items yet |
2586 | 2977 | ||
2587 | lock (TaskInventory) | 2978 | TaskInventory.LockItemsForRead(true); |
2979 | |||
2980 | foreach (KeyValuePair<UUID, TaskInventoryItem> item in TaskInventory) | ||
2588 | { | 2981 | { |
2589 | foreach (KeyValuePair<UUID, TaskInventoryItem> item in TaskInventory) | 2982 | if (item.Value.Name == sound) |
2590 | { | 2983 | { |
2591 | if (item.Value.Name == sound) | 2984 | soundID = item.Value.ItemID; |
2592 | { | 2985 | break; |
2593 | soundID = item.Value.ItemID; | ||
2594 | break; | ||
2595 | } | ||
2596 | } | 2986 | } |
2597 | } | 2987 | } |
2988 | |||
2989 | TaskInventory.LockItemsForRead(false); | ||
2598 | } | 2990 | } |
2599 | 2991 | ||
2600 | ParentGroup.Scene.ForEachRootScenePresence(delegate(ScenePresence sp) | 2992 | ParentGroup.Scene.ForEachRootScenePresence(delegate(ScenePresence sp) |
@@ -2715,6 +3107,19 @@ namespace OpenSim.Region.Framework.Scenes | |||
2715 | APIDTarget = Quaternion.Identity; | 3107 | APIDTarget = Quaternion.Identity; |
2716 | } | 3108 | } |
2717 | 3109 | ||
3110 | |||
3111 | |||
3112 | public void ScheduleFullUpdateIfNone() | ||
3113 | { | ||
3114 | if (ParentGroup == null) | ||
3115 | return; | ||
3116 | |||
3117 | // ??? ParentGroup.HasGroupChanged = true; | ||
3118 | |||
3119 | if (UpdateFlag != UpdateRequired.FULL) | ||
3120 | ScheduleFullUpdate(); | ||
3121 | } | ||
3122 | |||
2718 | /// <summary> | 3123 | /// <summary> |
2719 | /// Schedules this prim for a full update | 3124 | /// Schedules this prim for a full update |
2720 | /// </summary> | 3125 | /// </summary> |
@@ -2914,8 +3319,8 @@ namespace OpenSim.Region.Framework.Scenes | |||
2914 | { | 3319 | { |
2915 | const float ROTATION_TOLERANCE = 0.01f; | 3320 | const float ROTATION_TOLERANCE = 0.01f; |
2916 | const float VELOCITY_TOLERANCE = 0.001f; | 3321 | const float VELOCITY_TOLERANCE = 0.001f; |
2917 | const float POSITION_TOLERANCE = 0.05f; | 3322 | const float POSITION_TOLERANCE = 0.05f; // I don't like this, but I suppose it's necessary |
2918 | const int TIME_MS_TOLERANCE = 3000; | 3323 | const int TIME_MS_TOLERANCE = 200; //llSetPos has a 200ms delay. This should NOT be 3 seconds. |
2919 | 3324 | ||
2920 | switch (UpdateFlag) | 3325 | switch (UpdateFlag) |
2921 | { | 3326 | { |
@@ -2977,17 +3382,16 @@ namespace OpenSim.Region.Framework.Scenes | |||
2977 | if (!UUID.TryParse(sound, out soundID)) | 3382 | if (!UUID.TryParse(sound, out soundID)) |
2978 | { | 3383 | { |
2979 | // search sound file from inventory | 3384 | // search sound file from inventory |
2980 | lock (TaskInventory) | 3385 | TaskInventory.LockItemsForRead(true); |
3386 | foreach (KeyValuePair<UUID, TaskInventoryItem> item in TaskInventory) | ||
2981 | { | 3387 | { |
2982 | foreach (KeyValuePair<UUID, TaskInventoryItem> item in TaskInventory) | 3388 | if (item.Value.Name == sound && item.Value.Type == (int)AssetType.Sound) |
2983 | { | 3389 | { |
2984 | if (item.Value.Name == sound && item.Value.Type == (int)AssetType.Sound) | 3390 | soundID = item.Value.ItemID; |
2985 | { | 3391 | break; |
2986 | soundID = item.Value.ItemID; | ||
2987 | break; | ||
2988 | } | ||
2989 | } | 3392 | } |
2990 | } | 3393 | } |
3394 | TaskInventory.LockItemsForRead(false); | ||
2991 | } | 3395 | } |
2992 | 3396 | ||
2993 | if (soundID == UUID.Zero) | 3397 | if (soundID == UUID.Zero) |
@@ -3072,10 +3476,13 @@ namespace OpenSim.Region.Framework.Scenes | |||
3072 | 3476 | ||
3073 | public void SetBuoyancy(float fvalue) | 3477 | public void SetBuoyancy(float fvalue) |
3074 | { | 3478 | { |
3479 | Buoyancy = fvalue; | ||
3480 | /* | ||
3075 | if (PhysActor != null) | 3481 | if (PhysActor != null) |
3076 | { | 3482 | { |
3077 | PhysActor.Buoyancy = fvalue; | 3483 | PhysActor.Buoyancy = fvalue; |
3078 | } | 3484 | } |
3485 | */ | ||
3079 | } | 3486 | } |
3080 | 3487 | ||
3081 | public void SetDieAtEdge(bool p) | 3488 | public void SetDieAtEdge(bool p) |
@@ -3103,23 +3510,83 @@ namespace OpenSim.Region.Framework.Scenes | |||
3103 | 3510 | ||
3104 | public void SetForce(Vector3 force) | 3511 | public void SetForce(Vector3 force) |
3105 | { | 3512 | { |
3513 | Force = force; | ||
3514 | /* | ||
3106 | if (PhysActor != null) | 3515 | if (PhysActor != null) |
3107 | { | 3516 | { |
3108 | PhysActor.Force = force; | 3517 | PhysActor.Force = force; |
3109 | } | 3518 | } |
3519 | */ | ||
3520 | } | ||
3521 | |||
3522 | public SOPVehicle sopVehicle | ||
3523 | { | ||
3524 | get | ||
3525 | { | ||
3526 | return m_vehicle; | ||
3527 | } | ||
3528 | set | ||
3529 | { | ||
3530 | m_vehicle = value; | ||
3531 | } | ||
3532 | } | ||
3533 | |||
3534 | |||
3535 | public int VehicleType | ||
3536 | { | ||
3537 | get | ||
3538 | { | ||
3539 | if (m_vehicle == null) | ||
3540 | return (int)Vehicle.TYPE_NONE; | ||
3541 | else | ||
3542 | return (int)m_vehicle.Type; | ||
3543 | } | ||
3544 | set | ||
3545 | { | ||
3546 | SetVehicleType(value); | ||
3547 | } | ||
3110 | } | 3548 | } |
3111 | 3549 | ||
3112 | public void SetVehicleType(int type) | 3550 | public void SetVehicleType(int type) |
3113 | { | 3551 | { |
3114 | if (PhysActor != null) | 3552 | m_vehicle = null; |
3553 | |||
3554 | if (type == (int)Vehicle.TYPE_NONE) | ||
3555 | { | ||
3556 | if (_parentID ==0 && PhysActor != null) | ||
3557 | PhysActor.VehicleType = (int)Vehicle.TYPE_NONE; | ||
3558 | return; | ||
3559 | } | ||
3560 | m_vehicle = new SOPVehicle(); | ||
3561 | m_vehicle.ProcessTypeChange((Vehicle)type); | ||
3562 | { | ||
3563 | if (_parentID ==0 && PhysActor != null) | ||
3564 | PhysActor.VehicleType = type; | ||
3565 | return; | ||
3566 | } | ||
3567 | } | ||
3568 | |||
3569 | public void SetVehicleFlags(int param, bool remove) | ||
3570 | { | ||
3571 | if (m_vehicle == null) | ||
3572 | return; | ||
3573 | |||
3574 | m_vehicle.ProcessVehicleFlags(param, remove); | ||
3575 | |||
3576 | if (_parentID ==0 && PhysActor != null) | ||
3115 | { | 3577 | { |
3116 | PhysActor.VehicleType = type; | 3578 | PhysActor.VehicleFlags(param, remove); |
3117 | } | 3579 | } |
3118 | } | 3580 | } |
3119 | 3581 | ||
3120 | public void SetVehicleFloatParam(int param, float value) | 3582 | public void SetVehicleFloatParam(int param, float value) |
3121 | { | 3583 | { |
3122 | if (PhysActor != null) | 3584 | if (m_vehicle == null) |
3585 | return; | ||
3586 | |||
3587 | m_vehicle.ProcessFloatVehicleParam((Vehicle)param, value); | ||
3588 | |||
3589 | if (_parentID == 0 && PhysActor != null) | ||
3123 | { | 3590 | { |
3124 | PhysActor.VehicleFloatParam(param, value); | 3591 | PhysActor.VehicleFloatParam(param, value); |
3125 | } | 3592 | } |
@@ -3127,7 +3594,12 @@ namespace OpenSim.Region.Framework.Scenes | |||
3127 | 3594 | ||
3128 | public void SetVehicleVectorParam(int param, Vector3 value) | 3595 | public void SetVehicleVectorParam(int param, Vector3 value) |
3129 | { | 3596 | { |
3130 | if (PhysActor != null) | 3597 | if (m_vehicle == null) |
3598 | return; | ||
3599 | |||
3600 | m_vehicle.ProcessVectorVehicleParam((Vehicle)param, value); | ||
3601 | |||
3602 | if (_parentID == 0 && PhysActor != null) | ||
3131 | { | 3603 | { |
3132 | PhysActor.VehicleVectorParam(param, value); | 3604 | PhysActor.VehicleVectorParam(param, value); |
3133 | } | 3605 | } |
@@ -3135,7 +3607,12 @@ namespace OpenSim.Region.Framework.Scenes | |||
3135 | 3607 | ||
3136 | public void SetVehicleRotationParam(int param, Quaternion rotation) | 3608 | public void SetVehicleRotationParam(int param, Quaternion rotation) |
3137 | { | 3609 | { |
3138 | if (PhysActor != null) | 3610 | if (m_vehicle == null) |
3611 | return; | ||
3612 | |||
3613 | m_vehicle.ProcessRotationVehicleParam((Vehicle)param, rotation); | ||
3614 | |||
3615 | if (_parentID == 0 && PhysActor != null) | ||
3139 | { | 3616 | { |
3140 | PhysActor.VehicleRotationParam(param, rotation); | 3617 | PhysActor.VehicleRotationParam(param, rotation); |
3141 | } | 3618 | } |
@@ -3322,13 +3799,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
3322 | hasProfileCut = hasDimple; // is it the same thing? | 3799 | hasProfileCut = hasDimple; // is it the same thing? |
3323 | } | 3800 | } |
3324 | 3801 | ||
3325 | public void SetVehicleFlags(int param, bool remove) | ||
3326 | { | ||
3327 | if (PhysActor != null) | ||
3328 | { | ||
3329 | PhysActor.VehicleFlags(param, remove); | ||
3330 | } | ||
3331 | } | ||
3332 | 3802 | ||
3333 | public void SetGroup(UUID groupID, IClientAPI client) | 3803 | public void SetGroup(UUID groupID, IClientAPI client) |
3334 | { | 3804 | { |
@@ -3431,68 +3901,18 @@ namespace OpenSim.Region.Framework.Scenes | |||
3431 | //ParentGroup.ScheduleGroupForFullUpdate(); | 3901 | //ParentGroup.ScheduleGroupForFullUpdate(); |
3432 | } | 3902 | } |
3433 | 3903 | ||
3434 | public void StoreUndoState() | 3904 | public void StoreUndoState(ObjectChangeType change) |
3435 | { | 3905 | { |
3436 | StoreUndoState(false); | 3906 | if (m_UndoRedo == null) |
3437 | } | 3907 | m_UndoRedo = new UndoRedoState(5); |
3438 | 3908 | ||
3439 | public void StoreUndoState(bool forGroup) | 3909 | lock (m_UndoRedo) |
3440 | { | ||
3441 | if (!Undoing) | ||
3442 | { | 3910 | { |
3443 | if (!IgnoreUndoUpdate) | 3911 | if (!Undoing && !IgnoreUndoUpdate && ParentGroup != null) // just to read better - undo is in progress, or suspended |
3444 | { | 3912 | { |
3445 | if (ParentGroup != null) | 3913 | m_UndoRedo.StoreUndo(this, change); |
3446 | { | ||
3447 | lock (m_undo) | ||
3448 | { | ||
3449 | if (m_undo.Count > 0) | ||
3450 | { | ||
3451 | UndoState last = m_undo.Peek(); | ||
3452 | if (last != null) | ||
3453 | { | ||
3454 | // TODO: May need to fix for group comparison | ||
3455 | if (last.Compare(this)) | ||
3456 | { | ||
3457 | // m_log.DebugFormat( | ||
3458 | // "[SCENE OBJECT PART]: Not storing undo for {0} {1} since current state is same as last undo state, initial stack size {2}", | ||
3459 | // Name, LocalId, m_undo.Count); | ||
3460 | |||
3461 | return; | ||
3462 | } | ||
3463 | } | ||
3464 | } | ||
3465 | |||
3466 | // m_log.DebugFormat( | ||
3467 | // "[SCENE OBJECT PART]: Storing undo state for {0} {1}, forGroup {2}, initial stack size {3}", | ||
3468 | // Name, LocalId, forGroup, m_undo.Count); | ||
3469 | |||
3470 | if (ParentGroup.GetSceneMaxUndo() > 0) | ||
3471 | { | ||
3472 | UndoState nUndo = new UndoState(this, forGroup); | ||
3473 | |||
3474 | m_undo.Push(nUndo); | ||
3475 | |||
3476 | if (m_redo.Count > 0) | ||
3477 | m_redo.Clear(); | ||
3478 | |||
3479 | // m_log.DebugFormat( | ||
3480 | // "[SCENE OBJECT PART]: Stored undo state for {0} {1}, forGroup {2}, stack size now {3}", | ||
3481 | // Name, LocalId, forGroup, m_undo.Count); | ||
3482 | } | ||
3483 | } | ||
3484 | } | ||
3485 | } | 3914 | } |
3486 | // else | ||
3487 | // { | ||
3488 | // m_log.DebugFormat("[SCENE OBJECT PART]: Ignoring undo store for {0} {1}", Name, LocalId); | ||
3489 | // } | ||
3490 | } | 3915 | } |
3491 | // else | ||
3492 | // { | ||
3493 | // m_log.DebugFormat( | ||
3494 | // "[SCENE OBJECT PART]: Ignoring undo store for {0} {1} since already undoing", Name, LocalId); | ||
3495 | // } | ||
3496 | } | 3916 | } |
3497 | 3917 | ||
3498 | /// <summary> | 3918 | /// <summary> |
@@ -3502,84 +3922,46 @@ namespace OpenSim.Region.Framework.Scenes | |||
3502 | { | 3922 | { |
3503 | get | 3923 | get |
3504 | { | 3924 | { |
3505 | lock (m_undo) | 3925 | if (m_UndoRedo == null) |
3506 | return m_undo.Count; | 3926 | return 0; |
3927 | return m_UndoRedo.Count; | ||
3507 | } | 3928 | } |
3508 | } | 3929 | } |
3509 | 3930 | ||
3510 | public void Undo() | 3931 | public void Undo() |
3511 | { | 3932 | { |
3512 | lock (m_undo) | 3933 | if (m_UndoRedo == null || Undoing || ParentGroup == null) |
3513 | { | 3934 | return; |
3514 | // m_log.DebugFormat( | ||
3515 | // "[SCENE OBJECT PART]: Handling undo request for {0} {1}, stack size {2}", | ||
3516 | // Name, LocalId, m_undo.Count); | ||
3517 | |||
3518 | if (m_undo.Count > 0) | ||
3519 | { | ||
3520 | UndoState goback = m_undo.Pop(); | ||
3521 | |||
3522 | if (goback != null) | ||
3523 | { | ||
3524 | UndoState nUndo = null; | ||
3525 | |||
3526 | if (ParentGroup.GetSceneMaxUndo() > 0) | ||
3527 | { | ||
3528 | nUndo = new UndoState(this, goback.ForGroup); | ||
3529 | } | ||
3530 | |||
3531 | goback.PlaybackState(this); | ||
3532 | |||
3533 | if (nUndo != null) | ||
3534 | m_redo.Push(nUndo); | ||
3535 | } | ||
3536 | } | ||
3537 | 3935 | ||
3538 | // m_log.DebugFormat( | 3936 | lock (m_UndoRedo) |
3539 | // "[SCENE OBJECT PART]: Handled undo request for {0} {1}, stack size now {2}", | 3937 | { |
3540 | // Name, LocalId, m_undo.Count); | 3938 | Undoing = true; |
3939 | m_UndoRedo.Undo(this); | ||
3940 | Undoing = false; | ||
3541 | } | 3941 | } |
3542 | } | 3942 | } |
3543 | 3943 | ||
3544 | public void Redo() | 3944 | public void Redo() |
3545 | { | 3945 | { |
3546 | lock (m_undo) | 3946 | if (m_UndoRedo == null || Undoing || ParentGroup == null) |
3547 | { | 3947 | return; |
3548 | // m_log.DebugFormat( | ||
3549 | // "[SCENE OBJECT PART]: Handling redo request for {0} {1}, stack size {2}", | ||
3550 | // Name, LocalId, m_redo.Count); | ||
3551 | |||
3552 | if (m_redo.Count > 0) | ||
3553 | { | ||
3554 | UndoState gofwd = m_redo.Pop(); | ||
3555 | |||
3556 | if (gofwd != null) | ||
3557 | { | ||
3558 | if (ParentGroup.GetSceneMaxUndo() > 0) | ||
3559 | { | ||
3560 | UndoState nUndo = new UndoState(this, gofwd.ForGroup); | ||
3561 | |||
3562 | m_undo.Push(nUndo); | ||
3563 | } | ||
3564 | |||
3565 | gofwd.PlayfwdState(this); | ||
3566 | } | ||
3567 | 3948 | ||
3568 | // m_log.DebugFormat( | 3949 | lock (m_UndoRedo) |
3569 | // "[SCENE OBJECT PART]: Handled redo request for {0} {1}, stack size now {2}", | 3950 | { |
3570 | // Name, LocalId, m_redo.Count); | 3951 | Undoing = true; |
3571 | } | 3952 | m_UndoRedo.Redo(this); |
3953 | Undoing = false; | ||
3572 | } | 3954 | } |
3573 | } | 3955 | } |
3574 | 3956 | ||
3575 | public void ClearUndoState() | 3957 | public void ClearUndoState() |
3576 | { | 3958 | { |
3577 | // m_log.DebugFormat("[SCENE OBJECT PART]: Clearing undo and redo stacks in {0} {1}", Name, LocalId); | 3959 | if (m_UndoRedo == null || Undoing) |
3960 | return; | ||
3578 | 3961 | ||
3579 | lock (m_undo) | 3962 | lock (m_UndoRedo) |
3580 | { | 3963 | { |
3581 | m_undo.Clear(); | 3964 | m_UndoRedo.Clear(); |
3582 | m_redo.Clear(); | ||
3583 | } | 3965 | } |
3584 | } | 3966 | } |
3585 | 3967 | ||
@@ -4209,6 +4591,27 @@ namespace OpenSim.Region.Framework.Scenes | |||
4209 | } | 4591 | } |
4210 | } | 4592 | } |
4211 | 4593 | ||
4594 | |||
4595 | public void UpdateExtraPhysics(ExtraPhysicsData physdata) | ||
4596 | { | ||
4597 | if (physdata.PhysShapeType == PhysShapeType.invalid || ParentGroup == null) | ||
4598 | return; | ||
4599 | |||
4600 | if (PhysicsShapeType != (byte)physdata.PhysShapeType) | ||
4601 | { | ||
4602 | PhysicsShapeType = (byte)physdata.PhysShapeType; | ||
4603 | |||
4604 | } | ||
4605 | |||
4606 | if(Density != physdata.Density) | ||
4607 | Density = physdata.Density; | ||
4608 | if(GravityModifier != physdata.GravitationModifier) | ||
4609 | GravityModifier = physdata.GravitationModifier; | ||
4610 | if(Friction != physdata.Friction) | ||
4611 | Friction = physdata.Friction; | ||
4612 | if(Bounciness != physdata.Bounce) | ||
4613 | Bounciness = physdata.Bounce; | ||
4614 | } | ||
4212 | /// <summary> | 4615 | /// <summary> |
4213 | /// Update the flags on this prim. This covers properties such as phantom, physics and temporary. | 4616 | /// Update the flags on this prim. This covers properties such as phantom, physics and temporary. |
4214 | /// </summary> | 4617 | /// </summary> |
@@ -4216,7 +4619,8 @@ namespace OpenSim.Region.Framework.Scenes | |||
4216 | /// <param name="SetTemporary"></param> | 4619 | /// <param name="SetTemporary"></param> |
4217 | /// <param name="SetPhantom"></param> | 4620 | /// <param name="SetPhantom"></param> |
4218 | /// <param name="SetVD"></param> | 4621 | /// <param name="SetVD"></param> |
4219 | public void UpdatePrimFlags(bool UsePhysics, bool SetTemporary, bool SetPhantom, bool SetVD) | 4622 | // public void UpdatePrimFlags(bool UsePhysics, bool SetTemporary, bool SetPhantom, bool SetVD) |
4623 | public void UpdatePrimFlags(bool UsePhysics, bool SetTemporary, bool SetPhantom, bool SetVD, bool building) | ||
4220 | { | 4624 | { |
4221 | bool wasUsingPhysics = ((Flags & PrimFlags.Physics) != 0); | 4625 | bool wasUsingPhysics = ((Flags & PrimFlags.Physics) != 0); |
4222 | bool wasTemporary = ((Flags & PrimFlags.TemporaryOnRez) != 0); | 4626 | bool wasTemporary = ((Flags & PrimFlags.TemporaryOnRez) != 0); |
@@ -4226,41 +4630,58 @@ namespace OpenSim.Region.Framework.Scenes | |||
4226 | if ((UsePhysics == wasUsingPhysics) && (wasTemporary == SetTemporary) && (wasPhantom == SetPhantom) && (SetVD == wasVD)) | 4630 | if ((UsePhysics == wasUsingPhysics) && (wasTemporary == SetTemporary) && (wasPhantom == SetPhantom) && (SetVD == wasVD)) |
4227 | return; | 4631 | return; |
4228 | 4632 | ||
4633 | // do this first | ||
4634 | if (building && PhysActor != null && PhysActor.Building != building) | ||
4635 | PhysActor.Building = building; | ||
4636 | |||
4229 | // Special cases for VD. VD can only be called from a script | 4637 | // Special cases for VD. VD can only be called from a script |
4230 | // and can't be combined with changes to other states. So we can rely | 4638 | // and can't be combined with changes to other states. So we can rely |
4231 | // that... | 4639 | // that... |
4232 | // ... if VD is changed, all others are not. | 4640 | // ... if VD is changed, all others are not. |
4233 | // ... if one of the others is changed, VD is not. | 4641 | // ... if one of the others is changed, VD is not. |
4642 | |||
4643 | /* | ||
4234 | if (SetVD) // VD is active, special logic applies | 4644 | if (SetVD) // VD is active, special logic applies |
4235 | { | ||
4236 | // State machine logic for VolumeDetect | ||
4237 | // More logic below | ||
4238 | bool phanReset = (SetPhantom != wasPhantom) && !SetPhantom; | ||
4239 | 4645 | ||
4240 | if (phanReset) // Phantom changes from on to off switch VD off too | 4646 | volume detection is now independent of phantom in sl |
4241 | { | 4647 | |
4242 | SetVD = false; // Switch it of for the course of this routine | 4648 | { |
4243 | VolumeDetectActive = false; // and also permanently | 4649 | // State machine logic for VolumeDetect |
4244 | if (PhysActor != null) | 4650 | // More logic below |
4245 | PhysActor.SetVolumeDetect(0); // Let physics know about it too | 4651 | |
4246 | } | 4652 | |
4247 | else | 4653 | bool phanReset = (SetPhantom != wasPhantom) && !SetPhantom; |
4248 | { | 4654 | |
4249 | // If volumedetect is active we don't want phantom to be applied. | 4655 | if (phanReset) // Phantom changes from on to off switch VD off too |
4250 | // If this is a new call to VD out of the state "phantom" | 4656 | { |
4251 | // this will also cause the prim to be visible to physics | 4657 | SetVD = false; // Switch it of for the course of this routine |
4658 | VolumeDetectActive = false; // and also permanently | ||
4659 | if (PhysActor != null) | ||
4660 | PhysActor.SetVolumeDetect(0); // Let physics know about it too | ||
4661 | } | ||
4662 | else | ||
4663 | { | ||
4664 | // If volumedetect is active we don't want phantom to be applied. | ||
4665 | // If this is a new call to VD out of the state "phantom" | ||
4666 | // this will also cause the prim to be visible to physics | ||
4252 | SetPhantom = false; | 4667 | SetPhantom = false; |
4253 | } | 4668 | } |
4669 | } | ||
4670 | else if (wasVD) | ||
4671 | { | ||
4672 | // Correspondingly, if VD is turned off, also turn off phantom | ||
4673 | SetPhantom = false; | ||
4254 | } | 4674 | } |
4255 | 4675 | ||
4256 | if (UsePhysics && IsJoint()) | 4676 | if (UsePhysics && IsJoint()) |
4257 | { | 4677 | { |
4258 | SetPhantom = true; | 4678 | SetPhantom = true; |
4259 | } | 4679 | } |
4260 | 4680 | */ | |
4261 | if (UsePhysics) | 4681 | if (UsePhysics) |
4262 | { | 4682 | { |
4263 | AddFlag(PrimFlags.Physics); | 4683 | AddFlag(PrimFlags.Physics); |
4684 | /* | ||
4264 | if (!wasUsingPhysics) | 4685 | if (!wasUsingPhysics) |
4265 | { | 4686 | { |
4266 | DoPhysicsPropertyUpdate(UsePhysics, false); | 4687 | DoPhysicsPropertyUpdate(UsePhysics, false); |
@@ -4273,78 +4694,100 @@ namespace OpenSim.Region.Framework.Scenes | |||
4273 | } | 4694 | } |
4274 | } | 4695 | } |
4275 | } | 4696 | } |
4697 | */ | ||
4276 | } | 4698 | } |
4277 | else | 4699 | else |
4278 | { | 4700 | { |
4279 | RemFlag(PrimFlags.Physics); | 4701 | RemFlag(PrimFlags.Physics); |
4702 | /* | ||
4280 | if (wasUsingPhysics) | 4703 | if (wasUsingPhysics) |
4281 | { | 4704 | { |
4282 | DoPhysicsPropertyUpdate(UsePhysics, false); | 4705 | DoPhysicsPropertyUpdate(UsePhysics, false); |
4283 | } | 4706 | } |
4284 | } | 4707 | */ |
4708 | } | ||
4285 | 4709 | ||
4286 | if (SetPhantom | 4710 | if (SetPhantom) |
4287 | || ParentGroup.IsAttachment | 4711 | AddFlag(PrimFlags.Phantom); |
4712 | else | ||
4713 | RemFlag(PrimFlags.Phantom); | ||
4714 | |||
4715 | if ((SetPhantom && !UsePhysics) || ParentGroup.IsAttachment || PhysicsShapeType == (byte)PhysShapeType.none | ||
4288 | || (Shape.PathCurve == (byte)Extrusion.Flexible)) // note: this may have been changed above in the case of joints | 4716 | || (Shape.PathCurve == (byte)Extrusion.Flexible)) // note: this may have been changed above in the case of joints |
4289 | { | 4717 | { |
4290 | AddFlag(PrimFlags.Phantom); | 4718 | // AddFlag(PrimFlags.Phantom); |
4719 | |||
4720 | Velocity = new Vector3(0, 0, 0); | ||
4721 | Acceleration = new Vector3(0, 0, 0); | ||
4722 | if (ParentGroup.RootPart == this) | ||
4723 | AngularVelocity = new Vector3(0, 0, 0); | ||
4291 | 4724 | ||
4292 | if (PhysActor != null) | 4725 | if (PhysActor != null) |
4726 | { | ||
4727 | ParentGroup.Scene.RemovePhysicalPrim(1); | ||
4293 | RemoveFromPhysics(); | 4728 | RemoveFromPhysics(); |
4729 | } | ||
4294 | } | 4730 | } |
4295 | else // Not phantom | 4731 | else |
4296 | { | 4732 | { |
4297 | RemFlag(PrimFlags.Phantom); | ||
4298 | |||
4299 | if (ParentGroup.Scene == null) | 4733 | if (ParentGroup.Scene == null) |
4300 | return; | 4734 | return; |
4301 | 4735 | ||
4302 | if (ParentGroup.Scene.CollidablePrims && PhysActor == null) | 4736 | if (ParentGroup.Scene.CollidablePrims) |
4303 | { | 4737 | { |
4304 | // It's not phantom anymore. So make sure the physics engine get's knowledge of it | 4738 | if (PhysActor == null) |
4305 | PhysActor = ParentGroup.Scene.PhysicsScene.AddPrimShape( | ||
4306 | string.Format("{0}/{1}", Name, UUID), | ||
4307 | Shape, | ||
4308 | AbsolutePosition, | ||
4309 | Scale, | ||
4310 | RotationOffset, | ||
4311 | UsePhysics, | ||
4312 | m_localId); | ||
4313 | |||
4314 | PhysActor.SetMaterial(Material); | ||
4315 | DoPhysicsPropertyUpdate(UsePhysics, true); | ||
4316 | |||
4317 | if (!ParentGroup.IsDeleted) | ||
4318 | { | 4739 | { |
4319 | if (LocalId == ParentGroup.RootPart.LocalId) | 4740 | PhysActor = ParentGroup.Scene.PhysicsScene.AddPrimShape( |
4741 | string.Format("{0}/{1}", Name, UUID), | ||
4742 | Shape, | ||
4743 | AbsolutePosition, | ||
4744 | Scale, | ||
4745 | GetWorldRotation(), //physics wants world rotation like all other functions send | ||
4746 | UsePhysics, | ||
4747 | SetPhantom, | ||
4748 | PhysicsShapeType, | ||
4749 | m_localId); | ||
4750 | |||
4751 | PhysActor.SetMaterial(Material); | ||
4752 | |||
4753 | // if root part apply vehicle | ||
4754 | if (m_vehicle != null && LocalId == ParentGroup.RootPart.LocalId) | ||
4755 | m_vehicle.SetVehicle(PhysActor); | ||
4756 | |||
4757 | DoPhysicsPropertyUpdate(UsePhysics, true); | ||
4758 | |||
4759 | if (!ParentGroup.IsDeleted) | ||
4320 | { | 4760 | { |
4321 | ParentGroup.CheckSculptAndLoad(); | 4761 | if (LocalId == ParentGroup.RootPart.LocalId) |
4762 | { | ||
4763 | ParentGroup.CheckSculptAndLoad(); | ||
4764 | } | ||
4322 | } | 4765 | } |
4323 | } | ||
4324 | 4766 | ||
4325 | if ( | 4767 | if ( |
4326 | ((AggregateScriptEvents & scriptEvents.collision) != 0) || | 4768 | ((AggregateScriptEvents & scriptEvents.collision) != 0) || |
4327 | ((AggregateScriptEvents & scriptEvents.collision_end) != 0) || | 4769 | ((AggregateScriptEvents & scriptEvents.collision_end) != 0) || |
4328 | ((AggregateScriptEvents & scriptEvents.collision_start) != 0) || | 4770 | ((AggregateScriptEvents & scriptEvents.collision_start) != 0) || |
4329 | ((AggregateScriptEvents & scriptEvents.land_collision_start) != 0) || | 4771 | ((AggregateScriptEvents & scriptEvents.land_collision_start) != 0) || |
4330 | ((AggregateScriptEvents & scriptEvents.land_collision) != 0) || | 4772 | ((AggregateScriptEvents & scriptEvents.land_collision) != 0) || |
4331 | ((AggregateScriptEvents & scriptEvents.land_collision_end) != 0) || | 4773 | ((AggregateScriptEvents & scriptEvents.land_collision_end) != 0) || |
4332 | (CollisionSound != UUID.Zero) | 4774 | (CollisionSound != UUID.Zero) |
4333 | ) | 4775 | ) |
4334 | { | 4776 | { |
4335 | PhysActor.OnCollisionUpdate += PhysicsCollision; | 4777 | PhysActor.OnCollisionUpdate += PhysicsCollision; |
4336 | PhysActor.SubscribeEvents(1000); | 4778 | PhysActor.SubscribeEvents(1000); |
4779 | } | ||
4337 | } | 4780 | } |
4338 | } | 4781 | else // it already has a physical representation |
4339 | else // it already has a physical representation | ||
4340 | { | ||
4341 | DoPhysicsPropertyUpdate(UsePhysics, false); // Update physical status. If it's phantom this will remove the prim | ||
4342 | |||
4343 | if (!ParentGroup.IsDeleted) | ||
4344 | { | 4782 | { |
4345 | if (LocalId == ParentGroup.RootPart.LocalId) | 4783 | DoPhysicsPropertyUpdate(UsePhysics, false); // Update physical status. |
4784 | |||
4785 | if (!ParentGroup.IsDeleted) | ||
4346 | { | 4786 | { |
4347 | ParentGroup.CheckSculptAndLoad(); | 4787 | if (LocalId == ParentGroup.RootPart.LocalId) |
4788 | { | ||
4789 | ParentGroup.CheckSculptAndLoad(); | ||
4790 | } | ||
4348 | } | 4791 | } |
4349 | } | 4792 | } |
4350 | } | 4793 | } |
@@ -4360,7 +4803,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
4360 | if (this.PhysActor != null) | 4803 | if (this.PhysActor != null) |
4361 | { | 4804 | { |
4362 | PhysActor.SetVolumeDetect(1); | 4805 | PhysActor.SetVolumeDetect(1); |
4363 | AddFlag(PrimFlags.Phantom); // We set this flag also if VD is active | 4806 | // AddFlag(PrimFlags.Phantom); // We set this flag also if VD is active |
4364 | this.VolumeDetectActive = true; | 4807 | this.VolumeDetectActive = true; |
4365 | } | 4808 | } |
4366 | } | 4809 | } |
@@ -4368,8 +4811,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
4368 | { | 4811 | { |
4369 | // Remove VolumeDetect in any case. Note, it's safe to call SetVolumeDetect as often as you like | 4812 | // Remove VolumeDetect in any case. Note, it's safe to call SetVolumeDetect as often as you like |
4370 | // (mumbles, well, at least if you have infinte CPU powers :-)) | 4813 | // (mumbles, well, at least if you have infinte CPU powers :-)) |
4371 | PhysicsActor pa = this.PhysActor; | 4814 | if (this.PhysActor != null) |
4372 | if (pa != null) | ||
4373 | { | 4815 | { |
4374 | PhysActor.SetVolumeDetect(0); | 4816 | PhysActor.SetVolumeDetect(0); |
4375 | } | 4817 | } |
@@ -4387,12 +4829,15 @@ namespace OpenSim.Region.Framework.Scenes | |||
4387 | } | 4829 | } |
4388 | // m_log.Debug("Update: PHY:" + UsePhysics.ToString() + ", T:" + IsTemporary.ToString() + ", PHA:" + IsPhantom.ToString() + " S:" + CastsShadows.ToString()); | 4830 | // m_log.Debug("Update: PHY:" + UsePhysics.ToString() + ", T:" + IsTemporary.ToString() + ", PHA:" + IsPhantom.ToString() + " S:" + CastsShadows.ToString()); |
4389 | 4831 | ||
4832 | // and last in case we have a new actor and not building | ||
4833 | if (PhysActor != null && PhysActor.Building != building) | ||
4834 | PhysActor.Building = building; | ||
4390 | if (ParentGroup != null) | 4835 | if (ParentGroup != null) |
4391 | { | 4836 | { |
4392 | ParentGroup.HasGroupChanged = true; | 4837 | ParentGroup.HasGroupChanged = true; |
4393 | ScheduleFullUpdate(); | 4838 | ScheduleFullUpdate(); |
4394 | } | 4839 | } |
4395 | 4840 | ||
4396 | // m_log.DebugFormat("[SCENE OBJECT PART]: Updated PrimFlags on {0} {1} to {2}", Name, LocalId, Flags); | 4841 | // m_log.DebugFormat("[SCENE OBJECT PART]: Updated PrimFlags on {0} {1} to {2}", Name, LocalId, Flags); |
4397 | } | 4842 | } |
4398 | 4843 | ||
@@ -4750,5 +5195,17 @@ namespace OpenSim.Region.Framework.Scenes | |||
4750 | Color color = Color; | 5195 | Color color = Color; |
4751 | return new Color4(color.R, color.G, color.B, (byte)(0xFF - color.A)); | 5196 | return new Color4(color.R, color.G, color.B, (byte)(0xFF - color.A)); |
4752 | } | 5197 | } |
5198 | |||
5199 | public void ResetOwnerChangeFlag() | ||
5200 | { | ||
5201 | List<UUID> inv = Inventory.GetInventoryList(); | ||
5202 | |||
5203 | foreach (UUID itemID in inv) | ||
5204 | { | ||
5205 | TaskInventoryItem item = Inventory.GetInventoryItem(itemID); | ||
5206 | item.OwnerChanged = false; | ||
5207 | Inventory.UpdateInventoryItem(item, false, false); | ||
5208 | } | ||
5209 | } | ||
4753 | } | 5210 | } |
4754 | } | 5211 | } |