diff options
Diffstat (limited to 'OpenSim/Region/Framework/Scenes/SceneGraph.cs')
-rw-r--r-- | OpenSim/Region/Framework/Scenes/SceneGraph.cs | 159 |
1 files changed, 121 insertions, 38 deletions
diff --git a/OpenSim/Region/Framework/Scenes/SceneGraph.cs b/OpenSim/Region/Framework/Scenes/SceneGraph.cs index e7175c5..8823df1 100644 --- a/OpenSim/Region/Framework/Scenes/SceneGraph.cs +++ b/OpenSim/Region/Framework/Scenes/SceneGraph.cs | |||
@@ -43,6 +43,12 @@ namespace OpenSim.Region.Framework.Scenes | |||
43 | 43 | ||
44 | public delegate void ObjectDuplicateDelegate(EntityBase original, EntityBase clone); | 44 | public delegate void ObjectDuplicateDelegate(EntityBase original, EntityBase clone); |
45 | 45 | ||
46 | public delegate void AttachToBackupDelegate(SceneObjectGroup sog); | ||
47 | |||
48 | public delegate void DetachFromBackupDelegate(SceneObjectGroup sog); | ||
49 | |||
50 | public delegate void ChangedBackupDelegate(SceneObjectGroup sog); | ||
51 | |||
46 | public delegate void ObjectCreateDelegate(EntityBase obj); | 52 | public delegate void ObjectCreateDelegate(EntityBase obj); |
47 | 53 | ||
48 | public delegate void ObjectDeleteDelegate(EntityBase obj); | 54 | public delegate void ObjectDeleteDelegate(EntityBase obj); |
@@ -61,6 +67,9 @@ namespace OpenSim.Region.Framework.Scenes | |||
61 | private PhysicsCrash handlerPhysicsCrash = null; | 67 | private PhysicsCrash handlerPhysicsCrash = null; |
62 | 68 | ||
63 | public event ObjectDuplicateDelegate OnObjectDuplicate; | 69 | public event ObjectDuplicateDelegate OnObjectDuplicate; |
70 | public event AttachToBackupDelegate OnAttachToBackup; | ||
71 | public event DetachFromBackupDelegate OnDetachFromBackup; | ||
72 | public event ChangedBackupDelegate OnChangeBackup; | ||
64 | public event ObjectCreateDelegate OnObjectCreate; | 73 | public event ObjectCreateDelegate OnObjectCreate; |
65 | public event ObjectDeleteDelegate OnObjectRemove; | 74 | public event ObjectDeleteDelegate OnObjectRemove; |
66 | 75 | ||
@@ -68,7 +77,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
68 | 77 | ||
69 | #region Fields | 78 | #region Fields |
70 | 79 | ||
71 | protected object m_presenceLock = new object(); | 80 | protected OpenMetaverse.ReaderWriterLockSlim m_scenePresencesLock = new OpenMetaverse.ReaderWriterLockSlim(); |
72 | protected Dictionary<UUID, ScenePresence> m_scenePresenceMap = new Dictionary<UUID, ScenePresence>(); | 81 | protected Dictionary<UUID, ScenePresence> m_scenePresenceMap = new Dictionary<UUID, ScenePresence>(); |
73 | protected List<ScenePresence> m_scenePresenceArray = new List<ScenePresence>(); | 82 | protected List<ScenePresence> m_scenePresenceArray = new List<ScenePresence>(); |
74 | 83 | ||
@@ -127,13 +136,18 @@ namespace OpenSim.Region.Framework.Scenes | |||
127 | 136 | ||
128 | protected internal void Close() | 137 | protected internal void Close() |
129 | { | 138 | { |
130 | lock (m_presenceLock) | 139 | m_scenePresencesLock.EnterWriteLock(); |
140 | try | ||
131 | { | 141 | { |
132 | Dictionary<UUID, ScenePresence> newmap = new Dictionary<UUID, ScenePresence>(); | 142 | Dictionary<UUID, ScenePresence> newmap = new Dictionary<UUID, ScenePresence>(); |
133 | List<ScenePresence> newlist = new List<ScenePresence>(); | 143 | List<ScenePresence> newlist = new List<ScenePresence>(); |
134 | m_scenePresenceMap = newmap; | 144 | m_scenePresenceMap = newmap; |
135 | m_scenePresenceArray = newlist; | 145 | m_scenePresenceArray = newlist; |
136 | } | 146 | } |
147 | finally | ||
148 | { | ||
149 | m_scenePresencesLock.ExitWriteLock(); | ||
150 | } | ||
137 | 151 | ||
138 | lock (SceneObjectGroupsByFullID) | 152 | lock (SceneObjectGroupsByFullID) |
139 | SceneObjectGroupsByFullID.Clear(); | 153 | SceneObjectGroupsByFullID.Clear(); |
@@ -212,27 +226,8 @@ namespace OpenSim.Region.Framework.Scenes | |||
212 | if (sp.IsChildAgent) | 226 | if (sp.IsChildAgent) |
213 | return; | 227 | return; |
214 | 228 | ||
215 | if (sp.ParentID != 0) | 229 | coarseLocations.Add(sp.AbsolutePosition); |
216 | { | 230 | avatarUUIDs.Add(sp.UUID); |
217 | // sitting avatar | ||
218 | SceneObjectPart sop = m_parentScene.GetSceneObjectPart(sp.ParentID); | ||
219 | if (sop != null) | ||
220 | { | ||
221 | coarseLocations.Add(sop.AbsolutePosition + sp.AbsolutePosition); | ||
222 | avatarUUIDs.Add(sp.UUID); | ||
223 | } | ||
224 | else | ||
225 | { | ||
226 | // we can't find the parent.. ! arg! | ||
227 | coarseLocations.Add(sp.AbsolutePosition); | ||
228 | avatarUUIDs.Add(sp.UUID); | ||
229 | } | ||
230 | } | ||
231 | else | ||
232 | { | ||
233 | coarseLocations.Add(sp.AbsolutePosition); | ||
234 | avatarUUIDs.Add(sp.UUID); | ||
235 | } | ||
236 | } | 231 | } |
237 | } | 232 | } |
238 | 233 | ||
@@ -262,6 +257,33 @@ namespace OpenSim.Region.Framework.Scenes | |||
262 | protected internal bool AddRestoredSceneObject( | 257 | protected internal bool AddRestoredSceneObject( |
263 | SceneObjectGroup sceneObject, bool attachToBackup, bool alreadyPersisted, bool sendClientUpdates) | 258 | SceneObjectGroup sceneObject, bool attachToBackup, bool alreadyPersisted, bool sendClientUpdates) |
264 | { | 259 | { |
260 | if (!m_parentScene.CombineRegions) | ||
261 | { | ||
262 | // KF: Check for out-of-region, move inside and make static. | ||
263 | Vector3 npos = new Vector3(sceneObject.RootPart.GroupPosition.X, | ||
264 | sceneObject.RootPart.GroupPosition.Y, | ||
265 | sceneObject.RootPart.GroupPosition.Z); | ||
266 | if (!(((sceneObject.RootPart.Shape.PCode == (byte)PCode.Prim) && (sceneObject.RootPart.Shape.State != 0))) && (npos.X < 0.0 || npos.Y < 0.0 || npos.Z < 0.0 || | ||
267 | npos.X > Constants.RegionSize || | ||
268 | npos.Y > Constants.RegionSize)) | ||
269 | { | ||
270 | if (npos.X < 0.0) npos.X = 1.0f; | ||
271 | if (npos.Y < 0.0) npos.Y = 1.0f; | ||
272 | if (npos.Z < 0.0) npos.Z = 0.0f; | ||
273 | if (npos.X > Constants.RegionSize) npos.X = Constants.RegionSize - 1.0f; | ||
274 | if (npos.Y > Constants.RegionSize) npos.Y = Constants.RegionSize - 1.0f; | ||
275 | |||
276 | foreach (SceneObjectPart part in sceneObject.Children.Values) | ||
277 | { | ||
278 | part.GroupPosition = npos; | ||
279 | } | ||
280 | sceneObject.RootPart.Velocity = Vector3.Zero; | ||
281 | sceneObject.RootPart.AngularVelocity = Vector3.Zero; | ||
282 | sceneObject.RootPart.Acceleration = Vector3.Zero; | ||
283 | sceneObject.RootPart.Velocity = Vector3.Zero; | ||
284 | } | ||
285 | } | ||
286 | |||
265 | if (!alreadyPersisted) | 287 | if (!alreadyPersisted) |
266 | { | 288 | { |
267 | sceneObject.ForceInventoryPersistence(); | 289 | sceneObject.ForceInventoryPersistence(); |
@@ -473,6 +495,30 @@ namespace OpenSim.Region.Framework.Scenes | |||
473 | } | 495 | } |
474 | } | 496 | } |
475 | 497 | ||
498 | public void FireAttachToBackup(SceneObjectGroup obj) | ||
499 | { | ||
500 | if (OnAttachToBackup != null) | ||
501 | { | ||
502 | OnAttachToBackup(obj); | ||
503 | } | ||
504 | } | ||
505 | |||
506 | public void FireDetachFromBackup(SceneObjectGroup obj) | ||
507 | { | ||
508 | if (OnDetachFromBackup != null) | ||
509 | { | ||
510 | OnDetachFromBackup(obj); | ||
511 | } | ||
512 | } | ||
513 | |||
514 | public void FireChangeBackup(SceneObjectGroup obj) | ||
515 | { | ||
516 | if (OnChangeBackup != null) | ||
517 | { | ||
518 | OnChangeBackup(obj); | ||
519 | } | ||
520 | } | ||
521 | |||
476 | /// <summary> | 522 | /// <summary> |
477 | /// Process all pending updates | 523 | /// Process all pending updates |
478 | /// </summary> | 524 | /// </summary> |
@@ -609,7 +655,8 @@ namespace OpenSim.Region.Framework.Scenes | |||
609 | 655 | ||
610 | Entities[presence.UUID] = presence; | 656 | Entities[presence.UUID] = presence; |
611 | 657 | ||
612 | lock (m_presenceLock) | 658 | m_scenePresencesLock.EnterWriteLock(); |
659 | try | ||
613 | { | 660 | { |
614 | Dictionary<UUID, ScenePresence> newmap = new Dictionary<UUID, ScenePresence>(m_scenePresenceMap); | 661 | Dictionary<UUID, ScenePresence> newmap = new Dictionary<UUID, ScenePresence>(m_scenePresenceMap); |
615 | List<ScenePresence> newlist = new List<ScenePresence>(m_scenePresenceArray); | 662 | List<ScenePresence> newlist = new List<ScenePresence>(m_scenePresenceArray); |
@@ -633,6 +680,10 @@ namespace OpenSim.Region.Framework.Scenes | |||
633 | m_scenePresenceMap = newmap; | 680 | m_scenePresenceMap = newmap; |
634 | m_scenePresenceArray = newlist; | 681 | m_scenePresenceArray = newlist; |
635 | } | 682 | } |
683 | finally | ||
684 | { | ||
685 | m_scenePresencesLock.ExitWriteLock(); | ||
686 | } | ||
636 | } | 687 | } |
637 | 688 | ||
638 | /// <summary> | 689 | /// <summary> |
@@ -647,7 +698,8 @@ namespace OpenSim.Region.Framework.Scenes | |||
647 | agentID); | 698 | agentID); |
648 | } | 699 | } |
649 | 700 | ||
650 | lock (m_presenceLock) | 701 | m_scenePresencesLock.EnterWriteLock(); |
702 | try | ||
651 | { | 703 | { |
652 | Dictionary<UUID, ScenePresence> newmap = new Dictionary<UUID, ScenePresence>(m_scenePresenceMap); | 704 | Dictionary<UUID, ScenePresence> newmap = new Dictionary<UUID, ScenePresence>(m_scenePresenceMap); |
653 | List<ScenePresence> newlist = new List<ScenePresence>(m_scenePresenceArray); | 705 | List<ScenePresence> newlist = new List<ScenePresence>(m_scenePresenceArray); |
@@ -669,6 +721,10 @@ namespace OpenSim.Region.Framework.Scenes | |||
669 | m_log.WarnFormat("[SCENE]: Tried to remove non-existent scene presence with agent ID {0} from scene ScenePresences list", agentID); | 721 | m_log.WarnFormat("[SCENE]: Tried to remove non-existent scene presence with agent ID {0} from scene ScenePresences list", agentID); |
670 | } | 722 | } |
671 | } | 723 | } |
724 | finally | ||
725 | { | ||
726 | m_scenePresencesLock.ExitWriteLock(); | ||
727 | } | ||
672 | } | 728 | } |
673 | 729 | ||
674 | protected internal void SwapRootChildAgent(bool direction_RC_CR_T_F) | 730 | protected internal void SwapRootChildAgent(bool direction_RC_CR_T_F) |
@@ -1084,9 +1140,11 @@ namespace OpenSim.Region.Framework.Scenes | |||
1084 | /// <param name="action"></param> | 1140 | /// <param name="action"></param> |
1085 | protected internal void ForEachSOG(Action<SceneObjectGroup> action) | 1141 | protected internal void ForEachSOG(Action<SceneObjectGroup> action) |
1086 | { | 1142 | { |
1087 | List<SceneObjectGroup> objlist = new List<SceneObjectGroup>(SceneObjectGroupsByFullID.Values); | 1143 | List<EntityBase> objlist = Entities.GetAllByType<SceneObjectGroup>(); |
1088 | foreach (SceneObjectGroup obj in objlist) | 1144 | foreach (EntityBase ent in objlist) |
1089 | { | 1145 | { |
1146 | SceneObjectGroup obj = (SceneObjectGroup)ent; | ||
1147 | |||
1090 | try | 1148 | try |
1091 | { | 1149 | { |
1092 | action(obj); | 1150 | action(obj); |
@@ -1543,10 +1601,13 @@ namespace OpenSim.Region.Framework.Scenes | |||
1543 | /// <param name="childPrims"></param> | 1601 | /// <param name="childPrims"></param> |
1544 | protected internal void LinkObjects(SceneObjectPart root, List<SceneObjectPart> children) | 1602 | protected internal void LinkObjects(SceneObjectPart root, List<SceneObjectPart> children) |
1545 | { | 1603 | { |
1604 | SceneObjectGroup parentGroup = root.ParentGroup; | ||
1605 | if (parentGroup == null) return; | ||
1546 | Monitor.Enter(m_updateLock); | 1606 | Monitor.Enter(m_updateLock); |
1607 | |||
1547 | try | 1608 | try |
1548 | { | 1609 | { |
1549 | SceneObjectGroup parentGroup = root.ParentGroup; | 1610 | parentGroup.areUpdatesSuspended = true; |
1550 | 1611 | ||
1551 | List<SceneObjectGroup> childGroups = new List<SceneObjectGroup>(); | 1612 | List<SceneObjectGroup> childGroups = new List<SceneObjectGroup>(); |
1552 | if (parentGroup != null) | 1613 | if (parentGroup != null) |
@@ -1585,12 +1646,12 @@ namespace OpenSim.Region.Framework.Scenes | |||
1585 | // occur on link to invoke this elsewhere (such as object selection) | 1646 | // occur on link to invoke this elsewhere (such as object selection) |
1586 | parentGroup.RootPart.CreateSelected = true; | 1647 | parentGroup.RootPart.CreateSelected = true; |
1587 | parentGroup.TriggerScriptChangedEvent(Changed.LINK); | 1648 | parentGroup.TriggerScriptChangedEvent(Changed.LINK); |
1588 | parentGroup.HasGroupChanged = true; | ||
1589 | parentGroup.ScheduleGroupForFullUpdate(); | ||
1590 | |||
1591 | } | 1649 | } |
1592 | finally | 1650 | finally |
1593 | { | 1651 | { |
1652 | parentGroup.areUpdatesSuspended = false; | ||
1653 | parentGroup.HasGroupChanged = true; | ||
1654 | parentGroup.ScheduleGroupForFullUpdate(); | ||
1594 | Monitor.Exit(m_updateLock); | 1655 | Monitor.Exit(m_updateLock); |
1595 | } | 1656 | } |
1596 | } | 1657 | } |
@@ -1627,11 +1688,22 @@ namespace OpenSim.Region.Framework.Scenes | |||
1627 | } | 1688 | } |
1628 | } | 1689 | } |
1629 | 1690 | ||
1630 | foreach (SceneObjectPart child in childParts) | 1691 | if (childParts.Count > 0) |
1631 | { | 1692 | { |
1632 | // Unlink all child parts from their groups | 1693 | try |
1633 | // | 1694 | { |
1634 | child.ParentGroup.DelinkFromGroup(child, true); | 1695 | childParts[0].ParentGroup.areUpdatesSuspended = true; |
1696 | foreach (SceneObjectPart child in childParts) | ||
1697 | { | ||
1698 | // Unlink all child parts from their groups | ||
1699 | // | ||
1700 | child.ParentGroup.DelinkFromGroup(child, true); | ||
1701 | } | ||
1702 | } | ||
1703 | finally | ||
1704 | { | ||
1705 | childParts[0].ParentGroup.areUpdatesSuspended = false; | ||
1706 | } | ||
1635 | } | 1707 | } |
1636 | 1708 | ||
1637 | foreach (SceneObjectPart root in rootParts) | 1709 | foreach (SceneObjectPart root in rootParts) |
@@ -1662,10 +1734,21 @@ namespace OpenSim.Region.Framework.Scenes | |||
1662 | if (numChildren > 1) | 1734 | if (numChildren > 1) |
1663 | sendEventsToRemainder = false; | 1735 | sendEventsToRemainder = false; |
1664 | 1736 | ||
1665 | foreach (SceneObjectPart p in newSet) | 1737 | if (newSet.Count > 0) |
1666 | { | 1738 | { |
1667 | if (p != group.RootPart) | 1739 | try |
1668 | group.DelinkFromGroup(p, sendEventsToRemainder); | 1740 | { |
1741 | newSet[0].ParentGroup.areUpdatesSuspended = true; | ||
1742 | foreach (SceneObjectPart p in newSet) | ||
1743 | { | ||
1744 | if (p != group.RootPart) | ||
1745 | group.DelinkFromGroup(p, sendEventsToRemainder); | ||
1746 | } | ||
1747 | } | ||
1748 | finally | ||
1749 | { | ||
1750 | newSet[0].ParentGroup.areUpdatesSuspended = false; | ||
1751 | } | ||
1669 | } | 1752 | } |
1670 | 1753 | ||
1671 | // If there is more than one prim remaining, we | 1754 | // If there is more than one prim remaining, we |