diff options
Diffstat (limited to 'OpenSim/Region/CoreModules')
16 files changed, 560 insertions, 563 deletions
diff --git a/OpenSim/Region/CoreModules/Avatar/Chat/ChatModule.cs b/OpenSim/Region/CoreModules/Avatar/Chat/ChatModule.cs index 27ace68..10122e6 100644 --- a/OpenSim/Region/CoreModules/Avatar/Chat/ChatModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Chat/ChatModule.cs | |||
@@ -189,8 +189,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Chat | |||
189 | string message = c.Message; | 189 | string message = c.Message; |
190 | Scene scene = (Scene)c.Scene; | 190 | Scene scene = (Scene)c.Scene; |
191 | Vector3 fromPos = c.Position; | 191 | Vector3 fromPos = c.Position; |
192 | Vector3 regionPos = new Vector3(scene.RegionInfo.RegionLocX * Constants.RegionSize, | 192 | Vector3 regionPos = new Vector3(scene.RegionInfo.WorldLocX, scene.RegionInfo.WorldLocY, 0); |
193 | scene.RegionInfo.RegionLocY * Constants.RegionSize, 0); | ||
194 | 193 | ||
195 | if (c.Channel == DEBUG_CHANNEL) c.Type = ChatTypeEnum.DebugChannel; | 194 | if (c.Channel == DEBUG_CHANNEL) c.Type = ChatTypeEnum.DebugChannel; |
196 | 195 | ||
@@ -342,8 +341,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Chat | |||
342 | { | 341 | { |
343 | Vector3 fromRegionPos = fromPos + regionPos; | 342 | Vector3 fromRegionPos = fromPos + regionPos; |
344 | Vector3 toRegionPos = presence.AbsolutePosition + | 343 | Vector3 toRegionPos = presence.AbsolutePosition + |
345 | new Vector3(presence.Scene.RegionInfo.RegionLocX * Constants.RegionSize, | 344 | new Vector3(presence.Scene.RegionInfo.WorldLocX, presence.Scene.RegionInfo.WorldLocY, 0); |
346 | presence.Scene.RegionInfo.RegionLocY * Constants.RegionSize, 0); | ||
347 | 345 | ||
348 | int dis = (int)Util.GetDistanceTo(toRegionPos, fromRegionPos); | 346 | int dis = (int)Util.GetDistanceTo(toRegionPos, fromRegionPos); |
349 | 347 | ||
diff --git a/OpenSim/Region/CoreModules/Avatar/UserProfiles/UserProfileModule.cs b/OpenSim/Region/CoreModules/Avatar/UserProfiles/UserProfileModule.cs index bfa30e6..7e50cc6 100644 --- a/OpenSim/Region/CoreModules/Avatar/UserProfiles/UserProfileModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/UserProfiles/UserProfileModule.cs | |||
@@ -667,8 +667,8 @@ namespace OpenSim.Region.OptionalModules.Avatar.UserProfiles | |||
667 | 667 | ||
668 | Vector3 avaPos = p.AbsolutePosition; | 668 | Vector3 avaPos = p.AbsolutePosition; |
669 | // Getting the global position for the Avatar | 669 | // Getting the global position for the Avatar |
670 | Vector3 posGlobal = new Vector3(remoteClient.Scene.RegionInfo.RegionLocX*Constants.RegionSize + avaPos.X, | 670 | Vector3 posGlobal = new Vector3(remoteClient.Scene.RegionInfo.WorldLocX + avaPos.X, |
671 | remoteClient.Scene.RegionInfo.RegionLocY*Constants.RegionSize + avaPos.Y, | 671 | remoteClient.Scene.RegionInfo.WorldLocY + avaPos.Y, |
672 | avaPos.Z); | 672 | avaPos.Z); |
673 | 673 | ||
674 | string landOwnerName = string.Empty; | 674 | string landOwnerName = string.Empty; |
diff --git a/OpenSim/Region/CoreModules/Framework/Caps/CapabilitiesModule.cs b/OpenSim/Region/CoreModules/Framework/Caps/CapabilitiesModule.cs index 6545a99..13cc99a 100644 --- a/OpenSim/Region/CoreModules/Framework/Caps/CapabilitiesModule.cs +++ b/OpenSim/Region/CoreModules/Framework/Caps/CapabilitiesModule.cs | |||
@@ -269,9 +269,7 @@ namespace OpenSim.Region.CoreModules.Framework | |||
269 | foreach (KeyValuePair<ulong, string> kvp in m_childrenSeeds[agentID]) | 269 | foreach (KeyValuePair<ulong, string> kvp in m_childrenSeeds[agentID]) |
270 | { | 270 | { |
271 | uint x, y; | 271 | uint x, y; |
272 | Utils.LongToUInts(kvp.Key, out x, out y); | 272 | Util.RegionHandleToRegionLoc(kvp.Key, out x, out y); |
273 | x = x / Constants.RegionSize; | ||
274 | y = y / Constants.RegionSize; | ||
275 | m_log.Info(" >> "+x+", "+y+": "+kvp.Value); | 273 | m_log.Info(" >> "+x+", "+y+": "+kvp.Value); |
276 | } | 274 | } |
277 | } | 275 | } |
diff --git a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs index ef5239a..4954cd9 100644 --- a/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs +++ b/OpenSim/Region/CoreModules/Framework/EntityTransfer/EntityTransferModule.cs | |||
@@ -52,6 +52,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
52 | public class EntityTransferModule : INonSharedRegionModule, IEntityTransferModule | 52 | public class EntityTransferModule : INonSharedRegionModule, IEntityTransferModule |
53 | { | 53 | { |
54 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 54 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
55 | private static readonly string LogHeader = "[ENTITY TRANSFER MODULE]"; | ||
55 | 56 | ||
56 | public const int DefaultMaxTransferDistance = 4095; | 57 | public const int DefaultMaxTransferDistance = 4095; |
57 | public const bool WaitForAgentArrivedAtDestinationDefault = true; | 58 | public const bool WaitForAgentArrivedAtDestinationDefault = true; |
@@ -433,10 +434,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
433 | float posZLimit = 22; | 434 | float posZLimit = 22; |
434 | 435 | ||
435 | // TODO: Check other Scene HeightField | 436 | // TODO: Check other Scene HeightField |
436 | if (position.X > 0 && position.X <= (int)Constants.RegionSize && position.Y > 0 && position.Y <= (int)Constants.RegionSize) | 437 | posZLimit = (float)sp.Scene.Heightmap[(int)position.X, (int)position.Y]; |
437 | { | ||
438 | posZLimit = (float)sp.Scene.Heightmap[(int)position.X, (int)position.Y]; | ||
439 | } | ||
440 | 438 | ||
441 | float newPosZ = posZLimit + localAVHeight; | 439 | float newPosZ = posZLimit + localAVHeight; |
442 | if (posZLimit >= (position.Z - (localAVHeight / 2)) && !(Single.IsInfinity(newPosZ) || Single.IsNaN(newPosZ))) | 440 | if (posZLimit >= (position.Z - (localAVHeight / 2)) && !(Single.IsInfinity(newPosZ) || Single.IsNaN(newPosZ))) |
@@ -489,9 +487,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
489 | 487 | ||
490 | if (finalDestination == null) | 488 | if (finalDestination == null) |
491 | { | 489 | { |
492 | m_log.WarnFormat( | 490 | m_log.WarnFormat( "{0} Final destination is having problems. Unable to teleport {1} {2}", |
493 | "[ENTITY TRANSFER MODULE]: Final destination is having problems. Unable to teleport {0} {1}", | 491 | LogHeader, sp.Name, sp.UUID); |
494 | sp.Name, sp.UUID); | ||
495 | 492 | ||
496 | sp.ControllingClient.SendTeleportFailed("Problem at destination"); | 493 | sp.ControllingClient.SendTeleportFailed("Problem at destination"); |
497 | return; | 494 | return; |
@@ -532,11 +529,11 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
532 | 529 | ||
533 | // and set the map-tile to '(Offline)' | 530 | // and set the map-tile to '(Offline)' |
534 | uint regX, regY; | 531 | uint regX, regY; |
535 | Utils.LongToUInts(regionHandle, out regX, out regY); | 532 | Util.RegionHandleToRegionLoc(regionHandle, out regX, out regY); |
536 | 533 | ||
537 | MapBlockData block = new MapBlockData(); | 534 | MapBlockData block = new MapBlockData(); |
538 | block.X = (ushort)(regX / Constants.RegionSize); | 535 | block.X = (ushort)Util.WorldToRegionLoc(regX); |
539 | block.Y = (ushort)(regY / Constants.RegionSize); | 536 | block.Y = (ushort)Util.WorldToRegionLoc(regY); |
540 | block.Access = 254; // == not there | 537 | block.Access = 254; // == not there |
541 | 538 | ||
542 | List<MapBlockData> blocks = new List<MapBlockData>(); | 539 | List<MapBlockData> blocks = new List<MapBlockData>(); |
@@ -1342,6 +1339,8 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
1342 | if (uinfo.HomeRegionID == UUID.Zero) | 1339 | if (uinfo.HomeRegionID == UUID.Zero) |
1343 | { | 1340 | { |
1344 | // can't find the Home region: Tell viewer and abort | 1341 | // can't find the Home region: Tell viewer and abort |
1342 | m_log.ErrorFormat("{0} No grid user info found for {1} {2}. Cannot send home.", | ||
1343 | LogHeader, client.Name, client.AgentId); | ||
1345 | client.SendTeleportFailed("You don't have a home position set."); | 1344 | client.SendTeleportFailed("You don't have a home position set."); |
1346 | return false; | 1345 | return false; |
1347 | } | 1346 | } |
@@ -1375,7 +1374,11 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
1375 | 1374 | ||
1376 | #region Agent Crossings | 1375 | #region Agent Crossings |
1377 | 1376 | ||
1378 | public GridRegion GetDestination(Scene scene, UUID agentID, Vector3 pos, out uint xDest, out uint yDest, out string version, out Vector3 newpos) | 1377 | // Given a position relative to the current region (which has previously been tested to |
1378 | // see that it is actually outside the current region), find the new region that the | ||
1379 | // point is actually in. | ||
1380 | // Returns the coordinates and information of the new region or 'null' of it doesn't exist. | ||
1381 | public GridRegion GetDestination(Scene scene, UUID agentID, Vector3 pos, out string version, out Vector3 newpos) | ||
1379 | { | 1382 | { |
1380 | version = String.Empty; | 1383 | version = String.Empty; |
1381 | newpos = new Vector3(pos.X, pos.Y, pos.Z); | 1384 | newpos = new Vector3(pos.X, pos.Y, pos.Z); |
@@ -1383,130 +1386,59 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
1383 | // m_log.DebugFormat( | 1386 | // m_log.DebugFormat( |
1384 | // "[ENTITY TRANSFER MODULE]: Crossing agent {0} at pos {1} in {2}", agent.Name, pos, scene.Name); | 1387 | // "[ENTITY TRANSFER MODULE]: Crossing agent {0} at pos {1} in {2}", agent.Name, pos, scene.Name); |
1385 | 1388 | ||
1386 | uint neighbourx = scene.RegionInfo.RegionLocX; | 1389 | // Compute world location of the object's position |
1387 | uint neighboury = scene.RegionInfo.RegionLocY; | 1390 | double presenceWorldX = (double)scene.RegionInfo.WorldLocX + pos.X; |
1388 | const float boundaryDistance = 1.7f; | 1391 | double presenceWorldY = (double)scene.RegionInfo.WorldLocY + pos.Y; |
1389 | Vector3 northCross = new Vector3(0, boundaryDistance, 0); | 1392 | |
1390 | Vector3 southCross = new Vector3(0, -1 * boundaryDistance, 0); | 1393 | // Call the grid service to lookup the region containing the new position. |
1391 | Vector3 eastCross = new Vector3(boundaryDistance, 0, 0); | 1394 | GridRegion neighbourRegion = GetRegionContainingWorldLocation(scene.GridService, scene.RegionInfo.ScopeID, |
1392 | Vector3 westCross = new Vector3(-1 * boundaryDistance, 0, 0); | 1395 | presenceWorldX, presenceWorldY); |
1393 | 1396 | ||
1394 | // distance into new region to place avatar | 1397 | if (neighbourRegion != null) |
1395 | const float enterDistance = 0.5f; | 1398 | { |
1396 | 1399 | // Compute the entity's position relative to the new region | |
1397 | if (scene.TestBorderCross(pos + westCross, Cardinals.W)) | 1400 | newpos = new Vector3( (float)(presenceWorldX - (double)neighbourRegion.RegionLocX), |
1398 | { | 1401 | (float)(presenceWorldY - (double)neighbourRegion.RegionLocY), |
1399 | if (scene.TestBorderCross(pos + northCross, Cardinals.N)) | 1402 | pos.Z); |
1400 | { | 1403 | |
1401 | Border b = scene.GetCrossedBorder(pos + northCross, Cardinals.N); | 1404 | // Check if banned from destination region. |
1402 | neighboury += (uint)(int)(b.BorderLine.Z / (int)Constants.RegionSize); | 1405 | ExpiringCache<ulong, DateTime> r; |
1406 | DateTime banUntil; | ||
1407 | if (m_bannedRegions.TryGetValue(agentID, out r)) | ||
1408 | { | ||
1409 | if (r.TryGetValue(neighbourRegion.RegionHandle, out banUntil)) | ||
1410 | { | ||
1411 | if (DateTime.Now < banUntil) | ||
1412 | { | ||
1413 | // If we're banned from the destination, we just can't go there. | ||
1414 | neighbourRegion = null; | ||
1415 | } | ||
1416 | r.Remove(neighbourRegion.RegionHandle); | ||
1417 | } | ||
1418 | } | ||
1419 | else | ||
1420 | { | ||
1421 | r = null; | ||
1403 | } | 1422 | } |
1404 | else if (scene.TestBorderCross(pos + southCross, Cardinals.S)) | ||
1405 | { | ||
1406 | neighboury--; | ||
1407 | newpos.Y = Constants.RegionSize - enterDistance; | ||
1408 | } | ||
1409 | |||
1410 | neighbourx--; | ||
1411 | newpos.X = Constants.RegionSize - enterDistance; | ||
1412 | } | ||
1413 | else if (scene.TestBorderCross(pos + eastCross, Cardinals.E)) | ||
1414 | { | ||
1415 | Border b = scene.GetCrossedBorder(pos + eastCross, Cardinals.E); | ||
1416 | neighbourx += (uint)(int)(b.BorderLine.Z / (int)Constants.RegionSize); | ||
1417 | newpos.X = enterDistance; | ||
1418 | 1423 | ||
1419 | if (scene.TestBorderCross(pos + southCross, Cardinals.S)) | 1424 | // Check to see if we have access to the target region. |
1425 | string reason; | ||
1426 | if (neighbourRegion != null | ||
1427 | && !scene.SimulationService.QueryAccess(neighbourRegion, agentID, newpos, out version, out reason)) | ||
1420 | { | 1428 | { |
1421 | neighboury--; | 1429 | if (r == null) |
1422 | newpos.Y = Constants.RegionSize - enterDistance; | 1430 | { |
1423 | } | 1431 | r = new ExpiringCache<ulong, DateTime>(); |
1424 | else if (scene.TestBorderCross(pos + northCross, Cardinals.N)) | 1432 | r.Add(neighbourRegion.RegionHandle, DateTime.Now + TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(15)); |
1425 | { | ||
1426 | Border c = scene.GetCrossedBorder(pos + northCross, Cardinals.N); | ||
1427 | neighboury += (uint)(int)(c.BorderLine.Z / (int)Constants.RegionSize); | ||
1428 | newpos.Y = enterDistance; | ||
1429 | } | ||
1430 | } | ||
1431 | else if (scene.TestBorderCross(pos + southCross, Cardinals.S)) | ||
1432 | { | ||
1433 | Border b = scene.GetCrossedBorder(pos + southCross, Cardinals.S); | ||
1434 | neighboury--; | ||
1435 | newpos.Y = Constants.RegionSize - enterDistance; | ||
1436 | } | ||
1437 | else if (scene.TestBorderCross(pos + northCross, Cardinals.N)) | ||
1438 | { | ||
1439 | Border b = scene.GetCrossedBorder(pos + northCross, Cardinals.N); | ||
1440 | neighboury += (uint)(int)(b.BorderLine.Z / (int)Constants.RegionSize); | ||
1441 | newpos.Y = enterDistance; | ||
1442 | } | ||
1443 | |||
1444 | /* | ||
1445 | |||
1446 | if (pos.X < boundaryDistance) //West | ||
1447 | { | ||
1448 | neighbourx--; | ||
1449 | newpos.X = Constants.RegionSize - enterDistance; | ||
1450 | } | ||
1451 | else if (pos.X > Constants.RegionSize - boundaryDistance) // East | ||
1452 | { | ||
1453 | neighbourx++; | ||
1454 | newpos.X = enterDistance; | ||
1455 | } | ||
1456 | |||
1457 | if (pos.Y < boundaryDistance) // South | ||
1458 | { | ||
1459 | neighboury--; | ||
1460 | newpos.Y = Constants.RegionSize - enterDistance; | ||
1461 | } | ||
1462 | else if (pos.Y > Constants.RegionSize - boundaryDistance) // North | ||
1463 | { | ||
1464 | neighboury++; | ||
1465 | newpos.Y = enterDistance; | ||
1466 | } | ||
1467 | */ | ||
1468 | |||
1469 | xDest = neighbourx; | ||
1470 | yDest = neighboury; | ||
1471 | |||
1472 | int x = (int)(neighbourx * Constants.RegionSize), y = (int)(neighboury * Constants.RegionSize); | ||
1473 | |||
1474 | ulong neighbourHandle = Utils.UIntsToLong((uint)x, (uint)y); | ||
1475 | |||
1476 | ExpiringCache<ulong, DateTime> r; | ||
1477 | DateTime banUntil; | ||
1478 | |||
1479 | if (m_bannedRegions.TryGetValue(agentID, out r)) | ||
1480 | { | ||
1481 | if (r.TryGetValue(neighbourHandle, out banUntil)) | ||
1482 | { | ||
1483 | if (DateTime.Now < banUntil) | ||
1484 | return null; | ||
1485 | r.Remove(neighbourHandle); | ||
1486 | } | ||
1487 | } | ||
1488 | else | ||
1489 | { | ||
1490 | r = null; | ||
1491 | } | ||
1492 | |||
1493 | GridRegion neighbourRegion = scene.GridService.GetRegionByPosition(scene.RegionInfo.ScopeID, (int)x, (int)y); | ||
1494 | |||
1495 | string reason; | ||
1496 | if (!scene.SimulationService.QueryAccess(neighbourRegion, agentID, newpos, out version, out reason)) | ||
1497 | { | ||
1498 | if (r == null) | ||
1499 | { | ||
1500 | r = new ExpiringCache<ulong, DateTime>(); | ||
1501 | r.Add(neighbourHandle, DateTime.Now + TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(15)); | ||
1502 | 1433 | ||
1503 | m_bannedRegions.Add(agentID, r, TimeSpan.FromSeconds(45)); | 1434 | m_bannedRegions.Add(agentID, r, TimeSpan.FromSeconds(45)); |
1504 | } | 1435 | } |
1505 | else | 1436 | else |
1506 | { | 1437 | { |
1507 | r.Add(neighbourHandle, DateTime.Now + TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(15)); | 1438 | r.Add(neighbourRegion.RegionHandle, DateTime.Now + TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(15)); |
1508 | } | 1439 | } |
1509 | return null; | 1440 | neighbourRegion = null; |
1441 | } | ||
1510 | } | 1442 | } |
1511 | 1443 | ||
1512 | return neighbourRegion; | 1444 | return neighbourRegion; |
@@ -1519,7 +1451,7 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
1519 | Vector3 newpos; | 1451 | Vector3 newpos; |
1520 | string version; | 1452 | string version; |
1521 | 1453 | ||
1522 | GridRegion neighbourRegion = GetDestination(agent.Scene, agent.UUID, agent.AbsolutePosition, out x, out y, out version, out newpos); | 1454 | GridRegion neighbourRegion = GetDestination(agent.Scene, agent.UUID, agent.AbsolutePosition, out version, out newpos); |
1523 | if (neighbourRegion == null) | 1455 | if (neighbourRegion == null) |
1524 | { | 1456 | { |
1525 | agent.ControllingClient.SendAlertMessage("Cannot region cross into banned parcel"); | 1457 | agent.ControllingClient.SendAlertMessage("Cannot region cross into banned parcel"); |
@@ -2028,15 +1960,80 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
2028 | } | 1960 | } |
2029 | } | 1961 | } |
2030 | 1962 | ||
1963 | // Computes the difference between two region bases. | ||
1964 | // Returns a vector of world coordinates (meters) from base of first region to the second. | ||
1965 | // The first region is the home region of the passed scene presence. | ||
2031 | Vector3 CalculateOffset(ScenePresence sp, GridRegion neighbour) | 1966 | Vector3 CalculateOffset(ScenePresence sp, GridRegion neighbour) |
2032 | { | 1967 | { |
2033 | int rRegionX = (int)sp.Scene.RegionInfo.RegionLocX; | 1968 | /* |
2034 | int rRegionY = (int)sp.Scene.RegionInfo.RegionLocY; | 1969 | int rRegionX = (int)sp.Scene.RegionInfo.LegacyRegionLocX; |
1970 | int rRegionY = (int)sp.Scene.RegionInfo.LegacyRegionLocY; | ||
2035 | int tRegionX = neighbour.RegionLocX / (int)Constants.RegionSize; | 1971 | int tRegionX = neighbour.RegionLocX / (int)Constants.RegionSize; |
2036 | int tRegionY = neighbour.RegionLocY / (int)Constants.RegionSize; | 1972 | int tRegionY = neighbour.RegionLocY / (int)Constants.RegionSize; |
2037 | int shiftx = (rRegionX - tRegionX) * (int)Constants.RegionSize; | 1973 | int shiftx = (rRegionX - tRegionX) * (int)Constants.RegionSize; |
2038 | int shifty = (rRegionY - tRegionY) * (int)Constants.RegionSize; | 1974 | int shifty = (rRegionY - tRegionY) * (int)Constants.RegionSize; |
2039 | return new Vector3(shiftx, shifty, 0f); | 1975 | return new Vector3(shiftx, shifty, 0f); |
1976 | */ | ||
1977 | return new Vector3(sp.Scene.RegionInfo.RegionLocX - neighbour.RegionLocX, | ||
1978 | sp.Scene.RegionInfo.RegionLocY - neighbour.RegionLocY, | ||
1979 | 0f); | ||
1980 | } | ||
1981 | |||
1982 | // Given a world position (fractional meter coordinate), get the GridRegion info for | ||
1983 | // the region containing that point. | ||
1984 | // Return 'null' if no such region exists. | ||
1985 | private GridRegion GetRegionContainingWorldLocation(IGridService pGridService, UUID pScopeID, double px, double py) | ||
1986 | { | ||
1987 | m_log.DebugFormat("{0} GetRegionContainingWorldLocation: call, XY=<{1},{2}>", LogHeader, px, py); | ||
1988 | GridRegion ret = null; | ||
1989 | |||
1990 | // As an optimization, since most regions will be legacy sized regions (256x256), first try to get | ||
1991 | // the region at the appropriate legacy region location. | ||
1992 | uint possibleX = (uint)Math.Floor(px); | ||
1993 | possibleX -= possibleX % Constants.RegionSize; | ||
1994 | uint possibleY = (uint)Math.Floor(py); | ||
1995 | possibleY -= possibleY % Constants.RegionSize; | ||
1996 | ret = pGridService.GetRegionByPosition(pScopeID, (int)possibleX, (int)possibleY); | ||
1997 | if (ret != null) | ||
1998 | { | ||
1999 | m_log.DebugFormat("{0} GetRegionContainingWorldLocation: Found region using legacy size. rloc=<{1},{2}>. Rname={3}", | ||
2000 | LogHeader, possibleX, possibleY, ret.RegionName); | ||
2001 | } | ||
2002 | |||
2003 | if (ret == null) | ||
2004 | { | ||
2005 | // If the simple lookup failed, search the larger area for a region that contains this point | ||
2006 | double range = (double)Constants.RegionSize * 2 + 2; | ||
2007 | while (ret == null && range <= (Constants.MaximumRegionSize + Constants.RegionSize)) | ||
2008 | { | ||
2009 | // Get from the grid service a list of regions that might contain this point | ||
2010 | List<GridRegion> possibleRegions = pGridService.GetRegionRange(pScopeID, | ||
2011 | (int)(px - range), (int)(px + range), | ||
2012 | (int)(py - range), (int)(py + range)); | ||
2013 | m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegions cnt={1}, range={2}", | ||
2014 | LogHeader, possibleRegions.Count, range); | ||
2015 | if (possibleRegions != null && possibleRegions.Count > 0) | ||
2016 | { | ||
2017 | // If we found some regions, check to see if the point is within | ||
2018 | foreach (GridRegion gr in possibleRegions) | ||
2019 | { | ||
2020 | m_log.DebugFormat("{0} GetRegionContainingWorldLocation: possibleRegion nm={1}, regionLoc=<{2},{3}>, regionSize=<{4},{5}>", | ||
2021 | LogHeader, gr.RegionName, gr.RegionLocX, gr.RegionLocY, gr.RegionSizeX, gr.RegionSizeY); | ||
2022 | if (px >= (double)gr.RegionLocX && px < (double)(gr.RegionLocX + gr.RegionSizeX) | ||
2023 | && py >= (double)gr.RegionLocY && py < (double)(gr.RegionLocY + gr.RegionSizeY)) | ||
2024 | { | ||
2025 | // Found a region that contains the point | ||
2026 | ret = gr; | ||
2027 | m_log.DebugFormat("{0} GetRegionContainingWorldLocation: found. RegionName={1}", LogHeader, ret.RegionName); | ||
2028 | break; | ||
2029 | } | ||
2030 | } | ||
2031 | } | ||
2032 | // Larger search area for next time around if not found | ||
2033 | range *= 2; | ||
2034 | } | ||
2035 | } | ||
2036 | return ret; | ||
2040 | } | 2037 | } |
2041 | 2038 | ||
2042 | private void InformClientOfNeighbourCompleted(IAsyncResult iar) | 2039 | private void InformClientOfNeighbourCompleted(IAsyncResult iar) |
@@ -2245,10 +2242,13 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
2245 | /// Move the given scene object into a new region depending on which region its absolute position has moved | 2242 | /// Move the given scene object into a new region depending on which region its absolute position has moved |
2246 | /// into. | 2243 | /// into. |
2247 | /// | 2244 | /// |
2248 | /// This method locates the new region handle and offsets the prim position for the new region | 2245 | /// Using the objects new world location, ask the grid service for a the new region and adjust the prim |
2246 | /// position to be relative to the new region. | ||
2249 | /// </summary> | 2247 | /// </summary> |
2250 | /// <param name="attemptedPosition">the attempted out of region position of the scene object</param> | ||
2251 | /// <param name="grp">the scene object that we're crossing</param> | 2248 | /// <param name="grp">the scene object that we're crossing</param> |
2249 | /// <param name="attemptedPosition">the attempted out of region position of the scene object. This position is | ||
2250 | /// relative to the region the object currently is in.</param> | ||
2251 | /// <param name="silent">if 'true', the deletion of the client from the region is not broadcast to the clients</param> | ||
2252 | public void Cross(SceneObjectGroup grp, Vector3 attemptedPosition, bool silent) | 2252 | public void Cross(SceneObjectGroup grp, Vector3 attemptedPosition, bool silent) |
2253 | { | 2253 | { |
2254 | if (grp == null) | 2254 | if (grp == null) |
@@ -2274,208 +2274,51 @@ namespace OpenSim.Region.CoreModules.Framework.EntityTransfer | |||
2274 | return; | 2274 | return; |
2275 | } | 2275 | } |
2276 | 2276 | ||
2277 | int thisx = (int)scene.RegionInfo.RegionLocX; | 2277 | // Remember the old group position in case the region lookup fails so position can be restored. |
2278 | int thisy = (int)scene.RegionInfo.RegionLocY; | 2278 | Vector3 oldGroupPosition = grp.RootPart.GroupPosition; |
2279 | Vector3 EastCross = new Vector3(0.1f, 0, 0); | ||
2280 | Vector3 WestCross = new Vector3(-0.1f, 0, 0); | ||
2281 | Vector3 NorthCross = new Vector3(0, 0.1f, 0); | ||
2282 | Vector3 SouthCross = new Vector3(0, -0.1f, 0); | ||
2283 | |||
2284 | |||
2285 | // use this if no borders were crossed! | ||
2286 | ulong newRegionHandle | ||
2287 | = Util.UIntsToLong((uint)((thisx) * Constants.RegionSize), | ||
2288 | (uint)((thisy) * Constants.RegionSize)); | ||
2289 | |||
2290 | Vector3 pos = attemptedPosition; | ||
2291 | |||
2292 | int changeX = 1; | ||
2293 | int changeY = 1; | ||
2294 | |||
2295 | if (scene.TestBorderCross(attemptedPosition + WestCross, Cardinals.W)) | ||
2296 | { | ||
2297 | if (scene.TestBorderCross(attemptedPosition + SouthCross, Cardinals.S)) | ||
2298 | { | ||
2299 | |||
2300 | Border crossedBorderx = scene.GetCrossedBorder(attemptedPosition + WestCross, Cardinals.W); | ||
2301 | |||
2302 | if (crossedBorderx.BorderLine.Z > 0) | ||
2303 | { | ||
2304 | pos.X = ((pos.X + crossedBorderx.BorderLine.Z)); | ||
2305 | changeX = (int)(crossedBorderx.BorderLine.Z / (int)Constants.RegionSize); | ||
2306 | } | ||
2307 | else | ||
2308 | pos.X = ((pos.X + Constants.RegionSize)); | ||
2309 | |||
2310 | Border crossedBordery = scene.GetCrossedBorder(attemptedPosition + SouthCross, Cardinals.S); | ||
2311 | //(crossedBorderx.BorderLine.Z / (int)Constants.RegionSize) | ||
2312 | |||
2313 | if (crossedBordery.BorderLine.Z > 0) | ||
2314 | { | ||
2315 | pos.Y = ((pos.Y + crossedBordery.BorderLine.Z)); | ||
2316 | changeY = (int)(crossedBordery.BorderLine.Z / (int)Constants.RegionSize); | ||
2317 | } | ||
2318 | else | ||
2319 | pos.Y = ((pos.Y + Constants.RegionSize)); | ||
2320 | |||
2321 | |||
2322 | |||
2323 | newRegionHandle | ||
2324 | = Util.UIntsToLong((uint)((thisx - changeX) * Constants.RegionSize), | ||
2325 | (uint)((thisy - changeY) * Constants.RegionSize)); | ||
2326 | // x - 1 | ||
2327 | // y - 1 | ||
2328 | } | ||
2329 | else if (scene.TestBorderCross(attemptedPosition + NorthCross, Cardinals.N)) | ||
2330 | { | ||
2331 | Border crossedBorderx = scene.GetCrossedBorder(attemptedPosition + WestCross, Cardinals.W); | ||
2332 | |||
2333 | if (crossedBorderx.BorderLine.Z > 0) | ||
2334 | { | ||
2335 | pos.X = ((pos.X + crossedBorderx.BorderLine.Z)); | ||
2336 | changeX = (int)(crossedBorderx.BorderLine.Z / (int)Constants.RegionSize); | ||
2337 | } | ||
2338 | else | ||
2339 | pos.X = ((pos.X + Constants.RegionSize)); | ||
2340 | |||
2341 | |||
2342 | Border crossedBordery = scene.GetCrossedBorder(attemptedPosition + SouthCross, Cardinals.S); | ||
2343 | //(crossedBorderx.BorderLine.Z / (int)Constants.RegionSize) | ||
2344 | |||
2345 | if (crossedBordery.BorderLine.Z > 0) | ||
2346 | { | ||
2347 | pos.Y = ((pos.Y + crossedBordery.BorderLine.Z)); | ||
2348 | changeY = (int)(crossedBordery.BorderLine.Z / (int)Constants.RegionSize); | ||
2349 | } | ||
2350 | else | ||
2351 | pos.Y = ((pos.Y + Constants.RegionSize)); | ||
2352 | 2279 | ||
2353 | newRegionHandle | 2280 | // Compute the absolute position of the object. |
2354 | = Util.UIntsToLong((uint)((thisx - changeX) * Constants.RegionSize), | 2281 | double objectWorldLocX = (double)scene.RegionInfo.WorldLocX + attemptedPosition.X; |
2355 | (uint)((thisy + changeY) * Constants.RegionSize)); | 2282 | double objectWorldLocY = (double)scene.RegionInfo.WorldLocY + attemptedPosition.Y; |
2356 | // x - 1 | ||
2357 | // y + 1 | ||
2358 | } | ||
2359 | else | ||
2360 | { | ||
2361 | Border crossedBorderx = scene.GetCrossedBorder(attemptedPosition + WestCross, Cardinals.W); | ||
2362 | 2283 | ||
2363 | if (crossedBorderx.BorderLine.Z > 0) | 2284 | // Ask the grid service for the region that contains the passed address |
2364 | { | 2285 | GridRegion destination = GetRegionContainingWorldLocation(scene.GridService, scene.RegionInfo.ScopeID, objectWorldLocX, objectWorldLocY); |
2365 | pos.X = ((pos.X + crossedBorderx.BorderLine.Z)); | ||
2366 | changeX = (int)(crossedBorderx.BorderLine.Z / (int)Constants.RegionSize); | ||
2367 | } | ||
2368 | else | ||
2369 | pos.X = ((pos.X + Constants.RegionSize)); | ||
2370 | 2286 | ||
2371 | newRegionHandle | 2287 | Vector3 pos = Vector3.Zero; |
2372 | = Util.UIntsToLong((uint)((thisx - changeX) * Constants.RegionSize), | 2288 | if (destination != null) |
2373 | (uint)(thisy * Constants.RegionSize)); | ||
2374 | // x - 1 | ||
2375 | } | ||
2376 | } | ||
2377 | else if (scene.TestBorderCross(attemptedPosition + EastCross, Cardinals.E)) | ||
2378 | { | 2289 | { |
2379 | if (scene.TestBorderCross(attemptedPosition + SouthCross, Cardinals.S)) | 2290 | // Adjust the object's relative position from the old region (attemptedPosition) |
2380 | { | 2291 | // to be relative to the new region (pos). |
2381 | 2292 | pos = new Vector3( (float)(objectWorldLocX - (double)destination.RegionLocX), | |
2382 | pos.X = ((pos.X - Constants.RegionSize)); | 2293 | (float)(objectWorldLocY - (double)destination.RegionLocY), |
2383 | Border crossedBordery = scene.GetCrossedBorder(attemptedPosition + SouthCross, Cardinals.S); | 2294 | attemptedPosition.Z); |
2384 | //(crossedBorderx.BorderLine.Z / (int)Constants.RegionSize) | ||
2385 | |||
2386 | if (crossedBordery.BorderLine.Z > 0) | ||
2387 | { | ||
2388 | pos.Y = ((pos.Y + crossedBordery.BorderLine.Z)); | ||
2389 | changeY = (int)(crossedBordery.BorderLine.Z / (int)Constants.RegionSize); | ||
2390 | } | ||
2391 | else | ||
2392 | pos.Y = ((pos.Y + Constants.RegionSize)); | ||
2393 | |||
2394 | |||
2395 | newRegionHandle | ||
2396 | = Util.UIntsToLong((uint)((thisx + changeX) * Constants.RegionSize), | ||
2397 | (uint)((thisy - changeY) * Constants.RegionSize)); | ||
2398 | // x + 1 | ||
2399 | // y - 1 | ||
2400 | } | ||
2401 | else if (scene.TestBorderCross(attemptedPosition + NorthCross, Cardinals.N)) | ||
2402 | { | ||
2403 | pos.X = ((pos.X - Constants.RegionSize)); | ||
2404 | pos.Y = ((pos.Y - Constants.RegionSize)); | ||
2405 | newRegionHandle | ||
2406 | = Util.UIntsToLong((uint)((thisx + changeX) * Constants.RegionSize), | ||
2407 | (uint)((thisy + changeY) * Constants.RegionSize)); | ||
2408 | // x + 1 | ||
2409 | // y + 1 | ||
2410 | } | ||
2411 | else | ||
2412 | { | ||
2413 | pos.X = ((pos.X - Constants.RegionSize)); | ||
2414 | newRegionHandle | ||
2415 | = Util.UIntsToLong((uint)((thisx + changeX) * Constants.RegionSize), | ||
2416 | (uint)(thisy * Constants.RegionSize)); | ||
2417 | // x + 1 | ||
2418 | } | ||
2419 | } | 2295 | } |
2420 | else if (scene.TestBorderCross(attemptedPosition + SouthCross, Cardinals.S)) | ||
2421 | { | ||
2422 | Border crossedBordery = scene.GetCrossedBorder(attemptedPosition + SouthCross, Cardinals.S); | ||
2423 | //(crossedBorderx.BorderLine.Z / (int)Constants.RegionSize) | ||
2424 | 2296 | ||
2425 | if (crossedBordery.BorderLine.Z > 0) | 2297 | if (destination != null) |
2298 | { | ||
2299 | if (!CrossPrimGroupIntoNewRegion(destination, pos, grp, silent)) | ||
2426 | { | 2300 | { |
2427 | pos.Y = ((pos.Y + crossedBordery.BorderLine.Z)); | 2301 | m_log.InfoFormat("[ENTITY TRANSFER MODULE] cross region transfer failed for object {0}", grp.UUID); |
2428 | changeY = (int)(crossedBordery.BorderLine.Z / (int)Constants.RegionSize); | 2302 | |
2303 | // We are going to move the object back to the old position so long as the old position | ||
2304 | // is in the region | ||
2305 | oldGroupPosition.X = Util.Clamp<float>(oldGroupPosition.X, 1.0f, (float)(scene.RegionInfo.RegionSizeX - 1)); | ||
2306 | oldGroupPosition.Y = Util.Clamp<float>(oldGroupPosition.Y, 1.0f, (float)(scene.RegionInfo.RegionSizeY - 1)); | ||
2307 | oldGroupPosition.Z = Util.Clamp<float>(oldGroupPosition.Z, 1.0f, Constants.RegionHeight); | ||
2308 | |||
2309 | grp.AbsolutePosition = oldGroupPosition; | ||
2310 | grp.Velocity = Vector3.Zero; | ||
2311 | if (grp.RootPart.PhysActor != null) | ||
2312 | grp.RootPart.PhysActor.CrossingFailure(); | ||
2313 | |||
2314 | if (grp.RootPart.KeyframeMotion != null) | ||
2315 | grp.RootPart.KeyframeMotion.CrossingFailure(); | ||
2316 | |||
2317 | grp.ScheduleGroupForFullUpdate(); | ||
2429 | } | 2318 | } |
2430 | else | ||
2431 | pos.Y = ((pos.Y + Constants.RegionSize)); | ||
2432 | |||
2433 | newRegionHandle | ||
2434 | = Util.UIntsToLong((uint)(thisx * Constants.RegionSize), (uint)((thisy - changeY) * Constants.RegionSize)); | ||
2435 | // y - 1 | ||
2436 | } | 2319 | } |
2437 | else if (scene.TestBorderCross(attemptedPosition + NorthCross, Cardinals.N)) | ||
2438 | { | ||
2439 | |||
2440 | pos.Y = ((pos.Y - Constants.RegionSize)); | ||
2441 | newRegionHandle | ||
2442 | = Util.UIntsToLong((uint)(thisx * Constants.RegionSize), (uint)((thisy + changeY) * Constants.RegionSize)); | ||
2443 | // y + 1 | ||
2444 | } | ||
2445 | |||
2446 | // Offset the positions for the new region across the border | ||
2447 | Vector3 oldGroupPosition = grp.RootPart.GroupPosition; | ||
2448 | |||
2449 | // If we fail to cross the border, then reset the position of the scene object on that border. | ||
2450 | uint x = 0, y = 0; | ||
2451 | Utils.LongToUInts(newRegionHandle, out x, out y); | ||
2452 | GridRegion destination = scene.GridService.GetRegionByPosition(scene.RegionInfo.ScopeID, (int)x, (int)y); | ||
2453 | |||
2454 | if (destination != null) | ||
2455 | { | ||
2456 | if (CrossPrimGroupIntoNewRegion(destination, pos, grp, silent)) | ||
2457 | return; // we did it | ||
2458 | } | ||
2459 | |||
2460 | // no one or failed lets go back and tell physics to go on | ||
2461 | oldGroupPosition.X = Util.Clamp<float>(oldGroupPosition.X, 0.5f, (float)Constants.RegionSize - 0.5f); | ||
2462 | oldGroupPosition.Y = Util.Clamp<float>(oldGroupPosition.Y, 0.5f, (float)Constants.RegionSize - 0.5f); | ||
2463 | oldGroupPosition.Z = Util.Clamp<float>(oldGroupPosition.Z, 0.5f, 4096.0f); | ||
2464 | |||
2465 | grp.AbsolutePosition = oldGroupPosition; | ||
2466 | grp.Velocity = Vector3.Zero; | ||
2467 | |||
2468 | if (grp.RootPart.PhysActor != null) | ||
2469 | grp.RootPart.PhysActor.CrossingFailure(); | ||
2470 | |||
2471 | if (grp.RootPart.KeyframeMotion != null) | ||
2472 | grp.RootPart.KeyframeMotion.CrossingFailure(); | ||
2473 | |||
2474 | grp.ScheduleGroupForFullUpdate(); | ||
2475 | } | 2320 | } |
2476 | 2321 | ||
2477 | |||
2478 | |||
2479 | /// <summary> | 2322 | /// <summary> |
2480 | /// Move the given scene object into a new region | 2323 | /// Move the given scene object into a new region |
2481 | /// </summary> | 2324 | /// </summary> |
diff --git a/OpenSim/Region/CoreModules/Scripting/EMailModules/EmailModule.cs b/OpenSim/Region/CoreModules/Scripting/EMailModules/EmailModule.cs index d943b20..4e7ad75 100644 --- a/OpenSim/Region/CoreModules/Scripting/EMailModules/EmailModule.cs +++ b/OpenSim/Region/CoreModules/Scripting/EMailModules/EmailModule.cs | |||
@@ -213,8 +213,8 @@ namespace OpenSim.Region.CoreModules.Scripting.EmailModules | |||
213 | if (part != null) | 213 | if (part != null) |
214 | { | 214 | { |
215 | ObjectRegionName = s.RegionInfo.RegionName; | 215 | ObjectRegionName = s.RegionInfo.RegionName; |
216 | uint localX = (s.RegionInfo.RegionLocX * (int)Constants.RegionSize); | 216 | uint localX = s.RegionInfo.WorldLocX; |
217 | uint localY = (s.RegionInfo.RegionLocY * (int)Constants.RegionSize); | 217 | uint localY = s.RegionInfo.WorldLocY; |
218 | ObjectRegionName = ObjectRegionName + " (" + localX + ", " + localY + ")"; | 218 | ObjectRegionName = ObjectRegionName + " (" + localX + ", " + localY + ")"; |
219 | return part; | 219 | return part; |
220 | } | 220 | } |
diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/LocalGridServiceConnector.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/LocalGridServiceConnector.cs index 31ef79b..277293a 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/LocalGridServiceConnector.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/LocalGridServiceConnector.cs | |||
@@ -192,8 +192,12 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
192 | return m_GridService.GetRegionByUUID(scopeID, regionID); | 192 | return m_GridService.GetRegionByUUID(scopeID, regionID); |
193 | } | 193 | } |
194 | 194 | ||
195 | // Get a region given its base coordinates. | ||
196 | // NOTE: this is NOT 'get a region by some point in the region'. The coordinate MUST | ||
197 | // be the base coordinate of the region. | ||
195 | public GridRegion GetRegionByPosition(UUID scopeID, int x, int y) | 198 | public GridRegion GetRegionByPosition(UUID scopeID, int x, int y) |
196 | { | 199 | { |
200 | m_log.DebugFormat("{0} GetRegionByPosition. pos=<{1},{2}>", "[LOCAL GRID SERVICE CONNECTOR", x, y); | ||
197 | GridRegion region = null; | 201 | GridRegion region = null; |
198 | 202 | ||
199 | // First see if it's a neighbour, even if it isn't on this sim. | 203 | // First see if it's a neighbour, even if it isn't on this sim. |
@@ -206,6 +210,8 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
206 | region = rcache.GetRegionByPosition(x, y); | 210 | region = rcache.GetRegionByPosition(x, y); |
207 | if (region != null) | 211 | if (region != null) |
208 | { | 212 | { |
213 | m_log.DebugFormat("{0} GetRegionByPosition. Found region {1}. Pos=<{2},{3}>", | ||
214 | "[LOCAL GRID SERVICE CONNECTOR", region.RegionName, x, y); | ||
209 | return region; | 215 | return region; |
210 | } | 216 | } |
211 | } | 217 | } |
@@ -268,7 +274,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
268 | caps.AppendFormat("*** Neighbours of {0} ({1}) ***\n", kvp.Value.RegionName, kvp.Key); | 274 | caps.AppendFormat("*** Neighbours of {0} ({1}) ***\n", kvp.Value.RegionName, kvp.Key); |
269 | List<GridRegion> regions = kvp.Value.GetNeighbours(); | 275 | List<GridRegion> regions = kvp.Value.GetNeighbours(); |
270 | foreach (GridRegion r in regions) | 276 | foreach (GridRegion r in regions) |
271 | caps.AppendFormat(" {0} @ {1}-{2}\n", r.RegionName, r.RegionLocX / Constants.RegionSize, r.RegionLocY / Constants.RegionSize); | 277 | caps.AppendFormat(" {0} @ {1}-{2}\n", r.RegionName, Util.WorldToRegionLoc((uint)r.RegionLocX), Util.WorldToRegionLoc((uint)r.RegionLocY)); |
272 | } | 278 | } |
273 | } | 279 | } |
274 | 280 | ||
diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionCache.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionCache.cs index 9172536..33ff7ea 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionCache.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RegionCache.cs | |||
@@ -66,7 +66,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
66 | return; | 66 | return; |
67 | 67 | ||
68 | m_log.DebugFormat("[REGION CACHE]: (on region {0}) Region {1} is up @ {2}-{3}", | 68 | m_log.DebugFormat("[REGION CACHE]: (on region {0}) Region {1} is up @ {2}-{3}", |
69 | m_scene.RegionInfo.RegionName, otherRegion.RegionName, otherRegion.RegionLocX / Constants.RegionSize, otherRegion.RegionLocY / Constants.RegionSize); | 69 | m_scene.RegionInfo.RegionName, otherRegion.RegionName, Util.WorldToRegionLoc((uint)otherRegion.RegionLocX), Util.WorldToRegionLoc((uint)otherRegion.RegionLocY)); |
70 | 70 | ||
71 | m_neighbours[otherRegion.RegionHandle] = otherRegion; | 71 | m_neighbours[otherRegion.RegionHandle] = otherRegion; |
72 | } | 72 | } |
@@ -82,11 +82,16 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
82 | return new List<GridRegion>(m_neighbours.Values); | 82 | return new List<GridRegion>(m_neighbours.Values); |
83 | } | 83 | } |
84 | 84 | ||
85 | // Get a region given its base coordinates. | ||
86 | // NOTE: this is NOT 'get a region by some point in the region'. The coordinate MUST | ||
87 | // be the base coordinate of the region. | ||
88 | // The snapping is technically unnecessary but is harmless because regions are always | ||
89 | // multiples of the legacy region size (256). | ||
85 | public GridRegion GetRegionByPosition(int x, int y) | 90 | public GridRegion GetRegionByPosition(int x, int y) |
86 | { | 91 | { |
87 | uint xsnap = (uint)(x / Constants.RegionSize) * Constants.RegionSize; | 92 | uint xsnap = (uint)(x / Constants.RegionSize) * Constants.RegionSize; |
88 | uint ysnap = (uint)(y / Constants.RegionSize) * Constants.RegionSize; | 93 | uint ysnap = (uint)(y / Constants.RegionSize) * Constants.RegionSize; |
89 | ulong handle = Utils.UIntsToLong(xsnap, ysnap); | 94 | ulong handle = Util.RegionWorldLocToHandle(xsnap, ysnap); |
90 | 95 | ||
91 | if (m_neighbours.ContainsKey(handle)) | 96 | if (m_neighbours.ContainsKey(handle)) |
92 | return m_neighbours[handle]; | 97 | return m_neighbours[handle]; |
diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RemoteGridServiceConnector.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RemoteGridServiceConnector.cs index 6a57d1f..ac81337 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RemoteGridServiceConnector.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/RemoteGridServiceConnector.cs | |||
@@ -186,10 +186,14 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
186 | return rinfo; | 186 | return rinfo; |
187 | } | 187 | } |
188 | 188 | ||
189 | // Get a region given its base coordinates. | ||
190 | // NOTE: this is NOT 'get a region by some point in the region'. The coordinate MUST | ||
191 | // be the base coordinate of the region. | ||
192 | // The coordinates are world coords (meters), NOT region units. | ||
189 | public GridRegion GetRegionByPosition(UUID scopeID, int x, int y) | 193 | public GridRegion GetRegionByPosition(UUID scopeID, int x, int y) |
190 | { | 194 | { |
191 | bool inCache = false; | 195 | bool inCache = false; |
192 | GridRegion rinfo = m_RegionInfoCache.Get(scopeID, Util.UIntsToLong((uint)x, (uint)y), out inCache); | 196 | GridRegion rinfo = m_RegionInfoCache.Get(scopeID, Util.RegionWorldLocToHandle((uint)x, (uint)y), out inCache); |
193 | if (inCache) | 197 | if (inCache) |
194 | return rinfo; | 198 | return rinfo; |
195 | 199 | ||
diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/Tests/GridConnectorsTests.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/Tests/GridConnectorsTests.cs index 4338133..25ae689 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/Tests/GridConnectorsTests.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/Tests/GridConnectorsTests.cs | |||
@@ -34,6 +34,7 @@ using log4net.Config; | |||
34 | using Nini.Config; | 34 | using Nini.Config; |
35 | using NUnit.Framework; | 35 | using NUnit.Framework; |
36 | using OpenMetaverse; | 36 | using OpenMetaverse; |
37 | |||
37 | using OpenSim.Framework; | 38 | using OpenSim.Framework; |
38 | using OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid; | 39 | using OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid; |
39 | using OpenSim.Region.Framework.Scenes; | 40 | using OpenSim.Region.Framework.Scenes; |
@@ -141,7 +142,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid.Tests | |||
141 | Assert.IsNotNull(result, "Retrieved GetRegionByUUID is null"); | 142 | Assert.IsNotNull(result, "Retrieved GetRegionByUUID is null"); |
142 | Assert.That(result.RegionID, Is.EqualTo(new UUID(1)), "Retrieved region's UUID does not match"); | 143 | Assert.That(result.RegionID, Is.EqualTo(new UUID(1)), "Retrieved region's UUID does not match"); |
143 | 144 | ||
144 | result = m_LocalConnector.GetRegionByPosition(UUID.Zero, 1000 * (int)Constants.RegionSize, 1000 * (int)Constants.RegionSize); | 145 | result = m_LocalConnector.GetRegionByPosition(UUID.Zero, (int)Util.RegionToWorldLoc(1000), (int)Util.RegionToWorldLoc(1000)); |
145 | Assert.IsNotNull(result, "Retrieved GetRegionByPosition is null"); | 146 | Assert.IsNotNull(result, "Retrieved GetRegionByPosition is null"); |
146 | Assert.That(result.RegionLocX, Is.EqualTo(1000 * (int)Constants.RegionSize), "Retrieved region's position does not match"); | 147 | Assert.That(result.RegionLocX, Is.EqualTo(1000 * (int)Constants.RegionSize), "Retrieved region's position does not match"); |
147 | 148 | ||
diff --git a/OpenSim/Region/CoreModules/World/Land/LandManagementModule.cs b/OpenSim/Region/CoreModules/World/Land/LandManagementModule.cs index 73c4d6c..99db7ff 100644 --- a/OpenSim/Region/CoreModules/World/Land/LandManagementModule.cs +++ b/OpenSim/Region/CoreModules/World/Land/LandManagementModule.cs | |||
@@ -64,6 +64,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
64 | public class LandManagementModule : INonSharedRegionModule | 64 | public class LandManagementModule : INonSharedRegionModule |
65 | { | 65 | { |
66 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 66 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
67 | private static readonly string LogHeader = "[LAND MANAGEMENT MODULE]"; | ||
67 | 68 | ||
68 | private static readonly string remoteParcelRequestPath = "0009/"; | 69 | private static readonly string remoteParcelRequestPath = "0009/"; |
69 | 70 | ||
@@ -74,15 +75,11 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
74 | protected IPrimCountModule m_primCountModule; | 75 | protected IPrimCountModule m_primCountModule; |
75 | protected IDialogModule m_Dialog; | 76 | protected IDialogModule m_Dialog; |
76 | 77 | ||
77 | // Minimum for parcels to work is 64m even if we don't actually use them. | ||
78 | #pragma warning disable 0429 | ||
79 | private const int landArrayMax = ((int)((int)Constants.RegionSize / 4) >= 64) ? (int)((int)Constants.RegionSize / 4) : 64; | ||
80 | #pragma warning restore 0429 | ||
81 | |||
82 | /// <value> | 78 | /// <value> |
83 | /// Local land ids at specified region co-ordinates (region size / 4) | 79 | /// Local land ids at specified region co-ordinates (region size / 4) |
84 | /// </value> | 80 | /// </value> |
85 | private readonly int[,] m_landIDList = new int[landArrayMax, landArrayMax]; | 81 | private int[,] m_landIDList; |
82 | private const int landUnit = 4; | ||
86 | 83 | ||
87 | /// <value> | 84 | /// <value> |
88 | /// Land objects keyed by local id | 85 | /// Land objects keyed by local id |
@@ -115,6 +112,8 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
115 | public void AddRegion(Scene scene) | 112 | public void AddRegion(Scene scene) |
116 | { | 113 | { |
117 | m_scene = scene; | 114 | m_scene = scene; |
115 | m_landIDList = new int[m_scene.RegionInfo.RegionSizeX / landUnit, m_scene.RegionInfo.RegionSizeY / landUnit]; | ||
116 | |||
118 | m_landIDList.Initialize(); | 117 | m_landIDList.Initialize(); |
119 | landChannel = new LandChannel(scene, this); | 118 | landChannel = new LandChannel(scene, this); |
120 | 119 | ||
@@ -297,6 +296,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
297 | { | 296 | { |
298 | m_landList.Clear(); | 297 | m_landList.Clear(); |
299 | m_lastLandLocalID = LandChannel.START_LAND_LOCAL_ID - 1; | 298 | m_lastLandLocalID = LandChannel.START_LAND_LOCAL_ID - 1; |
299 | m_landIDList = new int[m_scene.RegionInfo.RegionSizeX / landUnit, m_scene.RegionInfo.RegionSizeY / landUnit]; | ||
300 | m_landIDList.Initialize(); | 300 | m_landIDList.Initialize(); |
301 | } | 301 | } |
302 | } | 302 | } |
@@ -311,7 +311,8 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
311 | "[LAND MANAGEMENT MODULE]: Creating default parcel for region {0}", m_scene.RegionInfo.RegionName); | 311 | "[LAND MANAGEMENT MODULE]: Creating default parcel for region {0}", m_scene.RegionInfo.RegionName); |
312 | 312 | ||
313 | ILandObject fullSimParcel = new LandObject(UUID.Zero, false, m_scene); | 313 | ILandObject fullSimParcel = new LandObject(UUID.Zero, false, m_scene); |
314 | fullSimParcel.SetLandBitmap(fullSimParcel.GetSquareLandBitmap(0, 0, (int)Constants.RegionSize, (int)Constants.RegionSize)); | 314 | fullSimParcel.SetLandBitmap(fullSimParcel.GetSquareLandBitmap(0, 0, |
315 | (int)m_scene.RegionInfo.RegionSizeX, (int)m_scene.RegionInfo.RegionSizeY)); | ||
315 | fullSimParcel.LandData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner; | 316 | fullSimParcel.LandData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner; |
316 | fullSimParcel.LandData.ClaimDate = Util.UnixTimeSinceEpoch(); | 317 | fullSimParcel.LandData.ClaimDate = Util.UnixTimeSinceEpoch(); |
317 | 318 | ||
@@ -438,8 +439,8 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
438 | 439 | ||
439 | public void SendLandUpdate(ScenePresence avatar, bool force) | 440 | public void SendLandUpdate(ScenePresence avatar, bool force) |
440 | { | 441 | { |
441 | ILandObject over = GetLandObject((int)Math.Min(((int)Constants.RegionSize - 1), Math.Max(0, Math.Round(avatar.AbsolutePosition.X))), | 442 | ILandObject over = GetLandObject((int)Math.Min(((int)m_scene.RegionInfo.RegionSizeX - 1), Math.Max(0, Math.Round(avatar.AbsolutePosition.X))), |
442 | (int)Math.Min(((int)Constants.RegionSize - 1), Math.Max(0, Math.Round(avatar.AbsolutePosition.Y)))); | 443 | (int)Math.Min(((int)m_scene.RegionInfo.RegionSizeY - 1), Math.Max(0, Math.Round(avatar.AbsolutePosition.Y)))); |
443 | 444 | ||
444 | if (over != null) | 445 | if (over != null) |
445 | { | 446 | { |
@@ -605,17 +606,29 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
605 | new_land.LandData.LocalID = newLandLocalID; | 606 | new_land.LandData.LocalID = newLandLocalID; |
606 | 607 | ||
607 | bool[,] landBitmap = new_land.GetLandBitmap(); | 608 | bool[,] landBitmap = new_land.GetLandBitmap(); |
608 | for (int x = 0; x < landArrayMax; x++) | 609 | // m_log.DebugFormat("{0} AddLandObject. new_land.bitmapSize=({1},{2}). newLocalID={3}", |
610 | // LogHeader, landBitmap.GetLength(0), landBitmap.GetLength(1), newLandLocalID); | ||
611 | |||
612 | if (landBitmap.GetLength(0) != m_landIDList.GetLength(0) || landBitmap.GetLength(1) != m_landIDList.GetLength(1)) | ||
609 | { | 613 | { |
610 | for (int y = 0; y < landArrayMax; y++) | 614 | // Going to variable sized regions can cause mismatches |
615 | m_log.ErrorFormat("{0} AddLandObject. Added land bitmap different size than region ID map. bitmapSize=({1},{2}), landIDSize=({3},{4})", | ||
616 | LogHeader, landBitmap.GetLength(0), landBitmap.GetLength(1), m_landIDList.GetLength(0), m_landIDList.GetLength(1) ); | ||
617 | } | ||
618 | else | ||
619 | { | ||
620 | for (int x = 0; x < landBitmap.GetLength(0); x++) | ||
611 | { | 621 | { |
612 | if (landBitmap[x, y]) | 622 | for (int y = 0; y < landBitmap.GetLength(1); y++) |
613 | { | 623 | { |
614 | // m_log.DebugFormat( | 624 | if (landBitmap[x, y]) |
615 | // "[LAND MANAGEMENT MODULE]: Registering parcel {0} for land co-ord ({1}, {2}) on {3}", | 625 | { |
616 | // new_land.LandData.Name, x, y, m_scene.RegionInfo.RegionName); | 626 | // m_log.DebugFormat( |
617 | 627 | // "[LAND MANAGEMENT MODULE]: Registering parcel {0} for land co-ord ({1}, {2}) on {3}", | |
618 | m_landIDList[x, y] = newLandLocalID; | 628 | // new_land.LandData.Name, x, y, m_scene.RegionInfo.RegionName); |
629 | |||
630 | m_landIDList[x, y] = newLandLocalID; | ||
631 | } | ||
619 | } | 632 | } |
620 | } | 633 | } |
621 | } | 634 | } |
@@ -637,9 +650,9 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
637 | ILandObject land; | 650 | ILandObject land; |
638 | lock (m_landList) | 651 | lock (m_landList) |
639 | { | 652 | { |
640 | for (int x = 0; x < 64; x++) | 653 | for (int x = 0; x < m_landIDList.GetLength(0); x++) |
641 | { | 654 | { |
642 | for (int y = 0; y < 64; y++) | 655 | for (int y = 0; y < m_landIDList.GetLength(1); y++) |
643 | { | 656 | { |
644 | if (m_landIDList[x, y] == local_id) | 657 | if (m_landIDList[x, y] == local_id) |
645 | { | 658 | { |
@@ -691,9 +704,9 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
691 | bool[,] landBitmapSlave = slave.GetLandBitmap(); | 704 | bool[,] landBitmapSlave = slave.GetLandBitmap(); |
692 | lock (m_landList) | 705 | lock (m_landList) |
693 | { | 706 | { |
694 | for (int x = 0; x < 64; x++) | 707 | for (int x = 0; x < landBitmapSlave.GetLength(0); x++) |
695 | { | 708 | { |
696 | for (int y = 0; y < 64; y++) | 709 | for (int y = 0; y < landBitmapSlave.GetLength(1); y++) |
697 | { | 710 | { |
698 | if (landBitmapSlave[x, y]) | 711 | if (landBitmapSlave[x, y]) |
699 | { | 712 | { |
@@ -727,23 +740,28 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
727 | /// <returns>Land object at the point supplied</returns> | 740 | /// <returns>Land object at the point supplied</returns> |
728 | public ILandObject GetLandObject(float x_float, float y_float) | 741 | public ILandObject GetLandObject(float x_float, float y_float) |
729 | { | 742 | { |
743 | return GetLandObject((int)x_float, (int)y_float, true /* returnNullIfLandObjectNotFound */); | ||
744 | /* | ||
730 | int x; | 745 | int x; |
731 | int y; | 746 | int y; |
732 | 747 | ||
733 | if (x_float >= Constants.RegionSize || x_float < 0 || y_float >= Constants.RegionSize || y_float < 0) | 748 | if (x_float >= m_scene.RegionInfo.RegionSizeX || x_float < 0 || y_float >= m_scene.RegionInfo.RegionSizeX || y_float < 0) |
734 | return null; | 749 | return null; |
735 | 750 | ||
736 | try | 751 | try |
737 | { | 752 | { |
738 | x = Convert.ToInt32(Math.Floor(Convert.ToDouble(x_float) / 4.0)); | 753 | x = Convert.ToInt32(Math.Floor(Convert.ToDouble(x_float) / (float)landUnit)); |
739 | y = Convert.ToInt32(Math.Floor(Convert.ToDouble(y_float) / 4.0)); | 754 | y = Convert.ToInt32(Math.Floor(Convert.ToDouble(y_float) / (float)landUnit)); |
740 | } | 755 | } |
741 | catch (OverflowException) | 756 | catch (OverflowException) |
742 | { | 757 | { |
743 | return null; | 758 | return null; |
744 | } | 759 | } |
745 | 760 | ||
746 | if (x >= 64 || y >= 64 || x < 0 || y < 0) | 761 | if (x >= (m_scene.RegionInfo.RegionSizeX / landUnit) |
762 | || y >= (m_scene.RegionInfo.RegionSizeY / landUnit) | ||
763 | || x < 0 | ||
764 | || y < 0) | ||
747 | { | 765 | { |
748 | return null; | 766 | return null; |
749 | } | 767 | } |
@@ -759,38 +777,122 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
759 | // m_log.DebugFormat( | 777 | // m_log.DebugFormat( |
760 | // "[LAND MANAGEMENT MODULE]: No land object found at ({0}, {1}) on {2}", | 778 | // "[LAND MANAGEMENT MODULE]: No land object found at ({0}, {1}) on {2}", |
761 | // x, y, m_scene.RegionInfo.RegionName); | 779 | // x, y, m_scene.RegionInfo.RegionName); |
762 | 780 | ||
763 | if (m_landList.ContainsKey(m_landIDList[x, y])) | 781 | try |
764 | return m_landList[m_landIDList[x, y]]; | 782 | { |
783 | if (m_landList.ContainsKey(m_landIDList[x, y])) | ||
784 | return m_landList[m_landIDList[x, y]]; | ||
785 | } | ||
786 | catch (Exception e) | ||
787 | { | ||
788 | m_log.DebugFormat("{0} GetLandObject exception. x={1}, y={2}, m_landIDList.len=({3},{4})", | ||
789 | LogHeader, x, y, m_landIDList.GetLength(0), m_landIDList.GetLength(1)); | ||
790 | } | ||
765 | 791 | ||
766 | return null; | 792 | return null; |
767 | } | 793 | } |
794 | */ | ||
768 | } | 795 | } |
769 | 796 | ||
797 | // Public entry. | ||
798 | // Throws exception if land object is not found | ||
770 | public ILandObject GetLandObject(int x, int y) | 799 | public ILandObject GetLandObject(int x, int y) |
771 | { | 800 | { |
772 | if (x >= Convert.ToInt32(Constants.RegionSize) || y >= Convert.ToInt32(Constants.RegionSize) || x < 0 || y < 0) | 801 | return GetLandObject(x, y, false /* returnNullIfLandObjectNotFound */); |
802 | } | ||
803 | |||
804 | // Given a region position, return the parcel land object for that location | ||
805 | private ILandObject GetLandObject(int x, int y, bool returnNullIfLandObjectNotFound) | ||
806 | { | ||
807 | ILandObject ret = null; | ||
808 | |||
809 | if (x >= m_scene.RegionInfo.RegionSizeX || y >= m_scene.RegionInfo.RegionSizeY || x < 0 || y < 0) | ||
773 | { | 810 | { |
774 | // These exceptions here will cause a lot of complaints from the users specifically because | 811 | // These exceptions here will cause a lot of complaints from the users specifically because |
775 | // they happen every time at border crossings | 812 | // they happen every time at border crossings |
776 | throw new Exception("Error: Parcel not found at point " + x + ", " + y); | 813 | if (returnNullIfLandObjectNotFound) |
814 | return null; | ||
815 | else | ||
816 | throw new Exception( | ||
817 | String.Format("{0} GetLandObject for non-existant position. Region={1}, pos=<{2},{3}", | ||
818 | LogHeader, m_scene.RegionInfo.RegionName, x, y) | ||
819 | ); | ||
777 | } | 820 | } |
778 | 821 | ||
779 | lock (m_landIDList) | 822 | lock (m_landIDList) |
780 | { | 823 | { |
781 | try | 824 | try |
782 | { | 825 | { |
783 | return m_landList[m_landIDList[x / 4, y / 4]]; | 826 | int landID = m_landIDList[x / landUnit, y / landUnit]; |
827 | if (landID == 0) | ||
828 | { | ||
829 | // Zero is the uninitialized value saying there is no parcel for this location. | ||
830 | // This sometimes happens when terrain is resized. | ||
831 | if (m_landList.Count == 1) | ||
832 | { | ||
833 | int onlyParcelID = 0; | ||
834 | ILandObject onlyLandObject = null; | ||
835 | foreach (KeyValuePair<int, ILandObject> kvp in m_landList) | ||
836 | { | ||
837 | onlyParcelID = kvp.Key; | ||
838 | onlyLandObject = kvp.Value; | ||
839 | break; | ||
840 | } | ||
841 | |||
842 | // There is only one parcel. Grow it to fill all the unallocated spaces. | ||
843 | for (int xx = 0; xx < m_landIDList.GetLength(0); xx++) | ||
844 | for (int yy = 0; yy < m_landIDList.GetLength(1); yy++) | ||
845 | if (m_landIDList[xx, yy] == 0) | ||
846 | m_landIDList[xx, yy] = onlyParcelID; | ||
847 | |||
848 | onlyLandObject.LandBitmap = CreateBitmapForID(onlyParcelID); | ||
849 | landID = onlyParcelID; | ||
850 | } | ||
851 | else | ||
852 | { | ||
853 | // There are several other parcels so we must create a new one for the unassigned space | ||
854 | ILandObject newLand = new LandObject(UUID.Zero, false, m_scene); | ||
855 | // Claim all the unclaimed "0" ids | ||
856 | newLand.SetLandBitmap(CreateBitmapForID(0)); | ||
857 | newLand.LandData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner; | ||
858 | newLand.LandData.ClaimDate = Util.UnixTimeSinceEpoch(); | ||
859 | AddLandObject(newLand); | ||
860 | landID = m_lastLandLocalID; | ||
861 | } | ||
862 | } | ||
863 | |||
864 | ret = m_landList[landID]; | ||
784 | } | 865 | } |
785 | catch (IndexOutOfRangeException) | 866 | catch (IndexOutOfRangeException) |
786 | { | 867 | { |
787 | // m_log.WarnFormat( | 868 | m_log.ErrorFormat( |
788 | // "[LAND MANAGEMENT MODULE]: Tried to retrieve land object from out of bounds co-ordinate ({0},{1}) in {2}", | 869 | "{0} GetLandObject: Tried to retrieve land object from out of bounds co-ordinate ({1},{2}) in {3}. landListSize=({4},{5})", |
789 | // x, y, m_scene.RegionInfo.RegionName); | 870 | LogHeader, x, y, m_scene.RegionInfo.RegionName, m_landIDList.GetLength(0), m_landIDList.GetLength(1)); |
790 | 871 | return null; | |
872 | } | ||
873 | catch | ||
874 | { | ||
875 | m_log.ErrorFormat( | ||
876 | "{0} GetLandObject: LandID not in landlist. XY=<{1},{2}> in {3}. landID[x,y]={4}", | ||
877 | LogHeader, x, y, m_scene.RegionInfo.RegionName, m_landIDList[x/landUnit, y/landUnit]); | ||
791 | return null; | 878 | return null; |
792 | } | 879 | } |
793 | } | 880 | } |
881 | return ret; | ||
882 | } | ||
883 | |||
884 | // Create a 'parcel is here' bitmap for the parcel identified by the passed landID | ||
885 | private bool[,] CreateBitmapForID(int landID) | ||
886 | { | ||
887 | bool[,] ret = new bool[m_landIDList.GetLength(0), m_landIDList.GetLength(1)]; | ||
888 | ret.Initialize(); | ||
889 | |||
890 | for (int xx = 0; xx < m_landIDList.GetLength(0); xx++) | ||
891 | for (int yy = 0; yy < m_landIDList.GetLength(0); yy++) | ||
892 | if (m_landIDList[xx, yy] == landID) | ||
893 | ret[xx, yy] = true; | ||
894 | |||
895 | return ret; | ||
794 | } | 896 | } |
795 | 897 | ||
796 | #endregion | 898 | #endregion |
@@ -1053,85 +1155,93 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
1053 | byte[] byteArray = new byte[LAND_BLOCKS_PER_PACKET]; | 1155 | byte[] byteArray = new byte[LAND_BLOCKS_PER_PACKET]; |
1054 | int byteArrayCount = 0; | 1156 | int byteArrayCount = 0; |
1055 | int sequenceID = 0; | 1157 | int sequenceID = 0; |
1056 | int blockmeters = 4 * (int) Constants.RegionSize/(int)Constants.TerrainPatchSize; | ||
1057 | |||
1058 | 1158 | ||
1059 | for (int y = 0; y < blockmeters; y++) | 1159 | // Layer data is in landUnit (4m) chunks |
1160 | for (int y = 0; y < m_scene.RegionInfo.RegionSizeY / Constants.TerrainPatchSize * (Constants.TerrainPatchSize / landUnit); y++) | ||
1060 | { | 1161 | { |
1061 | for (int x = 0; x < blockmeters; x++) | 1162 | for (int x = 0; x < m_scene.RegionInfo.RegionSizeX / Constants.TerrainPatchSize * (Constants.TerrainPatchSize / landUnit); x++) |
1062 | { | 1163 | { |
1063 | byte tempByte = 0; //This represents the byte for the current 4x4 | 1164 | byteArray[byteArrayCount] = BuildLayerByte(GetLandObject(x * landUnit, y * landUnit), x, y, remote_client); |
1165 | byteArrayCount++; | ||
1166 | if (byteArrayCount >= LAND_BLOCKS_PER_PACKET) | ||
1167 | { | ||
1168 | remote_client.SendLandParcelOverlay(byteArray, sequenceID); | ||
1169 | byteArrayCount = 0; | ||
1170 | sequenceID++; | ||
1171 | byteArray = new byte[LAND_BLOCKS_PER_PACKET]; | ||
1172 | } | ||
1064 | 1173 | ||
1065 | ILandObject currentParcelBlock = GetLandObject(x * 4, y * 4); | 1174 | } |
1175 | } | ||
1176 | if (byteArrayCount != 0) | ||
1177 | { | ||
1178 | remote_client.SendLandParcelOverlay(byteArray, sequenceID); | ||
1179 | } | ||
1180 | } | ||
1066 | 1181 | ||
1067 | if (currentParcelBlock != null) | 1182 | private byte BuildLayerByte(ILandObject currentParcelBlock, int x, int y, IClientAPI remote_client) |
1068 | { | 1183 | { |
1069 | if (currentParcelBlock.LandData.OwnerID == remote_client.AgentId) | 1184 | byte tempByte = 0; //This represents the byte for the current 4x4 |
1070 | { | ||
1071 | //Owner Flag | ||
1072 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_TYPE_OWNED_BY_REQUESTER); | ||
1073 | } | ||
1074 | else if (currentParcelBlock.LandData.SalePrice > 0 && | ||
1075 | (currentParcelBlock.LandData.AuthBuyerID == UUID.Zero || | ||
1076 | currentParcelBlock.LandData.AuthBuyerID == remote_client.AgentId)) | ||
1077 | { | ||
1078 | //Sale Flag | ||
1079 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_TYPE_IS_FOR_SALE); | ||
1080 | } | ||
1081 | else if (currentParcelBlock.LandData.OwnerID == UUID.Zero) | ||
1082 | { | ||
1083 | //Public Flag | ||
1084 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_TYPE_PUBLIC); | ||
1085 | } | ||
1086 | else | ||
1087 | { | ||
1088 | //Other Flag | ||
1089 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_TYPE_OWNED_BY_OTHER); | ||
1090 | } | ||
1091 | 1185 | ||
1092 | //Now for border control | 1186 | if (currentParcelBlock != null) |
1187 | { | ||
1188 | if (currentParcelBlock.LandData.OwnerID == remote_client.AgentId) | ||
1189 | { | ||
1190 | //Owner Flag | ||
1191 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_TYPE_OWNED_BY_REQUESTER); | ||
1192 | } | ||
1193 | else if (currentParcelBlock.LandData.SalePrice > 0 && | ||
1194 | (currentParcelBlock.LandData.AuthBuyerID == UUID.Zero || | ||
1195 | currentParcelBlock.LandData.AuthBuyerID == remote_client.AgentId)) | ||
1196 | { | ||
1197 | //Sale Flag | ||
1198 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_TYPE_IS_FOR_SALE); | ||
1199 | } | ||
1200 | else if (currentParcelBlock.LandData.OwnerID == UUID.Zero) | ||
1201 | { | ||
1202 | //Public Flag | ||
1203 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_TYPE_PUBLIC); | ||
1204 | } | ||
1205 | else | ||
1206 | { | ||
1207 | //Other Flag | ||
1208 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_TYPE_OWNED_BY_OTHER); | ||
1209 | } | ||
1093 | 1210 | ||
1094 | ILandObject westParcel = null; | 1211 | //Now for border control |
1095 | ILandObject southParcel = null; | ||
1096 | if (x > 0) | ||
1097 | { | ||
1098 | westParcel = GetLandObject((x - 1) * 4, y * 4); | ||
1099 | } | ||
1100 | if (y > 0) | ||
1101 | { | ||
1102 | southParcel = GetLandObject(x * 4, (y - 1) * 4); | ||
1103 | } | ||
1104 | 1212 | ||
1105 | if (x == 0) | 1213 | ILandObject westParcel = null; |
1106 | { | 1214 | ILandObject southParcel = null; |
1107 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_FLAG_PROPERTY_BORDER_WEST); | 1215 | if (x > 0) |
1108 | } | 1216 | { |
1109 | else if (westParcel != null && westParcel != currentParcelBlock) | 1217 | westParcel = GetLandObject((x - 1) * landUnit, y * landUnit); |
1110 | { | 1218 | } |
1111 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_FLAG_PROPERTY_BORDER_WEST); | 1219 | if (y > 0) |
1112 | } | 1220 | { |
1221 | southParcel = GetLandObject(x * landUnit, (y - 1) * landUnit); | ||
1222 | } | ||
1113 | 1223 | ||
1114 | if (y == 0) | 1224 | if (x == 0) |
1115 | { | 1225 | { |
1116 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_FLAG_PROPERTY_BORDER_SOUTH); | 1226 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_FLAG_PROPERTY_BORDER_WEST); |
1117 | } | 1227 | } |
1118 | else if (southParcel != null && southParcel != currentParcelBlock) | 1228 | else if (westParcel != null && westParcel != currentParcelBlock) |
1119 | { | 1229 | { |
1120 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_FLAG_PROPERTY_BORDER_SOUTH); | 1230 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_FLAG_PROPERTY_BORDER_WEST); |
1121 | } | 1231 | } |
1122 | 1232 | ||
1123 | byteArray[byteArrayCount] = tempByte; | 1233 | if (y == 0) |
1124 | byteArrayCount++; | 1234 | { |
1125 | if (byteArrayCount >= LAND_BLOCKS_PER_PACKET) | 1235 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_FLAG_PROPERTY_BORDER_SOUTH); |
1126 | { | 1236 | } |
1127 | remote_client.SendLandParcelOverlay(byteArray, sequenceID); | 1237 | else if (southParcel != null && southParcel != currentParcelBlock) |
1128 | byteArrayCount = 0; | 1238 | { |
1129 | sequenceID++; | 1239 | tempByte = Convert.ToByte(tempByte | LandChannel.LAND_FLAG_PROPERTY_BORDER_SOUTH); |
1130 | byteArray = new byte[LAND_BLOCKS_PER_PACKET]; | ||
1131 | } | ||
1132 | } | ||
1133 | } | 1240 | } |
1241 | |||
1134 | } | 1242 | } |
1243 | |||
1244 | return tempByte; | ||
1135 | } | 1245 | } |
1136 | 1246 | ||
1137 | public void ClientOnParcelPropertiesRequest(int start_x, int start_y, int end_x, int end_y, int sequence_id, | 1247 | public void ClientOnParcelPropertiesRequest(int start_x, int start_y, int end_x, int end_y, int sequence_id, |
@@ -1679,7 +1789,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
1679 | { | 1789 | { |
1680 | // most likely still cached from building the extLandData entry | 1790 | // most likely still cached from building the extLandData entry |
1681 | uint x = 0, y = 0; | 1791 | uint x = 0, y = 0; |
1682 | Utils.LongToUInts(data.RegionHandle, out x, out y); | 1792 | Util.RegionHandleToWorldLoc(data.RegionHandle, out x, out y); |
1683 | info = m_scene.GridService.GetRegionByPosition(m_scene.RegionInfo.ScopeID, (int)x, (int)y); | 1793 | info = m_scene.GridService.GetRegionByPosition(m_scene.RegionInfo.ScopeID, (int)x, (int)y); |
1684 | } | 1794 | } |
1685 | // we need to transfer the fake parcelID, not the one in landData, so the viewer can match it to the landmark. | 1795 | // we need to transfer the fake parcelID, not the one in landData, so the viewer can match it to the landmark. |
@@ -2007,4 +2117,4 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
2007 | cdl.AddToStringBuilder(report); | 2117 | cdl.AddToStringBuilder(report); |
2008 | } | 2118 | } |
2009 | } | 2119 | } |
2010 | } \ No newline at end of file | 2120 | } |
diff --git a/OpenSim/Region/CoreModules/World/Land/LandObject.cs b/OpenSim/Region/CoreModules/World/Land/LandObject.cs index e54c849..f8f4986 100644 --- a/OpenSim/Region/CoreModules/World/Land/LandObject.cs +++ b/OpenSim/Region/CoreModules/World/Land/LandObject.cs | |||
@@ -45,10 +45,10 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
45 | #region Member Variables | 45 | #region Member Variables |
46 | 46 | ||
47 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 47 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
48 | #pragma warning disable 0429 | 48 | private static readonly string LogHeader = "[LAND OBJECT]"; |
49 | private const int landArrayMax = ((int)((int)Constants.RegionSize / 4) >= 64) ? (int)((int)Constants.RegionSize / 4) : 64; | 49 | |
50 | #pragma warning restore 0429 | 50 | private bool[,] m_landBitmap; |
51 | private bool[,] m_landBitmap = new bool[landArrayMax,landArrayMax]; | 51 | private readonly int landUnit = 4; |
52 | 52 | ||
53 | private int m_lastSeqId = 0; | 53 | private int m_lastSeqId = 0; |
54 | 54 | ||
@@ -93,15 +93,17 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
93 | { | 93 | { |
94 | get | 94 | get |
95 | { | 95 | { |
96 | for (int y = 0; y < landArrayMax; y++) | 96 | for (int y = 0; y < LandBitmap.GetLength(1); y++) |
97 | { | 97 | { |
98 | for (int x = 0; x < landArrayMax; x++) | 98 | for (int x = 0; x < LandBitmap.GetLength(0); x++) |
99 | { | 99 | { |
100 | if (LandBitmap[x, y]) | 100 | if (LandBitmap[x, y]) |
101 | return new Vector3(x * 4, y * 4, 0); | 101 | return new Vector3(x * landUnit, y * landUnit, 0); |
102 | } | 102 | } |
103 | } | 103 | } |
104 | 104 | ||
105 | m_log.ErrorFormat("{0} StartPoint. No start point found. bitmapSize=<{1},{2}>", | ||
106 | LogHeader, LandBitmap.GetLength(0), LandBitmap.GetLength(1)); | ||
105 | return new Vector3(-1, -1, -1); | 107 | return new Vector3(-1, -1, -1); |
106 | } | 108 | } |
107 | } | 109 | } |
@@ -110,17 +112,19 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
110 | { | 112 | { |
111 | get | 113 | get |
112 | { | 114 | { |
113 | for (int y = landArrayMax - 1; y >= 0; y--) | 115 | for (int y = LandBitmap.GetLength(1) - 1; y >= 0; y--) |
114 | { | 116 | { |
115 | for (int x = landArrayMax - 1; x >= 0; x--) | 117 | for (int x = LandBitmap.GetLength(0) - 1; x >= 0; x--) |
116 | { | 118 | { |
117 | if (LandBitmap[x, y]) | 119 | if (LandBitmap[x, y]) |
118 | { | 120 | { |
119 | return new Vector3(x * 4 + 4, y * 4 + 4, 0); | 121 | return new Vector3(x * landUnit + landUnit, y * landUnit + landUnit, 0); |
120 | } | 122 | } |
121 | } | 123 | } |
122 | } | 124 | } |
123 | 125 | ||
126 | m_log.ErrorFormat("{0} EndPoint. No end point found. bitmapSize=<{1},{2}>", | ||
127 | LogHeader, LandBitmap.GetLength(0), LandBitmap.GetLength(1)); | ||
124 | return new Vector3(-1, -1, -1); | 128 | return new Vector3(-1, -1, -1); |
125 | } | 129 | } |
126 | } | 130 | } |
@@ -130,6 +134,8 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
130 | public LandObject(UUID owner_id, bool is_group_owned, Scene scene) | 134 | public LandObject(UUID owner_id, bool is_group_owned, Scene scene) |
131 | { | 135 | { |
132 | m_scene = scene; | 136 | m_scene = scene; |
137 | m_landBitmap = new bool[m_scene.RegionInfo.RegionSizeX / landUnit, m_scene.RegionInfo.RegionSizeY / landUnit]; | ||
138 | |||
133 | LandData.OwnerID = owner_id; | 139 | LandData.OwnerID = owner_id; |
134 | if (is_group_owned) | 140 | if (is_group_owned) |
135 | LandData.GroupID = owner_id; | 141 | LandData.GroupID = owner_id; |
@@ -152,9 +158,9 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
152 | /// <returns>Returns true if the piece of land contains the specified point</returns> | 158 | /// <returns>Returns true if the piece of land contains the specified point</returns> |
153 | public bool ContainsPoint(int x, int y) | 159 | public bool ContainsPoint(int x, int y) |
154 | { | 160 | { |
155 | if (x >= 0 && y >= 0 && x < Constants.RegionSize && y < Constants.RegionSize) | 161 | if (x >= 0 && y >= 0 && x < m_scene.RegionInfo.RegionSizeX && y < m_scene.RegionInfo.RegionSizeY) |
156 | { | 162 | { |
157 | return (LandBitmap[x / 4, y / 4] == true); | 163 | return (LandBitmap[x / landUnit, y / landUnit] == true); |
158 | } | 164 | } |
159 | else | 165 | else |
160 | { | 166 | { |
@@ -194,7 +200,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
194 | else | 200 | else |
195 | { | 201 | { |
196 | // Normal Calculations | 202 | // Normal Calculations |
197 | int parcelMax = (int)(((float)LandData.Area / 65536.0f) | 203 | int parcelMax = (int)(((float)LandData.Area / (m_scene.RegionInfo.RegionSizeX * m_scene.RegionInfo.RegionSizeY)) |
198 | * (float)m_scene.RegionInfo.ObjectCapacity | 204 | * (float)m_scene.RegionInfo.ObjectCapacity |
199 | * (float)m_scene.RegionInfo.RegionSettings.ObjectBonus); | 205 | * (float)m_scene.RegionInfo.RegionSettings.ObjectBonus); |
200 | // TODO: The calculation of ObjectBonus should be refactored. It does still not work in the same manner as SL! | 206 | // TODO: The calculation of ObjectBonus should be refactored. It does still not work in the same manner as SL! |
@@ -211,7 +217,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
211 | else | 217 | else |
212 | { | 218 | { |
213 | //Normal Calculations | 219 | //Normal Calculations |
214 | int simMax = (int)(((float)LandData.SimwideArea / 65536.0f) | 220 | int simMax = (int)(((float)LandData.SimwideArea / (m_scene.RegionInfo.RegionSizeX * m_scene.RegionInfo.RegionSizeY)) |
215 | * (float)m_scene.RegionInfo.ObjectCapacity); | 221 | * (float)m_scene.RegionInfo.ObjectCapacity); |
216 | return simMax; | 222 | return simMax; |
217 | } | 223 | } |
@@ -224,7 +230,12 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
224 | public void SendLandProperties(int sequence_id, bool snap_selection, int request_result, IClientAPI remote_client) | 230 | public void SendLandProperties(int sequence_id, bool snap_selection, int request_result, IClientAPI remote_client) |
225 | { | 231 | { |
226 | IEstateModule estateModule = m_scene.RequestModuleInterface<IEstateModule>(); | 232 | IEstateModule estateModule = m_scene.RequestModuleInterface<IEstateModule>(); |
227 | uint regionFlags = 336723974 & ~((uint)(RegionFlags.AllowLandmark | RegionFlags.AllowSetHome)); | 233 | // uint regionFlags = 336723974 & ~((uint)(RegionFlags.AllowLandmark | RegionFlags.AllowSetHome)); |
234 | uint regionFlags = (uint)(RegionFlags.PublicAllowed | ||
235 | | RegionFlags.AllowDirectTeleport | ||
236 | | RegionFlags.AllowParcelChanges | ||
237 | | RegionFlags.AllowVoice ); | ||
238 | |||
228 | if (estateModule != null) | 239 | if (estateModule != null) |
229 | regionFlags = estateModule.GetRegionFlags(); | 240 | regionFlags = estateModule.GetRegionFlags(); |
230 | 241 | ||
@@ -559,8 +570,8 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
559 | try | 570 | try |
560 | { | 571 | { |
561 | over = | 572 | over = |
562 | m_scene.LandChannel.GetLandObject(Util.Clamp<int>((int)Math.Round(avatar.AbsolutePosition.X), 0, ((int)Constants.RegionSize - 1)), | 573 | m_scene.LandChannel.GetLandObject(Util.Clamp<int>((int)Math.Round(avatar.AbsolutePosition.X), 0, ((int)m_scene.RegionInfo.RegionSizeX - 1)), |
563 | Util.Clamp<int>((int)Math.Round(avatar.AbsolutePosition.Y), 0, ((int)Constants.RegionSize - 1))); | 574 | Util.Clamp<int>((int)Math.Round(avatar.AbsolutePosition.Y), 0, ((int)m_scene.RegionInfo.RegionSizeY - 1))); |
564 | } | 575 | } |
565 | catch (Exception) | 576 | catch (Exception) |
566 | { | 577 | { |
@@ -707,15 +718,15 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
707 | /// </summary> | 718 | /// </summary> |
708 | private void UpdateAABBAndAreaValues() | 719 | private void UpdateAABBAndAreaValues() |
709 | { | 720 | { |
710 | int min_x = 64; | 721 | int min_x = 10000; |
711 | int min_y = 64; | 722 | int min_y = 10000; |
712 | int max_x = 0; | 723 | int max_x = 0; |
713 | int max_y = 0; | 724 | int max_y = 0; |
714 | int tempArea = 0; | 725 | int tempArea = 0; |
715 | int x, y; | 726 | int x, y; |
716 | for (x = 0; x < 64; x++) | 727 | for (x = 0; x < LandBitmap.GetLength(0); x++) |
717 | { | 728 | { |
718 | for (y = 0; y < 64; y++) | 729 | for (y = 0; y < LandBitmap.GetLength(1); y++) |
719 | { | 730 | { |
720 | if (LandBitmap[x, y] == true) | 731 | if (LandBitmap[x, y] == true) |
721 | { | 732 | { |
@@ -723,31 +734,31 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
723 | if (min_y > y) min_y = y; | 734 | if (min_y > y) min_y = y; |
724 | if (max_x < x) max_x = x; | 735 | if (max_x < x) max_x = x; |
725 | if (max_y < y) max_y = y; | 736 | if (max_y < y) max_y = y; |
726 | tempArea += 16; //16sqm peice of land | 737 | tempArea += landUnit * landUnit; //16sqm peice of land |
727 | } | 738 | } |
728 | } | 739 | } |
729 | } | 740 | } |
730 | int tx = min_x * 4; | 741 | int tx = min_x * landUnit; |
731 | if (tx > ((int)Constants.RegionSize - 1)) | 742 | if (tx > ((int)m_scene.RegionInfo.RegionSizeX - 1)) |
732 | tx = ((int)Constants.RegionSize - 1); | 743 | tx = ((int)m_scene.RegionInfo.RegionSizeX - 1); |
733 | int ty = min_y * 4; | 744 | int ty = min_y * landUnit; |
734 | if (ty > ((int)Constants.RegionSize - 1)) | 745 | if (ty > ((int)m_scene.RegionInfo.RegionSizeY - 1)) |
735 | ty = ((int)Constants.RegionSize - 1); | 746 | ty = ((int)m_scene.RegionInfo.RegionSizeY - 1); |
736 | 747 | ||
737 | LandData.AABBMin = | 748 | LandData.AABBMin = |
738 | new Vector3( | 749 | new Vector3( |
739 | (float)(min_x * 4), (float)(min_y * 4), m_scene != null ? (float)m_scene.Heightmap[tx, ty] : 0); | 750 | (float)(min_x * landUnit), (float)(min_y * landUnit), m_scene != null ? (float)m_scene.Heightmap[tx, ty] : 0); |
740 | 751 | ||
741 | tx = max_x * 4; | 752 | tx = max_x * landUnit; |
742 | if (tx > ((int)Constants.RegionSize - 1)) | 753 | if (tx > ((int)m_scene.RegionInfo.RegionSizeX - 1)) |
743 | tx = ((int)Constants.RegionSize - 1); | 754 | tx = ((int)m_scene.RegionInfo.RegionSizeX - 1); |
744 | ty = max_y * 4; | 755 | ty = max_y * landUnit; |
745 | if (ty > ((int)Constants.RegionSize - 1)) | 756 | if (ty > ((int)m_scene.RegionInfo.RegionSizeY - 1)) |
746 | ty = ((int)Constants.RegionSize - 1); | 757 | ty = ((int)m_scene.RegionInfo.RegionSizeY - 1); |
747 | 758 | ||
748 | LandData.AABBMax | 759 | LandData.AABBMax |
749 | = new Vector3( | 760 | = new Vector3( |
750 | (float)(max_x * 4), (float)(max_y * 4), m_scene != null ? (float)m_scene.Heightmap[tx, ty] : 0); | 761 | (float)(max_x * landUnit), (float)(max_y * landUnit), m_scene != null ? (float)m_scene.Heightmap[tx, ty] : 0); |
751 | 762 | ||
752 | LandData.Area = tempArea; | 763 | LandData.Area = tempArea; |
753 | } | 764 | } |
@@ -759,20 +770,12 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
759 | /// <summary> | 770 | /// <summary> |
760 | /// Sets the land's bitmap manually | 771 | /// Sets the land's bitmap manually |
761 | /// </summary> | 772 | /// </summary> |
762 | /// <param name="bitmap">64x64 block representing where this land is on a map</param> | 773 | /// <param name="bitmap">block representing where this land is on a map mapped in a 4x4 meter grid</param> |
763 | public void SetLandBitmap(bool[,] bitmap) | 774 | public void SetLandBitmap(bool[,] bitmap) |
764 | { | 775 | { |
765 | if (bitmap.GetLength(0) != 64 || bitmap.GetLength(1) != 64 || bitmap.Rank != 2) | 776 | LandBitmap = bitmap; |
766 | { | 777 | // m_log.DebugFormat("{0} SetLandBitmap. BitmapSize=<{1},{2}>", LogHeader, LandBitmap.GetLength(0), LandBitmap.GetLength(1)); |
767 | //Throw an exception - The bitmap is not 64x64 | 778 | ForceUpdateLandInfo(); |
768 | //throw new Exception("Error: Invalid Parcel Bitmap"); | ||
769 | } | ||
770 | else | ||
771 | { | ||
772 | //Valid: Lets set it | ||
773 | LandBitmap = bitmap; | ||
774 | ForceUpdateLandInfo(); | ||
775 | } | ||
776 | } | 779 | } |
777 | 780 | ||
778 | /// <summary> | 781 | /// <summary> |
@@ -786,15 +789,19 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
786 | 789 | ||
787 | public bool[,] BasicFullRegionLandBitmap() | 790 | public bool[,] BasicFullRegionLandBitmap() |
788 | { | 791 | { |
789 | return GetSquareLandBitmap(0, 0, (int) Constants.RegionSize, (int) Constants.RegionSize); | 792 | return GetSquareLandBitmap(0, 0, (int)m_scene.RegionInfo.RegionSizeX, (int) m_scene.RegionInfo.RegionSizeY); |
790 | } | 793 | } |
791 | 794 | ||
792 | public bool[,] GetSquareLandBitmap(int start_x, int start_y, int end_x, int end_y) | 795 | public bool[,] GetSquareLandBitmap(int start_x, int start_y, int end_x, int end_y) |
793 | { | 796 | { |
794 | bool[,] tempBitmap = new bool[64,64]; | 797 | // Empty bitmap for the whole region |
798 | bool[,] tempBitmap = new bool[m_scene.RegionInfo.RegionSizeX / landUnit, m_scene.RegionInfo.RegionSizeY / landUnit]; | ||
795 | tempBitmap.Initialize(); | 799 | tempBitmap.Initialize(); |
796 | 800 | ||
801 | // Fill the bitmap square area specified by state and end | ||
797 | tempBitmap = ModifyLandBitmapSquare(tempBitmap, start_x, start_y, end_x, end_y, true); | 802 | tempBitmap = ModifyLandBitmapSquare(tempBitmap, start_x, start_y, end_x, end_y, true); |
803 | // m_log.DebugFormat("{0} GetSquareLandBitmap. tempBitmapSize=<{1},{2}>", | ||
804 | // LogHeader, tempBitmap.GetLength(0), tempBitmap.GetLength(1)); | ||
798 | return tempBitmap; | 805 | return tempBitmap; |
799 | } | 806 | } |
800 | 807 | ||
@@ -811,24 +818,20 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
811 | public bool[,] ModifyLandBitmapSquare(bool[,] land_bitmap, int start_x, int start_y, int end_x, int end_y, | 818 | public bool[,] ModifyLandBitmapSquare(bool[,] land_bitmap, int start_x, int start_y, int end_x, int end_y, |
812 | bool set_value) | 819 | bool set_value) |
813 | { | 820 | { |
814 | if (land_bitmap.GetLength(0) != 64 || land_bitmap.GetLength(1) != 64 || land_bitmap.Rank != 2) | ||
815 | { | ||
816 | //Throw an exception - The bitmap is not 64x64 | ||
817 | //throw new Exception("Error: Invalid Parcel Bitmap in modifyLandBitmapSquare()"); | ||
818 | } | ||
819 | |||
820 | int x, y; | 821 | int x, y; |
821 | for (y = 0; y < 64; y++) | 822 | for (y = 0; y < land_bitmap.GetLength(1); y++) |
822 | { | 823 | { |
823 | for (x = 0; x < 64; x++) | 824 | for (x = 0; x < land_bitmap.GetLength(0); x++) |
824 | { | 825 | { |
825 | if (x >= start_x / 4 && x < end_x / 4 | 826 | if (x >= start_x / landUnit && x < end_x / landUnit |
826 | && y >= start_y / 4 && y < end_y / 4) | 827 | && y >= start_y / landUnit && y < end_y / landUnit) |
827 | { | 828 | { |
828 | land_bitmap[x, y] = set_value; | 829 | land_bitmap[x, y] = set_value; |
829 | } | 830 | } |
830 | } | 831 | } |
831 | } | 832 | } |
833 | // m_log.DebugFormat("{0} ModifyLandBitmapSquare. startXY=<{1},{2}>, endXY=<{3},{4}>, val={5}, landBitmapSize=<{6},{7}>", | ||
834 | // LogHeader, start_x, start_y, end_x, end_y, set_value, land_bitmap.GetLength(0), land_bitmap.GetLength(1)); | ||
832 | return land_bitmap; | 835 | return land_bitmap; |
833 | } | 836 | } |
834 | 837 | ||
@@ -840,21 +843,21 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
840 | /// <returns></returns> | 843 | /// <returns></returns> |
841 | public bool[,] MergeLandBitmaps(bool[,] bitmap_base, bool[,] bitmap_add) | 844 | public bool[,] MergeLandBitmaps(bool[,] bitmap_base, bool[,] bitmap_add) |
842 | { | 845 | { |
843 | if (bitmap_base.GetLength(0) != 64 || bitmap_base.GetLength(1) != 64 || bitmap_base.Rank != 2) | 846 | if (bitmap_base.GetLength(0) != bitmap_add.GetLength(0) |
847 | || bitmap_base.GetLength(1) != bitmap_add.GetLength(1) | ||
848 | || bitmap_add.Rank != 2 | ||
849 | || bitmap_base.Rank != 2) | ||
844 | { | 850 | { |
845 | //Throw an exception - The bitmap is not 64x64 | 851 | throw new Exception( |
846 | throw new Exception("Error: Invalid Parcel Bitmap - Bitmap_base in mergeLandBitmaps"); | 852 | String.Format("{0} MergeLandBitmaps. merging maps not same size. baseSizeXY=<{1},{2}>, addSizeXY=<{3},{4}>", |
847 | } | 853 | LogHeader, bitmap_base.GetLength(0), bitmap_base.GetLength(1), bitmap_add.GetLength(0), bitmap_add.GetLength(1)) |
848 | if (bitmap_add.GetLength(0) != 64 || bitmap_add.GetLength(1) != 64 || bitmap_add.Rank != 2) | 854 | ); |
849 | { | ||
850 | //Throw an exception - The bitmap is not 64x64 | ||
851 | throw new Exception("Error: Invalid Parcel Bitmap - Bitmap_add in mergeLandBitmaps"); | ||
852 | } | 855 | } |
853 | 856 | ||
854 | int x, y; | 857 | int x, y; |
855 | for (y = 0; y < 64; y++) | 858 | for (y = 0; y < bitmap_base.GetLength(1); y++) |
856 | { | 859 | { |
857 | for (x = 0; x < 64; x++) | 860 | for (x = 0; x < bitmap_add.GetLength(0); x++) |
858 | { | 861 | { |
859 | if (bitmap_add[x, y]) | 862 | if (bitmap_add[x, y]) |
860 | { | 863 | { |
@@ -871,13 +874,13 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
871 | /// <returns></returns> | 874 | /// <returns></returns> |
872 | private byte[] ConvertLandBitmapToBytes() | 875 | private byte[] ConvertLandBitmapToBytes() |
873 | { | 876 | { |
874 | byte[] tempConvertArr = new byte[512]; | 877 | byte[] tempConvertArr = new byte[LandBitmap.GetLength(0) * LandBitmap.GetLength(1) / 8]; |
875 | byte tempByte = 0; | 878 | byte tempByte = 0; |
876 | int x, y, i, byteNum = 0; | 879 | int byteNum = 0; |
877 | i = 0; | 880 | int i = 0; |
878 | for (y = 0; y < 64; y++) | 881 | for (int y = 0; y < LandBitmap.GetLength(1); y++) |
879 | { | 882 | { |
880 | for (x = 0; x < 64; x++) | 883 | for (int x = 0; x < LandBitmap.GetLength(0); x++) |
881 | { | 884 | { |
882 | tempByte = Convert.ToByte(tempByte | Convert.ToByte(LandBitmap[x, y]) << (i++ % 8)); | 885 | tempByte = Convert.ToByte(tempByte | Convert.ToByte(LandBitmap[x, y]) << (i++ % 8)); |
883 | if (i % 8 == 0) | 886 | if (i % 8 == 0) |
@@ -889,30 +892,52 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
889 | } | 892 | } |
890 | } | 893 | } |
891 | } | 894 | } |
895 | // m_log.DebugFormat("{0} ConvertLandBitmapToBytes. BitmapSize=<{1},{2}>", | ||
896 | // LogHeader, LandBitmap.GetLength(0), LandBitmap.GetLength(1)); | ||
892 | return tempConvertArr; | 897 | return tempConvertArr; |
893 | } | 898 | } |
894 | 899 | ||
895 | private bool[,] ConvertBytesToLandBitmap() | 900 | private bool[,] ConvertBytesToLandBitmap() |
896 | { | 901 | { |
897 | bool[,] tempConvertMap = new bool[landArrayMax, landArrayMax]; | 902 | bool[,] tempConvertMap = new bool[m_scene.RegionInfo.RegionSizeX / landUnit, m_scene.RegionInfo.RegionSizeY / landUnit]; |
898 | tempConvertMap.Initialize(); | 903 | tempConvertMap.Initialize(); |
899 | byte tempByte = 0; | 904 | byte tempByte = 0; |
900 | int x = 0, y = 0, i = 0, bitNum = 0; | 905 | // Math.Min overcomes an old bug that might have made it into the database. Only use the bytes that fit into convertMap. |
901 | for (i = 0; i < 512; i++) | 906 | int bitmapLen = Math.Min(LandData.Bitmap.Length, tempConvertMap.GetLength(0) * tempConvertMap.GetLength(1) / 8); |
907 | int xLen = (int)(m_scene.RegionInfo.RegionSizeX / landUnit); | ||
908 | |||
909 | if (bitmapLen == 512) | ||
910 | { | ||
911 | // Legacy bitmap being passed in. Use the legacy region size | ||
912 | // and only set the lower area of the larger region. | ||
913 | xLen = (int)(Constants.RegionSize / landUnit); | ||
914 | } | ||
915 | // m_log.DebugFormat("{0} ConvertBytesToLandBitmap: bitmapLen={1}, xLen={2}", LogHeader, bitmapLen, xLen); | ||
916 | |||
917 | int x = 0, y = 0; | ||
918 | for (int i = 0; i < bitmapLen; i++) | ||
902 | { | 919 | { |
903 | tempByte = LandData.Bitmap[i]; | 920 | tempByte = LandData.Bitmap[i]; |
904 | for (bitNum = 0; bitNum < 8; bitNum++) | 921 | for (int bitNum = 0; bitNum < 8; bitNum++) |
905 | { | 922 | { |
906 | bool bit = Convert.ToBoolean(Convert.ToByte(tempByte >> bitNum) & (byte) 1); | 923 | bool bit = Convert.ToBoolean(Convert.ToByte(tempByte >> bitNum) & (byte) 1); |
907 | tempConvertMap[x, y] = bit; | 924 | try |
925 | { | ||
926 | tempConvertMap[x, y] = bit; | ||
927 | } | ||
928 | catch (Exception e) | ||
929 | { | ||
930 | m_log.DebugFormat("{0} ConvertBytestoLandBitmap: i={1}, x={2}, y={3}", LogHeader, i, x, y); | ||
931 | } | ||
908 | x++; | 932 | x++; |
909 | if (x > 63) | 933 | if (x >= xLen) |
910 | { | 934 | { |
911 | x = 0; | 935 | x = 0; |
912 | y++; | 936 | y++; |
913 | } | 937 | } |
914 | } | 938 | } |
915 | } | 939 | } |
940 | |||
916 | return tempConvertMap; | 941 | return tempConvertMap; |
917 | } | 942 | } |
918 | 943 | ||
diff --git a/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs b/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs index f8e93e1..45617fc 100644 --- a/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs +++ b/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs | |||
@@ -1571,10 +1571,10 @@ namespace OpenSim.Region.CoreModules.World.Permissions | |||
1571 | float X = position.X; | 1571 | float X = position.X; |
1572 | float Y = position.Y; | 1572 | float Y = position.Y; |
1573 | 1573 | ||
1574 | if (X > ((int)Constants.RegionSize - 1)) | 1574 | if (X > ((int)m_scene.RegionInfo.RegionSizeX - 1)) |
1575 | X = ((int)Constants.RegionSize - 1); | 1575 | X = ((int)m_scene.RegionInfo.RegionSizeX - 1); |
1576 | if (Y > ((int)Constants.RegionSize - 1)) | 1576 | if (Y > ((int)m_scene.RegionInfo.RegionSizeY - 1)) |
1577 | Y = ((int)Constants.RegionSize - 1); | 1577 | Y = ((int)m_scene.RegionInfo.RegionSizeY - 1); |
1578 | if (X < 0) | 1578 | if (X < 0) |
1579 | X = 0; | 1579 | X = 0; |
1580 | if (Y < 0) | 1580 | if (Y < 0) |
diff --git a/OpenSim/Region/CoreModules/World/Terrain/Effects/DefaultTerrainGenerator.cs b/OpenSim/Region/CoreModules/World/Terrain/Effects/DefaultTerrainGenerator.cs index 7186dd7..89087b1 100644 --- a/OpenSim/Region/CoreModules/World/Terrain/Effects/DefaultTerrainGenerator.cs +++ b/OpenSim/Region/CoreModules/World/Terrain/Effects/DefaultTerrainGenerator.cs | |||
@@ -42,7 +42,7 @@ namespace OpenSim.Region.CoreModules.World.Terrain.Effects | |||
42 | for (y = 0; y < map.Height; y++) | 42 | for (y = 0; y < map.Height; y++) |
43 | { | 43 | { |
44 | map[x, y] = TerrainUtil.PerlinNoise2D(x, y, 3, 0.25) * 10; | 44 | map[x, y] = TerrainUtil.PerlinNoise2D(x, y, 3, 0.25) * 10; |
45 | double spherFac = TerrainUtil.SphericalFactor(x, y, Constants.RegionSize / 2, Constants.RegionSize / 2, 50) * 0.01; | 45 | double spherFac = TerrainUtil.SphericalFactor(x, y, map.Width / 2, map.Height / 2, 50) * 0.01; |
46 | if (map[x, y] < spherFac) | 46 | if (map[x, y] < spherFac) |
47 | { | 47 | { |
48 | map[x, y] = spherFac; | 48 | map[x, y] = spherFac; |
diff --git a/OpenSim/Region/CoreModules/World/Terrain/FileLoaders/GenericSystemDrawing.cs b/OpenSim/Region/CoreModules/World/Terrain/FileLoaders/GenericSystemDrawing.cs index d78ade5..d5c77ec 100644 --- a/OpenSim/Region/CoreModules/World/Terrain/FileLoaders/GenericSystemDrawing.cs +++ b/OpenSim/Region/CoreModules/World/Terrain/FileLoaders/GenericSystemDrawing.cs | |||
@@ -67,7 +67,7 @@ namespace OpenSim.Region.CoreModules.World.Terrain.FileLoaders | |||
67 | { | 67 | { |
68 | using (Bitmap bitmap = new Bitmap(filename)) | 68 | using (Bitmap bitmap = new Bitmap(filename)) |
69 | { | 69 | { |
70 | ITerrainChannel retval = new TerrainChannel(true); | 70 | ITerrainChannel retval = new TerrainChannel(w, h); |
71 | 71 | ||
72 | for (int x = 0; x < retval.Width; x++) | 72 | for (int x = 0; x < retval.Width; x++) |
73 | { | 73 | { |
diff --git a/OpenSim/Region/CoreModules/World/Terrain/TerrainModule.cs b/OpenSim/Region/CoreModules/World/Terrain/TerrainModule.cs index fd30c46..9766bfe 100644 --- a/OpenSim/Region/CoreModules/World/Terrain/TerrainModule.cs +++ b/OpenSim/Region/CoreModules/World/Terrain/TerrainModule.cs | |||
@@ -30,10 +30,14 @@ using System.Collections.Generic; | |||
30 | using System.IO; | 30 | using System.IO; |
31 | using System.Reflection; | 31 | using System.Reflection; |
32 | using System.Net; | 32 | using System.Net; |
33 | |||
33 | using log4net; | 34 | using log4net; |
34 | using Nini.Config; | 35 | using Nini.Config; |
36 | |||
35 | using OpenMetaverse; | 37 | using OpenMetaverse; |
36 | using Mono.Addins; | 38 | using Mono.Addins; |
39 | |||
40 | using OpenSim.Data; | ||
37 | using OpenSim.Framework; | 41 | using OpenSim.Framework; |
38 | using OpenSim.Region.CoreModules.Framework.InterfaceCommander; | 42 | using OpenSim.Region.CoreModules.Framework.InterfaceCommander; |
39 | using OpenSim.Region.CoreModules.World.Terrain.FileLoaders; | 43 | using OpenSim.Region.CoreModules.World.Terrain.FileLoaders; |
@@ -70,6 +74,7 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
70 | #endregion | 74 | #endregion |
71 | 75 | ||
72 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 76 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
77 | private static readonly string LogHeader = "[TERRAIN MODULE]"; | ||
73 | 78 | ||
74 | private readonly Commander m_commander = new Commander("terrain"); | 79 | private readonly Commander m_commander = new Commander("terrain"); |
75 | 80 | ||
@@ -130,15 +135,15 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
130 | { | 135 | { |
131 | if (m_scene.Heightmap == null) | 136 | if (m_scene.Heightmap == null) |
132 | { | 137 | { |
133 | m_channel = new TerrainChannel(m_InitialTerrain); | 138 | m_channel = new TerrainChannel(m_InitialTerrain, (int)m_scene.RegionInfo.RegionSizeX, |
139 | (int)m_scene.RegionInfo.RegionSizeY, | ||
140 | (int)m_scene.RegionInfo.RegionSizeZ); | ||
134 | m_scene.Heightmap = m_channel; | 141 | m_scene.Heightmap = m_channel; |
135 | m_revert = new TerrainChannel(); | ||
136 | UpdateRevertMap(); | 142 | UpdateRevertMap(); |
137 | } | 143 | } |
138 | else | 144 | else |
139 | { | 145 | { |
140 | m_channel = m_scene.Heightmap; | 146 | m_channel = m_scene.Heightmap; |
141 | m_revert = new TerrainChannel(); | ||
142 | UpdateRevertMap(); | 147 | UpdateRevertMap(); |
143 | } | 148 | } |
144 | 149 | ||
@@ -230,11 +235,11 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
230 | try | 235 | try |
231 | { | 236 | { |
232 | ITerrainChannel channel = loader.Value.LoadFile(filename); | 237 | ITerrainChannel channel = loader.Value.LoadFile(filename); |
233 | if (channel.Width != Constants.RegionSize || channel.Height != Constants.RegionSize) | 238 | if (channel.Width != m_scene.RegionInfo.RegionSizeX || channel.Height != m_scene.RegionInfo.RegionSizeY) |
234 | { | 239 | { |
235 | // TerrainChannel expects a RegionSize x RegionSize map, currently | 240 | // TerrainChannel expects a RegionSize x RegionSize map, currently |
236 | throw new ArgumentException(String.Format("wrong size, use a file with size {0} x {1}", | 241 | throw new ArgumentException(String.Format("wrong size, use a file with size {0} x {1}", |
237 | Constants.RegionSize, Constants.RegionSize)); | 242 | m_scene.RegionInfo.RegionSizeX, m_scene.RegionInfo.RegionSizeY)); |
238 | } | 243 | } |
239 | m_log.DebugFormat("[TERRAIN]: Loaded terrain, wd/ht: {0}/{1}", channel.Width, channel.Height); | 244 | m_log.DebugFormat("[TERRAIN]: Loaded terrain, wd/ht: {0}/{1}", channel.Width, channel.Height); |
240 | m_scene.Heightmap = channel; | 245 | m_scene.Heightmap = channel; |
@@ -532,6 +537,7 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
532 | /// </summary> | 537 | /// </summary> |
533 | public void UpdateRevertMap() | 538 | public void UpdateRevertMap() |
534 | { | 539 | { |
540 | /* | ||
535 | int x; | 541 | int x; |
536 | for (x = 0; x < m_channel.Width; x++) | 542 | for (x = 0; x < m_channel.Width; x++) |
537 | { | 543 | { |
@@ -541,6 +547,8 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
541 | m_revert[x, y] = m_channel[x, y]; | 547 | m_revert[x, y] = m_channel[x, y]; |
542 | } | 548 | } |
543 | } | 549 | } |
550 | */ | ||
551 | m_revert = m_channel.MakeCopy(); | ||
544 | } | 552 | } |
545 | 553 | ||
546 | /// <summary> | 554 | /// <summary> |
@@ -567,8 +575,8 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
567 | { | 575 | { |
568 | ITerrainChannel channel = loader.Value.LoadFile(filename, offsetX, offsetY, | 576 | ITerrainChannel channel = loader.Value.LoadFile(filename, offsetX, offsetY, |
569 | fileWidth, fileHeight, | 577 | fileWidth, fileHeight, |
570 | (int) Constants.RegionSize, | 578 | (int) m_scene.RegionInfo.RegionSizeX, |
571 | (int) Constants.RegionSize); | 579 | (int) m_scene.RegionInfo.RegionSizeY); |
572 | m_scene.Heightmap = channel; | 580 | m_scene.Heightmap = channel; |
573 | m_channel = channel; | 581 | m_channel = channel; |
574 | UpdateRevertMap(); | 582 | UpdateRevertMap(); |
@@ -615,8 +623,8 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
615 | { | 623 | { |
616 | loader.Value.SaveFile(m_channel, filename, offsetX, offsetY, | 624 | loader.Value.SaveFile(m_channel, filename, offsetX, offsetY, |
617 | fileWidth, fileHeight, | 625 | fileWidth, fileHeight, |
618 | (int)Constants.RegionSize, | 626 | (int)m_scene.RegionInfo.RegionSizeX, |
619 | (int)Constants.RegionSize); | 627 | (int)m_scene.RegionInfo.RegionSizeY); |
620 | 628 | ||
621 | MainConsole.Instance.OutputFormat( | 629 | MainConsole.Instance.OutputFormat( |
622 | "Saved terrain from ({0},{1}) to ({2},{3}) from {4} to {5}", | 630 | "Saved terrain from ({0},{1}) to ({2},{3}) from {4} to {5}", |
@@ -705,7 +713,7 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
705 | private void CheckForTerrainUpdates(bool respectEstateSettings) | 713 | private void CheckForTerrainUpdates(bool respectEstateSettings) |
706 | { | 714 | { |
707 | bool shouldTaint = false; | 715 | bool shouldTaint = false; |
708 | float[] serialised = m_channel.GetFloatsSerialised(); | 716 | float[] terrHeights = m_channel.GetFloatsSerialised(); |
709 | int x; | 717 | int x; |
710 | for (x = 0; x < m_channel.Width; x += Constants.TerrainPatchSize) | 718 | for (x = 0; x < m_channel.Width; x += Constants.TerrainPatchSize) |
711 | { | 719 | { |
@@ -714,16 +722,17 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
714 | { | 722 | { |
715 | if (m_channel.Tainted(x, y)) | 723 | if (m_channel.Tainted(x, y)) |
716 | { | 724 | { |
717 | // if we should respect the estate settings then | 725 | // If we should respect the estate settings then |
718 | // fixup and height deltas that don't respect them | 726 | // fixup and height deltas that don't respect them. |
727 | // Note that LimitChannelChanges() modifies the TerrainChannel with the limited height values. | ||
719 | if (respectEstateSettings && LimitChannelChanges(x, y)) | 728 | if (respectEstateSettings && LimitChannelChanges(x, y)) |
720 | { | 729 | { |
721 | // this has been vetoed, so update | 730 | // Terrain heights were modified. Refetch the terrain info. |
722 | // what we are going to send to the client | 731 | terrHeights = m_channel.GetFloatsSerialised(); |
723 | serialised = m_channel.GetFloatsSerialised(); | ||
724 | } | 732 | } |
725 | 733 | ||
726 | SendToClients(serialised, x, y); | 734 | // m_log.DebugFormat("{0} Patch modified. Sending (x,y) = ({1},{2})", LogHeader, x, y); |
735 | SendToClients(terrHeights, x, y); | ||
727 | shouldTaint = true; | 736 | shouldTaint = true; |
728 | } | 737 | } |
729 | } | 738 | } |
@@ -792,13 +801,11 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
792 | /// <param name="serialised">A copy of the terrain as a 1D float array of size w*h</param> | 801 | /// <param name="serialised">A copy of the terrain as a 1D float array of size w*h</param> |
793 | /// <param name="x">The patch corner to send</param> | 802 | /// <param name="x">The patch corner to send</param> |
794 | /// <param name="y">The patch corner to send</param> | 803 | /// <param name="y">The patch corner to send</param> |
795 | private void SendToClients(float[] serialised, int x, int y) | 804 | private void SendToClients(float[] heightMap, int x, int y) |
796 | { | 805 | { |
797 | m_scene.ForEachClient( | 806 | m_scene.ForEachClient( |
798 | delegate(IClientAPI controller) | 807 | delegate(IClientAPI controller) |
799 | { controller.SendLayerData( | 808 | { controller.SendLayerData( x / Constants.TerrainPatchSize, y / Constants.TerrainPatchSize, heightMap); } |
800 | x / Constants.TerrainPatchSize, y / Constants.TerrainPatchSize, serialised); | ||
801 | } | ||
802 | ); | 809 | ); |
803 | } | 810 | } |
804 | 811 | ||
@@ -984,28 +991,28 @@ namespace OpenSim.Region.CoreModules.World.Terrain | |||
984 | 991 | ||
985 | if (direction.ToLower().StartsWith("y")) | 992 | if (direction.ToLower().StartsWith("y")) |
986 | { | 993 | { |
987 | for (int x = 0; x < Constants.RegionSize; x++) | 994 | for (int x = 0; x < m_channel.Width; x++) |
988 | { | 995 | { |
989 | for (int y = 0; y < Constants.RegionSize / 2; y++) | 996 | for (int y = 0; y < m_channel.Height / 2; y++) |
990 | { | 997 | { |
991 | double height = m_channel[x, y]; | 998 | double height = m_channel[x, y]; |
992 | double flippedHeight = m_channel[x, (int)Constants.RegionSize - 1 - y]; | 999 | double flippedHeight = m_channel[x, (int)m_channel.Height - 1 - y]; |
993 | m_channel[x, y] = flippedHeight; | 1000 | m_channel[x, y] = flippedHeight; |
994 | m_channel[x, (int)Constants.RegionSize - 1 - y] = height; | 1001 | m_channel[x, (int)m_channel.Height - 1 - y] = height; |
995 | 1002 | ||
996 | } | 1003 | } |
997 | } | 1004 | } |
998 | } | 1005 | } |
999 | else if (direction.ToLower().StartsWith("x")) | 1006 | else if (direction.ToLower().StartsWith("x")) |
1000 | { | 1007 | { |
1001 | for (int y = 0; y < Constants.RegionSize; y++) | 1008 | for (int y = 0; y < m_channel.Height; y++) |
1002 | { | 1009 | { |
1003 | for (int x = 0; x < Constants.RegionSize / 2; x++) | 1010 | for (int x = 0; x < m_channel.Width / 2; x++) |
1004 | { | 1011 | { |
1005 | double height = m_channel[x, y]; | 1012 | double height = m_channel[x, y]; |
1006 | double flippedHeight = m_channel[(int)Constants.RegionSize - 1 - x, y]; | 1013 | double flippedHeight = m_channel[(int)m_channel.Width - 1 - x, y]; |
1007 | m_channel[x, y] = flippedHeight; | 1014 | m_channel[x, y] = flippedHeight; |
1008 | m_channel[(int)Constants.RegionSize - 1 - x, y] = height; | 1015 | m_channel[(int)m_channel.Width - 1 - x, y] = height; |
1009 | 1016 | ||
1010 | } | 1017 | } |
1011 | } | 1018 | } |
diff --git a/OpenSim/Region/CoreModules/World/WorldMap/WorldMapModule.cs b/OpenSim/Region/CoreModules/World/WorldMap/WorldMapModule.cs index cdf1467..cd315b1 100644 --- a/OpenSim/Region/CoreModules/World/WorldMap/WorldMapModule.cs +++ b/OpenSim/Region/CoreModules/World/WorldMap/WorldMapModule.cs | |||
@@ -803,7 +803,7 @@ namespace OpenSim.Region.CoreModules.World.WorldMap | |||
803 | if (httpserver.Length == 0) | 803 | if (httpserver.Length == 0) |
804 | { | 804 | { |
805 | uint x = 0, y = 0; | 805 | uint x = 0, y = 0; |
806 | Utils.LongToUInts(regionhandle, out x, out y); | 806 | Util.RegionHandleToWorldLoc(regionhandle, out x, out y); |
807 | GridRegion mreg = m_scene.GridService.GetRegionByPosition(m_scene.RegionInfo.ScopeID, (int)x, (int)y); | 807 | GridRegion mreg = m_scene.GridService.GetRegionByPosition(m_scene.RegionInfo.ScopeID, (int)x, (int)y); |
808 | 808 | ||
809 | if (mreg != null) | 809 | if (mreg != null) |