diff options
Diffstat (limited to '')
-rw-r--r-- | OpenSim/Region/Environment/Scenes/SceneCommunicationService.cs | 266 |
1 files changed, 200 insertions, 66 deletions
diff --git a/OpenSim/Region/Environment/Scenes/SceneCommunicationService.cs b/OpenSim/Region/Environment/Scenes/SceneCommunicationService.cs index 2b638e3..b89f753 100644 --- a/OpenSim/Region/Environment/Scenes/SceneCommunicationService.cs +++ b/OpenSim/Region/Environment/Scenes/SceneCommunicationService.cs | |||
@@ -255,7 +255,7 @@ namespace OpenSim.Region.Environment.Scenes | |||
255 | #region Inform Client of Neighbours | 255 | #region Inform Client of Neighbours |
256 | 256 | ||
257 | private delegate void InformClientOfNeighbourDelegate( | 257 | private delegate void InformClientOfNeighbourDelegate( |
258 | ScenePresence avatar, AgentCircuitData a, ulong regionHandle, IPEndPoint endPoint); | 258 | ScenePresence avatar, AgentCircuitData a, SimpleRegionInfo reg, IPEndPoint endPoint); |
259 | 259 | ||
260 | private void InformClientOfNeighbourCompleted(IAsyncResult iar) | 260 | private void InformClientOfNeighbourCompleted(IAsyncResult iar) |
261 | { | 261 | { |
@@ -273,28 +273,40 @@ namespace OpenSim.Region.Environment.Scenes | |||
273 | /// <param name="a"></param> | 273 | /// <param name="a"></param> |
274 | /// <param name="regionHandle"></param> | 274 | /// <param name="regionHandle"></param> |
275 | /// <param name="endPoint"></param> | 275 | /// <param name="endPoint"></param> |
276 | private void InformClientOfNeighbourAsync(ScenePresence avatar, AgentCircuitData a, ulong regionHandle, | 276 | private void InformClientOfNeighbourAsync(ScenePresence avatar, AgentCircuitData a, SimpleRegionInfo reg, |
277 | IPEndPoint endPoint) | 277 | IPEndPoint endPoint) |
278 | { | 278 | { |
279 | m_log.Info("[INTERGRID]: Starting to inform client about neighbours"); | 279 | uint x, y; |
280 | bool regionAccepted = m_commsProvider.InterRegion.InformRegionOfChildAgent(regionHandle, a); | 280 | Utils.LongToUInts(reg.RegionHandle, out x, out y); |
281 | x = x / Constants.RegionSize; | ||
282 | y = y / Constants.RegionSize; | ||
283 | m_log.Info("[INTERGRID]: Starting to inform client about neighbour " + x + ", " + y + "(" + endPoint.ToString() + ")"); | ||
284 | |||
285 | string capsPath = "http://" + reg.ExternalHostName + ":" + reg.HttpPort | ||
286 | + "/CAPS/" + a.CapsPath + "0000/"; | ||
287 | |||
288 | bool regionAccepted = m_commsProvider.InterRegion.InformRegionOfChildAgent(reg.RegionHandle, a); | ||
281 | 289 | ||
282 | if (regionAccepted) | 290 | if (regionAccepted) |
283 | { | 291 | { |
284 | IEventQueue eq = avatar.Scene.RequestModuleInterface<IEventQueue>(); | 292 | IEventQueue eq = avatar.Scene.RequestModuleInterface<IEventQueue>(); |
285 | if (eq != null) | 293 | if (eq != null) |
286 | { | 294 | { |
287 | OSD Item = EventQueueHelper.EnableSimulator(regionHandle, endPoint); | 295 | OSD Item = EventQueueHelper.EnableSimulator(reg.RegionHandle, endPoint); |
288 | eq.Enqueue(Item, avatar.UUID); | 296 | eq.Enqueue(Item, avatar.UUID); |
297 | |||
298 | Item = EventQueueHelper.EstablishAgentCommunication(avatar.UUID, endPoint.ToString(), capsPath); | ||
299 | eq.Enqueue(Item, avatar.UUID); | ||
300 | |||
301 | m_log.DebugFormat("[CAPS]: Sending new CAPS seed url {0} to client {1} in region {2}", capsPath, avatar.UUID, avatar.Scene.RegionInfo.RegionName); | ||
289 | } | 302 | } |
290 | else | 303 | else |
291 | { | 304 | { |
292 | avatar.ControllingClient.InformClientOfNeighbour(regionHandle, endPoint); | 305 | avatar.ControllingClient.InformClientOfNeighbour(reg.RegionHandle, endPoint); |
293 | // TODO: make Event Queue disablable! | 306 | // TODO: make Event Queue disablable! |
294 | } | 307 | } |
295 | 308 | ||
296 | avatar.AddNeighbourRegion(regionHandle); | 309 | m_log.Info("[INTERGRID]: Completed inform client about neighbour " + endPoint.ToString()); |
297 | m_log.Info("[INTERGRID]: Completed inform client about neighbours"); | ||
298 | } | 310 | } |
299 | } | 311 | } |
300 | 312 | ||
@@ -330,21 +342,72 @@ namespace OpenSim.Region.Environment.Scenes | |||
330 | neighbours = | 342 | neighbours = |
331 | m_commsProvider.GridService.RequestNeighbours(m_regionInfo.RegionLocX, m_regionInfo.RegionLocY); | 343 | m_commsProvider.GridService.RequestNeighbours(m_regionInfo.RegionLocX, m_regionInfo.RegionLocY); |
332 | 344 | ||
333 | if (neighbours != null) | 345 | m_log.Debug("[SCM]: EnableChildAgents from " + avatar.Scene.RegionInfo.RegionName); |
346 | |||
347 | /// We need to find the difference between the new regions where there are no child agents | ||
348 | /// and the regions where there are already child agents. We only send notification to the former. | ||
349 | List<ulong> neighbourHandles = NeighbourHandles(neighbours); // on this region | ||
350 | neighbourHandles.Add(avatar.Scene.RegionInfo.RegionHandle); // add this region too | ||
351 | List<ulong> previousRegionNeighbourHandles = new List<ulong>(avatar.Scene.GetChildrenSeeds(avatar.UUID).Keys); | ||
352 | List<ulong> newRegions = NewNeighbours(neighbourHandles, previousRegionNeighbourHandles); | ||
353 | List<ulong> oldRegions = OldNeighbours(neighbourHandles, previousRegionNeighbourHandles); | ||
354 | |||
355 | //Dump("Current Neighbors", neighbourHandles); | ||
356 | //Dump("Previous Neighbours", previousRegionNeighbourHandles); | ||
357 | //Dump("New Neighbours", newRegions); | ||
358 | //Dump("Old Neighbours", oldRegions); | ||
359 | |||
360 | /// Update the scene presence's known regions here on this region | ||
361 | avatar.DropOldNeighbours(oldRegions); | ||
362 | |||
363 | /// Collect as many seeds as possible | ||
364 | Dictionary<ulong, string> seeds = new Dictionary<ulong, string>(avatar.Scene.GetChildrenSeeds(avatar.UUID)); | ||
365 | if (!seeds.ContainsKey(avatar.Scene.RegionInfo.RegionHandle)) | ||
366 | seeds.Add(avatar.Scene.RegionInfo.RegionHandle, avatar.ControllingClient.RequestClientInfo().CapsPath); | ||
367 | |||
368 | /// Create the necessary child agents | ||
369 | List<AgentCircuitData> cagents = new List<AgentCircuitData>(); | ||
370 | foreach (SimpleRegionInfo neighbour in neighbours) | ||
334 | { | 371 | { |
335 | for (int i = 0; i < neighbours.Count; i++) | 372 | AgentCircuitData agent = avatar.ControllingClient.RequestClientInfo(); |
373 | agent.BaseFolder = UUID.Zero; | ||
374 | agent.InventoryFolder = UUID.Zero; | ||
375 | agent.startpos = new Vector3(128, 128, 70); | ||
376 | agent.child = true; | ||
377 | |||
378 | if (newRegions.Contains(neighbour.RegionHandle)) | ||
336 | { | 379 | { |
337 | AgentCircuitData agent = avatar.ControllingClient.RequestClientInfo(); | 380 | agent.CapsPath = Util.GetRandomCapsPath(); |
338 | agent.BaseFolder = UUID.Zero; | 381 | avatar.AddNeighbourRegion(neighbour.RegionHandle, agent.CapsPath); |
339 | agent.InventoryFolder = UUID.Zero; | 382 | seeds.Add(neighbour.RegionHandle, agent.CapsPath); |
340 | agent.startpos = new Vector3(128, 128, 70); | 383 | } |
341 | agent.child = true; | 384 | else |
385 | agent.CapsPath = avatar.Scene.GetChildSeed(avatar.UUID, neighbour.RegionHandle); | ||
342 | 386 | ||
343 | InformClientOfNeighbourDelegate d = InformClientOfNeighbourAsync; | 387 | cagents.Add(agent); |
388 | } | ||
344 | 389 | ||
390 | /// Update all child agent with everyone's seeds | ||
391 | foreach (AgentCircuitData a in cagents) | ||
392 | { | ||
393 | a.ChildrenCapSeeds = new Dictionary<ulong, string>(seeds); | ||
394 | } | ||
395 | // These two are the same thing! | ||
396 | avatar.Scene.SetChildrenSeed(avatar.UUID, seeds); | ||
397 | avatar.KnownRegions = seeds; | ||
398 | //avatar.Scene.DumpChildrenSeeds(avatar.UUID); | ||
399 | //avatar.DumpKnownRegions(); | ||
400 | |||
401 | int count = 0; | ||
402 | foreach (SimpleRegionInfo neighbour in neighbours) | ||
403 | { | ||
404 | // Don't do it if there's already an agent in that region | ||
405 | if (newRegions.Contains(neighbour.RegionHandle)) | ||
406 | { | ||
407 | InformClientOfNeighbourDelegate d = InformClientOfNeighbourAsync; | ||
345 | try | 408 | try |
346 | { | 409 | { |
347 | d.BeginInvoke(avatar, agent, neighbours[i].RegionHandle, neighbours[i].ExternalEndPoint, | 410 | d.BeginInvoke(avatar, cagents[count], neighbour, neighbour.ExternalEndPoint, |
348 | InformClientOfNeighbourCompleted, | 411 | InformClientOfNeighbourCompleted, |
349 | d); | 412 | d); |
350 | } | 413 | } |
@@ -352,10 +415,10 @@ namespace OpenSim.Region.Environment.Scenes | |||
352 | { | 415 | { |
353 | m_log.ErrorFormat( | 416 | m_log.ErrorFormat( |
354 | "[REGIONINFO]: Could not resolve external hostname {0} for region {1} ({2}, {3}). {4}", | 417 | "[REGIONINFO]: Could not resolve external hostname {0} for region {1} ({2}, {3}). {4}", |
355 | neighbours[i].ExternalHostName, | 418 | neighbour.ExternalHostName, |
356 | neighbours[i].RegionHandle, | 419 | neighbour.RegionHandle, |
357 | neighbours[i].RegionLocX, | 420 | neighbour.RegionLocX, |
358 | neighbours[i].RegionLocY, | 421 | neighbour.RegionLocY, |
359 | e); | 422 | e); |
360 | 423 | ||
361 | // FIXME: Okay, even though we've failed, we're still going to throw the exception on, | 424 | // FIXME: Okay, even though we've failed, we're still going to throw the exception on, |
@@ -366,6 +429,11 @@ namespace OpenSim.Region.Environment.Scenes | |||
366 | 429 | ||
367 | } | 430 | } |
368 | } | 431 | } |
432 | else | ||
433 | m_log.Debug("[SCM]: Skipping common neighbor " + neighbour.RegionLocX + ", " + neighbour.RegionLocY); | ||
434 | |||
435 | count++; | ||
436 | |||
369 | } | 437 | } |
370 | } | 438 | } |
371 | 439 | ||
@@ -373,7 +441,7 @@ namespace OpenSim.Region.Environment.Scenes | |||
373 | /// This informs a single neighboring region about agent "avatar". | 441 | /// This informs a single neighboring region about agent "avatar". |
374 | /// Calls an asynchronous method to do so.. so it doesn't lag the sim. | 442 | /// Calls an asynchronous method to do so.. so it doesn't lag the sim. |
375 | /// </summary> | 443 | /// </summary> |
376 | public void InformNeighborChildAgent(ScenePresence avatar, RegionInfo region, List<RegionInfo> neighbours) | 444 | public void InformNeighborChildAgent(ScenePresence avatar, SimpleRegionInfo region, List<RegionInfo> neighbours) |
377 | { | 445 | { |
378 | AgentCircuitData agent = avatar.ControllingClient.RequestClientInfo(); | 446 | AgentCircuitData agent = avatar.ControllingClient.RequestClientInfo(); |
379 | agent.BaseFolder = UUID.Zero; | 447 | agent.BaseFolder = UUID.Zero; |
@@ -382,7 +450,7 @@ namespace OpenSim.Region.Environment.Scenes | |||
382 | agent.child = true; | 450 | agent.child = true; |
383 | 451 | ||
384 | InformClientOfNeighbourDelegate d = InformClientOfNeighbourAsync; | 452 | InformClientOfNeighbourDelegate d = InformClientOfNeighbourAsync; |
385 | d.BeginInvoke(avatar, agent, region.RegionHandle, region.ExternalEndPoint, | 453 | d.BeginInvoke(avatar, agent, region, region.ExternalEndPoint, |
386 | InformClientOfNeighbourCompleted, | 454 | InformClientOfNeighbourCompleted, |
387 | d); | 455 | d); |
388 | } | 456 | } |
@@ -463,10 +531,10 @@ namespace OpenSim.Region.Environment.Scenes | |||
463 | /// </summary> | 531 | /// </summary> |
464 | private void SendChildAgentDataUpdateAsync(ChildAgentDataUpdate cAgentData, ScenePresence presence) | 532 | private void SendChildAgentDataUpdateAsync(ChildAgentDataUpdate cAgentData, ScenePresence presence) |
465 | { | 533 | { |
466 | //m_log.Info("[INTERGRID]: Informing neighbors about my agent."); | 534 | m_log.Info("[INTERGRID]: Informing neighbors about my agent in " + presence.Scene.RegionInfo.RegionName); |
467 | try | 535 | try |
468 | { | 536 | { |
469 | foreach (ulong regionHandle in presence.KnownChildRegions) | 537 | foreach (ulong regionHandle in presence.KnownChildRegionHandles) |
470 | { | 538 | { |
471 | bool regionAccepted = m_commsProvider.InterRegion.ChildAgentUpdate(regionHandle, cAgentData); | 539 | bool regionAccepted = m_commsProvider.InterRegion.ChildAgentUpdate(regionHandle, cAgentData); |
472 | 540 | ||
@@ -508,11 +576,12 @@ namespace OpenSim.Region.Environment.Scenes | |||
508 | /// This Closes child agents on neighboring regions | 576 | /// This Closes child agents on neighboring regions |
509 | /// Calls an asynchronous method to do so.. so it doesn't lag the sim. | 577 | /// Calls an asynchronous method to do so.. so it doesn't lag the sim. |
510 | /// </summary> | 578 | /// </summary> |
511 | private void SendCloseChildAgentAsync(UUID agentID, List<ulong> regionlst) | 579 | protected void SendCloseChildAgentAsync(UUID agentID, List<ulong> regionlst) |
512 | { | 580 | { |
513 | 581 | ||
514 | foreach (ulong regionHandle in regionlst) | 582 | foreach (ulong regionHandle in regionlst) |
515 | { | 583 | { |
584 | m_log.Debug("[INTERGRID]: Sending close agent to " + regionHandle); | ||
516 | bool regionAccepted = m_commsProvider.InterRegion.TellRegionToCloseChildConnection(regionHandle, agentID); | 585 | bool regionAccepted = m_commsProvider.InterRegion.TellRegionToCloseChildConnection(regionHandle, agentID); |
517 | 586 | ||
518 | if (regionAccepted) | 587 | if (regionAccepted) |
@@ -527,14 +596,14 @@ namespace OpenSim.Region.Environment.Scenes | |||
527 | } | 596 | } |
528 | 597 | ||
529 | } | 598 | } |
530 | // We remove the list of known regions from the agent's known region list through an event | 599 | //// We remove the list of known regions from the agent's known region list through an event |
531 | // to scene, because, if an agent logged of, it's likely that there will be no scene presence | 600 | //// to scene, because, if an agent logged of, it's likely that there will be no scene presence |
532 | // by the time we get to this part of the method. | 601 | //// by the time we get to this part of the method. |
533 | handlerRemoveKnownRegionFromAvatar = OnRemoveKnownRegionFromAvatar; | 602 | //handlerRemoveKnownRegionFromAvatar = OnRemoveKnownRegionFromAvatar; |
534 | if (handlerRemoveKnownRegionFromAvatar != null) | 603 | //if (handlerRemoveKnownRegionFromAvatar != null) |
535 | { | 604 | //{ |
536 | handlerRemoveKnownRegionFromAvatar(agentID, regionlst); | 605 | // handlerRemoveKnownRegionFromAvatar(agentID, regionlst); |
537 | } | 606 | //} |
538 | } | 607 | } |
539 | 608 | ||
540 | private void SendCloseChildAgentCompleted(IAsyncResult iar) | 609 | private void SendCloseChildAgentCompleted(IAsyncResult iar) |
@@ -643,12 +712,6 @@ namespace OpenSim.Region.Environment.Scenes | |||
643 | if (eq == null) | 712 | if (eq == null) |
644 | avatar.ControllingClient.SendTeleportLocationStart(); | 713 | avatar.ControllingClient.SendTeleportLocationStart(); |
645 | 714 | ||
646 | AgentCircuitData agent = avatar.ControllingClient.RequestClientInfo(); | ||
647 | agent.BaseFolder = UUID.Zero; | ||
648 | agent.InventoryFolder = UUID.Zero; | ||
649 | agent.startpos = position; | ||
650 | agent.child = true; | ||
651 | |||
652 | if (reg.RemotingAddress != "" && reg.RemotingPort != 0) | 715 | if (reg.RemotingAddress != "" && reg.RemotingPort != 0) |
653 | { | 716 | { |
654 | // region is remote. see if it is up | 717 | // region is remote. see if it is up |
@@ -662,6 +725,10 @@ namespace OpenSim.Region.Environment.Scenes | |||
662 | 725 | ||
663 | if (destRegionUp) | 726 | if (destRegionUp) |
664 | { | 727 | { |
728 | uint newRegionX = (uint)(reg.RegionHandle >> 40); | ||
729 | uint newRegionY = (((uint)(reg.RegionHandle)) >> 8); | ||
730 | uint oldRegionX = (uint)(m_regionInfo.RegionHandle >> 40); | ||
731 | uint oldRegionY = (((uint)(m_regionInfo.RegionHandle)) >> 8); | ||
665 | 732 | ||
666 | // Fixing a bug where teleporting while sitting results in the avatar ending up removed from | 733 | // Fixing a bug where teleporting while sitting results in the avatar ending up removed from |
667 | // both regions | 734 | // both regions |
@@ -675,33 +742,64 @@ namespace OpenSim.Region.Environment.Scenes | |||
675 | 742 | ||
676 | // the avatar.Close below will clear the child region list. We need this below for (possibly) | 743 | // the avatar.Close below will clear the child region list. We need this below for (possibly) |
677 | // closing the child agents, so save it here (we need a copy as it is Clear()-ed). | 744 | // closing the child agents, so save it here (we need a copy as it is Clear()-ed). |
678 | List<ulong> childRegions = new List<ulong>(avatar.GetKnownRegionList()); | 745 | //List<ulong> childRegions = new List<ulong>(avatar.GetKnownRegionList()); |
679 | // Compared to ScenePresence.CrossToNewRegion(), there's no obvious code to handle a teleport | 746 | // Compared to ScenePresence.CrossToNewRegion(), there's no obvious code to handle a teleport |
680 | // failure at this point (unlike a border crossing failure). So perhaps this can never fail | 747 | // failure at this point (unlike a border crossing failure). So perhaps this can never fail |
681 | // once we reach here... | 748 | // once we reach here... |
682 | avatar.Scene.RemoveCapsHandler(avatar.UUID); | 749 | //avatar.Scene.RemoveCapsHandler(avatar.UUID); |
683 | agent.child = false; | 750 | |
684 | m_commsProvider.InterRegion.InformRegionOfChildAgent(reg.RegionHandle, agent); | 751 | AgentCircuitData agent = avatar.ControllingClient.RequestClientInfo(); |
752 | agent.BaseFolder = UUID.Zero; | ||
753 | agent.InventoryFolder = UUID.Zero; | ||
754 | agent.startpos = position; | ||
755 | agent.child = true; | ||
756 | if (Util.IsOutsideView(oldRegionX, newRegionX, oldRegionY, newRegionY)) | ||
757 | { | ||
758 | // brand new agent | ||
759 | agent.CapsPath = Util.GetRandomCapsPath(); | ||
760 | } | ||
761 | else | ||
762 | { | ||
763 | // child agent already there | ||
764 | agent.CapsPath = avatar.Scene.GetChildSeed(avatar.UUID, reg.RegionHandle); | ||
765 | } | ||
766 | |||
767 | if (!m_commsProvider.InterRegion.InformRegionOfChildAgent(reg.RegionHandle, agent)) | ||
768 | { | ||
769 | avatar.ControllingClient.SendTeleportFailed("Destination is not accepting teleports."); | ||
770 | return; | ||
771 | } | ||
772 | |||
773 | // TODO Should construct this behind a method | ||
774 | string capsPath = | ||
775 | "http://" + reg.ExternalHostName + ":" + reg.HttpPort | ||
776 | + "/CAPS/" + agent.CapsPath + "0000/"; | ||
685 | 777 | ||
686 | if (eq != null) | 778 | if (eq != null) |
687 | { | 779 | { |
688 | OSD Item = EventQueueHelper.EnableSimulator(reg.RegionHandle, reg.ExternalEndPoint); | 780 | OSD Item = EventQueueHelper.EnableSimulator(reg.RegionHandle, reg.ExternalEndPoint); |
689 | eq.Enqueue(Item, avatar.UUID); | 781 | eq.Enqueue(Item, avatar.UUID); |
782 | |||
783 | Item = EventQueueHelper.EstablishAgentCommunication(avatar.UUID, reg.ExternalEndPoint.ToString(), capsPath); | ||
784 | eq.Enqueue(Item, avatar.UUID); | ||
690 | } | 785 | } |
691 | else | 786 | else |
692 | { | 787 | { |
693 | avatar.ControllingClient.InformClientOfNeighbour(reg.RegionHandle, reg.ExternalEndPoint); | 788 | avatar.ControllingClient.InformClientOfNeighbour(reg.RegionHandle, reg.ExternalEndPoint); |
694 | } | 789 | } |
695 | |||
696 | m_commsProvider.InterRegion.ExpectAvatarCrossing(reg.RegionHandle, avatar.ControllingClient.AgentId, | ||
697 | position, false); | ||
698 | Thread.Sleep(2000); | ||
699 | AgentCircuitData circuitdata = avatar.ControllingClient.RequestClientInfo(); | ||
700 | 790 | ||
701 | // TODO Should construct this behind a method | 791 | if (!m_commsProvider.InterRegion.ExpectAvatarCrossing(reg.RegionHandle, avatar.ControllingClient.AgentId, |
702 | string capsPath = | 792 | position, false)) |
703 | "http://" + reg.ExternalHostName + ":" + reg.HttpPort | 793 | { |
704 | + "/CAPS/" + circuitdata.CapsPath + "0000/"; | 794 | avatar.ControllingClient.SendTeleportFailed("Problem with destination."); |
795 | // We should close that agent we just created over at destination... | ||
796 | List<ulong> lst = new List<ulong>(); | ||
797 | lst.Add(reg.RegionHandle); | ||
798 | SendCloseChildAgentAsync(avatar.UUID, lst); | ||
799 | return; | ||
800 | } | ||
801 | |||
802 | Thread.Sleep(2000); | ||
705 | 803 | ||
706 | m_log.DebugFormat( | 804 | m_log.DebugFormat( |
707 | "[CAPS]: Sending new CAPS seed url {0} to client {1}", capsPath, avatar.UUID); | 805 | "[CAPS]: Sending new CAPS seed url {0} to client {1}", capsPath, avatar.UUID); |
@@ -720,26 +818,25 @@ namespace OpenSim.Region.Environment.Scenes | |||
720 | } | 818 | } |
721 | 819 | ||
722 | avatar.MakeChildAgent(); | 820 | avatar.MakeChildAgent(); |
723 | Thread.Sleep(7000); | 821 | Thread.Sleep(5000); |
724 | avatar.CrossAttachmentsIntoNewRegion(reg.RegionHandle, true); | 822 | avatar.CrossAttachmentsIntoNewRegion(reg.RegionHandle, true); |
725 | if (KiPrimitive != null) | 823 | if (KiPrimitive != null) |
726 | { | 824 | { |
727 | KiPrimitive(avatar.LocalId); | 825 | KiPrimitive(avatar.LocalId); |
728 | } | 826 | } |
729 | 827 | ||
730 | avatar.Close(); | ||
731 | 828 | ||
732 | uint newRegionX = (uint)(reg.RegionHandle >> 40); | 829 | // Let's close some children agents |
733 | uint newRegionY = (((uint)(reg.RegionHandle)) >> 8); | 830 | avatar.CloseChildAgents(newRegionX, newRegionY); |
734 | uint oldRegionX = (uint)(m_regionInfo.RegionHandle >> 40); | 831 | // Close this ScenePresence too |
735 | uint oldRegionY = (((uint)(m_regionInfo.RegionHandle)) >> 8); | 832 | //avatar.Close(); |
736 | 833 | ||
737 | if (Util.fast_distance2d((int)(newRegionX - oldRegionX), (int)(newRegionY - oldRegionY)) > 3) | 834 | // Finally, let's close this previously-known-as-root agent, when the jump is outside the view zone |
738 | { | 835 | |
739 | //SendCloseChildAgentConnections(avatar.UUID,avatar.GetKnownRegionList()); | 836 | //if (Util.IsOutsideView(oldRegionX, newRegionX, oldRegionY, newRegionY)) |
740 | SendCloseChildAgentConnections(avatar.UUID, childRegions); | 837 | //{ |
741 | CloseConnection(avatar.UUID); | 838 | // CloseConnection(avatar.UUID); |
742 | } | 839 | //} |
743 | 840 | ||
744 | // if (teleport success) // seems to be always success here | 841 | // if (teleport success) // seems to be always success here |
745 | // the user may change their profile information in other region, | 842 | // the user may change their profile information in other region, |
@@ -775,6 +872,30 @@ namespace OpenSim.Region.Environment.Scenes | |||
775 | } | 872 | } |
776 | } | 873 | } |
777 | 874 | ||
875 | private List<ulong> NeighbourHandles(List<SimpleRegionInfo> neighbours) | ||
876 | { | ||
877 | List<ulong> handles = new List<ulong>(); | ||
878 | foreach (SimpleRegionInfo reg in neighbours) | ||
879 | { | ||
880 | handles.Add(reg.RegionHandle); | ||
881 | } | ||
882 | return handles; | ||
883 | } | ||
884 | |||
885 | private List<ulong> NewNeighbours(List<ulong> currentNeighbours, List<ulong> previousNeighbours) | ||
886 | { | ||
887 | return currentNeighbours.FindAll(delegate(ulong handle) { return !previousNeighbours.Contains(handle); }); | ||
888 | } | ||
889 | |||
890 | private List<ulong> CommonNeighbours(List<ulong> currentNeighbours, List<ulong> previousNeighbours) | ||
891 | { | ||
892 | return currentNeighbours.FindAll(delegate(ulong handle) { return previousNeighbours.Contains(handle); }); | ||
893 | } | ||
894 | |||
895 | private List<ulong> OldNeighbours(List<ulong> currentNeighbours, List<ulong> previousNeighbours) | ||
896 | { | ||
897 | return previousNeighbours.FindAll(delegate(ulong handle) { return !currentNeighbours.Contains(handle); }); | ||
898 | } | ||
778 | /// <summary> | 899 | /// <summary> |
779 | /// Inform a neighbouring region that an avatar is about to cross into it. | 900 | /// Inform a neighbouring region that an avatar is about to cross into it. |
780 | /// </summary> | 901 | /// </summary> |
@@ -846,5 +967,18 @@ namespace OpenSim.Region.Environment.Scenes | |||
846 | { | 967 | { |
847 | return m_commsProvider.GridService.RequestNamedRegions(name, maxNumber); | 968 | return m_commsProvider.GridService.RequestNamedRegions(name, maxNumber); |
848 | } | 969 | } |
970 | |||
971 | private void Dump(string msg, List<ulong> handles) | ||
972 | { | ||
973 | Console.WriteLine("-------------- HANDLE DUMP ({0}) ---------", msg); | ||
974 | foreach (ulong handle in handles) | ||
975 | { | ||
976 | uint x, y; | ||
977 | Utils.LongToUInts(handle, out x, out y); | ||
978 | x = x / Constants.RegionSize; | ||
979 | y = y / Constants.RegionSize; | ||
980 | Console.WriteLine("({0}, {1})", x, y); | ||
981 | } | ||
982 | } | ||
849 | } | 983 | } |
850 | } | 984 | } |