diff options
Diffstat (limited to 'OpenSim/Region')
67 files changed, 1866 insertions, 1568 deletions
diff --git a/OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs b/OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs index db0c3b8..7eb829e 100644 --- a/OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs +++ b/OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs | |||
@@ -220,6 +220,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
220 | public event FriendActionDelegate OnApproveFriendRequest; | 220 | public event FriendActionDelegate OnApproveFriendRequest; |
221 | public event FriendActionDelegate OnDenyFriendRequest; | 221 | public event FriendActionDelegate OnDenyFriendRequest; |
222 | public event FriendshipTermination OnTerminateFriendship; | 222 | public event FriendshipTermination OnTerminateFriendship; |
223 | public event GrantUserFriendRights OnGrantUserRights; | ||
223 | public event MoneyTransferRequest OnMoneyTransferRequest; | 224 | public event MoneyTransferRequest OnMoneyTransferRequest; |
224 | public event EconomyDataRequest OnEconomyDataRequest; | 225 | public event EconomyDataRequest OnEconomyDataRequest; |
225 | public event MoneyBalanceRequest OnMoneyBalanceRequest; | 226 | public event MoneyBalanceRequest OnMoneyBalanceRequest; |
@@ -1251,7 +1252,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
1251 | /// <param name="fetchFolders">Do we need to send folder information?</param> | 1252 | /// <param name="fetchFolders">Do we need to send folder information?</param> |
1252 | /// <param name="fetchItems">Do we need to send item information?</param> | 1253 | /// <param name="fetchItems">Do we need to send item information?</param> |
1253 | public void SendInventoryFolderDetails(UUID ownerID, UUID folderID, List<InventoryItemBase> items, | 1254 | public void SendInventoryFolderDetails(UUID ownerID, UUID folderID, List<InventoryItemBase> items, |
1254 | List<InventoryFolderBase> folders, | 1255 | List<InventoryFolderBase> folders, int version, |
1255 | bool fetchFolders, bool fetchItems) | 1256 | bool fetchFolders, bool fetchItems) |
1256 | { | 1257 | { |
1257 | // An inventory descendents packet consists of a single agent section and an inventory details | 1258 | // An inventory descendents packet consists of a single agent section and an inventory details |
@@ -1264,174 +1265,107 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
1264 | // | 1265 | // |
1265 | // for one example of this kind of thing. In fact, the Linden servers appear to only send about | 1266 | // for one example of this kind of thing. In fact, the Linden servers appear to only send about |
1266 | // 6 to 7 items at a time, so let's stick with 6 | 1267 | // 6 to 7 items at a time, so let's stick with 6 |
1267 | int MAX_ITEMS_PER_PACKET = 6; | 1268 | int MAX_ITEMS_PER_PACKET = 5; |
1268 | 1269 | int MAX_FOLDERS_PER_PACKET = 6; | |
1269 | //Ckrinke This variable is not used, so comment out to remove the warning from the compiler (3-21-08) | ||
1270 | //Ckrinke uint FULL_MASK_PERMISSIONS = 2147483647; | ||
1271 | 1270 | ||
1271 | int totalItems = fetchItems ? items.Count : 0; | ||
1272 | int totalFolders = fetchFolders ? folders.Count : 0; | ||
1272 | int itemsSent = 0; | 1273 | int itemsSent = 0; |
1273 | if (fetchItems) | 1274 | int foldersSent = 0; |
1274 | { | 1275 | int foldersToSend = 0; |
1275 | InventoryDescendentsPacket descend = CreateInventoryDescendentsPacket(ownerID, folderID); | 1276 | int itemsToSend = 0; |
1276 | 1277 | ||
1277 | if (items.Count < MAX_ITEMS_PER_PACKET) | 1278 | InventoryDescendentsPacket currentPacket = null; |
1278 | { | ||
1279 | descend.ItemData = new InventoryDescendentsPacket.ItemDataBlock[items.Count]; | ||
1280 | } | ||
1281 | else | ||
1282 | { | ||
1283 | descend.ItemData = new InventoryDescendentsPacket.ItemDataBlock[MAX_ITEMS_PER_PACKET]; | ||
1284 | } | ||
1285 | |||
1286 | // Descendents must contain the *total* number of descendents (plus folders, whether we | ||
1287 | // fetch them or not), not the number of entries we send in this packet. For consistency, | ||
1288 | // I'll use it for folder-requests, too, although I wasn't able to get one with | ||
1289 | // FetchFolders = true. | ||
1290 | // TODO this should be checked with FetchFolders = true | ||
1291 | descend.AgentData.Descendents = items.Count + folders.Count; | ||
1292 | 1279 | ||
1293 | int count = 0; | 1280 | // Handle empty folders |
1294 | int i = 0; | 1281 | // |
1295 | foreach (InventoryItemBase item in items) | 1282 | if (totalItems == 0 && totalFolders == 0) |
1283 | currentPacket = CreateInventoryDescendentsPacket(ownerID, folderID, version, items.Count + folders.Count, 0, 0); | ||
1284 | |||
1285 | // To preserve SL compatibility, we will NOT combine folders and items in one packet | ||
1286 | // | ||
1287 | while(itemsSent < totalItems || foldersSent < totalFolders) | ||
1288 | { | ||
1289 | if (currentPacket == null) // Start a new packet | ||
1296 | { | 1290 | { |
1297 | descend.ItemData[i] = new InventoryDescendentsPacket.ItemDataBlock(); | 1291 | foldersToSend = totalFolders - foldersSent; |
1298 | descend.ItemData[i].ItemID = item.ID; | 1292 | if (foldersToSend > MAX_FOLDERS_PER_PACKET) |
1299 | descend.ItemData[i].AssetID = item.AssetID; | 1293 | foldersToSend = MAX_FOLDERS_PER_PACKET; |
1300 | descend.ItemData[i].CreatorID = item.CreatorIdAsUuid; | 1294 | |
1301 | descend.ItemData[i].BaseMask = item.BasePermissions; | 1295 | if (foldersToSend == 0) |
1302 | descend.ItemData[i].Description = Util.StringToBytes256(item.Description); | 1296 | { |
1303 | descend.ItemData[i].EveryoneMask = item.EveryOnePermissions; | 1297 | itemsToSend = totalItems - itemsSent; |
1304 | descend.ItemData[i].OwnerMask = item.CurrentPermissions; | 1298 | if (itemsToSend > MAX_ITEMS_PER_PACKET) |
1305 | descend.ItemData[i].FolderID = item.Folder; | 1299 | itemsToSend = MAX_ITEMS_PER_PACKET; |
1306 | descend.ItemData[i].InvType = (sbyte)item.InvType; | ||
1307 | descend.ItemData[i].Name = Util.StringToBytes256(item.Name); | ||
1308 | descend.ItemData[i].NextOwnerMask = item.NextPermissions; | ||
1309 | descend.ItemData[i].OwnerID = item.Owner; | ||
1310 | descend.ItemData[i].Type = (sbyte)item.AssetType; | ||
1311 | |||
1312 | descend.ItemData[i].GroupID = item.GroupID; | ||
1313 | descend.ItemData[i].GroupOwned = item.GroupOwned; | ||
1314 | descend.ItemData[i].GroupMask = item.GroupPermissions; | ||
1315 | descend.ItemData[i].CreationDate = item.CreationDate; | ||
1316 | descend.ItemData[i].SalePrice = item.SalePrice; | ||
1317 | descend.ItemData[i].SaleType = item.SaleType; | ||
1318 | descend.ItemData[i].Flags = item.Flags; | ||
1319 | |||
1320 | descend.ItemData[i].CRC = | ||
1321 | Helpers.InventoryCRC(descend.ItemData[i].CreationDate, descend.ItemData[i].SaleType, | ||
1322 | descend.ItemData[i].InvType, descend.ItemData[i].Type, | ||
1323 | descend.ItemData[i].AssetID, descend.ItemData[i].GroupID, | ||
1324 | descend.ItemData[i].SalePrice, | ||
1325 | descend.ItemData[i].OwnerID, descend.ItemData[i].CreatorID, | ||
1326 | descend.ItemData[i].ItemID, descend.ItemData[i].FolderID, | ||
1327 | descend.ItemData[i].EveryoneMask, | ||
1328 | descend.ItemData[i].Flags, descend.ItemData[i].OwnerMask, | ||
1329 | descend.ItemData[i].GroupMask, item.CurrentPermissions); | ||
1330 | |||
1331 | i++; | ||
1332 | count++; | ||
1333 | itemsSent++; | ||
1334 | if (i == MAX_ITEMS_PER_PACKET) | ||
1335 | { | ||
1336 | descend.Header.Zerocoded = true; | ||
1337 | AddNullFolderBlockToDecendentsPacket(ref descend); | ||
1338 | OutPacket(descend, ThrottleOutPacketType.Asset); | ||
1339 | |||
1340 | if ((items.Count - count) > 0) | ||
1341 | { | ||
1342 | descend = CreateInventoryDescendentsPacket(ownerID, folderID); | ||
1343 | if ((items.Count - count) < MAX_ITEMS_PER_PACKET) | ||
1344 | { | ||
1345 | descend.ItemData = new InventoryDescendentsPacket.ItemDataBlock[items.Count - count]; | ||
1346 | } | ||
1347 | else | ||
1348 | { | ||
1349 | descend.ItemData = new InventoryDescendentsPacket.ItemDataBlock[MAX_ITEMS_PER_PACKET]; | ||
1350 | } | ||
1351 | descend.AgentData.Descendents = items.Count + folders.Count; | ||
1352 | i = 0; | ||
1353 | } | ||
1354 | } | 1300 | } |
1355 | } | ||
1356 | 1301 | ||
1357 | if (0 < i && i < MAX_ITEMS_PER_PACKET) | 1302 | currentPacket = CreateInventoryDescendentsPacket(ownerID, folderID, version, items.Count + folders.Count, foldersToSend, itemsToSend); |
1358 | { | ||
1359 | AddNullFolderBlockToDecendentsPacket(ref descend); | ||
1360 | OutPacket(descend, ThrottleOutPacketType.Asset); | ||
1361 | } | 1303 | } |
1362 | } | ||
1363 | 1304 | ||
1364 | //send subfolders | 1305 | if (foldersToSend-- > 0) |
1365 | if (fetchFolders) | 1306 | currentPacket.FolderData[foldersSent % MAX_FOLDERS_PER_PACKET] = CreateFolderDataBlock(folders[foldersSent++]); |
1366 | { | 1307 | else if(itemsToSend-- > 0) |
1367 | InventoryDescendentsPacket descend = CreateInventoryDescendentsPacket(ownerID, folderID); | 1308 | currentPacket.ItemData[itemsSent % MAX_ITEMS_PER_PACKET] = CreateItemDataBlock(items[itemsSent++]); |
1368 | |||
1369 | if (folders.Count < MAX_ITEMS_PER_PACKET) | ||
1370 | { | ||
1371 | descend.FolderData = new InventoryDescendentsPacket.FolderDataBlock[folders.Count]; | ||
1372 | } | ||
1373 | else | 1309 | else |
1374 | { | 1310 | { |
1375 | descend.FolderData = new InventoryDescendentsPacket.FolderDataBlock[MAX_ITEMS_PER_PACKET]; | 1311 | OutPacket(currentPacket, ThrottleOutPacketType.Asset, false); |
1312 | currentPacket = null; | ||
1376 | } | 1313 | } |
1377 | 1314 | ||
1378 | // Not sure if this scenario ever actually occurs, but nonetheless we include the items | 1315 | } |
1379 | // count even if we're not sending item data for the same reasons as above. | ||
1380 | descend.AgentData.Descendents = items.Count + folders.Count; | ||
1381 | 1316 | ||
1382 | int i = 0; | 1317 | if (currentPacket != null) |
1383 | int count = 0; | 1318 | OutPacket(currentPacket, ThrottleOutPacketType.Asset, false); |
1384 | foreach (InventoryFolderBase folder in folders) | 1319 | } |
1385 | { | ||
1386 | descend.FolderData[i] = new InventoryDescendentsPacket.FolderDataBlock(); | ||
1387 | descend.FolderData[i].FolderID = folder.ID; | ||
1388 | descend.FolderData[i].Name = Util.StringToBytes256(folder.Name); | ||
1389 | descend.FolderData[i].ParentID = folder.ParentID; | ||
1390 | descend.FolderData[i].Type = (sbyte)folder.Type; | ||
1391 | 1320 | ||
1392 | i++; | 1321 | private InventoryDescendentsPacket.FolderDataBlock CreateFolderDataBlock(InventoryFolderBase folder) |
1393 | count++; | 1322 | { |
1394 | itemsSent++; | 1323 | InventoryDescendentsPacket.FolderDataBlock newBlock = new InventoryDescendentsPacket.FolderDataBlock(); |
1395 | if (i == MAX_ITEMS_PER_PACKET) | 1324 | newBlock.FolderID = folder.ID; |
1396 | { | 1325 | newBlock.Name = Util.StringToBytes256(folder.Name); |
1397 | AddNullItemBlockToDescendentsPacket(ref descend); | 1326 | newBlock.ParentID = folder.ParentID; |
1398 | OutPacket(descend, ThrottleOutPacketType.Asset); | 1327 | newBlock.Type = (sbyte)folder.Type; |
1399 | 1328 | ||
1400 | if ((folders.Count - count) > 0) | 1329 | return newBlock; |
1401 | { | 1330 | } |
1402 | descend = CreateInventoryDescendentsPacket(ownerID, folderID); | ||
1403 | if ((folders.Count - count) < MAX_ITEMS_PER_PACKET) | ||
1404 | { | ||
1405 | descend.FolderData = | ||
1406 | new InventoryDescendentsPacket.FolderDataBlock[folders.Count - count]; | ||
1407 | } | ||
1408 | else | ||
1409 | { | ||
1410 | descend.FolderData = | ||
1411 | new InventoryDescendentsPacket.FolderDataBlock[MAX_ITEMS_PER_PACKET]; | ||
1412 | } | ||
1413 | descend.AgentData.Descendents = items.Count + folders.Count; | ||
1414 | i = 0; | ||
1415 | } | ||
1416 | } | ||
1417 | } | ||
1418 | 1331 | ||
1419 | if (0 < i && i < MAX_ITEMS_PER_PACKET) | 1332 | private InventoryDescendentsPacket.ItemDataBlock CreateItemDataBlock(InventoryItemBase item) |
1420 | { | 1333 | { |
1421 | AddNullItemBlockToDescendentsPacket(ref descend); | 1334 | InventoryDescendentsPacket.ItemDataBlock newBlock = new InventoryDescendentsPacket.ItemDataBlock(); |
1422 | OutPacket(descend, ThrottleOutPacketType.Asset); | 1335 | newBlock.ItemID = item.ID; |
1423 | } | 1336 | newBlock.AssetID = item.AssetID; |
1424 | } | 1337 | newBlock.CreatorID = item.CreatorIdAsUuid; |
1338 | newBlock.BaseMask = item.BasePermissions; | ||
1339 | newBlock.Description = Util.StringToBytes256(item.Description); | ||
1340 | newBlock.EveryoneMask = item.EveryOnePermissions; | ||
1341 | newBlock.OwnerMask = item.CurrentPermissions; | ||
1342 | newBlock.FolderID = item.Folder; | ||
1343 | newBlock.InvType = (sbyte)item.InvType; | ||
1344 | newBlock.Name = Util.StringToBytes256(item.Name); | ||
1345 | newBlock.NextOwnerMask = item.NextPermissions; | ||
1346 | newBlock.OwnerID = item.Owner; | ||
1347 | newBlock.Type = (sbyte)item.AssetType; | ||
1425 | 1348 | ||
1426 | if (itemsSent == 0) | 1349 | newBlock.GroupID = item.GroupID; |
1427 | { | 1350 | newBlock.GroupOwned = item.GroupOwned; |
1428 | // no items found. | 1351 | newBlock.GroupMask = item.GroupPermissions; |
1429 | InventoryDescendentsPacket descend = CreateInventoryDescendentsPacket(ownerID, folderID); | 1352 | newBlock.CreationDate = item.CreationDate; |
1430 | descend.AgentData.Descendents = 0; | 1353 | newBlock.SalePrice = item.SalePrice; |
1431 | AddNullItemBlockToDescendentsPacket(ref descend); | 1354 | newBlock.SaleType = item.SaleType; |
1432 | AddNullFolderBlockToDecendentsPacket(ref descend); | 1355 | newBlock.Flags = item.Flags; |
1433 | OutPacket(descend, ThrottleOutPacketType.Asset); | 1356 | |
1434 | } | 1357 | newBlock.CRC = |
1358 | Helpers.InventoryCRC(newBlock.CreationDate, newBlock.SaleType, | ||
1359 | newBlock.InvType, newBlock.Type, | ||
1360 | newBlock.AssetID, newBlock.GroupID, | ||
1361 | newBlock.SalePrice, | ||
1362 | newBlock.OwnerID, newBlock.CreatorID, | ||
1363 | newBlock.ItemID, newBlock.FolderID, | ||
1364 | newBlock.EveryoneMask, | ||
1365 | newBlock.Flags, newBlock.OwnerMask, | ||
1366 | newBlock.GroupMask, newBlock.NextOwnerMask); | ||
1367 | |||
1368 | return newBlock; | ||
1435 | } | 1369 | } |
1436 | 1370 | ||
1437 | private void AddNullFolderBlockToDecendentsPacket(ref InventoryDescendentsPacket packet) | 1371 | private void AddNullFolderBlockToDecendentsPacket(ref InventoryDescendentsPacket packet) |
@@ -1473,14 +1407,25 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
1473 | // No need to add CRC | 1407 | // No need to add CRC |
1474 | } | 1408 | } |
1475 | 1409 | ||
1476 | private InventoryDescendentsPacket CreateInventoryDescendentsPacket(UUID ownerID, UUID folderID) | 1410 | private InventoryDescendentsPacket CreateInventoryDescendentsPacket(UUID ownerID, UUID folderID, int version, int descendents, int folders, int items) |
1477 | { | 1411 | { |
1478 | InventoryDescendentsPacket descend = (InventoryDescendentsPacket)PacketPool.Instance.GetPacket(PacketType.InventoryDescendents); | 1412 | InventoryDescendentsPacket descend = (InventoryDescendentsPacket)PacketPool.Instance.GetPacket(PacketType.InventoryDescendents); |
1479 | descend.Header.Zerocoded = true; | 1413 | descend.Header.Zerocoded = true; |
1480 | descend.AgentData.AgentID = AgentId; | 1414 | descend.AgentData.AgentID = AgentId; |
1481 | descend.AgentData.OwnerID = ownerID; | 1415 | descend.AgentData.OwnerID = ownerID; |
1482 | descend.AgentData.FolderID = folderID; | 1416 | descend.AgentData.FolderID = folderID; |
1483 | descend.AgentData.Version = 1; | 1417 | descend.AgentData.Version = version; |
1418 | descend.AgentData.Descendents = descendents; | ||
1419 | |||
1420 | if (folders > 0) | ||
1421 | descend.FolderData = new InventoryDescendentsPacket.FolderDataBlock[folders]; | ||
1422 | else | ||
1423 | AddNullFolderBlockToDecendentsPacket(ref descend); | ||
1424 | |||
1425 | if (items > 0) | ||
1426 | descend.ItemData = new InventoryDescendentsPacket.ItemDataBlock[items]; | ||
1427 | else | ||
1428 | AddNullItemBlockToDescendentsPacket(ref descend); | ||
1484 | 1429 | ||
1485 | return descend; | 1430 | return descend; |
1486 | } | 1431 | } |
@@ -3251,12 +3196,17 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
3251 | if (!IsActive) return; // We don't need to update inactive clients. | 3196 | if (!IsActive) return; // We don't need to update inactive clients. |
3252 | 3197 | ||
3253 | CoarseLocationUpdatePacket loc = (CoarseLocationUpdatePacket)PacketPool.Instance.GetPacket(PacketType.CoarseLocationUpdate); | 3198 | CoarseLocationUpdatePacket loc = (CoarseLocationUpdatePacket)PacketPool.Instance.GetPacket(PacketType.CoarseLocationUpdate); |
3254 | // TODO: don't create new blocks if recycling an old packet | 3199 | loc.Header.Reliable = false; |
3255 | int total = CoarseLocations.Count; | 3200 | |
3256 | CoarseLocationUpdatePacket.IndexBlock ib = | 3201 | // Each packet can only hold around 62 avatar positions and the client clears the mini-map each time |
3257 | new CoarseLocationUpdatePacket.IndexBlock(); | 3202 | // a CoarseLocationUpdate packet is received. Oh well. |
3203 | int total = Math.Min(CoarseLocations.Count, 60); | ||
3204 | |||
3205 | CoarseLocationUpdatePacket.IndexBlock ib = new CoarseLocationUpdatePacket.IndexBlock(); | ||
3206 | |||
3258 | loc.Location = new CoarseLocationUpdatePacket.LocationBlock[total]; | 3207 | loc.Location = new CoarseLocationUpdatePacket.LocationBlock[total]; |
3259 | loc.AgentData = new CoarseLocationUpdatePacket.AgentDataBlock[total]; | 3208 | loc.AgentData = new CoarseLocationUpdatePacket.AgentDataBlock[total]; |
3209 | |||
3260 | int selfindex = -1; | 3210 | int selfindex = -1; |
3261 | for (int i = 0; i < total; i++) | 3211 | for (int i = 0; i < total; i++) |
3262 | { | 3212 | { |
@@ -3266,18 +3216,17 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
3266 | lb.X = (byte)CoarseLocations[i].X; | 3216 | lb.X = (byte)CoarseLocations[i].X; |
3267 | lb.Y = (byte)CoarseLocations[i].Y; | 3217 | lb.Y = (byte)CoarseLocations[i].Y; |
3268 | 3218 | ||
3269 | lb.Z = CoarseLocations[i].Z > 1024 ? (byte)0 : (byte)(CoarseLocations[i].Z * 0.25); | 3219 | lb.Z = CoarseLocations[i].Z > 1024 ? (byte)0 : (byte)(CoarseLocations[i].Z * 0.25f); |
3270 | loc.Location[i] = lb; | 3220 | loc.Location[i] = lb; |
3271 | loc.AgentData[i] = new CoarseLocationUpdatePacket.AgentDataBlock(); | 3221 | loc.AgentData[i] = new CoarseLocationUpdatePacket.AgentDataBlock(); |
3272 | loc.AgentData[i].AgentID = users[i]; | 3222 | loc.AgentData[i].AgentID = users[i]; |
3273 | if (users[i] == AgentId) | 3223 | if (users[i] == AgentId) |
3274 | selfindex = i; | 3224 | selfindex = i; |
3275 | } | 3225 | } |
3226 | |||
3276 | ib.You = (short)selfindex; | 3227 | ib.You = (short)selfindex; |
3277 | ib.Prey = -1; | 3228 | ib.Prey = -1; |
3278 | loc.Index = ib; | 3229 | loc.Index = ib; |
3279 | loc.Header.Reliable = false; | ||
3280 | loc.Header.Zerocoded = true; | ||
3281 | 3230 | ||
3282 | OutPacket(loc, ThrottleOutPacketType.Task); | 3231 | OutPacket(loc, ThrottleOutPacketType.Task); |
3283 | } | 3232 | } |
@@ -4088,11 +4037,11 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
4088 | 4037 | ||
4089 | protected ImprovedTerseObjectUpdatePacket.ObjectDataBlock CreateImprovedTerseBlock(SendPrimitiveTerseData data) | 4038 | protected ImprovedTerseObjectUpdatePacket.ObjectDataBlock CreateImprovedTerseBlock(SendPrimitiveTerseData data) |
4090 | { | 4039 | { |
4091 | return CreateImprovedTerseBlock(false, data.LocalID, data.State, Vector4.Zero, data.Position, data.Velocity, | 4040 | return CreateImprovedTerseBlock(false, data.LocalID, data.AttachPoint, Vector4.Zero, data.Position, data.Velocity, |
4092 | data.Acceleration, data.Rotation, data.AngularVelocity, data.TextureEntry); | 4041 | data.Acceleration, data.Rotation, data.AngularVelocity, data.TextureEntry); |
4093 | } | 4042 | } |
4094 | 4043 | ||
4095 | protected ImprovedTerseObjectUpdatePacket.ObjectDataBlock CreateImprovedTerseBlock(bool avatar, uint localID, byte state, | 4044 | protected ImprovedTerseObjectUpdatePacket.ObjectDataBlock CreateImprovedTerseBlock(bool avatar, uint localID, int attachPoint, |
4096 | Vector4 collisionPlane, Vector3 position, Vector3 velocity, Vector3 acceleration, Quaternion rotation, | 4045 | Vector4 collisionPlane, Vector3 position, Vector3 velocity, Vector3 acceleration, Quaternion rotation, |
4097 | Vector3 angularVelocity, byte[] textureEntry) | 4046 | Vector3 angularVelocity, byte[] textureEntry) |
4098 | { | 4047 | { |
@@ -4104,7 +4053,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
4104 | pos += 4; | 4053 | pos += 4; |
4105 | 4054 | ||
4106 | // Avatar/CollisionPlane | 4055 | // Avatar/CollisionPlane |
4107 | data[pos++] = state; | 4056 | data[pos++] = (byte)((attachPoint % 16) * 16 + (attachPoint / 16)); ; |
4108 | if (avatar) | 4057 | if (avatar) |
4109 | { | 4058 | { |
4110 | data[pos++] = 1; | 4059 | data[pos++] = 1; |
@@ -4960,9 +4909,26 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
4960 | /// <param name="throttlePacketType">Throttling category for the packet</param> | 4909 | /// <param name="throttlePacketType">Throttling category for the packet</param> |
4961 | protected void OutPacket(Packet packet, ThrottleOutPacketType throttlePacketType) | 4910 | protected void OutPacket(Packet packet, ThrottleOutPacketType throttlePacketType) |
4962 | { | 4911 | { |
4912 | #region BinaryStats | ||
4913 | LLUDPServer.LogPacketHeader(false, m_circuitCode, 0, packet.Type, (ushort)packet.Length); | ||
4914 | #endregion BinaryStats | ||
4915 | |||
4963 | m_udpServer.SendPacket(m_udpClient, packet, throttlePacketType, true); | 4916 | m_udpServer.SendPacket(m_udpClient, packet, throttlePacketType, true); |
4964 | } | 4917 | } |
4965 | 4918 | ||
4919 | /// <summary> | ||
4920 | /// This is the starting point for sending a simulator packet out to the client | ||
4921 | /// </summary> | ||
4922 | /// <param name="packet">Packet to send</param> | ||
4923 | /// <param name="throttlePacketType">Throttling category for the packet</param> | ||
4924 | /// <param name="doAutomaticSplitting">True to automatically split oversized | ||
4925 | /// packets (the default), or false to disable splitting if the calling code | ||
4926 | /// handles splitting manually</param> | ||
4927 | protected void OutPacket(Packet packet, ThrottleOutPacketType throttlePacketType, bool doAutomaticSplitting) | ||
4928 | { | ||
4929 | m_udpServer.SendPacket(m_udpClient, packet, throttlePacketType, doAutomaticSplitting); | ||
4930 | } | ||
4931 | |||
4966 | public bool AddMoney(int debit) | 4932 | public bool AddMoney(int debit) |
4967 | { | 4933 | { |
4968 | if (m_moneyBalance + debit >= 0) | 4934 | if (m_moneyBalance + debit >= 0) |
@@ -9762,7 +9728,26 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
9762 | Utils.BytesToString(avatarInterestUpdate.PropertiesData.SkillsText), | 9728 | Utils.BytesToString(avatarInterestUpdate.PropertiesData.SkillsText), |
9763 | Utils.BytesToString(avatarInterestUpdate.PropertiesData.LanguagesText)); | 9729 | Utils.BytesToString(avatarInterestUpdate.PropertiesData.LanguagesText)); |
9764 | break; | 9730 | break; |
9765 | 9731 | ||
9732 | case PacketType.GrantUserRights: | ||
9733 | GrantUserRightsPacket GrantUserRights = | ||
9734 | (GrantUserRightsPacket)Pack; | ||
9735 | #region Packet Session and User Check | ||
9736 | if (m_checkPackets) | ||
9737 | { | ||
9738 | if (GrantUserRights.AgentData.SessionID != SessionId || | ||
9739 | GrantUserRights.AgentData.AgentID != AgentId) | ||
9740 | break; | ||
9741 | } | ||
9742 | #endregion | ||
9743 | GrantUserFriendRights GrantUserRightsHandler = OnGrantUserRights; | ||
9744 | if (GrantUserRightsHandler != null) | ||
9745 | GrantUserRightsHandler(this, | ||
9746 | GrantUserRights.AgentData.AgentID, | ||
9747 | GrantUserRights.Rights[0].AgentRelated, | ||
9748 | GrantUserRights.Rights[0].RelatedRights); | ||
9749 | break; | ||
9750 | |||
9766 | case PacketType.PlacesQuery: | 9751 | case PacketType.PlacesQuery: |
9767 | PlacesQueryPacket placesQueryPacket = | 9752 | PlacesQueryPacket placesQueryPacket = |
9768 | (PlacesQueryPacket)Pack; | 9753 | (PlacesQueryPacket)Pack; |
diff --git a/OpenSim/Region/ClientStack/LindenUDP/LLFileTransfer.cs b/OpenSim/Region/ClientStack/LindenUDP/LLFileTransfer.cs index 697bbe6..adf171e 100644 --- a/OpenSim/Region/ClientStack/LindenUDP/LLFileTransfer.cs +++ b/OpenSim/Region/ClientStack/LindenUDP/LLFileTransfer.cs | |||
@@ -197,11 +197,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
197 | 197 | ||
198 | private void Initialise(UUID fileID, string fileName) | 198 | private void Initialise(UUID fileID, string fileName) |
199 | { | 199 | { |
200 | m_asset = new AssetBase(); | 200 | m_asset = new AssetBase(fileID, fileName, type); |
201 | m_asset.FullID = fileID; | ||
202 | m_asset.Type = type; | ||
203 | m_asset.Data = new byte[0]; | 201 | m_asset.Data = new byte[0]; |
204 | m_asset.Name = fileName; | ||
205 | m_asset.Description = "empty"; | 202 | m_asset.Description = "empty"; |
206 | m_asset.Local = true; | 203 | m_asset.Local = true; |
207 | m_asset.Temporary = true; | 204 | m_asset.Temporary = true; |
diff --git a/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs b/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs index 93946ae..c773c05 100644 --- a/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs +++ b/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs | |||
@@ -27,6 +27,7 @@ | |||
27 | 27 | ||
28 | using System; | 28 | using System; |
29 | using System.Collections.Generic; | 29 | using System.Collections.Generic; |
30 | using System.IO; | ||
30 | using System.Net; | 31 | using System.Net; |
31 | using System.Net.Sockets; | 32 | using System.Net.Sockets; |
32 | using System.Reflection; | 33 | using System.Reflection; |
@@ -204,6 +205,31 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
204 | TextureSendLimit = 20; | 205 | TextureSendLimit = 20; |
205 | } | 206 | } |
206 | 207 | ||
208 | #region BinaryStats | ||
209 | config = configSource.Configs["Statistics.Binary"]; | ||
210 | m_shouldCollectStats = false; | ||
211 | if (config != null) | ||
212 | { | ||
213 | if (config.Contains("enabled") && config.GetBoolean("enabled")) | ||
214 | { | ||
215 | if (config.Contains("collect_packet_headers")) | ||
216 | m_shouldCollectStats = config.GetBoolean("collect_packet_headers"); | ||
217 | if (config.Contains("packet_headers_period_seconds")) | ||
218 | { | ||
219 | binStatsMaxFilesize = TimeSpan.FromSeconds(config.GetInt("region_stats_period_seconds")); | ||
220 | } | ||
221 | if (config.Contains("stats_dir")) | ||
222 | { | ||
223 | binStatsDir = config.GetString("stats_dir"); | ||
224 | } | ||
225 | } | ||
226 | else | ||
227 | { | ||
228 | m_shouldCollectStats = false; | ||
229 | } | ||
230 | } | ||
231 | #endregion BinaryStats | ||
232 | |||
207 | m_throttle = new TokenBucket(null, sceneThrottleBps, sceneThrottleBps); | 233 | m_throttle = new TokenBucket(null, sceneThrottleBps, sceneThrottleBps); |
208 | m_throttleRates = new ThrottleRates(configSource); | 234 | m_throttleRates = new ThrottleRates(configSource); |
209 | } | 235 | } |
@@ -359,9 +385,12 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
359 | } | 385 | } |
360 | else | 386 | else |
361 | { | 387 | { |
362 | m_log.Error("[LLUDPSERVER]: Packet exceeded buffer size! This could be an indication of packet assembly not obeying the MTU. Type=" + | 388 | bufferSize = dataLength; |
363 | type + ", DataLength=" + dataLength + ", BufferLength=" + buffer.Data.Length + ". Dropping packet"); | 389 | buffer = new UDPPacketBuffer(udpClient.RemoteEndPoint, bufferSize); |
364 | return; | 390 | |
391 | // m_log.Error("[LLUDPSERVER]: Packet exceeded buffer size! This could be an indication of packet assembly not obeying the MTU. Type=" + | ||
392 | // type + ", DataLength=" + dataLength + ", BufferLength=" + buffer.Data.Length + ". Dropping packet"); | ||
393 | Buffer.BlockCopy(data, 0, buffer.Data, 0, dataLength); | ||
365 | } | 394 | } |
366 | } | 395 | } |
367 | 396 | ||
@@ -676,6 +705,10 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
676 | 705 | ||
677 | #endregion Incoming Packet Accounting | 706 | #endregion Incoming Packet Accounting |
678 | 707 | ||
708 | #region BinaryStats | ||
709 | LogPacketHeader(true, udpClient.CircuitCode, 0, packet.Type, (ushort)packet.Length); | ||
710 | #endregion BinaryStats | ||
711 | |||
679 | #region Ping Check Handling | 712 | #region Ping Check Handling |
680 | 713 | ||
681 | if (packet.Type == PacketType.StartPingCheck) | 714 | if (packet.Type == PacketType.StartPingCheck) |
@@ -697,6 +730,87 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
697 | packetInbox.Enqueue(new IncomingPacket(udpClient, packet)); | 730 | packetInbox.Enqueue(new IncomingPacket(udpClient, packet)); |
698 | } | 731 | } |
699 | 732 | ||
733 | #region BinaryStats | ||
734 | |||
735 | public class PacketLogger | ||
736 | { | ||
737 | public DateTime StartTime; | ||
738 | public string Path = null; | ||
739 | public System.IO.BinaryWriter Log = null; | ||
740 | } | ||
741 | |||
742 | public static PacketLogger PacketLog; | ||
743 | |||
744 | protected static bool m_shouldCollectStats = false; | ||
745 | // Number of seconds to log for | ||
746 | static TimeSpan binStatsMaxFilesize = TimeSpan.FromSeconds(300); | ||
747 | static object binStatsLogLock = new object(); | ||
748 | static string binStatsDir = ""; | ||
749 | |||
750 | public static void LogPacketHeader(bool incoming, uint circuit, byte flags, PacketType packetType, ushort size) | ||
751 | { | ||
752 | if (!m_shouldCollectStats) return; | ||
753 | |||
754 | // Binary logging format is TTTTTTTTCCCCFPPPSS, T=Time, C=Circuit, F=Flags, P=PacketType, S=size | ||
755 | |||
756 | // Put the incoming bit into the least significant bit of the flags byte | ||
757 | if (incoming) | ||
758 | flags |= 0x01; | ||
759 | else | ||
760 | flags &= 0xFE; | ||
761 | |||
762 | // Put the flags byte into the most significant bits of the type integer | ||
763 | uint type = (uint)packetType; | ||
764 | type |= (uint)flags << 24; | ||
765 | |||
766 | // m_log.Debug("1 LogPacketHeader(): Outside lock"); | ||
767 | lock (binStatsLogLock) | ||
768 | { | ||
769 | DateTime now = DateTime.Now; | ||
770 | |||
771 | // m_log.Debug("2 LogPacketHeader(): Inside lock. now is " + now.Ticks); | ||
772 | try | ||
773 | { | ||
774 | if (PacketLog == null || (now > PacketLog.StartTime + binStatsMaxFilesize)) | ||
775 | { | ||
776 | if (PacketLog != null && PacketLog.Log != null) | ||
777 | { | ||
778 | PacketLog.Log.Close(); | ||
779 | } | ||
780 | |||
781 | // First log file or time has expired, start writing to a new log file | ||
782 | PacketLog = new PacketLogger(); | ||
783 | PacketLog.StartTime = now; | ||
784 | PacketLog.Path = (binStatsDir.Length > 0 ? binStatsDir + System.IO.Path.DirectorySeparatorChar.ToString() : "") | ||
785 | + String.Format("packets-{0}.log", now.ToString("yyyyMMddHHmmss")); | ||
786 | PacketLog.Log = new BinaryWriter(File.Open(PacketLog.Path, FileMode.Append, FileAccess.Write)); | ||
787 | } | ||
788 | |||
789 | // Serialize the data | ||
790 | byte[] output = new byte[18]; | ||
791 | Buffer.BlockCopy(BitConverter.GetBytes(now.Ticks), 0, output, 0, 8); | ||
792 | Buffer.BlockCopy(BitConverter.GetBytes(circuit), 0, output, 8, 4); | ||
793 | Buffer.BlockCopy(BitConverter.GetBytes(type), 0, output, 12, 4); | ||
794 | Buffer.BlockCopy(BitConverter.GetBytes(size), 0, output, 16, 2); | ||
795 | |||
796 | // Write the serialized data to disk | ||
797 | if (PacketLog != null && PacketLog.Log != null) | ||
798 | PacketLog.Log.Write(output); | ||
799 | } | ||
800 | catch (Exception ex) | ||
801 | { | ||
802 | m_log.Error("Packet statistics gathering failed: " + ex.Message, ex); | ||
803 | if (PacketLog.Log != null) | ||
804 | { | ||
805 | PacketLog.Log.Close(); | ||
806 | } | ||
807 | PacketLog = null; | ||
808 | } | ||
809 | } | ||
810 | } | ||
811 | |||
812 | #endregion BinaryStats | ||
813 | |||
700 | private void HandleUseCircuitCode(object o) | 814 | private void HandleUseCircuitCode(object o) |
701 | { | 815 | { |
702 | object[] array = (object[])o; | 816 | object[] array = (object[])o; |
diff --git a/OpenSim/Region/ClientStack/LindenUDP/OpenSimUDPBase.cs b/OpenSim/Region/ClientStack/LindenUDP/OpenSimUDPBase.cs index 552cc4a..d2779ba 100644 --- a/OpenSim/Region/ClientStack/LindenUDP/OpenSimUDPBase.cs +++ b/OpenSim/Region/ClientStack/LindenUDP/OpenSimUDPBase.cs | |||
@@ -270,8 +270,8 @@ namespace OpenMetaverse | |||
270 | { | 270 | { |
271 | try | 271 | try |
272 | { | 272 | { |
273 | UDPPacketBuffer buf = (UDPPacketBuffer)result.AsyncState; | 273 | // UDPPacketBuffer buf = (UDPPacketBuffer)result.AsyncState; |
274 | int bytesSent = m_udpSocket.EndSendTo(result); | 274 | m_udpSocket.EndSendTo(result); |
275 | } | 275 | } |
276 | catch (SocketException) { } | 276 | catch (SocketException) { } |
277 | catch (ObjectDisposedException) { } | 277 | catch (ObjectDisposedException) { } |
diff --git a/OpenSim/Region/Communications/Hypergrid/HGUserServices.cs b/OpenSim/Region/Communications/Hypergrid/HGUserServices.cs index 49a2261..09d8285 100644 --- a/OpenSim/Region/Communications/Hypergrid/HGUserServices.cs +++ b/OpenSim/Region/Communications/Hypergrid/HGUserServices.cs | |||
@@ -204,6 +204,14 @@ namespace OpenSim.Region.Communications.Hypergrid | |||
204 | return base.UpdateUserProfile(userProfile); | 204 | return base.UpdateUserProfile(userProfile); |
205 | } | 205 | } |
206 | 206 | ||
207 | public override bool AuthenticateUserByPassword(UUID userID, string password) | ||
208 | { | ||
209 | if (m_localUserServices != null) | ||
210 | return m_localUserServices.AuthenticateUserByPassword(userID, password); | ||
211 | else | ||
212 | return base.AuthenticateUserByPassword(userID, password); | ||
213 | } | ||
214 | |||
207 | #region IUserServices Friend Methods | 215 | #region IUserServices Friend Methods |
208 | 216 | ||
209 | // NOTE: We're still not dealing with foreign user friends | 217 | // NOTE: We're still not dealing with foreign user friends |
diff --git a/OpenSim/Region/CoreModules/Agent/AssetTransaction/AssetXferUploader.cs b/OpenSim/Region/CoreModules/Agent/AssetTransaction/AssetXferUploader.cs index e192b81..f698ea1 100644 --- a/OpenSim/Region/CoreModules/Agent/AssetTransaction/AssetXferUploader.cs +++ b/OpenSim/Region/CoreModules/Agent/AssetTransaction/AssetXferUploader.cs | |||
@@ -112,11 +112,8 @@ namespace OpenSim.Region.CoreModules.Agent.AssetTransaction | |||
112 | bool storeLocal, bool tempFile) | 112 | bool storeLocal, bool tempFile) |
113 | { | 113 | { |
114 | ourClient = remoteClient; | 114 | ourClient = remoteClient; |
115 | m_asset = new AssetBase(); | 115 | m_asset = new AssetBase(assetID, "blank", type); |
116 | m_asset.FullID = assetID; | ||
117 | m_asset.Type = type; | ||
118 | m_asset.Data = data; | 116 | m_asset.Data = data; |
119 | m_asset.Name = "blank"; | ||
120 | m_asset.Description = "empty"; | 117 | m_asset.Description = "empty"; |
121 | m_asset.Local = storeLocal; | 118 | m_asset.Local = storeLocal; |
122 | m_asset.Temporary = tempFile; | 119 | m_asset.Temporary = tempFile; |
diff --git a/OpenSim/Region/CoreModules/Agent/TextureSender/J2KDecoderModule.cs b/OpenSim/Region/CoreModules/Agent/TextureSender/J2KDecoderModule.cs index 7456e8c..7ac8bed 100644 --- a/OpenSim/Region/CoreModules/Agent/TextureSender/J2KDecoderModule.cs +++ b/OpenSim/Region/CoreModules/Agent/TextureSender/J2KDecoderModule.cs | |||
@@ -144,8 +144,8 @@ namespace OpenSim.Region.CoreModules.Agent.TextureSender | |||
144 | /// <param name="j2kData">JPEG2000 data</param> | 144 | /// <param name="j2kData">JPEG2000 data</param> |
145 | private void DoJ2KDecode(UUID assetID, byte[] j2kData) | 145 | private void DoJ2KDecode(UUID assetID, byte[] j2kData) |
146 | { | 146 | { |
147 | int DecodeTime = 0; | 147 | // int DecodeTime = 0; |
148 | DecodeTime = Environment.TickCount; | 148 | // DecodeTime = Environment.TickCount; |
149 | OpenJPEG.J2KLayerInfo[] layers; | 149 | OpenJPEG.J2KLayerInfo[] layers; |
150 | 150 | ||
151 | if (!TryLoadCacheForAsset(assetID, out layers)) | 151 | if (!TryLoadCacheForAsset(assetID, out layers)) |
@@ -238,12 +238,11 @@ namespace OpenSim.Region.CoreModules.Agent.TextureSender | |||
238 | 238 | ||
239 | if (m_cache != null) | 239 | if (m_cache != null) |
240 | { | 240 | { |
241 | AssetBase layerDecodeAsset = new AssetBase(); | 241 | string assetID = "j2kCache_" + AssetId.ToString(); |
242 | layerDecodeAsset.ID = "j2kCache_" + AssetId.ToString(); | 242 | |
243 | AssetBase layerDecodeAsset = new AssetBase(assetID, assetID, (sbyte)AssetType.Notecard); | ||
243 | layerDecodeAsset.Local = true; | 244 | layerDecodeAsset.Local = true; |
244 | layerDecodeAsset.Name = layerDecodeAsset.ID; | ||
245 | layerDecodeAsset.Temporary = true; | 245 | layerDecodeAsset.Temporary = true; |
246 | layerDecodeAsset.Type = (sbyte)AssetType.Notecard; | ||
247 | 246 | ||
248 | #region Serialize Layer Data | 247 | #region Serialize Layer Data |
249 | 248 | ||
diff --git a/OpenSim/Region/CoreModules/Asset/FlotsamAssetCache.cs b/OpenSim/Region/CoreModules/Asset/FlotsamAssetCache.cs index c6af806..adcf6bd 100644 --- a/OpenSim/Region/CoreModules/Asset/FlotsamAssetCache.cs +++ b/OpenSim/Region/CoreModules/Asset/FlotsamAssetCache.cs | |||
@@ -831,7 +831,7 @@ namespace Flotsam.RegionModules.AssetCache | |||
831 | 831 | ||
832 | public string Store(AssetBase asset) | 832 | public string Store(AssetBase asset) |
833 | { | 833 | { |
834 | if ((asset.FullID == null) || (asset.FullID == UUID.Zero)) | 834 | if (asset.FullID == UUID.Zero) |
835 | { | 835 | { |
836 | asset.FullID = UUID.Random(); | 836 | asset.FullID = UUID.Random(); |
837 | } | 837 | } |
diff --git a/OpenSim/Region/CoreModules/Avatar/Friends/FriendsModule.cs b/OpenSim/Region/CoreModules/Avatar/Friends/FriendsModule.cs index fc7d63a..bb4e032 100644 --- a/OpenSim/Region/CoreModules/Avatar/Friends/FriendsModule.cs +++ b/OpenSim/Region/CoreModules/Avatar/Friends/FriendsModule.cs | |||
@@ -395,6 +395,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Friends | |||
395 | 395 | ||
396 | // if it leaves, we want to know, too | 396 | // if it leaves, we want to know, too |
397 | client.OnLogout += OnLogout; | 397 | client.OnLogout += OnLogout; |
398 | client.OnGrantUserRights += GrantUserFriendRights; | ||
399 | |||
398 | } | 400 | } |
399 | 401 | ||
400 | private void ClientClosed(UUID AgentId, Scene scene) | 402 | private void ClientClosed(UUID AgentId, Scene scene) |
@@ -1108,7 +1110,22 @@ namespace OpenSim.Region.CoreModules.Avatar.Friends | |||
1108 | // tell everyone that we are offline | 1110 | // tell everyone that we are offline |
1109 | SendPresenceState(remoteClient, fl, false); | 1111 | SendPresenceState(remoteClient, fl, false); |
1110 | } | 1112 | } |
1111 | } | 1113 | private void GrantUserFriendRights(IClientAPI remoteClient, UUID requester, UUID target, int rights) |
1114 | { | ||
1115 | ((Scene)remoteClient.Scene).CommsManager.UpdateUserFriendPerms(requester, target, (uint)rights); | ||
1116 | } | ||
1112 | 1117 | ||
1118 | public List<FriendListItem> GetUserFriends(UUID agentID) | ||
1119 | { | ||
1120 | List<FriendListItem> fl; | ||
1121 | lock (m_friendLists) | ||
1122 | { | ||
1123 | fl = (List<FriendListItem>)m_friendLists.Get(agentID.ToString(), | ||
1124 | m_initialScene.GetFriendList); | ||
1125 | } | ||
1126 | |||
1127 | return fl; | ||
1128 | } | ||
1129 | } | ||
1113 | #endregion | 1130 | #endregion |
1114 | } | 1131 | } |
diff --git a/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveReadRequest.cs b/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveReadRequest.cs index f761bf0..aafcfa2 100644 --- a/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveReadRequest.cs +++ b/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveReadRequest.cs | |||
@@ -99,36 +99,6 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
99 | int failedAssetRestores = 0; | 99 | int failedAssetRestores = 0; |
100 | int successfulItemRestores = 0; | 100 | int successfulItemRestores = 0; |
101 | List<InventoryNodeBase> nodesLoaded = new List<InventoryNodeBase>(); | 101 | List<InventoryNodeBase> nodesLoaded = new List<InventoryNodeBase>(); |
102 | |||
103 | /* | ||
104 | if (!m_userInfo.HasReceivedInventory) | ||
105 | { | ||
106 | // If the region server has access to the user admin service (by which users are created), | ||
107 | // then we'll assume that it's okay to fiddle with the user's inventory even if they are not on the | ||
108 | // server. | ||
109 | // | ||
110 | // FIXME: FetchInventory should probably be assumed to by async anyway, since even standalones might | ||
111 | // use a remote inventory service, though this is vanishingly rare at the moment. | ||
112 | if (null == m_scene.CommsManager.UserAdminService) | ||
113 | { | ||
114 | m_log.ErrorFormat( | ||
115 | "[INVENTORY ARCHIVER]: Have not yet received inventory info for user {0} {1}", | ||
116 | m_userInfo.UserProfile.Name, m_userInfo.UserProfile.ID); | ||
117 | |||
118 | return nodesLoaded; | ||
119 | } | ||
120 | else | ||
121 | { | ||
122 | m_userInfo.FetchInventory(); | ||
123 | for (int i = 0 ; i < 50 ; i++) | ||
124 | { | ||
125 | if (m_userInfo.HasReceivedInventory == true) | ||
126 | break; | ||
127 | Thread.Sleep(200); | ||
128 | } | ||
129 | } | ||
130 | } | ||
131 | */ | ||
132 | 102 | ||
133 | //InventoryFolderImpl rootDestinationFolder = m_userInfo.RootFolder.FindFolderByPath(m_invPath); | 103 | //InventoryFolderImpl rootDestinationFolder = m_userInfo.RootFolder.FindFolderByPath(m_invPath); |
134 | InventoryFolderBase rootDestinationFolder | 104 | InventoryFolderBase rootDestinationFolder |
@@ -159,9 +129,14 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
159 | successfulAssetRestores++; | 129 | successfulAssetRestores++; |
160 | else | 130 | else |
161 | failedAssetRestores++; | 131 | failedAssetRestores++; |
132 | |||
133 | if ((successfulAssetRestores) % 50 == 0) | ||
134 | m_log.DebugFormat( | ||
135 | "[INVENTORY ARCHIVER]: Loaded {0} assets...", | ||
136 | successfulAssetRestores); | ||
162 | } | 137 | } |
163 | else if (filePath.StartsWith(ArchiveConstants.INVENTORY_PATH)) | 138 | else if (filePath.StartsWith(ArchiveConstants.INVENTORY_PATH)) |
164 | { | 139 | { |
165 | InventoryFolderBase foundFolder | 140 | InventoryFolderBase foundFolder |
166 | = ReplicateArchivePathToUserInventory( | 141 | = ReplicateArchivePathToUserInventory( |
167 | filePath, TarArchiveReader.TarEntryType.TYPE_DIRECTORY == entryType, | 142 | filePath, TarArchiveReader.TarEntryType.TYPE_DIRECTORY == entryType, |
@@ -169,38 +144,27 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
169 | 144 | ||
170 | if (TarArchiveReader.TarEntryType.TYPE_DIRECTORY != entryType) | 145 | if (TarArchiveReader.TarEntryType.TYPE_DIRECTORY != entryType) |
171 | { | 146 | { |
172 | InventoryItemBase item = UserInventoryItemSerializer.Deserialize(data); | 147 | InventoryItemBase item = LoadItem(data, foundFolder); |
173 | |||
174 | // Don't use the item ID that's in the file | ||
175 | item.ID = UUID.Random(); | ||
176 | |||
177 | UUID ospResolvedId = OspResolver.ResolveOspa(item.CreatorId, m_scene.CommsManager); | ||
178 | if (UUID.Zero != ospResolvedId) | ||
179 | item.CreatorIdAsUuid = ospResolvedId; | ||
180 | else | ||
181 | item.CreatorIdAsUuid = m_userInfo.UserProfile.ID; | ||
182 | |||
183 | item.Owner = m_userInfo.UserProfile.ID; | ||
184 | |||
185 | // Reset folder ID to the one in which we want to load it | ||
186 | item.Folder = foundFolder.ID; | ||
187 | 148 | ||
188 | //m_userInfo.AddItem(item); | 149 | if (item != null) |
189 | m_scene.InventoryService.AddItem(item); | 150 | { |
190 | successfulItemRestores++; | 151 | successfulItemRestores++; |
191 | 152 | ||
192 | // If we're loading an item directly into the given destination folder then we need to record | 153 | // If we're loading an item directly into the given destination folder then we need to record |
193 | // it separately from any loaded root folders | 154 | // it separately from any loaded root folders |
194 | if (rootDestinationFolder == foundFolder) | 155 | if (rootDestinationFolder == foundFolder) |
195 | nodesLoaded.Add(item); | 156 | nodesLoaded.Add(item); |
157 | } | ||
196 | } | 158 | } |
197 | } | 159 | } |
198 | } | 160 | } |
199 | 161 | ||
200 | archive.Close(); | 162 | archive.Close(); |
201 | 163 | ||
202 | m_log.DebugFormat("[INVENTORY ARCHIVER]: Restored {0} assets", successfulAssetRestores); | 164 | m_log.DebugFormat( |
203 | m_log.InfoFormat("[INVENTORY ARCHIVER]: Restored {0} items", successfulItemRestores); | 165 | "[INVENTORY ARCHIVER]: Successfully loaded {0} assets with {1} failures", |
166 | successfulAssetRestores, failedAssetRestores); | ||
167 | m_log.InfoFormat("[INVENTORY ARCHIVER]: Successfully loaded {0} items", successfulItemRestores); | ||
204 | 168 | ||
205 | return nodesLoaded; | 169 | return nodesLoaded; |
206 | } | 170 | } |
@@ -234,8 +198,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
234 | 198 | ||
235 | string originalArchivePath = archivePath; | 199 | string originalArchivePath = archivePath; |
236 | 200 | ||
237 | m_log.DebugFormat( | 201 | // m_log.DebugFormat( |
238 | "[INVENTORY ARCHIVER]: Loading to folder {0} {1}", rootDestFolder.Name, rootDestFolder.ID); | 202 | // "[INVENTORY ARCHIVER]: Loading folder {0} {1}", rootDestFolder.Name, rootDestFolder.ID); |
239 | 203 | ||
240 | InventoryFolderBase destFolder = null; | 204 | InventoryFolderBase destFolder = null; |
241 | 205 | ||
@@ -246,8 +210,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
246 | { | 210 | { |
247 | if (foldersCreated.ContainsKey(archivePath)) | 211 | if (foldersCreated.ContainsKey(archivePath)) |
248 | { | 212 | { |
249 | m_log.DebugFormat( | 213 | // m_log.DebugFormat( |
250 | "[INVENTORY ARCHIVER]: Found previously created folder from archive path {0}", archivePath); | 214 | // "[INVENTORY ARCHIVER]: Found previously created folder from archive path {0}", archivePath); |
251 | destFolder = foldersCreated[archivePath]; | 215 | destFolder = foldersCreated[archivePath]; |
252 | } | 216 | } |
253 | else | 217 | else |
@@ -289,6 +253,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
289 | ArchiveConstants.INVENTORY_NODE_NAME_COMPONENT_SEPARATOR); | 253 | ArchiveConstants.INVENTORY_NODE_NAME_COMPONENT_SEPARATOR); |
290 | 254 | ||
291 | string newFolderName = rawDirsToCreate[i].Remove(identicalNameIdentifierIndex); | 255 | string newFolderName = rawDirsToCreate[i].Remove(identicalNameIdentifierIndex); |
256 | |||
257 | newFolderName = InventoryArchiveUtils.UnescapeArchivePath(newFolderName); | ||
292 | UUID newFolderId = UUID.Random(); | 258 | UUID newFolderId = UUID.Random(); |
293 | 259 | ||
294 | // Asset type has to be Unknown here rather than Folder, otherwise the created folder can't be | 260 | // Asset type has to be Unknown here rather than Folder, otherwise the created folder can't be |
@@ -361,6 +327,37 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
361 | } | 327 | } |
362 | 328 | ||
363 | /// <summary> | 329 | /// <summary> |
330 | /// Load an item from the archive | ||
331 | /// </summary> | ||
332 | /// <param name="filePath">The archive path for the item</param> | ||
333 | /// <param name="data">The raw item data</param> | ||
334 | /// <param name="rootDestinationFolder">The root destination folder for loaded items</param> | ||
335 | /// <param name="nodesLoaded">All the inventory nodes (items and folders) loaded so far</param> | ||
336 | protected InventoryItemBase LoadItem(byte[] data, InventoryFolderBase loadFolder) | ||
337 | { | ||
338 | InventoryItemBase item = UserInventoryItemSerializer.Deserialize(data); | ||
339 | |||
340 | // Don't use the item ID that's in the file | ||
341 | item.ID = UUID.Random(); | ||
342 | |||
343 | UUID ospResolvedId = OspResolver.ResolveOspa(item.CreatorId, m_scene.CommsManager); | ||
344 | if (UUID.Zero != ospResolvedId) | ||
345 | item.CreatorIdAsUuid = ospResolvedId; | ||
346 | else | ||
347 | item.CreatorIdAsUuid = m_userInfo.UserProfile.ID; | ||
348 | |||
349 | item.Owner = m_userInfo.UserProfile.ID; | ||
350 | |||
351 | // Reset folder ID to the one in which we want to load it | ||
352 | item.Folder = loadFolder.ID; | ||
353 | |||
354 | //m_userInfo.AddItem(item); | ||
355 | m_scene.InventoryService.AddItem(item); | ||
356 | |||
357 | return item; | ||
358 | } | ||
359 | |||
360 | /// <summary> | ||
364 | /// Load an asset | 361 | /// Load an asset |
365 | /// </summary> | 362 | /// </summary> |
366 | /// <param name="assetFilename"></param> | 363 | /// <param name="assetFilename"></param> |
@@ -389,11 +386,12 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
389 | { | 386 | { |
390 | sbyte assetType = ArchiveConstants.EXTENSION_TO_ASSET_TYPE[extension]; | 387 | sbyte assetType = ArchiveConstants.EXTENSION_TO_ASSET_TYPE[extension]; |
391 | 388 | ||
392 | //m_log.DebugFormat("[INVENTORY ARCHIVER]: Importing asset {0}, type {1}", uuid, assetType); | 389 | if (assetType == (sbyte)AssetType.Unknown) |
390 | m_log.WarnFormat("[INVENTORY ARCHIVER]: Importing {0} byte asset {1} with unknown type", data.Length, uuid); | ||
393 | 391 | ||
394 | AssetBase asset = new AssetBase(new UUID(uuid), "RandomName"); | 392 | //m_log.DebugFormat("[INVENTORY ARCHIVER]: Importing asset {0}, type {1}", uuid, assetType); |
395 | 393 | ||
396 | asset.Type = assetType; | 394 | AssetBase asset = new AssetBase(new UUID(uuid), "RandomName", assetType); |
397 | asset.Data = data; | 395 | asset.Data = data; |
398 | 396 | ||
399 | m_scene.AssetService.Store(asset); | 397 | m_scene.AssetService.Store(asset); |
diff --git a/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveUtils.cs b/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveUtils.cs index a822d10..247cee4 100644 --- a/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveUtils.cs +++ b/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveUtils.cs | |||
@@ -27,6 +27,9 @@ | |||
27 | 27 | ||
28 | using System; | 28 | using System; |
29 | using System.Collections.Generic; | 29 | using System.Collections.Generic; |
30 | using System.Reflection; | ||
31 | using System.Text; | ||
32 | using log4net; | ||
30 | using OpenMetaverse; | 33 | using OpenMetaverse; |
31 | using OpenSim.Framework; | 34 | using OpenSim.Framework; |
32 | using OpenSim.Services.Interfaces; | 35 | using OpenSim.Services.Interfaces; |
@@ -38,7 +41,13 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
38 | /// </summary> | 41 | /// </summary> |
39 | public static class InventoryArchiveUtils | 42 | public static class InventoryArchiveUtils |
40 | { | 43 | { |
41 | public static readonly string PATH_DELIMITER = "/"; | 44 | // private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
45 | |||
46 | // Character used for escaping the path delimter ("\/") and itself ("\\") in human escaped strings | ||
47 | public static readonly char ESCAPE_CHARACTER = '\\'; | ||
48 | |||
49 | // The character used to separate inventory path components (different folders and items) | ||
50 | public static readonly char PATH_DELIMITER = '/'; | ||
42 | 51 | ||
43 | /// <summary> | 52 | /// <summary> |
44 | /// Find a folder given a PATH_DELIMITER delimited path starting from a user's root folder | 53 | /// Find a folder given a PATH_DELIMITER delimited path starting from a user's root folder |
@@ -103,10 +112,14 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
103 | 112 | ||
104 | path = path.Trim(); | 113 | path = path.Trim(); |
105 | 114 | ||
106 | if (path == PATH_DELIMITER) | 115 | if (path == PATH_DELIMITER.ToString()) |
107 | return startFolder; | 116 | return startFolder; |
108 | 117 | ||
109 | string[] components = path.Split(new string[] { PATH_DELIMITER }, 2, StringSplitOptions.None); | 118 | string[] components = SplitEscapedPath(path); |
119 | components[0] = UnescapePath(components[0]); | ||
120 | |||
121 | //string[] components = path.Split(new string[] { PATH_DELIMITER.ToString() }, 2, StringSplitOptions.None); | ||
122 | |||
110 | InventoryCollection contents = inventoryService.GetFolderContent(startFolder.Owner, startFolder.ID); | 123 | InventoryCollection contents = inventoryService.GetFolderContent(startFolder.Owner, startFolder.ID); |
111 | 124 | ||
112 | foreach (InventoryFolderBase folder in contents.Folders) | 125 | foreach (InventoryFolderBase folder in contents.Folders) |
@@ -181,10 +194,15 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
181 | public static InventoryItemBase FindItemByPath( | 194 | public static InventoryItemBase FindItemByPath( |
182 | IInventoryService inventoryService, InventoryFolderBase startFolder, string path) | 195 | IInventoryService inventoryService, InventoryFolderBase startFolder, string path) |
183 | { | 196 | { |
184 | string[] components = path.Split(new string[] { PATH_DELIMITER }, 2, StringSplitOptions.None); | 197 | string[] components = SplitEscapedPath(path); |
198 | components[0] = UnescapePath(components[0]); | ||
199 | |||
200 | //string[] components = path.Split(new string[] { PATH_DELIMITER }, 2, StringSplitOptions.None); | ||
185 | 201 | ||
186 | if (components.Length == 1) | 202 | if (components.Length == 1) |
187 | { | 203 | { |
204 | // m_log.DebugFormat("FOUND SINGLE COMPONENT [{0}]", components[0]); | ||
205 | |||
188 | List<InventoryItemBase> items = inventoryService.GetFolderItems(startFolder.Owner, startFolder.ID); | 206 | List<InventoryItemBase> items = inventoryService.GetFolderItems(startFolder.Owner, startFolder.ID); |
189 | foreach (InventoryItemBase item in items) | 207 | foreach (InventoryItemBase item in items) |
190 | { | 208 | { |
@@ -194,6 +212,8 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
194 | } | 212 | } |
195 | else | 213 | else |
196 | { | 214 | { |
215 | // m_log.DebugFormat("FOUND COMPONENTS [{0}] and [{1}]", components[0], components[1]); | ||
216 | |||
197 | InventoryCollection contents = inventoryService.GetFolderContent(startFolder.Owner, startFolder.ID); | 217 | InventoryCollection contents = inventoryService.GetFolderContent(startFolder.Owner, startFolder.ID); |
198 | 218 | ||
199 | foreach (InventoryFolderBase folder in contents.Folders) | 219 | foreach (InventoryFolderBase folder in contents.Folders) |
@@ -206,5 +226,97 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
206 | // We didn't find an item or intermediate folder with the given name | 226 | // We didn't find an item or intermediate folder with the given name |
207 | return null; | 227 | return null; |
208 | } | 228 | } |
229 | |||
230 | /// <summary> | ||
231 | /// Split a human escaped path into two components if it contains an unescaped path delimiter, or one component | ||
232 | /// if no delimiter is present | ||
233 | /// </summary> | ||
234 | /// <param name="path"></param> | ||
235 | /// <returns> | ||
236 | /// The split path. We leave the components in their originally unescaped state (though we remove the delimiter | ||
237 | /// which originally split them if applicable). | ||
238 | /// </returns> | ||
239 | public static string[] SplitEscapedPath(string path) | ||
240 | { | ||
241 | // m_log.DebugFormat("SPLITTING PATH {0}", path); | ||
242 | |||
243 | bool singleEscapeChar = false; | ||
244 | |||
245 | for (int i = 0; i < path.Length; i++) | ||
246 | { | ||
247 | if (path[i] == ESCAPE_CHARACTER && !singleEscapeChar) | ||
248 | { | ||
249 | singleEscapeChar = true; | ||
250 | } | ||
251 | else | ||
252 | { | ||
253 | if (PATH_DELIMITER == path[i] && !singleEscapeChar) | ||
254 | return new string[2] { path.Remove(i), path.Substring(i + 1) }; | ||
255 | else | ||
256 | singleEscapeChar = false; | ||
257 | } | ||
258 | } | ||
259 | |||
260 | // We didn't find a delimiter | ||
261 | return new string[1] { path }; | ||
262 | } | ||
263 | |||
264 | /// <summary> | ||
265 | /// Unescapes a human escaped path. This means that "\\" goes to "\", and "\/" goes to "/" | ||
266 | /// </summary> | ||
267 | /// <param name="path"></param> | ||
268 | /// <returns></returns> | ||
269 | public static string UnescapePath(string path) | ||
270 | { | ||
271 | // m_log.DebugFormat("ESCAPING PATH {0}", path); | ||
272 | |||
273 | StringBuilder sb = new StringBuilder(); | ||
274 | |||
275 | bool singleEscapeChar = false; | ||
276 | for (int i = 0; i < path.Length; i++) | ||
277 | { | ||
278 | if (path[i] == ESCAPE_CHARACTER && !singleEscapeChar) | ||
279 | singleEscapeChar = true; | ||
280 | else | ||
281 | singleEscapeChar = false; | ||
282 | |||
283 | if (singleEscapeChar) | ||
284 | { | ||
285 | if (PATH_DELIMITER == path[i]) | ||
286 | sb.Append(PATH_DELIMITER); | ||
287 | } | ||
288 | else | ||
289 | { | ||
290 | sb.Append(path[i]); | ||
291 | } | ||
292 | } | ||
293 | |||
294 | // m_log.DebugFormat("ESCAPED PATH TO {0}", sb); | ||
295 | |||
296 | return sb.ToString(); | ||
297 | } | ||
298 | |||
299 | /// <summary> | ||
300 | /// Escape an archive path. | ||
301 | /// </summary> | ||
302 | /// This has to be done differently from human paths because we can't leave in any "/" characters (due to | ||
303 | /// problems if the archive is built from or extracted to a filesystem | ||
304 | /// <param name="path"></param> | ||
305 | /// <returns></returns> | ||
306 | public static string EscapeArchivePath(string path) | ||
307 | { | ||
308 | // Only encode ampersands (for escaping anything) and / (since this is used as general dir separator). | ||
309 | return path.Replace("&", "&").Replace("/", "/"); | ||
310 | } | ||
311 | |||
312 | /// <summary> | ||
313 | /// Unescape an archive path. | ||
314 | /// </summary> | ||
315 | /// <param name="path"></param> | ||
316 | /// <returns></returns> | ||
317 | public static string UnescapeArchivePath(string path) | ||
318 | { | ||
319 | return path.Replace("/", "/").Replace("&", "&"); | ||
320 | } | ||
209 | } | 321 | } |
210 | } \ No newline at end of file | 322 | } \ No newline at end of file |
diff --git a/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveWriteRequest.cs b/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveWriteRequest.cs index 499c552..bbb49f6 100644 --- a/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveWriteRequest.cs +++ b/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/InventoryArchiveWriteRequest.cs | |||
@@ -217,37 +217,6 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
217 | InventoryItemBase inventoryItem = null; | 217 | InventoryItemBase inventoryItem = null; |
218 | InventoryFolderBase rootFolder = m_scene.InventoryService.GetRootFolder(m_userInfo.UserProfile.ID); | 218 | InventoryFolderBase rootFolder = m_scene.InventoryService.GetRootFolder(m_userInfo.UserProfile.ID); |
219 | 219 | ||
220 | // XXX: Very temporarily, drop and refetch inventory to make sure we have any newly created items in cache | ||
221 | // This will disappear very soon once we stop using the old cached inventory. | ||
222 | /* | ||
223 | m_userInfo.DropInventory(); | ||
224 | m_userInfo.FetchInventory(); | ||
225 | */ | ||
226 | |||
227 | /* | ||
228 | if (!m_userInfo.HasReceivedInventory) | ||
229 | { | ||
230 | // If the region server has access to the user admin service (by which users are created), | ||
231 | // then we'll assume that it's okay to fiddle with the user's inventory even if they are not on the | ||
232 | // server. | ||
233 | // | ||
234 | // FIXME: FetchInventory should probably be assumed to by async anyway, since even standalones might | ||
235 | // use a remote inventory service, though this is vanishingly rare at the moment. | ||
236 | if (null == m_scene.CommsManager.UserAdminService) | ||
237 | { | ||
238 | m_log.ErrorFormat( | ||
239 | "[INVENTORY ARCHIVER]: Have not yet received inventory info for user {0} {1}", | ||
240 | m_userInfo.UserProfile.Name, m_userInfo.UserProfile.ID); | ||
241 | |||
242 | return; | ||
243 | } | ||
244 | else | ||
245 | { | ||
246 | m_userInfo.FetchInventory(); | ||
247 | } | ||
248 | } | ||
249 | */ | ||
250 | |||
251 | bool foundStar = false; | 220 | bool foundStar = false; |
252 | 221 | ||
253 | // Eliminate double slashes and any leading / on the path. | 222 | // Eliminate double slashes and any leading / on the path. |
@@ -294,34 +263,33 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
294 | 263 | ||
295 | m_archiveWriter = new TarArchiveWriter(m_saveStream); | 264 | m_archiveWriter = new TarArchiveWriter(m_saveStream); |
296 | 265 | ||
297 | if (null == inventoryFolder) | 266 | if (inventoryFolder != null) |
298 | { | ||
299 | if (null == inventoryItem) | ||
300 | { | ||
301 | // We couldn't find the path indicated | ||
302 | m_saveStream.Close(); | ||
303 | m_module.TriggerInventoryArchiveSaved( | ||
304 | m_id, false, m_userInfo, m_invPath, m_saveStream, | ||
305 | new Exception(string.Format("Could not find inventory entry at path {0}", m_invPath))); | ||
306 | return; | ||
307 | } | ||
308 | else | ||
309 | { | ||
310 | m_log.DebugFormat( | ||
311 | "[INVENTORY ARCHIVER]: Found item {0} {1} at {2}", | ||
312 | inventoryItem.Name, inventoryItem.ID, m_invPath); | ||
313 | |||
314 | SaveInvItem(inventoryItem, ArchiveConstants.INVENTORY_PATH); | ||
315 | } | ||
316 | } | ||
317 | else | ||
318 | { | 267 | { |
319 | m_log.DebugFormat( | 268 | m_log.DebugFormat( |
320 | "[INVENTORY ARCHIVER]: Found folder {0} {1} at {2}", | 269 | "[INVENTORY ARCHIVER]: Found folder {0} {1} at {2}", |
321 | inventoryFolder.Name, inventoryFolder.ID, m_invPath); | 270 | inventoryFolder.Name, inventoryFolder.ID, m_invPath); |
322 | 271 | ||
323 | //recurse through all dirs getting dirs and files | 272 | //recurse through all dirs getting dirs and files |
324 | SaveInvFolder(inventoryFolder, ArchiveConstants.INVENTORY_PATH, !foundStar); | 273 | SaveInvFolder(inventoryFolder, ArchiveConstants.INVENTORY_PATH, !foundStar); |
274 | } | ||
275 | else if (inventoryItem != null) | ||
276 | { | ||
277 | m_log.DebugFormat( | ||
278 | "[INVENTORY ARCHIVER]: Found item {0} {1} at {2}", | ||
279 | inventoryItem.Name, inventoryItem.ID, m_invPath); | ||
280 | |||
281 | SaveInvItem(inventoryItem, ArchiveConstants.INVENTORY_PATH); | ||
282 | } | ||
283 | else | ||
284 | { | ||
285 | // We couldn't find the path indicated | ||
286 | m_saveStream.Close(); | ||
287 | string errorMessage = string.Format("Aborted save. Could not find inventory path {0}", m_invPath); | ||
288 | m_log.ErrorFormat("[INVENTORY ARCHIVER]: {0}", errorMessage); | ||
289 | m_module.TriggerInventoryArchiveSaved( | ||
290 | m_id, false, m_userInfo, m_invPath, m_saveStream, | ||
291 | new Exception(errorMessage)); | ||
292 | return; | ||
325 | } | 293 | } |
326 | 294 | ||
327 | // Don't put all this profile information into the archive right now. | 295 | // Don't put all this profile information into the archive right now. |
@@ -396,7 +364,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
396 | { | 364 | { |
397 | return string.Format( | 365 | return string.Format( |
398 | "{0}{1}{2}/", | 366 | "{0}{1}{2}/", |
399 | name, | 367 | InventoryArchiveUtils.EscapeArchivePath(name), |
400 | ArchiveConstants.INVENTORY_NODE_NAME_COMPONENT_SEPARATOR, | 368 | ArchiveConstants.INVENTORY_NODE_NAME_COMPONENT_SEPARATOR, |
401 | id); | 369 | id); |
402 | } | 370 | } |
@@ -411,7 +379,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver | |||
411 | { | 379 | { |
412 | return string.Format( | 380 | return string.Format( |
413 | "{0}{1}{2}.xml", | 381 | "{0}{1}{2}.xml", |
414 | name, | 382 | InventoryArchiveUtils.EscapeArchivePath(name), |
415 | ArchiveConstants.INVENTORY_NODE_NAME_COMPONENT_SEPARATOR, | 383 | ArchiveConstants.INVENTORY_NODE_NAME_COMPONENT_SEPARATOR, |
416 | id); | 384 | id); |
417 | } | 385 | } |
diff --git a/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/Tests/InventoryArchiverTests.cs b/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/Tests/InventoryArchiverTests.cs index b0fdcd6..f8a010c 100644 --- a/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/Tests/InventoryArchiverTests.cs +++ b/OpenSim/Region/CoreModules/Avatar/Inventory/Archiver/Tests/InventoryArchiverTests.cs | |||
@@ -29,7 +29,6 @@ using System; | |||
29 | using System.Collections.Generic; | 29 | using System.Collections.Generic; |
30 | using System.IO; | 30 | using System.IO; |
31 | using System.Reflection; | 31 | using System.Reflection; |
32 | using System.Text; | ||
33 | using System.Threading; | 32 | using System.Threading; |
34 | using NUnit.Framework; | 33 | using NUnit.Framework; |
35 | using NUnit.Framework.SyntaxHelpers; | 34 | using NUnit.Framework.SyntaxHelpers; |
@@ -122,9 +121,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver.Tests | |||
122 | } | 121 | } |
123 | 122 | ||
124 | UUID asset1Id = UUID.Parse("00000000-0000-0000-0000-000000000060"); | 123 | UUID asset1Id = UUID.Parse("00000000-0000-0000-0000-000000000060"); |
125 | AssetBase asset1 = new AssetBase(); | 124 | AssetBase asset1 = AssetHelpers.CreateAsset(asset1Id, object1); |
126 | asset1.FullID = asset1Id; | ||
127 | asset1.Data = Encoding.ASCII.GetBytes(SceneObjectSerializer.ToXml2Format(object1)); | ||
128 | scene.AssetService.Store(asset1); | 125 | scene.AssetService.Store(asset1); |
129 | 126 | ||
130 | // Create item | 127 | // Create item |
@@ -136,7 +133,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver.Tests | |||
136 | InventoryFolderBase objsFolder | 133 | InventoryFolderBase objsFolder |
137 | = InventoryArchiveUtils.FindFolderByPath(scene.InventoryService, userId, "Objects"); | 134 | = InventoryArchiveUtils.FindFolderByPath(scene.InventoryService, userId, "Objects"); |
138 | item1.Folder = objsFolder.ID; | 135 | item1.Folder = objsFolder.ID; |
139 | scene.AddInventoryItem(userId, item1); | 136 | scene.AddInventoryItem(userId, item1); |
140 | 137 | ||
141 | MemoryStream archiveWriteStream = new MemoryStream(); | 138 | MemoryStream archiveWriteStream = new MemoryStream(); |
142 | archiverModule.OnInventoryArchiveSaved += SaveCompleted; | 139 | archiverModule.OnInventoryArchiveSaved += SaveCompleted; |
@@ -218,14 +215,14 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver.Tests | |||
218 | string userItemCreatorLastName = "Lucan"; | 215 | string userItemCreatorLastName = "Lucan"; |
219 | UUID userItemCreatorUuid = UUID.Parse("00000000-0000-0000-0000-000000000666"); | 216 | UUID userItemCreatorUuid = UUID.Parse("00000000-0000-0000-0000-000000000666"); |
220 | 217 | ||
221 | string itemName = "b.lsl"; | 218 | string item1Name = "b.lsl"; |
222 | string archiveItemName = InventoryArchiveWriteRequest.CreateArchiveItemName(itemName, UUID.Random()); | 219 | string archiveItemName = InventoryArchiveWriteRequest.CreateArchiveItemName(item1Name, UUID.Random()); |
223 | 220 | ||
224 | MemoryStream archiveWriteStream = new MemoryStream(); | 221 | MemoryStream archiveWriteStream = new MemoryStream(); |
225 | TarArchiveWriter tar = new TarArchiveWriter(archiveWriteStream); | 222 | TarArchiveWriter tar = new TarArchiveWriter(archiveWriteStream); |
226 | 223 | ||
227 | InventoryItemBase item1 = new InventoryItemBase(); | 224 | InventoryItemBase item1 = new InventoryItemBase(); |
228 | item1.Name = itemName; | 225 | item1.Name = item1Name; |
229 | item1.AssetID = UUID.Random(); | 226 | item1.AssetID = UUID.Random(); |
230 | item1.GroupID = UUID.Random(); | 227 | item1.GroupID = UUID.Random(); |
231 | item1.CreatorId = OspResolver.MakeOspa(userItemCreatorFirstName, userItemCreatorLastName); | 228 | item1.CreatorId = OspResolver.MakeOspa(userItemCreatorFirstName, userItemCreatorLastName); |
@@ -259,7 +256,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver.Tests | |||
259 | = scene.CommsManager.UserProfileCacheService.GetUserDetails(userFirstName, userLastName); | 256 | = scene.CommsManager.UserProfileCacheService.GetUserDetails(userFirstName, userLastName); |
260 | 257 | ||
261 | InventoryItemBase foundItem1 | 258 | InventoryItemBase foundItem1 |
262 | = InventoryArchiveUtils.FindItemByPath(scene.InventoryService, userInfo.UserProfile.ID, itemName); | 259 | = InventoryArchiveUtils.FindItemByPath(scene.InventoryService, userInfo.UserProfile.ID, item1Name); |
263 | 260 | ||
264 | Assert.That(foundItem1, Is.Not.Null, "Didn't find loaded item 1"); | 261 | Assert.That(foundItem1, Is.Not.Null, "Didn't find loaded item 1"); |
265 | Assert.That( | 262 | Assert.That( |
@@ -277,7 +274,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver.Tests | |||
277 | archiverModule.DearchiveInventory(userFirstName, userLastName, "xA", "meowfood", archiveReadStream); | 274 | archiverModule.DearchiveInventory(userFirstName, userLastName, "xA", "meowfood", archiveReadStream); |
278 | 275 | ||
279 | InventoryItemBase foundItem2 | 276 | InventoryItemBase foundItem2 |
280 | = InventoryArchiveUtils.FindItemByPath(scene.InventoryService, userInfo.UserProfile.ID, "xA/" + itemName); | 277 | = InventoryArchiveUtils.FindItemByPath(scene.InventoryService, userInfo.UserProfile.ID, "xA/" + item1Name); |
281 | Assert.That(foundItem2, Is.Not.Null, "Didn't find loaded item 2"); | 278 | Assert.That(foundItem2, Is.Not.Null, "Didn't find loaded item 2"); |
282 | 279 | ||
283 | // Now try loading to a more deeply nested folder | 280 | // Now try loading to a more deeply nested folder |
@@ -286,10 +283,99 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver.Tests | |||
286 | archiverModule.DearchiveInventory(userFirstName, userLastName, "xB/xC", "meowfood", archiveReadStream); | 283 | archiverModule.DearchiveInventory(userFirstName, userLastName, "xB/xC", "meowfood", archiveReadStream); |
287 | 284 | ||
288 | InventoryItemBase foundItem3 | 285 | InventoryItemBase foundItem3 |
289 | = InventoryArchiveUtils.FindItemByPath(scene.InventoryService, userInfo.UserProfile.ID, "xB/xC/" + itemName); | 286 | = InventoryArchiveUtils.FindItemByPath(scene.InventoryService, userInfo.UserProfile.ID, "xB/xC/" + item1Name); |
290 | Assert.That(foundItem3, Is.Not.Null, "Didn't find loaded item 3"); | 287 | Assert.That(foundItem3, Is.Not.Null, "Didn't find loaded item 3"); |
291 | } | 288 | } |
292 | 289 | ||
290 | [Test] | ||
291 | public void TestIarV0_1WithEscapedChars() | ||
292 | { | ||
293 | TestHelper.InMethod(); | ||
294 | // log4net.Config.XmlConfigurator.Configure(); | ||
295 | |||
296 | string itemName = "You & you are a mean/man/"; | ||
297 | string humanEscapedItemName = @"You & you are a mean\/man\/"; | ||
298 | string userPassword = "meowfood"; | ||
299 | |||
300 | InventoryArchiverModule archiverModule = new InventoryArchiverModule(true); | ||
301 | |||
302 | Scene scene = SceneSetupHelpers.SetupScene("Inventory"); | ||
303 | SceneSetupHelpers.SetupSceneModules(scene, archiverModule); | ||
304 | CommunicationsManager cm = scene.CommsManager; | ||
305 | |||
306 | // Create user | ||
307 | string userFirstName = "Jock"; | ||
308 | string userLastName = "Stirrup"; | ||
309 | UUID userId = UUID.Parse("00000000-0000-0000-0000-000000000020"); | ||
310 | |||
311 | lock (this) | ||
312 | { | ||
313 | UserProfileTestUtils.CreateUserWithInventory( | ||
314 | cm, userFirstName, userLastName, userPassword, userId, InventoryReceived); | ||
315 | Monitor.Wait(this, 60000); | ||
316 | } | ||
317 | |||
318 | // Create asset | ||
319 | SceneObjectGroup object1; | ||
320 | SceneObjectPart part1; | ||
321 | { | ||
322 | string partName = "part name"; | ||
323 | UUID ownerId = UUID.Parse("00000000-0000-0000-0000-000000000040"); | ||
324 | PrimitiveBaseShape shape = PrimitiveBaseShape.CreateSphere(); | ||
325 | Vector3 groupPosition = new Vector3(10, 20, 30); | ||
326 | Quaternion rotationOffset = new Quaternion(20, 30, 40, 50); | ||
327 | Vector3 offsetPosition = new Vector3(5, 10, 15); | ||
328 | |||
329 | part1 | ||
330 | = new SceneObjectPart( | ||
331 | ownerId, shape, groupPosition, rotationOffset, offsetPosition); | ||
332 | part1.Name = partName; | ||
333 | |||
334 | object1 = new SceneObjectGroup(part1); | ||
335 | scene.AddNewSceneObject(object1, false); | ||
336 | } | ||
337 | |||
338 | UUID asset1Id = UUID.Parse("00000000-0000-0000-0000-000000000060"); | ||
339 | AssetBase asset1 = AssetHelpers.CreateAsset(asset1Id, object1); | ||
340 | scene.AssetService.Store(asset1); | ||
341 | |||
342 | // Create item | ||
343 | UUID item1Id = UUID.Parse("00000000-0000-0000-0000-000000000080"); | ||
344 | InventoryItemBase item1 = new InventoryItemBase(); | ||
345 | item1.Name = itemName; | ||
346 | item1.AssetID = asset1.FullID; | ||
347 | item1.ID = item1Id; | ||
348 | InventoryFolderBase objsFolder | ||
349 | = InventoryArchiveUtils.FindFolderByPath(scene.InventoryService, userId, "Objects"); | ||
350 | item1.Folder = objsFolder.ID; | ||
351 | scene.AddInventoryItem(userId, item1); | ||
352 | |||
353 | MemoryStream archiveWriteStream = new MemoryStream(); | ||
354 | archiverModule.OnInventoryArchiveSaved += SaveCompleted; | ||
355 | |||
356 | mre.Reset(); | ||
357 | archiverModule.ArchiveInventory( | ||
358 | Guid.NewGuid(), userFirstName, userLastName, "Objects", userPassword, archiveWriteStream); | ||
359 | mre.WaitOne(60000, false); | ||
360 | |||
361 | // LOAD ITEM | ||
362 | MemoryStream archiveReadStream = new MemoryStream(archiveWriteStream.ToArray()); | ||
363 | |||
364 | archiverModule.DearchiveInventory(userFirstName, userLastName, "Scripts", userPassword, archiveReadStream); | ||
365 | |||
366 | InventoryItemBase foundItem1 | ||
367 | = InventoryArchiveUtils.FindItemByPath( | ||
368 | scene.InventoryService, userId, "Scripts/Objects/" + humanEscapedItemName); | ||
369 | |||
370 | Assert.That(foundItem1, Is.Not.Null, "Didn't find loaded item 1"); | ||
371 | // Assert.That( | ||
372 | // foundItem1.CreatorId, Is.EqualTo(userUuid), | ||
373 | // "Loaded item non-uuid creator doesn't match that of the loading user"); | ||
374 | Assert.That( | ||
375 | foundItem1.Name, Is.EqualTo(itemName), | ||
376 | "Loaded item name doesn't match saved name"); | ||
377 | } | ||
378 | |||
293 | /// <summary> | 379 | /// <summary> |
294 | /// Test loading a V0.1 OpenSim Inventory Archive (subject to change since there is no fixed format yet) where | 380 | /// Test loading a V0.1 OpenSim Inventory Archive (subject to change since there is no fixed format yet) where |
295 | /// embedded creators do not exist in the system | 381 | /// embedded creators do not exist in the system |
@@ -302,7 +388,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver.Tests | |||
302 | { | 388 | { |
303 | TestHelper.InMethod(); | 389 | TestHelper.InMethod(); |
304 | 390 | ||
305 | log4net.Config.XmlConfigurator.Configure(); | 391 | //log4net.Config.XmlConfigurator.Configure(); |
306 | 392 | ||
307 | string userFirstName = "Charlie"; | 393 | string userFirstName = "Charlie"; |
308 | string userLastName = "Chan"; | 394 | string userLastName = "Chan"; |
@@ -370,7 +456,7 @@ namespace OpenSim.Region.CoreModules.Avatar.Inventory.Archiver.Tests | |||
370 | { | 456 | { |
371 | TestHelper.InMethod(); | 457 | TestHelper.InMethod(); |
372 | 458 | ||
373 | log4net.Config.XmlConfigurator.Configure(); | 459 | //log4net.Config.XmlConfigurator.Configure(); |
374 | 460 | ||
375 | string userFirstName = "Dennis"; | 461 | string userFirstName = "Dennis"; |
376 | string userLastName = "Menace"; | 462 | string userLastName = "Menace"; |
diff --git a/OpenSim/Region/CoreModules/Framework/Monitoring/MonitorModule.cs b/OpenSim/Region/CoreModules/Framework/Monitoring/MonitorModule.cs index 769af8d..11aca99 100644 --- a/OpenSim/Region/CoreModules/Framework/Monitoring/MonitorModule.cs +++ b/OpenSim/Region/CoreModules/Framework/Monitoring/MonitorModule.cs | |||
@@ -1,7 +1,10 @@ | |||
1 | using System.Collections.Generic; | 1 | using System.Collections; |
2 | using System.Collections.Generic; | ||
2 | using System.Reflection; | 3 | using System.Reflection; |
3 | using log4net; | 4 | using log4net; |
4 | using Nini.Config; | 5 | using Nini.Config; |
6 | using OpenMetaverse; | ||
7 | using OpenSim.Framework; | ||
5 | using OpenSim.Region.CoreModules.Framework.Monitoring.Alerts; | 8 | using OpenSim.Region.CoreModules.Framework.Monitoring.Alerts; |
6 | using OpenSim.Region.CoreModules.Framework.Monitoring.Monitors; | 9 | using OpenSim.Region.CoreModules.Framework.Monitoring.Monitors; |
7 | using OpenSim.Region.Framework.Interfaces; | 10 | using OpenSim.Region.Framework.Interfaces; |
@@ -43,6 +46,56 @@ namespace OpenSim.Region.CoreModules.Framework.Monitoring | |||
43 | "monitor report", | 46 | "monitor report", |
44 | "Returns a variety of statistics about the current region and/or simulator", | 47 | "Returns a variety of statistics about the current region and/or simulator", |
45 | DebugMonitors); | 48 | DebugMonitors); |
49 | |||
50 | MainServer.Instance.AddHTTPHandler("/monitorstats/" + m_scene.RegionInfo.RegionID + "/", StatsPage); | ||
51 | } | ||
52 | |||
53 | public Hashtable StatsPage(Hashtable request) | ||
54 | { | ||
55 | // If request was for a specific monitor | ||
56 | // eg url/?monitor=Monitor.Name | ||
57 | if (request.ContainsKey("monitor")) | ||
58 | { | ||
59 | string monID = (string) request["monitor"]; | ||
60 | |||
61 | foreach (IMonitor monitor in m_monitors) | ||
62 | { | ||
63 | if (monitor.ToString() == monID) | ||
64 | { | ||
65 | Hashtable ereply3 = new Hashtable(); | ||
66 | |||
67 | ereply3["int_response_code"] = 404; // 200 OK | ||
68 | ereply3["str_response_string"] = monitor.GetValue().ToString(); | ||
69 | ereply3["content_type"] = "text/plain"; | ||
70 | |||
71 | return ereply3; | ||
72 | } | ||
73 | } | ||
74 | |||
75 | // No monitor with that name | ||
76 | Hashtable ereply2 = new Hashtable(); | ||
77 | |||
78 | ereply2["int_response_code"] = 404; // 200 OK | ||
79 | ereply2["str_response_string"] = "No such monitor"; | ||
80 | ereply2["content_type"] = "text/plain"; | ||
81 | |||
82 | return ereply2; | ||
83 | } | ||
84 | |||
85 | string xml = "<data>"; | ||
86 | foreach (IMonitor monitor in m_monitors) | ||
87 | { | ||
88 | xml += "<" + monitor.ToString() + ">" + monitor.GetValue() + "</" + monitor.ToString() + ">"; | ||
89 | } | ||
90 | xml += "</data>"; | ||
91 | |||
92 | Hashtable ereply = new Hashtable(); | ||
93 | |||
94 | ereply["int_response_code"] = 200; // 200 OK | ||
95 | ereply["str_response_string"] = xml; | ||
96 | ereply["content_type"] = "text/xml"; | ||
97 | |||
98 | return ereply; | ||
46 | } | 99 | } |
47 | 100 | ||
48 | public void PostInitialise() | 101 | public void PostInitialise() |
diff --git a/OpenSim/Region/CoreModules/Resources/CoreModulePlugin.addin.xml b/OpenSim/Region/CoreModules/Resources/CoreModulePlugin.addin.xml index 8f82718..9757072 100644 --- a/OpenSim/Region/CoreModules/Resources/CoreModulePlugin.addin.xml +++ b/OpenSim/Region/CoreModules/Resources/CoreModulePlugin.addin.xml | |||
@@ -13,7 +13,6 @@ | |||
13 | <RegionModule id="ArchiverModule" type="OpenSim.Region.CoreModules.World.Archiver.ArchiverModule" /> | 13 | <RegionModule id="ArchiverModule" type="OpenSim.Region.CoreModules.World.Archiver.ArchiverModule" /> |
14 | <RegionModule id="CapabilitiesModule" type="OpenSim.Region.CoreModules.Agent.Capabilities.CapabilitiesModule" /> | 14 | <RegionModule id="CapabilitiesModule" type="OpenSim.Region.CoreModules.Agent.Capabilities.CapabilitiesModule" /> |
15 | <RegionModule id="TerrainModule" type="OpenSim.Region.CoreModules.World.Terrain.TerrainModule" /> | 15 | <RegionModule id="TerrainModule" type="OpenSim.Region.CoreModules.World.Terrain.TerrainModule" /> |
16 | <RegionModule id="RegionCombinerModule" type="OpenSim.Region.CoreModules.World.Land.RegionCombinerModule" /> | ||
17 | <RegionModule id="WorldMapModule" type="OpenSim.Region.CoreModules.World.WorldMap.WorldMapModule" /> | 16 | <RegionModule id="WorldMapModule" type="OpenSim.Region.CoreModules.World.WorldMap.WorldMapModule" /> |
18 | <RegionModule id="HGWorldMapModule" type="OpenSim.Region.CoreModules.Hypergrid.HGWorldMapModule" /> | 17 | <RegionModule id="HGWorldMapModule" type="OpenSim.Region.CoreModules.Hypergrid.HGWorldMapModule" /> |
19 | <RegionModule id="UrlModule" type="OpenSim.Region.CoreModules.Scripting.LSLHttp.UrlModule" /> | 18 | <RegionModule id="UrlModule" type="OpenSim.Region.CoreModules.Scripting.LSLHttp.UrlModule" /> |
diff --git a/OpenSim/Region/CoreModules/Scripting/DynamicTexture/DynamicTextureModule.cs b/OpenSim/Region/CoreModules/Scripting/DynamicTexture/DynamicTextureModule.cs index 9a6c49a..43761fc 100644 --- a/OpenSim/Region/CoreModules/Scripting/DynamicTexture/DynamicTextureModule.cs +++ b/OpenSim/Region/CoreModules/Scripting/DynamicTexture/DynamicTextureModule.cs | |||
@@ -311,11 +311,8 @@ namespace OpenSim.Region.CoreModules.Scripting.DynamicTexture | |||
311 | } | 311 | } |
312 | 312 | ||
313 | // Create a new asset for user | 313 | // Create a new asset for user |
314 | AssetBase asset = new AssetBase(); | 314 | AssetBase asset = new AssetBase(UUID.Random(), "DynamicImage" + Util.RandomClass.Next(1, 10000), (sbyte)AssetType.Texture); |
315 | asset.FullID = UUID.Random(); | ||
316 | asset.Data = assetData; | 315 | asset.Data = assetData; |
317 | asset.Name = "DynamicImage" + Util.RandomClass.Next(1, 10000); | ||
318 | asset.Type = 0; | ||
319 | asset.Description = String.Format("URL image : {0}", Url); | 316 | asset.Description = String.Format("URL image : {0}", Url); |
320 | asset.Local = false; | 317 | asset.Local = false; |
321 | asset.Temporary = ((Disp & DISP_TEMP) != 0); | 318 | asset.Temporary = ((Disp & DISP_TEMP) != 0); |
diff --git a/OpenSim/Region/CoreModules/Scripting/XMLRPC/XMLRPCModule.cs b/OpenSim/Region/CoreModules/Scripting/XMLRPC/XMLRPCModule.cs index 97899a7..27b64bf 100644 --- a/OpenSim/Region/CoreModules/Scripting/XMLRPC/XMLRPCModule.cs +++ b/OpenSim/Region/CoreModules/Scripting/XMLRPC/XMLRPCModule.cs | |||
@@ -689,7 +689,7 @@ namespace OpenSim.Region.CoreModules.Scripting.XMLRPC | |||
689 | } | 689 | } |
690 | if (respParms.Contains("IntValue")) | 690 | if (respParms.Contains("IntValue")) |
691 | { | 691 | { |
692 | Idata = Convert.ToInt32((string) respParms["IntValue"]); | 692 | Idata = Convert.ToInt32(respParms["IntValue"]); |
693 | } | 693 | } |
694 | if (respParms.Contains("faultString")) | 694 | if (respParms.Contains("faultString")) |
695 | { | 695 | { |
diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsIn/Grid/HypergridServiceInConnectorModule.cs b/OpenSim/Region/CoreModules/ServiceConnectorsIn/Grid/HypergridServiceInConnectorModule.cs index 92db15b..b12d778 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsIn/Grid/HypergridServiceInConnectorModule.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsIn/Grid/HypergridServiceInConnectorModule.cs | |||
@@ -118,7 +118,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsIn.Grid | |||
118 | 118 | ||
119 | m_log.Info("[HypergridService]: Starting..."); | 119 | m_log.Info("[HypergridService]: Starting..."); |
120 | 120 | ||
121 | Object[] args = new Object[] { m_Config, MainServer.Instance }; | 121 | // Object[] args = new Object[] { m_Config, MainServer.Instance }; |
122 | 122 | ||
123 | m_HypergridHandler = new HypergridServiceInConnector(m_Config, MainServer.Instance, scene.RequestModuleInterface<IHyperlinkService>()); | 123 | m_HypergridHandler = new HypergridServiceInConnector(m_Config, MainServer.Instance, scene.RequestModuleInterface<IHyperlinkService>()); |
124 | //ServerUtils.LoadPlugin<HypergridServiceInConnector>("OpenSim.Server.Handlers.dll:HypergridServiceInConnector", args); | 124 | //ServerUtils.LoadPlugin<HypergridServiceInConnector>("OpenSim.Server.Handlers.dll:HypergridServiceInConnector", args); |
diff --git a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/HGGridConnector.cs b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/HGGridConnector.cs index 40ac647..f2d8579 100644 --- a/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/HGGridConnector.cs +++ b/OpenSim/Region/CoreModules/ServiceConnectorsOut/Grid/HGGridConnector.cs | |||
@@ -336,7 +336,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
336 | public List<GridRegion> GetRegionRange(UUID scopeID, int xmin, int xmax, int ymin, int ymax) | 336 | public List<GridRegion> GetRegionRange(UUID scopeID, int xmin, int xmax, int ymin, int ymax) |
337 | { | 337 | { |
338 | int snapXmin = (int)(xmin / Constants.RegionSize) * (int)Constants.RegionSize; | 338 | int snapXmin = (int)(xmin / Constants.RegionSize) * (int)Constants.RegionSize; |
339 | int snapXmax = (int)(xmax / Constants.RegionSize) * (int)Constants.RegionSize; | 339 | // int snapXmax = (int)(xmax / Constants.RegionSize) * (int)Constants.RegionSize; |
340 | int snapYmin = (int)(ymin / Constants.RegionSize) * (int)Constants.RegionSize; | 340 | int snapYmin = (int)(ymin / Constants.RegionSize) * (int)Constants.RegionSize; |
341 | int snapYmax = (int)(ymax / Constants.RegionSize) * (int)Constants.RegionSize; | 341 | int snapYmax = (int)(ymax / Constants.RegionSize) * (int)Constants.RegionSize; |
342 | 342 | ||
@@ -604,13 +604,16 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
604 | { | 604 | { |
605 | CachedUserInfo uinfo = m_aScene.CommsManager.UserProfileCacheService.GetUserDetails(agentData.AgentID); | 605 | CachedUserInfo uinfo = m_aScene.CommsManager.UserProfileCacheService.GetUserDetails(agentData.AgentID); |
606 | 606 | ||
607 | if (uinfo == null) | ||
608 | return false; | ||
609 | |||
607 | if ((IsLocalUser(uinfo) && (GetHyperlinkRegion(regInfo.RegionHandle) != null)) || | 610 | if ((IsLocalUser(uinfo) && (GetHyperlinkRegion(regInfo.RegionHandle) != null)) || |
608 | (!IsLocalUser(uinfo) && !IsGoingHome(uinfo, regInfo))) | 611 | (!IsLocalUser(uinfo) && !IsGoingHome(uinfo, regInfo))) |
609 | { | 612 | { |
610 | m_log.Info("[HGrid]: Local user is going to foreign region or foreign user is going elsewhere"); | 613 | m_log.Info("[HGrid]: Local user is going to foreign region or foreign user is going elsewhere"); |
611 | 614 | ||
612 | // Set the position of the region on the remote grid | 615 | // Set the position of the region on the remote grid |
613 | ulong realHandle = FindRegionHandle(regInfo.RegionHandle); | 616 | // ulong realHandle = FindRegionHandle(regInfo.RegionHandle); |
614 | uint x = 0, y = 0; | 617 | uint x = 0, y = 0; |
615 | Utils.LongToUInts(regInfo.RegionHandle, out x, out y); | 618 | Utils.LongToUInts(regInfo.RegionHandle, out x, out y); |
616 | GridRegion clonedRegion = new GridRegion(regInfo); | 619 | GridRegion clonedRegion = new GridRegion(regInfo); |
@@ -737,6 +740,9 @@ namespace OpenSim.Region.CoreModules.ServiceConnectorsOut.Grid | |||
737 | // Is the user going back to the home region or the home grid? | 740 | // Is the user going back to the home region or the home grid? |
738 | protected bool IsGoingHome(CachedUserInfo uinfo, GridRegion rinfo) | 741 | protected bool IsGoingHome(CachedUserInfo uinfo, GridRegion rinfo) |
739 | { | 742 | { |
743 | if (uinfo == null) | ||
744 | return false; | ||
745 | |||
740 | if (uinfo.UserProfile == null) | 746 | if (uinfo.UserProfile == null) |
741 | return false; | 747 | return false; |
742 | 748 | ||
diff --git a/OpenSim/Region/CoreModules/World/Archiver/ArchiveReadRequest.cs b/OpenSim/Region/CoreModules/World/Archiver/ArchiveReadRequest.cs index c261943..70a225e 100644 --- a/OpenSim/Region/CoreModules/World/Archiver/ArchiveReadRequest.cs +++ b/OpenSim/Region/CoreModules/World/Archiver/ArchiveReadRequest.cs | |||
@@ -332,10 +332,12 @@ namespace OpenSim.Region.CoreModules.World.Archiver | |||
332 | { | 332 | { |
333 | sbyte assetType = ArchiveConstants.EXTENSION_TO_ASSET_TYPE[extension]; | 333 | sbyte assetType = ArchiveConstants.EXTENSION_TO_ASSET_TYPE[extension]; |
334 | 334 | ||
335 | if (assetType == (sbyte)AssetType.Unknown) | ||
336 | m_log.WarnFormat("[ARCHIVER]: Importing {0} byte asset {1} with unknown type", data.Length, uuid); | ||
337 | |||
335 | //m_log.DebugFormat("[ARCHIVER]: Importing asset {0}, type {1}", uuid, assetType); | 338 | //m_log.DebugFormat("[ARCHIVER]: Importing asset {0}, type {1}", uuid, assetType); |
336 | 339 | ||
337 | AssetBase asset = new AssetBase(new UUID(uuid), String.Empty); | 340 | AssetBase asset = new AssetBase(new UUID(uuid), String.Empty, assetType); |
338 | asset.Type = assetType; | ||
339 | asset.Data = data; | 341 | asset.Data = data; |
340 | 342 | ||
341 | // We're relying on the asset service to do the sensible thing and not store the asset if it already | 343 | // We're relying on the asset service to do the sensible thing and not store the asset if it already |
diff --git a/OpenSim/Region/CoreModules/World/Archiver/AssetsDearchiver.cs b/OpenSim/Region/CoreModules/World/Archiver/AssetsDearchiver.cs index 5208e7a..2d2c570 100644 --- a/OpenSim/Region/CoreModules/World/Archiver/AssetsDearchiver.cs +++ b/OpenSim/Region/CoreModules/World/Archiver/AssetsDearchiver.cs | |||
@@ -158,9 +158,8 @@ namespace OpenSim.Region.CoreModules.World.Archiver | |||
158 | 158 | ||
159 | m_log.DebugFormat("[ARCHIVER]: Importing asset {0}", filename); | 159 | m_log.DebugFormat("[ARCHIVER]: Importing asset {0}", filename); |
160 | 160 | ||
161 | AssetBase asset = new AssetBase(new UUID(filename), metadata.Name); | 161 | AssetBase asset = new AssetBase(new UUID(filename), metadata.Name, metadata.AssetType); |
162 | asset.Description = metadata.Description; | 162 | asset.Description = metadata.Description; |
163 | asset.Type = metadata.AssetType; | ||
164 | asset.Data = data; | 163 | asset.Data = data; |
165 | 164 | ||
166 | m_cache.Store(asset); | 165 | m_cache.Store(asset); |
diff --git a/OpenSim/Region/CoreModules/World/Estate/EstateTerrainXferHandler.cs b/OpenSim/Region/CoreModules/World/Estate/EstateTerrainXferHandler.cs index ddac515..2ff635b 100644 --- a/OpenSim/Region/CoreModules/World/Estate/EstateTerrainXferHandler.cs +++ b/OpenSim/Region/CoreModules/World/Estate/EstateTerrainXferHandler.cs | |||
@@ -52,16 +52,11 @@ namespace OpenSim.Region.CoreModules.World.Estate | |||
52 | 52 | ||
53 | public EstateTerrainXferHandler(IClientAPI pRemoteClient, string pClientFilename) | 53 | public EstateTerrainXferHandler(IClientAPI pRemoteClient, string pClientFilename) |
54 | { | 54 | { |
55 | 55 | m_asset = new AssetBase(UUID.Zero, pClientFilename, type); | |
56 | m_asset = new AssetBase(); | ||
57 | m_asset.FullID = UUID.Zero; | ||
58 | m_asset.Type = type; | ||
59 | m_asset.Data = new byte[0]; | 56 | m_asset.Data = new byte[0]; |
60 | m_asset.Name = pClientFilename; | ||
61 | m_asset.Description = "empty"; | 57 | m_asset.Description = "empty"; |
62 | m_asset.Local = true; | 58 | m_asset.Local = true; |
63 | m_asset.Temporary = true; | 59 | m_asset.Temporary = true; |
64 | |||
65 | } | 60 | } |
66 | 61 | ||
67 | public ulong XferID | 62 | public ulong XferID |
diff --git a/OpenSim/Region/CoreModules/World/Land/LandManagementModule.cs b/OpenSim/Region/CoreModules/World/Land/LandManagementModule.cs index 93a949a..968f46a 100644 --- a/OpenSim/Region/CoreModules/World/Land/LandManagementModule.cs +++ b/OpenSim/Region/CoreModules/World/Land/LandManagementModule.cs | |||
@@ -1059,9 +1059,11 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
1059 | if (m_scene.Permissions.IsGod(remote_client.AgentId)) | 1059 | if (m_scene.Permissions.IsGod(remote_client.AgentId)) |
1060 | { | 1060 | { |
1061 | land.LandData.OwnerID = ownerID; | 1061 | land.LandData.OwnerID = ownerID; |
1062 | land.LandData.GroupID = UUID.Zero; | ||
1063 | land.LandData.IsGroupOwned = false; | ||
1062 | 1064 | ||
1063 | m_scene.ForEachClient(SendParcelOverlay); | 1065 | m_scene.ForEachClient(SendParcelOverlay); |
1064 | land.SendLandUpdateToClient(remote_client); | 1066 | land.SendLandUpdateToClient(true, remote_client); |
1065 | } | 1067 | } |
1066 | } | 1068 | } |
1067 | } | 1069 | } |
@@ -1082,8 +1084,10 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
1082 | land.LandData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner; | 1084 | land.LandData.OwnerID = m_scene.RegionInfo.EstateSettings.EstateOwner; |
1083 | else | 1085 | else |
1084 | land.LandData.OwnerID = m_scene.RegionInfo.MasterAvatarAssignedUUID; | 1086 | land.LandData.OwnerID = m_scene.RegionInfo.MasterAvatarAssignedUUID; |
1087 | land.LandData.GroupID = UUID.Zero; | ||
1088 | land.LandData.IsGroupOwned = false; | ||
1085 | m_scene.ForEachClient(SendParcelOverlay); | 1089 | m_scene.ForEachClient(SendParcelOverlay); |
1086 | land.SendLandUpdateToClient(remote_client); | 1090 | land.SendLandUpdateToClient(true, remote_client); |
1087 | } | 1091 | } |
1088 | } | 1092 | } |
1089 | } | 1093 | } |
@@ -1105,9 +1109,10 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
1105 | else | 1109 | else |
1106 | land.LandData.OwnerID = m_scene.RegionInfo.MasterAvatarAssignedUUID; | 1110 | land.LandData.OwnerID = m_scene.RegionInfo.MasterAvatarAssignedUUID; |
1107 | land.LandData.ClaimDate = Util.UnixTimeSinceEpoch(); | 1111 | land.LandData.ClaimDate = Util.UnixTimeSinceEpoch(); |
1112 | land.LandData.GroupID = UUID.Zero; | ||
1108 | land.LandData.IsGroupOwned = false; | 1113 | land.LandData.IsGroupOwned = false; |
1109 | m_scene.ForEachClient(SendParcelOverlay); | 1114 | m_scene.ForEachClient(SendParcelOverlay); |
1110 | land.SendLandUpdateToClient(remote_client); | 1115 | land.SendLandUpdateToClient(true, remote_client); |
1111 | } | 1116 | } |
1112 | } | 1117 | } |
1113 | } | 1118 | } |
diff --git a/OpenSim/Region/CoreModules/World/Land/LandObject.cs b/OpenSim/Region/CoreModules/World/Land/LandObject.cs index bfe85f1..0bd225e 100644 --- a/OpenSim/Region/CoreModules/World/Land/LandObject.cs +++ b/OpenSim/Region/CoreModules/World/Land/LandObject.cs | |||
@@ -49,6 +49,8 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
49 | #pragma warning restore 0429 | 49 | #pragma warning restore 0429 |
50 | private bool[,] m_landBitmap = new bool[landArrayMax,landArrayMax]; | 50 | private bool[,] m_landBitmap = new bool[landArrayMax,landArrayMax]; |
51 | 51 | ||
52 | private int m_lastSeqId = 0; | ||
53 | |||
52 | protected LandData m_landData = new LandData(); | 54 | protected LandData m_landData = new LandData(); |
53 | protected Scene m_scene; | 55 | protected Scene m_scene; |
54 | protected List<SceneObjectGroup> primsOverMe = new List<SceneObjectGroup>(); | 56 | protected List<SceneObjectGroup> primsOverMe = new List<SceneObjectGroup>(); |
@@ -81,6 +83,10 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
81 | { | 83 | { |
82 | m_scene = scene; | 84 | m_scene = scene; |
83 | LandData.OwnerID = owner_id; | 85 | LandData.OwnerID = owner_id; |
86 | if (is_group_owned) | ||
87 | LandData.GroupID = owner_id; | ||
88 | else | ||
89 | LandData.GroupID = UUID.Zero; | ||
84 | LandData.IsGroupOwned = is_group_owned; | 90 | LandData.IsGroupOwned = is_group_owned; |
85 | } | 91 | } |
86 | 92 | ||
@@ -172,7 +178,19 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
172 | // regionFlags |= (uint)RegionFlags.AllowLandmark; | 178 | // regionFlags |= (uint)RegionFlags.AllowLandmark; |
173 | // if (landData.OwnerID == remote_client.AgentId) | 179 | // if (landData.OwnerID == remote_client.AgentId) |
174 | // regionFlags |= (uint)RegionFlags.AllowSetHome; | 180 | // regionFlags |= (uint)RegionFlags.AllowSetHome; |
175 | remote_client.SendLandProperties(sequence_id, | 181 | |
182 | int seq_id; | ||
183 | if (snap_selection && (sequence_id == 0)) | ||
184 | { | ||
185 | seq_id = m_lastSeqId; | ||
186 | } | ||
187 | else | ||
188 | { | ||
189 | seq_id = sequence_id; | ||
190 | m_lastSeqId = seq_id; | ||
191 | } | ||
192 | |||
193 | remote_client.SendLandProperties(seq_id, | ||
176 | snap_selection, request_result, LandData, | 194 | snap_selection, request_result, LandData, |
177 | (float)m_scene.RegionInfo.RegionSettings.ObjectBonus, | 195 | (float)m_scene.RegionInfo.RegionSettings.ObjectBonus, |
178 | GetParcelMaxPrimCount(this), | 196 | GetParcelMaxPrimCount(this), |
@@ -184,6 +202,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
184 | if (m_scene.Permissions.CanEditParcel(remote_client.AgentId,this)) | 202 | if (m_scene.Permissions.CanEditParcel(remote_client.AgentId,this)) |
185 | { | 203 | { |
186 | //Needs later group support | 204 | //Needs later group support |
205 | bool snap_selection = false; | ||
187 | LandData newData = LandData.Copy(); | 206 | LandData newData = LandData.Copy(); |
188 | 207 | ||
189 | if (args.AuthBuyerID != newData.AuthBuyerID || args.SalePrice != newData.SalePrice) | 208 | if (args.AuthBuyerID != newData.AuthBuyerID || args.SalePrice != newData.SalePrice) |
@@ -192,6 +211,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
192 | { | 211 | { |
193 | newData.AuthBuyerID = args.AuthBuyerID; | 212 | newData.AuthBuyerID = args.AuthBuyerID; |
194 | newData.SalePrice = args.SalePrice; | 213 | newData.SalePrice = args.SalePrice; |
214 | snap_selection = true; | ||
195 | } | 215 | } |
196 | } | 216 | } |
197 | newData.Category = args.Category; | 217 | newData.Category = args.Category; |
@@ -212,7 +232,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
212 | 232 | ||
213 | m_scene.LandChannel.UpdateLandObject(LandData.LocalID, newData); | 233 | m_scene.LandChannel.UpdateLandObject(LandData.LocalID, newData); |
214 | 234 | ||
215 | SendLandUpdateToAvatarsOverMe(); | 235 | SendLandUpdateToAvatarsOverMe(snap_selection); |
216 | } | 236 | } |
217 | } | 237 | } |
218 | 238 | ||
@@ -230,7 +250,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
230 | newData.Flags &= ~(uint) (ParcelFlags.ForSale | ParcelFlags.ForSaleObjects | ParcelFlags.SellParcelObjects); | 250 | newData.Flags &= ~(uint) (ParcelFlags.ForSale | ParcelFlags.ForSaleObjects | ParcelFlags.SellParcelObjects); |
231 | m_scene.LandChannel.UpdateLandObject(LandData.LocalID, newData); | 251 | m_scene.LandChannel.UpdateLandObject(LandData.LocalID, newData); |
232 | 252 | ||
233 | SendLandUpdateToAvatarsOverMe(); | 253 | SendLandUpdateToAvatarsOverMe(true); |
234 | } | 254 | } |
235 | 255 | ||
236 | public void DeedToGroup(UUID groupID) | 256 | public void DeedToGroup(UUID groupID) |
@@ -242,7 +262,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
242 | 262 | ||
243 | m_scene.LandChannel.UpdateLandObject(LandData.LocalID, newData); | 263 | m_scene.LandChannel.UpdateLandObject(LandData.LocalID, newData); |
244 | 264 | ||
245 | SendLandUpdateToAvatarsOverMe(); | 265 | SendLandUpdateToAvatarsOverMe(true); |
246 | } | 266 | } |
247 | 267 | ||
248 | public bool IsEitherBannedOrRestricted(UUID avatar) | 268 | public bool IsEitherBannedOrRestricted(UUID avatar) |
@@ -297,8 +317,18 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
297 | SendLandProperties(0, false, 0, remote_client); | 317 | SendLandProperties(0, false, 0, remote_client); |
298 | } | 318 | } |
299 | 319 | ||
320 | public void SendLandUpdateToClient(bool snap_selection, IClientAPI remote_client) | ||
321 | { | ||
322 | SendLandProperties(0, snap_selection, 0, remote_client); | ||
323 | } | ||
324 | |||
300 | public void SendLandUpdateToAvatarsOverMe() | 325 | public void SendLandUpdateToAvatarsOverMe() |
301 | { | 326 | { |
327 | SendLandUpdateToAvatarsOverMe(false); | ||
328 | } | ||
329 | |||
330 | public void SendLandUpdateToAvatarsOverMe(bool snap_selection) | ||
331 | { | ||
302 | List<ScenePresence> avatars = m_scene.GetAvatars(); | 332 | List<ScenePresence> avatars = m_scene.GetAvatars(); |
303 | ILandObject over = null; | 333 | ILandObject over = null; |
304 | for (int i = 0; i < avatars.Count; i++) | 334 | for (int i = 0; i < avatars.Count; i++) |
@@ -325,7 +355,7 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
325 | else | 355 | else |
326 | avatars[i].Invulnerable = true; | 356 | avatars[i].Invulnerable = true; |
327 | 357 | ||
328 | SendLandUpdateToClient(avatars[i].ControllingClient); | 358 | SendLandUpdateToClient(snap_selection, avatars[i].ControllingClient); |
329 | } | 359 | } |
330 | } | 360 | } |
331 | } | 361 | } |
diff --git a/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs b/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs index fe9de1b..c790624 100644 --- a/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs +++ b/OpenSim/Region/CoreModules/World/Permissions/PermissionsModule.cs | |||
@@ -144,6 +144,8 @@ namespace OpenSim.Region.CoreModules.World.Permissions | |||
144 | private Dictionary<string, bool> GrantVB = new Dictionary<string, bool>(); | 144 | private Dictionary<string, bool> GrantVB = new Dictionary<string, bool>(); |
145 | private Dictionary<string, bool> GrantJS = new Dictionary<string, bool>(); | 145 | private Dictionary<string, bool> GrantJS = new Dictionary<string, bool>(); |
146 | private Dictionary<string, bool> GrantYP = new Dictionary<string, bool>(); | 146 | private Dictionary<string, bool> GrantYP = new Dictionary<string, bool>(); |
147 | private IFriendsModule m_friendsModule = null; | ||
148 | |||
147 | #endregion | 149 | #endregion |
148 | 150 | ||
149 | #region IRegionModule Members | 151 | #region IRegionModule Members |
@@ -363,6 +365,12 @@ namespace OpenSim.Region.CoreModules.World.Permissions | |||
363 | 365 | ||
364 | public void PostInitialise() | 366 | public void PostInitialise() |
365 | { | 367 | { |
368 | m_friendsModule = m_scene.RequestModuleInterface<IFriendsModule>(); | ||
369 | |||
370 | if (m_friendsModule == null) | ||
371 | m_log.Error("[PERMISSIONS]: Friends module not found, friend permissions will not work"); | ||
372 | else | ||
373 | m_log.Info("[PERMISSIONS]: Friends module found, friend permissions enabled"); | ||
366 | } | 374 | } |
367 | 375 | ||
368 | public void Close() | 376 | public void Close() |
@@ -476,6 +484,24 @@ namespace OpenSim.Region.CoreModules.World.Permissions | |||
476 | 484 | ||
477 | return false; | 485 | return false; |
478 | } | 486 | } |
487 | protected bool IsFriendWithPerms(UUID user,UUID objectOwner) | ||
488 | { | ||
489 | |||
490 | if (user == UUID.Zero) | ||
491 | return false; | ||
492 | |||
493 | if (m_friendsModule == null) | ||
494 | return false; | ||
495 | |||
496 | List<FriendListItem> profile = m_friendsModule.GetUserFriends(user); | ||
497 | |||
498 | foreach (FriendListItem item in profile) | ||
499 | { | ||
500 | if(item.Friend == objectOwner && (item.FriendPerms & (uint)FriendRights.CanModifyObjects) != 0) | ||
501 | return true; | ||
502 | } | ||
503 | return false; | ||
504 | } | ||
479 | 505 | ||
480 | protected bool IsEstateManager(UUID user) | 506 | protected bool IsEstateManager(UUID user) |
481 | { | 507 | { |
@@ -565,6 +591,9 @@ namespace OpenSim.Region.CoreModules.World.Permissions | |||
565 | // Object owners should be able to edit their own content | 591 | // Object owners should be able to edit their own content |
566 | if (user == objectOwner) | 592 | if (user == objectOwner) |
567 | return objectOwnerMask; | 593 | return objectOwnerMask; |
594 | |||
595 | if (IsFriendWithPerms(user, objectOwner)) | ||
596 | return objectOwnerMask; | ||
568 | 597 | ||
569 | // Estate users should be able to edit anything in the sim | 598 | // Estate users should be able to edit anything in the sim |
570 | if (IsEstateManager(user) && m_RegionOwnerIsGod && !IsAdministrator(objectOwner)) | 599 | if (IsEstateManager(user) && m_RegionOwnerIsGod && !IsAdministrator(objectOwner)) |
diff --git a/OpenSim/Region/CoreModules/World/WorldMap/WorldMapModule.cs b/OpenSim/Region/CoreModules/World/WorldMap/WorldMapModule.cs index f4b54aa..44a651f 100644 --- a/OpenSim/Region/CoreModules/World/WorldMap/WorldMapModule.cs +++ b/OpenSim/Region/CoreModules/World/WorldMap/WorldMapModule.cs | |||
@@ -1077,14 +1077,12 @@ namespace OpenSim.Region.CoreModules.World.WorldMap | |||
1077 | 1077 | ||
1078 | m_scene.RegionInfo.RegionSettings.TerrainImageID = TerrainImageUUID; | 1078 | m_scene.RegionInfo.RegionSettings.TerrainImageID = TerrainImageUUID; |
1079 | 1079 | ||
1080 | AssetBase asset = new AssetBase(); | 1080 | AssetBase asset = new AssetBase( |
1081 | asset.FullID = m_scene.RegionInfo.RegionSettings.TerrainImageID; | 1081 | m_scene.RegionInfo.RegionSettings.TerrainImageID, |
1082 | "terrainImage_" + m_scene.RegionInfo.RegionID.ToString() + "_" + lastMapRefresh.ToString(), | ||
1083 | (sbyte)AssetType.Texture); | ||
1082 | asset.Data = data; | 1084 | asset.Data = data; |
1083 | asset.Name | ||
1084 | = "terrainImage_" + m_scene.RegionInfo.RegionID.ToString() + "_" + lastMapRefresh.ToString(); | ||
1085 | asset.Description = m_scene.RegionInfo.RegionName; | 1085 | asset.Description = m_scene.RegionInfo.RegionName; |
1086 | |||
1087 | asset.Type = 0; | ||
1088 | asset.Temporary = temporary; | 1086 | asset.Temporary = temporary; |
1089 | m_scene.AssetService.Store(asset); | 1087 | m_scene.AssetService.Store(asset); |
1090 | } | 1088 | } |
diff --git a/OpenSim/Region/Examples/SimpleModule/MyNpcCharacter.cs b/OpenSim/Region/Examples/SimpleModule/MyNpcCharacter.cs index 5a5fcfe..9754da3 100644 --- a/OpenSim/Region/Examples/SimpleModule/MyNpcCharacter.cs +++ b/OpenSim/Region/Examples/SimpleModule/MyNpcCharacter.cs | |||
@@ -179,6 +179,7 @@ namespace OpenSim.Region.Examples.SimpleModule | |||
179 | public event FriendActionDelegate OnApproveFriendRequest; | 179 | public event FriendActionDelegate OnApproveFriendRequest; |
180 | public event FriendActionDelegate OnDenyFriendRequest; | 180 | public event FriendActionDelegate OnDenyFriendRequest; |
181 | public event FriendshipTermination OnTerminateFriendship; | 181 | public event FriendshipTermination OnTerminateFriendship; |
182 | public event GrantUserFriendRights OnGrantUserRights; | ||
182 | 183 | ||
183 | public event EconomyDataRequest OnEconomyDataRequest; | 184 | public event EconomyDataRequest OnEconomyDataRequest; |
184 | public event MoneyBalanceRequest OnMoneyBalanceRequest; | 185 | public event MoneyBalanceRequest OnMoneyBalanceRequest; |
@@ -538,6 +539,7 @@ namespace OpenSim.Region.Examples.SimpleModule | |||
538 | public virtual void SendInventoryFolderDetails(UUID ownerID, UUID folderID, | 539 | public virtual void SendInventoryFolderDetails(UUID ownerID, UUID folderID, |
539 | List<InventoryItemBase> items, | 540 | List<InventoryItemBase> items, |
540 | List<InventoryFolderBase> folders, | 541 | List<InventoryFolderBase> folders, |
542 | int version, | ||
541 | bool fetchFolders, | 543 | bool fetchFolders, |
542 | bool fetchItems) | 544 | bool fetchItems) |
543 | { | 545 | { |
diff --git a/OpenSim/Region/Framework/Interfaces/IFriendsModule.cs b/OpenSim/Region/Framework/Interfaces/IFriendsModule.cs index 7a8aba2..8386030 100644 --- a/OpenSim/Region/Framework/Interfaces/IFriendsModule.cs +++ b/OpenSim/Region/Framework/Interfaces/IFriendsModule.cs | |||
@@ -27,6 +27,7 @@ | |||
27 | 27 | ||
28 | using OpenMetaverse; | 28 | using OpenMetaverse; |
29 | using OpenSim.Framework; | 29 | using OpenSim.Framework; |
30 | using System.Collections.Generic; | ||
30 | 31 | ||
31 | namespace OpenSim.Region.Framework.Interfaces | 32 | namespace OpenSim.Region.Framework.Interfaces |
32 | { | 33 | { |
@@ -45,5 +46,6 @@ namespace OpenSim.Region.Framework.Interfaces | |||
45 | /// </param> | 46 | /// </param> |
46 | /// <param name="offerMessage"></param> | 47 | /// <param name="offerMessage"></param> |
47 | void OfferFriendship(UUID fromUserId, IClientAPI toUserClient, string offerMessage); | 48 | void OfferFriendship(UUID fromUserId, IClientAPI toUserClient, string offerMessage); |
49 | List<FriendListItem> GetUserFriends(UUID agentID); | ||
48 | } | 50 | } |
49 | } | 51 | } |
diff --git a/OpenSim/Region/Framework/Interfaces/ILandObject.cs b/OpenSim/Region/Framework/Interfaces/ILandObject.cs index c2b1292..084184f 100644 --- a/OpenSim/Region/Framework/Interfaces/ILandObject.cs +++ b/OpenSim/Region/Framework/Interfaces/ILandObject.cs | |||
@@ -54,6 +54,7 @@ namespace OpenSim.Region.Framework.Interfaces | |||
54 | bool IsBannedFromLand(UUID avatar); | 54 | bool IsBannedFromLand(UUID avatar); |
55 | bool IsRestrictedFromLand(UUID avatar); | 55 | bool IsRestrictedFromLand(UUID avatar); |
56 | void SendLandUpdateToClient(IClientAPI remote_client); | 56 | void SendLandUpdateToClient(IClientAPI remote_client); |
57 | void SendLandUpdateToClient(bool snap_selection, IClientAPI remote_client); | ||
57 | List<UUID> CreateAccessListArrayByFlag(AccessList flag); | 58 | List<UUID> CreateAccessListArrayByFlag(AccessList flag); |
58 | void SendAccessList(UUID agentID, UUID sessionID, uint flags, int sequenceID, IClientAPI remote_client); | 59 | void SendAccessList(UUID agentID, UUID sessionID, uint flags, int sequenceID, IClientAPI remote_client); |
59 | void UpdateAccessList(uint flags, List<ParcelManager.ParcelAccessEntry> entries, IClientAPI remote_client); | 60 | void UpdateAccessList(uint flags, List<ParcelManager.ParcelAccessEntry> entries, IClientAPI remote_client); |
diff --git a/OpenSim/Region/Framework/Interfaces/IScriptModuleComms.cs b/OpenSim/Region/Framework/Interfaces/IScriptModuleComms.cs new file mode 100644 index 0000000..5cdf191 --- /dev/null +++ b/OpenSim/Region/Framework/Interfaces/IScriptModuleComms.cs | |||
@@ -0,0 +1,44 @@ | |||
1 | /* | ||
2 | * Copyright (c) Contributors, http://opensimulator.org/ | ||
3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. | ||
4 | * | ||
5 | * Redistribution and use in source and binary forms, with or without | ||
6 | * modification, are permitted provided that the following conditions are met: | ||
7 | * * Redistributions of source code must retain the above copyright | ||
8 | * notice, this list of conditions and the following disclaimer. | ||
9 | * * Redistributions in binary form must reproduce the above copyright | ||
10 | * notice, this list of conditions and the following disclaimer in the | ||
11 | * documentation and/or other materials provided with the distribution. | ||
12 | * * Neither the name of the OpenSimulator Project nor the | ||
13 | * names of its contributors may be used to endorse or promote products | ||
14 | * derived from this software without specific prior written permission. | ||
15 | * | ||
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY | ||
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | ||
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
26 | */ | ||
27 | |||
28 | using System; | ||
29 | using OpenMetaverse; | ||
30 | |||
31 | namespace OpenSim.Region.Framework.Interfaces | ||
32 | { | ||
33 | public delegate void ScriptCommand(UUID script, string id, string module, string command, string k); | ||
34 | |||
35 | public interface IScriptModuleComms | ||
36 | { | ||
37 | event ScriptCommand OnScriptCommand; | ||
38 | |||
39 | void DispatchReply(UUID script, int code, string text, string k); | ||
40 | |||
41 | // For use ONLY by the script API | ||
42 | void RaiseEvent(UUID script, string id, string module, string command, string k); | ||
43 | } | ||
44 | } | ||
diff --git a/OpenSim/Region/Framework/Scenes/EntityBase.cs b/OpenSim/Region/Framework/Scenes/EntityBase.cs index c2ec6a5..1c76c54 100644 --- a/OpenSim/Region/Framework/Scenes/EntityBase.cs +++ b/OpenSim/Region/Framework/Scenes/EntityBase.cs | |||
@@ -94,14 +94,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
94 | set { m_velocity = value; } | 94 | set { m_velocity = value; } |
95 | } | 95 | } |
96 | 96 | ||
97 | protected Quaternion m_rotation = new Quaternion(0f, 0f, 1f, 0f); | ||
98 | |||
99 | public virtual Quaternion Rotation | ||
100 | { | ||
101 | get { return m_rotation; } | ||
102 | set { m_rotation = value; } | ||
103 | } | ||
104 | |||
105 | protected uint m_localId; | 97 | protected uint m_localId; |
106 | 98 | ||
107 | public virtual uint LocalId | 99 | public virtual uint LocalId |
@@ -115,13 +107,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
115 | /// </summary> | 107 | /// </summary> |
116 | public EntityBase() | 108 | public EntityBase() |
117 | { | 109 | { |
118 | m_uuid = UUID.Zero; | ||
119 | |||
120 | m_pos = Vector3.Zero; | ||
121 | m_velocity = Vector3.Zero; | ||
122 | Rotation = Quaternion.Identity; | ||
123 | m_name = "(basic entity)"; | 110 | m_name = "(basic entity)"; |
124 | m_rotationalvelocity = Vector3.Zero; | ||
125 | } | 111 | } |
126 | 112 | ||
127 | /// <summary> | 113 | /// <summary> |
diff --git a/OpenSim/Region/Framework/Scenes/Hypergrid/HGAssetMapper.cs b/OpenSim/Region/Framework/Scenes/Hypergrid/HGAssetMapper.cs index 244ac3b..ec50598 100644 --- a/OpenSim/Region/Framework/Scenes/Hypergrid/HGAssetMapper.cs +++ b/OpenSim/Region/Framework/Scenes/Hypergrid/HGAssetMapper.cs | |||
@@ -77,13 +77,13 @@ namespace OpenSim.Region.Framework.Scenes.Hypergrid | |||
77 | 77 | ||
78 | #region Internal functions | 78 | #region Internal functions |
79 | 79 | ||
80 | private string UserAssetURL(UUID userID) | 80 | // private string UserAssetURL(UUID userID) |
81 | { | 81 | // { |
82 | CachedUserInfo uinfo = m_scene.CommsManager.UserProfileCacheService.GetUserDetails(userID); | 82 | // CachedUserInfo uinfo = m_scene.CommsManager.UserProfileCacheService.GetUserDetails(userID); |
83 | if (uinfo != null) | 83 | // if (uinfo != null) |
84 | return (uinfo.UserProfile.UserAssetURI == "") ? null : uinfo.UserProfile.UserAssetURI; | 84 | // return (uinfo.UserProfile.UserAssetURI == "") ? null : uinfo.UserProfile.UserAssetURI; |
85 | return null; | 85 | // return null; |
86 | } | 86 | // } |
87 | 87 | ||
88 | // private string UserInventoryURL(UUID userID) | 88 | // private string UserInventoryURL(UUID userID) |
89 | // { | 89 | // { |
@@ -118,7 +118,7 @@ namespace OpenSim.Region.Framework.Scenes.Hypergrid | |||
118 | // HGAssetService dispatches it to the remote grid. | 118 | // HGAssetService dispatches it to the remote grid. |
119 | // It's not pretty, but the best that can be done while | 119 | // It's not pretty, but the best that can be done while |
120 | // not having a global naming infrastructure | 120 | // not having a global naming infrastructure |
121 | AssetBase asset1 = new AssetBase(); | 121 | AssetBase asset1 = new AssetBase(asset.FullID, asset.Name, asset.Type); |
122 | Copy(asset, asset1); | 122 | Copy(asset, asset1); |
123 | try | 123 | try |
124 | { | 124 | { |
diff --git a/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs b/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs index 4d76b4ef..66fb918 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.Inventory.cs | |||
@@ -93,7 +93,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
93 | 93 | ||
94 | public void AddInventoryItem(UUID AgentID, InventoryItemBase item) | 94 | public void AddInventoryItem(UUID AgentID, InventoryItemBase item) |
95 | { | 95 | { |
96 | |||
97 | if (InventoryService.AddItem(item)) | 96 | if (InventoryService.AddItem(item)) |
98 | { | 97 | { |
99 | int userlevel = 0; | 98 | int userlevel = 0; |
@@ -627,11 +626,8 @@ namespace OpenSim.Region.Framework.Scenes | |||
627 | /// <returns></returns> | 626 | /// <returns></returns> |
628 | private AssetBase CreateAsset(string name, string description, sbyte assetType, byte[] data) | 627 | private AssetBase CreateAsset(string name, string description, sbyte assetType, byte[] data) |
629 | { | 628 | { |
630 | AssetBase asset = new AssetBase(); | 629 | AssetBase asset = new AssetBase(UUID.Random(), name, assetType); |
631 | asset.Name = name; | ||
632 | asset.Description = description; | 630 | asset.Description = description; |
633 | asset.Type = assetType; | ||
634 | asset.FullID = UUID.Random(); | ||
635 | asset.Data = (data == null) ? new byte[1] : data; | 631 | asset.Data = (data == null) ? new byte[1] : data; |
636 | 632 | ||
637 | return asset; | 633 | return asset; |
@@ -807,20 +803,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
807 | InventoryService.DeleteFolders(remoteClient.AgentId, folderIDs); | 803 | InventoryService.DeleteFolders(remoteClient.AgentId, folderIDs); |
808 | } | 804 | } |
809 | 805 | ||
810 | private SceneObjectGroup GetGroupByPrim(uint localID) | ||
811 | { | ||
812 | List<EntityBase> EntityList = GetEntities(); | ||
813 | |||
814 | foreach (EntityBase ent in EntityList) | ||
815 | { | ||
816 | if (ent is SceneObjectGroup) | ||
817 | { | ||
818 | if (((SceneObjectGroup) ent).HasChildPrim(localID)) | ||
819 | return (SceneObjectGroup) ent; | ||
820 | } | ||
821 | } | ||
822 | return null; | ||
823 | } | ||
824 | 806 | ||
825 | /// <summary> | 807 | /// <summary> |
826 | /// Send the details of a prim's inventory to the client. | 808 | /// Send the details of a prim's inventory to the client. |
@@ -1175,7 +1157,13 @@ namespace OpenSim.Region.Framework.Scenes | |||
1175 | { | 1157 | { |
1176 | m_log.DebugFormat("[AGENT INVENTORY]: Send Inventory Folder {0} Update to {1} {2}", folder.Name, client.FirstName, client.LastName); | 1158 | m_log.DebugFormat("[AGENT INVENTORY]: Send Inventory Folder {0} Update to {1} {2}", folder.Name, client.FirstName, client.LastName); |
1177 | InventoryCollection contents = InventoryService.GetFolderContent(client.AgentId, folder.ID); | 1159 | InventoryCollection contents = InventoryService.GetFolderContent(client.AgentId, folder.ID); |
1178 | client.SendInventoryFolderDetails(client.AgentId, folder.ID, contents.Items, contents.Folders, fetchFolders, fetchItems); | 1160 | InventoryFolderBase containingFolder = new InventoryFolderBase(); |
1161 | containingFolder.ID = folder.ID; | ||
1162 | containingFolder.Owner = client.AgentId; | ||
1163 | containingFolder = InventoryService.GetFolder(containingFolder); | ||
1164 | int version = containingFolder.Version; | ||
1165 | |||
1166 | client.SendInventoryFolderDetails(client.AgentId, folder.ID, contents.Items, contents.Folders, version, fetchFolders, fetchItems); | ||
1179 | } | 1167 | } |
1180 | 1168 | ||
1181 | /// <summary> | 1169 | /// <summary> |
diff --git a/OpenSim/Region/Framework/Scenes/Scene.PacketHandlers.cs b/OpenSim/Region/Framework/Scenes/Scene.PacketHandlers.cs index 1a91f0c..47fbeb4 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.PacketHandlers.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.PacketHandlers.cs | |||
@@ -462,7 +462,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
462 | { | 462 | { |
463 | remoteClient.SendInventoryFolderDetails( | 463 | remoteClient.SendInventoryFolderDetails( |
464 | fold.Owner, folderID, fold.RequestListOfItems(), | 464 | fold.Owner, folderID, fold.RequestListOfItems(), |
465 | fold.RequestListOfFolders(), fetchFolders, fetchItems); | 465 | fold.RequestListOfFolders(), fold.Version, fetchFolders, fetchItems); |
466 | return; | 466 | return; |
467 | } | 467 | } |
468 | 468 | ||
diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index a6ee40a..aeca7df 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs | |||
@@ -36,6 +36,7 @@ using System.Timers; | |||
36 | using System.Xml; | 36 | using System.Xml; |
37 | using Nini.Config; | 37 | using Nini.Config; |
38 | using OpenMetaverse; | 38 | using OpenMetaverse; |
39 | using OpenMetaverse.Packets; | ||
39 | using OpenMetaverse.Imaging; | 40 | using OpenMetaverse.Imaging; |
40 | using OpenSim.Framework; | 41 | using OpenSim.Framework; |
41 | using OpenSim.Services.Interfaces; | 42 | using OpenSim.Services.Interfaces; |
@@ -87,8 +88,18 @@ namespace OpenSim.Region.Framework.Scenes | |||
87 | protected List<RegionInfo> m_regionRestartNotifyList = new List<RegionInfo>(); | 88 | protected List<RegionInfo> m_regionRestartNotifyList = new List<RegionInfo>(); |
88 | protected List<RegionInfo> m_neighbours = new List<RegionInfo>(); | 89 | protected List<RegionInfo> m_neighbours = new List<RegionInfo>(); |
89 | 90 | ||
90 | public volatile bool BordersLocked = false; | 91 | private volatile int m_bordersLocked = 0; |
91 | 92 | public bool BordersLocked | |
93 | { | ||
94 | get { return m_bordersLocked == 1; } | ||
95 | set | ||
96 | { | ||
97 | if (value == true) | ||
98 | m_bordersLocked = 1; | ||
99 | else | ||
100 | m_bordersLocked = 0; | ||
101 | } | ||
102 | } | ||
92 | public List<Border> NorthBorders = new List<Border>(); | 103 | public List<Border> NorthBorders = new List<Border>(); |
93 | public List<Border> EastBorders = new List<Border>(); | 104 | public List<Border> EastBorders = new List<Border>(); |
94 | public List<Border> SouthBorders = new List<Border>(); | 105 | public List<Border> SouthBorders = new List<Border>(); |
@@ -397,6 +408,73 @@ namespace OpenSim.Region.Framework.Scenes | |||
397 | 408 | ||
398 | #endregion | 409 | #endregion |
399 | 410 | ||
411 | #region BinaryStats | ||
412 | |||
413 | public class StatLogger | ||
414 | { | ||
415 | public DateTime StartTime; | ||
416 | public string Path; | ||
417 | public System.IO.BinaryWriter Log; | ||
418 | } | ||
419 | static StatLogger m_statLog = null; | ||
420 | static TimeSpan m_statLogPeriod = TimeSpan.FromSeconds(300); | ||
421 | static string m_statsDir = String.Empty; | ||
422 | static Object m_statLockObject = new Object(); | ||
423 | private void LogSimStats(SimStats stats) | ||
424 | { | ||
425 | SimStatsPacket pack = new SimStatsPacket(); | ||
426 | pack.Region = new SimStatsPacket.RegionBlock(); | ||
427 | pack.Region.RegionX = stats.RegionX; | ||
428 | pack.Region.RegionY = stats.RegionY; | ||
429 | pack.Region.RegionFlags = stats.RegionFlags; | ||
430 | pack.Region.ObjectCapacity = stats.ObjectCapacity; | ||
431 | //pack.Region = //stats.RegionBlock; | ||
432 | pack.Stat = stats.StatsBlock; | ||
433 | pack.Header.Reliable = false; | ||
434 | |||
435 | // note that we are inside the reporter lock when called | ||
436 | DateTime now = DateTime.Now; | ||
437 | |||
438 | // hide some time information into the packet | ||
439 | pack.Header.Sequence = (uint)now.Ticks; | ||
440 | |||
441 | lock (m_statLockObject) // m_statLog is shared so make sure there is only executer here | ||
442 | { | ||
443 | try | ||
444 | { | ||
445 | if (m_statLog == null || now > m_statLog.StartTime + m_statLogPeriod) | ||
446 | { | ||
447 | // First log file or time has expired, start writing to a new log file | ||
448 | if (m_statLog != null && m_statLog.Log != null) | ||
449 | { | ||
450 | m_statLog.Log.Close(); | ||
451 | } | ||
452 | m_statLog = new StatLogger(); | ||
453 | m_statLog.StartTime = now; | ||
454 | m_statLog.Path = (m_statsDir.Length > 0 ? m_statsDir + System.IO.Path.DirectorySeparatorChar.ToString() : "") | ||
455 | + String.Format("stats-{0}.log", now.ToString("yyyyMMddHHmmss")); | ||
456 | m_statLog.Log = new BinaryWriter(File.Open(m_statLog.Path, FileMode.Append, FileAccess.Write)); | ||
457 | } | ||
458 | |||
459 | // Write the serialized data to disk | ||
460 | if (m_statLog != null && m_statLog.Log != null) | ||
461 | m_statLog.Log.Write(pack.ToBytes()); | ||
462 | } | ||
463 | catch (Exception ex) | ||
464 | { | ||
465 | m_log.Error("statistics gathering failed: " + ex.Message, ex); | ||
466 | if (m_statLog != null && m_statLog.Log != null) | ||
467 | { | ||
468 | m_statLog.Log.Close(); | ||
469 | } | ||
470 | m_statLog = null; | ||
471 | } | ||
472 | } | ||
473 | return; | ||
474 | } | ||
475 | |||
476 | #endregion | ||
477 | |||
400 | #region Constructors | 478 | #region Constructors |
401 | 479 | ||
402 | public Scene(RegionInfo regInfo, AgentCircuitManager authen, | 480 | public Scene(RegionInfo regInfo, AgentCircuitManager authen, |
@@ -582,6 +660,38 @@ namespace OpenSim.Region.Framework.Scenes | |||
582 | } | 660 | } |
583 | 661 | ||
584 | m_log.Info("[SCENE]: Using the " + m_update_prioritization_scheme + " prioritization scheme"); | 662 | m_log.Info("[SCENE]: Using the " + m_update_prioritization_scheme + " prioritization scheme"); |
663 | |||
664 | #region BinaryStats | ||
665 | |||
666 | try | ||
667 | { | ||
668 | IConfig statConfig = m_config.Configs["Statistics.Binary"]; | ||
669 | if (statConfig.Contains("enabled") && statConfig.GetBoolean("enabled")) | ||
670 | { | ||
671 | if (statConfig.Contains("collect_region_stats")) | ||
672 | { | ||
673 | if (statConfig.GetBoolean("collect_region_stats")) | ||
674 | { | ||
675 | // if enabled, add us to the event. If not enabled, I won't get called | ||
676 | StatsReporter.OnSendStatsResult += LogSimStats; | ||
677 | } | ||
678 | } | ||
679 | if (statConfig.Contains("region_stats_period_seconds")) | ||
680 | { | ||
681 | m_statLogPeriod = TimeSpan.FromSeconds(statConfig.GetInt("region_stats_period_seconds")); | ||
682 | } | ||
683 | if (statConfig.Contains("stats_dir")) | ||
684 | { | ||
685 | m_statsDir = statConfig.GetString("stats_dir"); | ||
686 | } | ||
687 | } | ||
688 | } | ||
689 | catch | ||
690 | { | ||
691 | // if it doesn't work, we don't collect anything | ||
692 | } | ||
693 | |||
694 | #endregion BinaryStats | ||
585 | } | 695 | } |
586 | catch | 696 | catch |
587 | { | 697 | { |
@@ -1043,7 +1153,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
1043 | TimeSpan SinceLastFrame = DateTime.UtcNow - m_lastupdate; | 1153 | TimeSpan SinceLastFrame = DateTime.UtcNow - m_lastupdate; |
1044 | physicsFPS = 0f; | 1154 | physicsFPS = 0f; |
1045 | 1155 | ||
1046 | maintc = maintc = otherMS = Environment.TickCount; | 1156 | maintc = otherMS = Environment.TickCount; |
1047 | int tmpFrameMS = maintc; | 1157 | int tmpFrameMS = maintc; |
1048 | 1158 | ||
1049 | // Increment the frame counter | 1159 | // Increment the frame counter |
@@ -4273,6 +4383,16 @@ namespace OpenSim.Region.Framework.Scenes | |||
4273 | return m_sceneGraph.GetSceneObjectPart(fullID); | 4383 | return m_sceneGraph.GetSceneObjectPart(fullID); |
4274 | } | 4384 | } |
4275 | 4385 | ||
4386 | /// <summary> | ||
4387 | /// Get a scene object group that contains the prim with the given local id | ||
4388 | /// </summary> | ||
4389 | /// <param name="localID"></param> | ||
4390 | /// <returns>null if no scene object group containing that prim is found</returns> | ||
4391 | public SceneObjectGroup GetGroupByPrim(uint localID) | ||
4392 | { | ||
4393 | return m_sceneGraph.GetGroupByPrim(localID); | ||
4394 | } | ||
4395 | |||
4276 | public bool TryGetAvatar(UUID avatarId, out ScenePresence avatar) | 4396 | public bool TryGetAvatar(UUID avatarId, out ScenePresence avatar) |
4277 | { | 4397 | { |
4278 | return m_sceneGraph.TryGetAvatar(avatarId, out avatar); | 4398 | return m_sceneGraph.TryGetAvatar(avatarId, out avatar); |
diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs index 0b752c9..bcc9b37 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs | |||
@@ -204,6 +204,14 @@ namespace OpenSim.Region.Framework.Scenes | |||
204 | get { return m_parts.Count; } | 204 | get { return m_parts.Count; } |
205 | } | 205 | } |
206 | 206 | ||
207 | protected Quaternion m_rotation = Quaternion.Identity; | ||
208 | |||
209 | public virtual Quaternion Rotation | ||
210 | { | ||
211 | get { return m_rotation; } | ||
212 | set { m_rotation = value; } | ||
213 | } | ||
214 | |||
207 | public Quaternion GroupRotation | 215 | public Quaternion GroupRotation |
208 | { | 216 | { |
209 | get { return m_rootPart.RotationOffset; } | 217 | get { return m_rootPart.RotationOffset; } |
@@ -1959,12 +1967,12 @@ namespace OpenSim.Region.Framework.Scenes | |||
1959 | /// Note: this may not be cused by opensim (it probably should) but it's used by | 1967 | /// Note: this may not be cused by opensim (it probably should) but it's used by |
1960 | /// external modules. | 1968 | /// external modules. |
1961 | /// </summary> | 1969 | /// </summary> |
1962 | public void SendGroupRootUpdate() | 1970 | public void SendGroupRootTerseUpdate() |
1963 | { | 1971 | { |
1964 | if (IsDeleted) | 1972 | if (IsDeleted) |
1965 | return; | 1973 | return; |
1966 | 1974 | ||
1967 | RootPart.SendFullUpdateToAllClients(); | 1975 | RootPart.SendTerseUpdateToAllClients(); |
1968 | } | 1976 | } |
1969 | 1977 | ||
1970 | public void QueueForUpdateCheck() | 1978 | public void QueueForUpdateCheck() |
@@ -2946,12 +2954,13 @@ namespace OpenSim.Region.Framework.Scenes | |||
2946 | /// <param name="rot"></param> | 2954 | /// <param name="rot"></param> |
2947 | public void UpdateGroupRotationR(Quaternion rot) | 2955 | public void UpdateGroupRotationR(Quaternion rot) |
2948 | { | 2956 | { |
2949 | |||
2950 | m_rootPart.UpdateRotation(rot); | 2957 | m_rootPart.UpdateRotation(rot); |
2951 | if (m_rootPart.PhysActor != null) | 2958 | |
2959 | PhysicsActor actor = m_rootPart.PhysActor; | ||
2960 | if (actor != null) | ||
2952 | { | 2961 | { |
2953 | m_rootPart.PhysActor.Orientation = m_rootPart.RotationOffset; | 2962 | actor.Orientation = m_rootPart.RotationOffset; |
2954 | m_scene.PhysicsScene.AddPhysicsActorTaint(m_rootPart.PhysActor); | 2963 | m_scene.PhysicsScene.AddPhysicsActorTaint(actor); |
2955 | } | 2964 | } |
2956 | 2965 | ||
2957 | HasGroupChanged = true; | 2966 | HasGroupChanged = true; |
@@ -2966,11 +2975,14 @@ namespace OpenSim.Region.Framework.Scenes | |||
2966 | public void UpdateGroupRotationPR(Vector3 pos, Quaternion rot) | 2975 | public void UpdateGroupRotationPR(Vector3 pos, Quaternion rot) |
2967 | { | 2976 | { |
2968 | m_rootPart.UpdateRotation(rot); | 2977 | m_rootPart.UpdateRotation(rot); |
2969 | if (m_rootPart.PhysActor != null) | 2978 | |
2979 | PhysicsActor actor = m_rootPart.PhysActor; | ||
2980 | if (actor != null) | ||
2970 | { | 2981 | { |
2971 | m_rootPart.PhysActor.Orientation = m_rootPart.RotationOffset; | 2982 | actor.Orientation = m_rootPart.RotationOffset; |
2972 | m_scene.PhysicsScene.AddPhysicsActorTaint(m_rootPart.PhysActor); | 2983 | m_scene.PhysicsScene.AddPhysicsActorTaint(actor); |
2973 | } | 2984 | } |
2985 | |||
2974 | AbsolutePosition = pos; | 2986 | AbsolutePosition = pos; |
2975 | 2987 | ||
2976 | HasGroupChanged = true; | 2988 | HasGroupChanged = true; |
diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs index 2bc7f66..73d0984 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectPart.cs | |||
@@ -243,7 +243,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
243 | protected SceneObjectGroup m_parentGroup; | 243 | protected SceneObjectGroup m_parentGroup; |
244 | protected byte[] m_particleSystem = Utils.EmptyBytes; | 244 | protected byte[] m_particleSystem = Utils.EmptyBytes; |
245 | protected ulong m_regionHandle; | 245 | protected ulong m_regionHandle; |
246 | protected Quaternion m_rotationOffset; | 246 | protected Quaternion m_rotationOffset = Quaternion.Identity; |
247 | protected PrimitiveBaseShape m_shape; | 247 | protected PrimitiveBaseShape m_shape; |
248 | protected UUID m_uuid; | 248 | protected UUID m_uuid; |
249 | protected Vector3 m_velocity; | 249 | protected Vector3 m_velocity; |
@@ -3758,14 +3758,12 @@ namespace OpenSim.Region.Framework.Scenes | |||
3758 | 3758 | ||
3759 | Vector3 lPos = OffsetPosition; | 3759 | Vector3 lPos = OffsetPosition; |
3760 | 3760 | ||
3761 | byte state = Shape.State; | ||
3762 | if (IsAttachment) | 3761 | if (IsAttachment) |
3763 | { | 3762 | { |
3764 | if (ParentGroup.RootPart != this) | 3763 | if (ParentGroup.RootPart != this) |
3765 | return; | 3764 | return; |
3766 | 3765 | ||
3767 | lPos = ParentGroup.RootPart.AttachedPos; | 3766 | lPos = ParentGroup.RootPart.AttachedPos; |
3768 | state = (byte)AttachmentPoint; | ||
3769 | } | 3767 | } |
3770 | else | 3768 | else |
3771 | { | 3769 | { |
@@ -3778,7 +3776,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
3778 | remoteClient.SendPrimTerseUpdate(new SendPrimitiveTerseData(m_regionHandle, | 3776 | remoteClient.SendPrimTerseUpdate(new SendPrimitiveTerseData(m_regionHandle, |
3779 | m_parentGroup.GetTimeDilation(), LocalId, lPos, | 3777 | m_parentGroup.GetTimeDilation(), LocalId, lPos, |
3780 | RotationOffset, Velocity, Acceleration, | 3778 | RotationOffset, Velocity, Acceleration, |
3781 | AngularVelocity, state, FromItemID, | 3779 | AngularVelocity, FromItemID, |
3782 | OwnerID, (int)AttachmentPoint, null, ParentGroup.GetUpdatePriority(remoteClient))); | 3780 | OwnerID, (int)AttachmentPoint, null, ParentGroup.GetUpdatePriority(remoteClient))); |
3783 | } | 3781 | } |
3784 | 3782 | ||
diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 6c0d9f2..08c144a 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs | |||
@@ -76,7 +76,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
76 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 76 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
77 | 77 | ||
78 | private static readonly byte[] BAKE_INDICES = new byte[] { 8, 9, 10, 11, 19, 20 }; | 78 | private static readonly byte[] BAKE_INDICES = new byte[] { 8, 9, 10, 11, 19, 20 }; |
79 | private static readonly byte[] DEFAULT_TEXTURE = AvatarAppearance.GetDefaultTexture().GetBytes(); | 79 | // private static readonly byte[] DEFAULT_TEXTURE = AvatarAppearance.GetDefaultTexture().GetBytes(); |
80 | private static readonly Array DIR_CONTROL_FLAGS = Enum.GetValues(typeof(Dir_ControlFlags)); | 80 | private static readonly Array DIR_CONTROL_FLAGS = Enum.GetValues(typeof(Dir_ControlFlags)); |
81 | private static readonly Vector3 HEAD_ADJUSTMENT = new Vector3(0f, 0f, 0.3f); | 81 | private static readonly Vector3 HEAD_ADJUSTMENT = new Vector3(0f, 0f, 0.3f); |
82 | /// <summary> | 82 | /// <summary> |
@@ -181,7 +181,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
181 | private byte m_state; | 181 | private byte m_state; |
182 | 182 | ||
183 | //Reuse the Vector3 instead of creating a new one on the UpdateMovement method | 183 | //Reuse the Vector3 instead of creating a new one on the UpdateMovement method |
184 | private Vector3 movementvector; | 184 | // private Vector3 movementvector; |
185 | 185 | ||
186 | private bool m_autopilotMoving; | 186 | private bool m_autopilotMoving; |
187 | private Vector3 m_autoPilotTarget; | 187 | private Vector3 m_autoPilotTarget; |
@@ -481,6 +481,12 @@ namespace OpenSim.Region.Framework.Scenes | |||
481 | } | 481 | } |
482 | } | 482 | } |
483 | 483 | ||
484 | public Quaternion Rotation | ||
485 | { | ||
486 | get { return m_bodyRot; } | ||
487 | set { m_bodyRot = value; } | ||
488 | } | ||
489 | |||
484 | /// <summary> | 490 | /// <summary> |
485 | /// If this is true, agent doesn't have a representation in this scene. | 491 | /// If this is true, agent doesn't have a representation in this scene. |
486 | /// this is an agent 'looking into' this scene from a nearby scene(region) | 492 | /// this is an agent 'looking into' this scene from a nearby scene(region) |
@@ -1912,14 +1918,10 @@ namespace OpenSim.Region.Framework.Scenes | |||
1912 | } | 1918 | } |
1913 | 1919 | ||
1914 | 1920 | ||
1915 | AssetBase Animasset = new AssetBase(); | 1921 | AssetBase Animasset = new AssetBase(UUID.Random(), "Random Animation", (sbyte)AssetType.Animation); |
1916 | Animasset.Data = anim.ToBytes(); | 1922 | Animasset.Data = anim.ToBytes(); |
1917 | Animasset.Temporary = true; | 1923 | Animasset.Temporary = true; |
1918 | Animasset.Local = true; | 1924 | Animasset.Local = true; |
1919 | Animasset.FullID = UUID.Random(); | ||
1920 | Animasset.ID = Animasset.FullID.ToString(); | ||
1921 | Animasset.Name = "Random Animation"; | ||
1922 | Animasset.Type = (sbyte)AssetType.Animation; | ||
1923 | Animasset.Description = "dance"; | 1925 | Animasset.Description = "dance"; |
1924 | //BinBVHAnimation bbvhanim = new BinBVHAnimation(Animasset.Data); | 1926 | //BinBVHAnimation bbvhanim = new BinBVHAnimation(Animasset.Data); |
1925 | 1927 | ||
@@ -2068,7 +2070,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
2068 | if (heldDown) { move.Z -= 1; } | 2070 | if (heldDown) { move.Z -= 1; } |
2069 | 2071 | ||
2070 | // Is the avatar trying to move? | 2072 | // Is the avatar trying to move? |
2071 | bool moving = (move != Vector3.Zero); | 2073 | // bool moving = (move != Vector3.Zero); |
2072 | bool jumping = m_animTickJump != 0; | 2074 | bool jumping = m_animTickJump != 0; |
2073 | 2075 | ||
2074 | #endregion Inputs | 2076 | #endregion Inputs |
@@ -2256,7 +2258,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
2256 | 2258 | ||
2257 | m_perfMonMS = Environment.TickCount; | 2259 | m_perfMonMS = Environment.TickCount; |
2258 | 2260 | ||
2259 | m_rotation = rotation; | 2261 | Rotation = rotation; |
2260 | Vector3 direc = vec * rotation; | 2262 | Vector3 direc = vec * rotation; |
2261 | direc.Normalize(); | 2263 | direc.Normalize(); |
2262 | 2264 | ||
@@ -2320,7 +2322,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
2320 | 2322 | ||
2321 | if (m_isChildAgent == false) | 2323 | if (m_isChildAgent == false) |
2322 | { | 2324 | { |
2323 | PhysicsActor actor = m_physicsActor; | 2325 | // PhysicsActor actor = m_physicsActor; |
2324 | 2326 | ||
2325 | // NOTE: Velocity is not the same as m_velocity. Velocity will attempt to | 2327 | // NOTE: Velocity is not the same as m_velocity. Velocity will attempt to |
2326 | // grab the latest PhysicsActor velocity, whereas m_velocity is often | 2328 | // grab the latest PhysicsActor velocity, whereas m_velocity is often |
@@ -3256,7 +3258,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
3256 | Vector3 force = m_forceToApply.Value; | 3258 | Vector3 force = m_forceToApply.Value; |
3257 | 3259 | ||
3258 | m_updateflag = true; | 3260 | m_updateflag = true; |
3259 | movementvector = force; | 3261 | // movementvector = force; |
3260 | Velocity = force; | 3262 | Velocity = force; |
3261 | 3263 | ||
3262 | m_forceToApply = null; | 3264 | m_forceToApply = null; |
@@ -3905,7 +3907,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
3905 | } | 3907 | } |
3906 | else | 3908 | else |
3907 | { | 3909 | { |
3908 | group = Scene.SceneGraph.GetGroupByPrim(data.localID); | 3910 | group = Scene.GetGroupByPrim(data.localID); |
3909 | if (group != null) | 3911 | if (group != null) |
3910 | return GetSOGUpdatePriority(group); | 3912 | return GetSOGUpdatePriority(group); |
3911 | } | 3913 | } |
diff --git a/OpenSim/Region/Framework/Scenes/Tests/UuidGathererTests.cs b/OpenSim/Region/Framework/Scenes/Tests/UuidGathererTests.cs new file mode 100644 index 0000000..b68a044 --- /dev/null +++ b/OpenSim/Region/Framework/Scenes/Tests/UuidGathererTests.cs | |||
@@ -0,0 +1,88 @@ | |||
1 | /* | ||
2 | * Copyright (c) Contributors, http://opensimulator.org/ | ||
3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. | ||
4 | * | ||
5 | * Redistribution and use in source and binary forms, with or without | ||
6 | * modification, are permitted provided that the following conditions are met: | ||
7 | * * Redistributions of source code must retain the above copyright | ||
8 | * notice, this list of conditions and the following disclaimer. | ||
9 | * * Redistributions in binary form must reproduce the above copyright | ||
10 | * notice, this list of conditions and the following disclaimer in the | ||
11 | * documentation and/or other materials provided with the distribution. | ||
12 | * * Neither the name of the OpenSimulator Project nor the | ||
13 | * names of its contributors may be used to endorse or promote products | ||
14 | * derived from this software without specific prior written permission. | ||
15 | * | ||
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY | ||
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | ||
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
26 | */ | ||
27 | |||
28 | using System.Collections.Generic; | ||
29 | using System.Text; | ||
30 | using NUnit.Framework; | ||
31 | using NUnit.Framework.SyntaxHelpers; | ||
32 | using OpenMetaverse; | ||
33 | using OpenSim.Framework; | ||
34 | using OpenSim.Region.Framework.Scenes; | ||
35 | using OpenSim.Services.Interfaces; | ||
36 | using OpenSim.Tests.Common; | ||
37 | using OpenSim.Tests.Common.Setup; | ||
38 | using OpenSim.Tests.Common.Mock; | ||
39 | |||
40 | namespace OpenSim.Region.Framework.Scenes.Tests | ||
41 | { | ||
42 | [TestFixture] | ||
43 | public class UuidGathererTests | ||
44 | { | ||
45 | protected IAssetService m_assetService; | ||
46 | protected UuidGatherer m_uuidGatherer; | ||
47 | |||
48 | [SetUp] | ||
49 | public void Init() | ||
50 | { | ||
51 | m_assetService = new MockAssetService(); | ||
52 | m_uuidGatherer = new UuidGatherer(m_assetService); | ||
53 | } | ||
54 | |||
55 | [Test] | ||
56 | public void TestCorruptAsset() | ||
57 | { | ||
58 | TestHelper.InMethod(); | ||
59 | |||
60 | UUID corruptAssetUuid = UUID.Parse("00000000-0000-0000-0000-000000000666"); | ||
61 | AssetBase corruptAsset = AssetHelpers.CreateAsset(corruptAssetUuid, "CORRUPT ASSET"); | ||
62 | m_assetService.Store(corruptAsset); | ||
63 | |||
64 | IDictionary<UUID, int> foundAssetUuids = new Dictionary<UUID, int>(); | ||
65 | m_uuidGatherer.GatherAssetUuids(corruptAssetUuid, AssetType.Object, foundAssetUuids); | ||
66 | |||
67 | // We count the uuid as gathered even if the asset itself is corrupt. | ||
68 | Assert.That(foundAssetUuids.Count, Is.EqualTo(1)); | ||
69 | } | ||
70 | |||
71 | /// <summary> | ||
72 | /// Test requests made for non-existent assets while we're gathering | ||
73 | /// </summary> | ||
74 | [Test] | ||
75 | public void TestMissingAsset() | ||
76 | { | ||
77 | TestHelper.InMethod(); | ||
78 | |||
79 | UUID missingAssetUuid = UUID.Parse("00000000-0000-0000-0000-000000000666"); | ||
80 | IDictionary<UUID, int> foundAssetUuids = new Dictionary<UUID, int>(); | ||
81 | |||
82 | m_uuidGatherer.GatherAssetUuids(missingAssetUuid, AssetType.Object, foundAssetUuids); | ||
83 | |||
84 | // We count the uuid as gathered even if the asset itself is missing. | ||
85 | Assert.That(foundAssetUuids.Count, Is.EqualTo(1)); | ||
86 | } | ||
87 | } | ||
88 | } | ||
diff --git a/OpenSim/Region/Framework/Scenes/UuidGatherer.cs b/OpenSim/Region/Framework/Scenes/UuidGatherer.cs index 525a93a..930af81 100644 --- a/OpenSim/Region/Framework/Scenes/UuidGatherer.cs +++ b/OpenSim/Region/Framework/Scenes/UuidGatherer.cs | |||
@@ -273,7 +273,9 @@ namespace OpenSim.Region.Framework.Scenes | |||
273 | { | 273 | { |
274 | string xml = Utils.BytesToString(objectAsset.Data); | 274 | string xml = Utils.BytesToString(objectAsset.Data); |
275 | SceneObjectGroup sog = SceneObjectSerializer.FromOriginalXmlFormat(xml); | 275 | SceneObjectGroup sog = SceneObjectSerializer.FromOriginalXmlFormat(xml); |
276 | GatherAssetUuids(sog, assetUuids); | 276 | |
277 | if (null != sog) | ||
278 | GatherAssetUuids(sog, assetUuids); | ||
277 | } | 279 | } |
278 | } | 280 | } |
279 | } | 281 | } |
diff --git a/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/IRCStackModule.cs b/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/IRCStackModule.cs index 4c2a4b9..cfe1278 100644 --- a/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/IRCStackModule.cs +++ b/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/IRCStackModule.cs | |||
@@ -40,7 +40,7 @@ namespace OpenSim.Region.OptionalModules.Agent.InternetRelayClientView | |||
40 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 40 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
41 | 41 | ||
42 | private IRCServer m_server; | 42 | private IRCServer m_server; |
43 | private Scene m_scene; | 43 | // private Scene m_scene; |
44 | 44 | ||
45 | #region Implementation of IRegionModule | 45 | #region Implementation of IRegionModule |
46 | 46 | ||
@@ -50,7 +50,7 @@ namespace OpenSim.Region.OptionalModules.Agent.InternetRelayClientView | |||
50 | source.Configs["IRCd"].GetBoolean("Enabled",false)) | 50 | source.Configs["IRCd"].GetBoolean("Enabled",false)) |
51 | { | 51 | { |
52 | int portNo = source.Configs["IRCd"].GetInt("Port",6666); | 52 | int portNo = source.Configs["IRCd"].GetInt("Port",6666); |
53 | m_scene = scene; | 53 | // m_scene = scene; |
54 | m_server = new IRCServer(IPAddress.Parse("0.0.0.0"), portNo, scene); | 54 | m_server = new IRCServer(IPAddress.Parse("0.0.0.0"), portNo, scene); |
55 | m_server.OnNewIRCClient += m_server_OnNewIRCClient; | 55 | m_server.OnNewIRCClient += m_server_OnNewIRCClient; |
56 | } | 56 | } |
diff --git a/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/Server/IRCClientView.cs b/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/Server/IRCClientView.cs index 4b0d01a..6c3e7eb 100644 --- a/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/Server/IRCClientView.cs +++ b/OpenSim/Region/OptionalModules/Agent/InternetRelayClientView/Server/IRCClientView.cs | |||
@@ -758,6 +758,7 @@ namespace OpenSim.Region.OptionalModules.Agent.InternetRelayClientView.Server | |||
758 | public event FriendActionDelegate OnApproveFriendRequest; | 758 | public event FriendActionDelegate OnApproveFriendRequest; |
759 | public event FriendActionDelegate OnDenyFriendRequest; | 759 | public event FriendActionDelegate OnDenyFriendRequest; |
760 | public event FriendshipTermination OnTerminateFriendship; | 760 | public event FriendshipTermination OnTerminateFriendship; |
761 | public event GrantUserFriendRights OnGrantUserRights; | ||
761 | public event MoneyTransferRequest OnMoneyTransferRequest; | 762 | public event MoneyTransferRequest OnMoneyTransferRequest; |
762 | public event EconomyDataRequest OnEconomyDataRequest; | 763 | public event EconomyDataRequest OnEconomyDataRequest; |
763 | public event MoneyBalanceRequest OnMoneyBalanceRequest; | 764 | public event MoneyBalanceRequest OnMoneyBalanceRequest; |
@@ -1055,7 +1056,7 @@ namespace OpenSim.Region.OptionalModules.Agent.InternetRelayClientView.Server | |||
1055 | 1056 | ||
1056 | } | 1057 | } |
1057 | 1058 | ||
1058 | public void SendInventoryFolderDetails(UUID ownerID, UUID folderID, List<InventoryItemBase> items, List<InventoryFolderBase> folders, bool fetchFolders, bool fetchItems) | 1059 | public void SendInventoryFolderDetails(UUID ownerID, UUID folderID, List<InventoryItemBase> items, List<InventoryFolderBase> folders, int version, bool fetchFolders, bool fetchItems) |
1059 | { | 1060 | { |
1060 | 1061 | ||
1061 | } | 1062 | } |
diff --git a/OpenSim/Region/OptionalModules/Scripting/Minimodule/Graphics.cs b/OpenSim/Region/OptionalModules/Scripting/Minimodule/Graphics.cs index 963cab5..8ea7ad3 100644 --- a/OpenSim/Region/OptionalModules/Scripting/Minimodule/Graphics.cs +++ b/OpenSim/Region/OptionalModules/Scripting/Minimodule/Graphics.cs | |||
@@ -49,11 +49,8 @@ namespace OpenSim.Region.OptionalModules.Scripting.Minimodule | |||
49 | 49 | ||
50 | public UUID SaveBitmap(Bitmap data, bool lossless, bool temporary) | 50 | public UUID SaveBitmap(Bitmap data, bool lossless, bool temporary) |
51 | { | 51 | { |
52 | AssetBase asset = new AssetBase(); | 52 | AssetBase asset = new AssetBase(UUID.Random(), "MRMDynamicImage", (sbyte)AssetType.Texture); |
53 | asset.FullID = UUID.Random(); | ||
54 | asset.Data = OpenJPEG.EncodeFromImage(data, lossless); | 53 | asset.Data = OpenJPEG.EncodeFromImage(data, lossless); |
55 | asset.Name = "MRMDynamicImage"; | ||
56 | asset.Type = 0; | ||
57 | asset.Description = "MRM Image"; | 54 | asset.Description = "MRM Image"; |
58 | asset.Local = false; | 55 | asset.Local = false; |
59 | asset.Temporary = temporary; | 56 | asset.Temporary = temporary; |
diff --git a/OpenSim/Region/OptionalModules/Scripting/ScriptModuleComms/ScriptModuleCommsModule.cs b/OpenSim/Region/OptionalModules/Scripting/ScriptModuleComms/ScriptModuleCommsModule.cs new file mode 100644 index 0000000..44c9ada --- /dev/null +++ b/OpenSim/Region/OptionalModules/Scripting/ScriptModuleComms/ScriptModuleCommsModule.cs | |||
@@ -0,0 +1,105 @@ | |||
1 | /* | ||
2 | * Copyright (c) Contributors, http://opensimulator.org/ | ||
3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. | ||
4 | * | ||
5 | * Redistribution and use in source and binary forms, with or without | ||
6 | * modification, are permitted provided that the following conditions are met: | ||
7 | * * Redistributions of source code must retain the above copyright | ||
8 | * notice, this list of conditions and the following disclaimer. | ||
9 | * * Redistributions in binary form must reproduce the above copyright | ||
10 | * notice, this list of conditions and the following disclaimer in the | ||
11 | * documentation and/or other materials provided with the distribution. | ||
12 | * * Neither the name of the OpenSimulator Project nor the | ||
13 | * names of its contributors may be used to endorse or promote products | ||
14 | * derived from this software without specific prior written permission. | ||
15 | * | ||
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY | ||
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | ||
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
26 | */ | ||
27 | |||
28 | using System; | ||
29 | using System.Reflection; | ||
30 | using Nini.Config; | ||
31 | using log4net; | ||
32 | using OpenSim.Framework; | ||
33 | using OpenSim.Region.Framework.Interfaces; | ||
34 | using OpenSim.Region.Framework.Scenes; | ||
35 | using Mono.Addins; | ||
36 | using OpenMetaverse; | ||
37 | |||
38 | namespace OpenSim.Region.OptionalModules.Scripting.ScriptModuleComms | ||
39 | { | ||
40 | [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule", Id = "ScriptModuleCommsModule")] | ||
41 | class ScriptModuleCommsModule : INonSharedRegionModule, IScriptModuleComms | ||
42 | { | ||
43 | private static readonly ILog m_log = | ||
44 | LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | ||
45 | |||
46 | private IScriptModule m_scriptModule = null; | ||
47 | |||
48 | public event ScriptCommand OnScriptCommand; | ||
49 | |||
50 | public void Initialise(IConfigSource config) | ||
51 | { | ||
52 | } | ||
53 | |||
54 | public void AddRegion(Scene scene) | ||
55 | { | ||
56 | scene.RegisterModuleInterface<IScriptModuleComms>(this); | ||
57 | } | ||
58 | |||
59 | public void RemoveRegion(Scene scene) | ||
60 | { | ||
61 | } | ||
62 | |||
63 | public void RegionLoaded(Scene scene) | ||
64 | { | ||
65 | m_scriptModule = scene.RequestModuleInterface<IScriptModule>(); | ||
66 | |||
67 | if (m_scriptModule != null) | ||
68 | m_log.Info("[MODULE COMMANDS]: Script engine found, module active"); | ||
69 | } | ||
70 | |||
71 | public string Name | ||
72 | { | ||
73 | get { return "ScriptModuleCommsModule"; } | ||
74 | } | ||
75 | |||
76 | public Type ReplaceableInterface | ||
77 | { | ||
78 | get { return null; } | ||
79 | } | ||
80 | |||
81 | public void Close() | ||
82 | { | ||
83 | } | ||
84 | |||
85 | public void RaiseEvent(UUID script, string id, string module, string command, string k) | ||
86 | { | ||
87 | ScriptCommand c = OnScriptCommand; | ||
88 | |||
89 | if (c == null) | ||
90 | return; | ||
91 | |||
92 | c(script, id, module, command, k); | ||
93 | } | ||
94 | |||
95 | public void DispatchReply(UUID script, int code, string text, string k) | ||
96 | { | ||
97 | if (m_scriptModule == null) | ||
98 | return; | ||
99 | |||
100 | Object[] args = new Object[] {-1, code, text, k}; | ||
101 | |||
102 | m_scriptModule.PostScriptEvent(script, "link_message", args); | ||
103 | } | ||
104 | } | ||
105 | } | ||
diff --git a/OpenSim/Region/OptionalModules/World/NPC/NPCAvatar.cs b/OpenSim/Region/OptionalModules/World/NPC/NPCAvatar.cs index f7cadaa..cf36d08 100644 --- a/OpenSim/Region/OptionalModules/World/NPC/NPCAvatar.cs +++ b/OpenSim/Region/OptionalModules/World/NPC/NPCAvatar.cs | |||
@@ -283,6 +283,7 @@ namespace OpenSim.Region.OptionalModules.World.NPC | |||
283 | public event FriendActionDelegate OnApproveFriendRequest; | 283 | public event FriendActionDelegate OnApproveFriendRequest; |
284 | public event FriendActionDelegate OnDenyFriendRequest; | 284 | public event FriendActionDelegate OnDenyFriendRequest; |
285 | public event FriendshipTermination OnTerminateFriendship; | 285 | public event FriendshipTermination OnTerminateFriendship; |
286 | public event GrantUserFriendRights OnGrantUserRights; | ||
286 | 287 | ||
287 | public event EconomyDataRequest OnEconomyDataRequest; | 288 | public event EconomyDataRequest OnEconomyDataRequest; |
288 | public event MoneyBalanceRequest OnMoneyBalanceRequest; | 289 | public event MoneyBalanceRequest OnMoneyBalanceRequest; |
@@ -627,6 +628,7 @@ namespace OpenSim.Region.OptionalModules.World.NPC | |||
627 | public virtual void SendInventoryFolderDetails(UUID ownerID, UUID folderID, | 628 | public virtual void SendInventoryFolderDetails(UUID ownerID, UUID folderID, |
628 | List<InventoryItemBase> items, | 629 | List<InventoryItemBase> items, |
629 | List<InventoryFolderBase> folders, | 630 | List<InventoryFolderBase> folders, |
631 | int version, | ||
630 | bool fetchFolders, | 632 | bool fetchFolders, |
631 | bool fetchItems) | 633 | bool fetchItems) |
632 | { | 634 | { |
diff --git a/OpenSim/Region/Physics/BulletXPlugin/BulletXPlugin.cs b/OpenSim/Region/Physics/BulletXPlugin/BulletXPlugin.cs index cbe73bb..1e94ee2 100644 --- a/OpenSim/Region/Physics/BulletXPlugin/BulletXPlugin.cs +++ b/OpenSim/Region/Physics/BulletXPlugin/BulletXPlugin.cs | |||
@@ -347,6 +347,7 @@ namespace OpenSim.Region.Physics.BulletXPlugin | |||
347 | { | 347 | { |
348 | indexBase = mesh.getIndexListAsInt(); | 348 | indexBase = mesh.getIndexListAsInt(); |
349 | vertexBase = new Vector3[iVertexCount]; | 349 | vertexBase = new Vector3[iVertexCount]; |
350 | |||
350 | for (int i = 0; i < iVertexCount; i++) | 351 | for (int i = 0; i < iVertexCount; i++) |
351 | { | 352 | { |
352 | OpenMetaverse.Vector3 v = mesh.getVertexList()[i]; | 353 | OpenMetaverse.Vector3 v = mesh.getVertexList()[i]; |
@@ -355,6 +356,7 @@ namespace OpenSim.Region.Physics.BulletXPlugin | |||
355 | else | 356 | else |
356 | vertexBase[i] = Vector3.Zero; | 357 | vertexBase[i] = Vector3.Zero; |
357 | } | 358 | } |
359 | |||
358 | for (int ix = 0; ix < iIndexCount; ix += 3) | 360 | for (int ix = 0; ix < iIndexCount; ix += 3) |
359 | { | 361 | { |
360 | int ia = indexBase[ix + 0]; | 362 | int ia = indexBase[ix + 0]; |
diff --git a/OpenSim/Region/Physics/Meshing/PrimMesher.cs b/OpenSim/Region/Physics/Meshing/PrimMesher.cs index 47ce615..2a213c3 100644 --- a/OpenSim/Region/Physics/Meshing/PrimMesher.cs +++ b/OpenSim/Region/Physics/Meshing/PrimMesher.cs | |||
@@ -67,11 +67,6 @@ namespace PrimMesher | |||
67 | Normalize(); | 67 | Normalize(); |
68 | } | 68 | } |
69 | 69 | ||
70 | public Quat Identity() | ||
71 | { | ||
72 | return new Quat(0.0f, 0.0f, 0.0f, 1.0f); | ||
73 | } | ||
74 | |||
75 | public float Length() | 70 | public float Length() |
76 | { | 71 | { |
77 | return (float)Math.Sqrt(X * X + Y * Y + Z * Z + W * W); | 72 | return (float)Math.Sqrt(X * X + Y * Y + Z * Z + W * W); |
@@ -660,7 +655,7 @@ namespace PrimMesher | |||
660 | this.faceNumbers = new List<int>(); | 655 | this.faceNumbers = new List<int>(); |
661 | 656 | ||
662 | Coord center = new Coord(0.0f, 0.0f, 0.0f); | 657 | Coord center = new Coord(0.0f, 0.0f, 0.0f); |
663 | bool hasCenter = false; | 658 | //bool hasCenter = false; |
664 | 659 | ||
665 | List<Coord> hollowCoords = new List<Coord>(); | 660 | List<Coord> hollowCoords = new List<Coord>(); |
666 | List<Coord> hollowNormals = new List<Coord>(); | 661 | List<Coord> hollowNormals = new List<Coord>(); |
@@ -727,7 +722,7 @@ namespace PrimMesher | |||
727 | else if (!simpleFace) | 722 | else if (!simpleFace) |
728 | { | 723 | { |
729 | this.coords.Add(center); | 724 | this.coords.Add(center); |
730 | hasCenter = true; | 725 | //hasCenter = true; |
731 | if (this.calcVertexNormals) | 726 | if (this.calcVertexNormals) |
732 | this.vertexNormals.Add(new Coord(0.0f, 0.0f, 1.0f)); | 727 | this.vertexNormals.Add(new Coord(0.0f, 0.0f, 1.0f)); |
733 | this.us.Add(0.0f); | 728 | this.us.Add(0.0f); |
@@ -1353,7 +1348,7 @@ namespace PrimMesher | |||
1353 | float stepSize = twoPi / this.stepsPerRevolution; | 1348 | float stepSize = twoPi / this.stepsPerRevolution; |
1354 | 1349 | ||
1355 | int step = (int)(startAngle / stepSize); | 1350 | int step = (int)(startAngle / stepSize); |
1356 | int firstStep = step; | 1351 | // int firstStep = step; |
1357 | float angle = startAngle; | 1352 | float angle = startAngle; |
1358 | 1353 | ||
1359 | bool done = false; | 1354 | bool done = false; |
@@ -1541,7 +1536,7 @@ namespace PrimMesher | |||
1541 | } | 1536 | } |
1542 | 1537 | ||
1543 | /// <summary> | 1538 | /// <summary> |
1544 | /// Extrudes a profile along a straight line path. Used for prim types box, cylinder, and prism. | 1539 | /// Extrudes a profile along a path. |
1545 | /// </summary> | 1540 | /// </summary> |
1546 | public void Extrude(PathType pathType) | 1541 | public void Extrude(PathType pathType) |
1547 | { | 1542 | { |
@@ -1557,7 +1552,6 @@ namespace PrimMesher | |||
1557 | if (this.calcVertexNormals) | 1552 | if (this.calcVertexNormals) |
1558 | this.normals = new List<Coord>(); | 1553 | this.normals = new List<Coord>(); |
1559 | 1554 | ||
1560 | //int step = 0; | ||
1561 | int steps = 1; | 1555 | int steps = 1; |
1562 | 1556 | ||
1563 | float length = this.pathCutEnd - this.pathCutBegin; | 1557 | float length = this.pathCutEnd - this.pathCutBegin; |
@@ -1579,20 +1573,6 @@ namespace PrimMesher | |||
1579 | if (twistTotalAbs > 0.01f) | 1573 | if (twistTotalAbs > 0.01f) |
1580 | steps += (int)(twistTotalAbs * 3.66); // dahlia's magic number | 1574 | steps += (int)(twistTotalAbs * 3.66); // dahlia's magic number |
1581 | 1575 | ||
1582 | //float start = -0.5f; | ||
1583 | //float stepSize = length / (float)steps; | ||
1584 | //float percentOfPathMultiplier = stepSize; | ||
1585 | //float xProfileScale = 1.0f; | ||
1586 | //float yProfileScale = 1.0f; | ||
1587 | //float xOffset = 0.0f; | ||
1588 | //float yOffset = 0.0f; | ||
1589 | //float zOffset = start; | ||
1590 | //float xOffsetStepIncrement = this.topShearX / steps; | ||
1591 | //float yOffsetStepIncrement = this.topShearY / steps; | ||
1592 | |||
1593 | //float percentOfPath = this.pathCutBegin; | ||
1594 | //zOffset += percentOfPath; | ||
1595 | |||
1596 | float hollow = this.hollow; | 1576 | float hollow = this.hollow; |
1597 | 1577 | ||
1598 | // sanity checks | 1578 | // sanity checks |
@@ -1662,7 +1642,6 @@ namespace PrimMesher | |||
1662 | cut2Vert = hasHollow ? profile.numOuterVerts - 1 : profile.numOuterVerts; | 1642 | cut2Vert = hasHollow ? profile.numOuterVerts - 1 : profile.numOuterVerts; |
1663 | } | 1643 | } |
1664 | 1644 | ||
1665 | |||
1666 | if (initialProfileRot != 0.0f) | 1645 | if (initialProfileRot != 0.0f) |
1667 | { | 1646 | { |
1668 | profile.AddRot(new Quat(new Coord(0.0f, 0.0f, 1.0f), initialProfileRot)); | 1647 | profile.AddRot(new Quat(new Coord(0.0f, 0.0f, 1.0f), initialProfileRot)); |
@@ -1693,24 +1672,6 @@ namespace PrimMesher | |||
1693 | path.stepsPerRevolution = stepsPerRevolution; | 1672 | path.stepsPerRevolution = stepsPerRevolution; |
1694 | 1673 | ||
1695 | path.Create(pathType, steps); | 1674 | path.Create(pathType, steps); |
1696 | /* | ||
1697 | public int twistBegin = 0; | ||
1698 | public int twistEnd = 0; | ||
1699 | public float topShearX = 0.0f; | ||
1700 | public float topShearY = 0.0f; | ||
1701 | public float pathCutBegin = 0.0f; | ||
1702 | public float pathCutEnd = 1.0f; | ||
1703 | public float dimpleBegin = 0.0f; | ||
1704 | public float dimpleEnd = 1.0f; | ||
1705 | public float skew = 0.0f; | ||
1706 | public float holeSizeX = 1.0f; // called pathScaleX in pbs | ||
1707 | public float holeSizeY = 0.25f; | ||
1708 | public float taperX = 0.0f; | ||
1709 | public float taperY = 0.0f; | ||
1710 | public float radius = 0.0f; | ||
1711 | public float revolutions = 1.0f; | ||
1712 | public int stepsPerRevolution = 24; | ||
1713 | */ | ||
1714 | 1675 | ||
1715 | bool needEndFaces = false; | 1676 | bool needEndFaces = false; |
1716 | if (pathType == PathType.Circular) | 1677 | if (pathType == PathType.Circular) |
@@ -1777,7 +1738,7 @@ namespace PrimMesher | |||
1777 | // append this layer | 1738 | // append this layer |
1778 | 1739 | ||
1779 | int coordsLen = this.coords.Count; | 1740 | int coordsLen = this.coords.Count; |
1780 | int lastCoordsLen = coordsLen; | 1741 | // int lastCoordsLen = coordsLen; |
1781 | newLayer.AddValue2FaceVertexIndices(coordsLen); | 1742 | newLayer.AddValue2FaceVertexIndices(coordsLen); |
1782 | 1743 | ||
1783 | this.coords.AddRange(newLayer.coords); | 1744 | this.coords.AddRange(newLayer.coords); |
@@ -1796,7 +1757,6 @@ namespace PrimMesher | |||
1796 | int numVerts = newLayer.coords.Count; | 1757 | int numVerts = newLayer.coords.Count; |
1797 | Face newFace = new Face(); | 1758 | Face newFace = new Face(); |
1798 | 1759 | ||
1799 | //if (step > 0) | ||
1800 | if (nodeIndex > 0) | 1760 | if (nodeIndex > 0) |
1801 | { | 1761 | { |
1802 | int startVert = coordsLen + 1; | 1762 | int startVert = coordsLen + 1; |
@@ -1812,7 +1772,6 @@ namespace PrimMesher | |||
1812 | iNext = startVert; | 1772 | iNext = startVert; |
1813 | 1773 | ||
1814 | int whichVert = i - startVert; | 1774 | int whichVert = i - startVert; |
1815 | //int whichVert2 = i - lastCoordsLen; | ||
1816 | 1775 | ||
1817 | newFace.v1 = i; | 1776 | newFace.v1 = i; |
1818 | newFace.v2 = i - numVerts; | 1777 | newFace.v2 = i - numVerts; |
@@ -1982,809 +1941,27 @@ namespace PrimMesher | |||
1982 | 1941 | ||
1983 | 1942 | ||
1984 | /// <summary> | 1943 | /// <summary> |
1944 | /// DEPRICATED - use Extrude(PathType.Linear) instead | ||
1985 | /// Extrudes a profile along a straight line path. Used for prim types box, cylinder, and prism. | 1945 | /// Extrudes a profile along a straight line path. Used for prim types box, cylinder, and prism. |
1986 | /// </summary> | 1946 | /// </summary> |
1947 | /// | ||
1987 | public void ExtrudeLinear() | 1948 | public void ExtrudeLinear() |
1988 | { | 1949 | { |
1989 | this.coords = new List<Coord>(); | 1950 | this.Extrude(PathType.Linear); |
1990 | this.faces = new List<Face>(); | ||
1991 | |||
1992 | if (this.viewerMode) | ||
1993 | { | ||
1994 | this.viewerFaces = new List<ViewerFace>(); | ||
1995 | this.calcVertexNormals = true; | ||
1996 | } | ||
1997 | |||
1998 | if (this.calcVertexNormals) | ||
1999 | this.normals = new List<Coord>(); | ||
2000 | |||
2001 | int step = 0; | ||
2002 | int steps = 1; | ||
2003 | |||
2004 | float length = this.pathCutEnd - this.pathCutBegin; | ||
2005 | normalsProcessed = false; | ||
2006 | |||
2007 | if (this.viewerMode && this.sides == 3) | ||
2008 | { | ||
2009 | // prisms don't taper well so add some vertical resolution | ||
2010 | // other prims may benefit from this but just do prisms for now | ||
2011 | if (Math.Abs(this.taperX) > 0.01 || Math.Abs(this.taperY) > 0.01) | ||
2012 | steps = (int)(steps * 4.5 * length); | ||
2013 | } | ||
2014 | |||
2015 | |||
2016 | float twistBegin = this.twistBegin / 360.0f * twoPi; | ||
2017 | float twistEnd = this.twistEnd / 360.0f * twoPi; | ||
2018 | float twistTotal = twistEnd - twistBegin; | ||
2019 | float twistTotalAbs = Math.Abs(twistTotal); | ||
2020 | if (twistTotalAbs > 0.01f) | ||
2021 | steps += (int)(twistTotalAbs * 3.66); // dahlia's magic number | ||
2022 | |||
2023 | float start = -0.5f; | ||
2024 | float stepSize = length / (float)steps; | ||
2025 | float percentOfPathMultiplier = stepSize; | ||
2026 | float xProfileScale = 1.0f; | ||
2027 | float yProfileScale = 1.0f; | ||
2028 | float xOffset = 0.0f; | ||
2029 | float yOffset = 0.0f; | ||
2030 | float zOffset = start; | ||
2031 | float xOffsetStepIncrement = this.topShearX / steps; | ||
2032 | float yOffsetStepIncrement = this.topShearY / steps; | ||
2033 | |||
2034 | float percentOfPath = this.pathCutBegin; | ||
2035 | zOffset += percentOfPath; | ||
2036 | |||
2037 | float hollow = this.hollow; | ||
2038 | |||
2039 | // sanity checks | ||
2040 | float initialProfileRot = 0.0f; | ||
2041 | if (this.sides == 3) | ||
2042 | { | ||
2043 | if (this.hollowSides == 4) | ||
2044 | { | ||
2045 | if (hollow > 0.7f) | ||
2046 | hollow = 0.7f; | ||
2047 | hollow *= 0.707f; | ||
2048 | } | ||
2049 | else hollow *= 0.5f; | ||
2050 | } | ||
2051 | else if (this.sides == 4) | ||
2052 | { | ||
2053 | initialProfileRot = 1.25f * (float)Math.PI; | ||
2054 | if (this.hollowSides != 4) | ||
2055 | hollow *= 0.707f; | ||
2056 | } | ||
2057 | else if (this.sides == 24 && this.hollowSides == 4) | ||
2058 | hollow *= 1.414f; | ||
2059 | |||
2060 | Profile profile = new Profile(this.sides, this.profileStart, this.profileEnd, hollow, this.hollowSides, true, calcVertexNormals); | ||
2061 | this.errorMessage = profile.errorMessage; | ||
2062 | |||
2063 | this.numPrimFaces = profile.numPrimFaces; | ||
2064 | |||
2065 | int cut1Vert = -1; | ||
2066 | int cut2Vert = -1; | ||
2067 | if (hasProfileCut) | ||
2068 | { | ||
2069 | cut1Vert = hasHollow ? profile.coords.Count - 1 : 0; | ||
2070 | cut2Vert = hasHollow ? profile.numOuterVerts - 1 : profile.numOuterVerts; | ||
2071 | } | ||
2072 | |||
2073 | if (initialProfileRot != 0.0f) | ||
2074 | { | ||
2075 | profile.AddRot(new Quat(new Coord(0.0f, 0.0f, 1.0f), initialProfileRot)); | ||
2076 | if (viewerMode) | ||
2077 | profile.MakeFaceUVs(); | ||
2078 | } | ||
2079 | |||
2080 | Coord lastCutNormal1 = new Coord(); | ||
2081 | Coord lastCutNormal2 = new Coord(); | ||
2082 | float lastV = 1.0f; | ||
2083 | |||
2084 | bool done = false; | ||
2085 | while (!done) | ||
2086 | { | ||
2087 | Profile newLayer = profile.Copy(); | ||
2088 | |||
2089 | if (this.taperX == 0.0f) | ||
2090 | xProfileScale = 1.0f; | ||
2091 | else if (this.taperX > 0.0f) | ||
2092 | xProfileScale = 1.0f - percentOfPath * this.taperX; | ||
2093 | else xProfileScale = 1.0f + (1.0f - percentOfPath) * this.taperX; | ||
2094 | |||
2095 | if (this.taperY == 0.0f) | ||
2096 | yProfileScale = 1.0f; | ||
2097 | else if (this.taperY > 0.0f) | ||
2098 | yProfileScale = 1.0f - percentOfPath * this.taperY; | ||
2099 | else yProfileScale = 1.0f + (1.0f - percentOfPath) * this.taperY; | ||
2100 | |||
2101 | if (xProfileScale != 1.0f || yProfileScale != 1.0f) | ||
2102 | newLayer.Scale(xProfileScale, yProfileScale); | ||
2103 | |||
2104 | float twist = twistBegin + twistTotal * percentOfPath; | ||
2105 | if (twist != 0.0f) | ||
2106 | newLayer.AddRot(new Quat(new Coord(0.0f, 0.0f, 1.0f), twist)); | ||
2107 | |||
2108 | newLayer.AddPos(xOffset, yOffset, zOffset); | ||
2109 | |||
2110 | if (step == 0) | ||
2111 | { | ||
2112 | newLayer.FlipNormals(); | ||
2113 | |||
2114 | // add the top faces to the viewerFaces list here | ||
2115 | if (this.viewerMode) | ||
2116 | { | ||
2117 | Coord faceNormal = newLayer.faceNormal; | ||
2118 | ViewerFace newViewerFace = new ViewerFace(profile.bottomFaceNumber); | ||
2119 | int numFaces = newLayer.faces.Count; | ||
2120 | List<Face> faces = newLayer.faces; | ||
2121 | |||
2122 | for (int i = 0; i < numFaces; i++) | ||
2123 | { | ||
2124 | Face face = faces[i]; | ||
2125 | newViewerFace.v1 = newLayer.coords[face.v1]; | ||
2126 | newViewerFace.v2 = newLayer.coords[face.v2]; | ||
2127 | newViewerFace.v3 = newLayer.coords[face.v3]; | ||
2128 | |||
2129 | newViewerFace.coordIndex1 = face.v1; | ||
2130 | newViewerFace.coordIndex2 = face.v2; | ||
2131 | newViewerFace.coordIndex3 = face.v3; | ||
2132 | |||
2133 | newViewerFace.n1 = faceNormal; | ||
2134 | newViewerFace.n2 = faceNormal; | ||
2135 | newViewerFace.n3 = faceNormal; | ||
2136 | |||
2137 | newViewerFace.uv1 = newLayer.faceUVs[face.v1]; | ||
2138 | newViewerFace.uv2 = newLayer.faceUVs[face.v2]; | ||
2139 | newViewerFace.uv3 = newLayer.faceUVs[face.v3]; | ||
2140 | |||
2141 | this.viewerFaces.Add(newViewerFace); | ||
2142 | } | ||
2143 | } | ||
2144 | } | ||
2145 | |||
2146 | // append this layer | ||
2147 | |||
2148 | int coordsLen = this.coords.Count; | ||
2149 | int lastCoordsLen = coordsLen; | ||
2150 | newLayer.AddValue2FaceVertexIndices(coordsLen); | ||
2151 | |||
2152 | this.coords.AddRange(newLayer.coords); | ||
2153 | |||
2154 | if (this.calcVertexNormals) | ||
2155 | { | ||
2156 | newLayer.AddValue2FaceNormalIndices(this.normals.Count); | ||
2157 | this.normals.AddRange(newLayer.vertexNormals); | ||
2158 | } | ||
2159 | |||
2160 | if (percentOfPath < this.pathCutBegin + 0.01f || percentOfPath > this.pathCutEnd - 0.01f) | ||
2161 | this.faces.AddRange(newLayer.faces); | ||
2162 | |||
2163 | // fill faces between layers | ||
2164 | |||
2165 | int numVerts = newLayer.coords.Count; | ||
2166 | Face newFace = new Face(); | ||
2167 | |||
2168 | if (step > 0) | ||
2169 | { | ||
2170 | int startVert = coordsLen + 1; | ||
2171 | int endVert = this.coords.Count; | ||
2172 | |||
2173 | if (sides < 5 || this.hasProfileCut || hollow > 0.0f) | ||
2174 | startVert--; | ||
2175 | |||
2176 | for (int i = startVert; i < endVert; i++) | ||
2177 | { | ||
2178 | int iNext = i + 1; | ||
2179 | if (i == endVert - 1) | ||
2180 | iNext = startVert; | ||
2181 | |||
2182 | int whichVert = i - startVert; | ||
2183 | //int whichVert2 = i - lastCoordsLen; | ||
2184 | |||
2185 | newFace.v1 = i; | ||
2186 | newFace.v2 = i - numVerts; | ||
2187 | newFace.v3 = iNext - numVerts; | ||
2188 | this.faces.Add(newFace); | ||
2189 | |||
2190 | newFace.v2 = iNext - numVerts; | ||
2191 | newFace.v3 = iNext; | ||
2192 | this.faces.Add(newFace); | ||
2193 | |||
2194 | if (this.viewerMode) | ||
2195 | { | ||
2196 | // add the side faces to the list of viewerFaces here | ||
2197 | //int primFaceNum = 1; | ||
2198 | //if (whichVert >= sides) | ||
2199 | // primFaceNum = 2; | ||
2200 | int primFaceNum = profile.faceNumbers[whichVert]; | ||
2201 | |||
2202 | ViewerFace newViewerFace1 = new ViewerFace(primFaceNum); | ||
2203 | ViewerFace newViewerFace2 = new ViewerFace(primFaceNum); | ||
2204 | |||
2205 | float u1 = newLayer.us[whichVert]; | ||
2206 | float u2 = 1.0f; | ||
2207 | if (whichVert < newLayer.us.Count - 1) | ||
2208 | u2 = newLayer.us[whichVert + 1]; | ||
2209 | |||
2210 | if (whichVert == cut1Vert || whichVert == cut2Vert) | ||
2211 | { | ||
2212 | u1 = 0.0f; | ||
2213 | u2 = 1.0f; | ||
2214 | } | ||
2215 | else if (sides < 5) | ||
2216 | { // boxes and prisms have one texture face per side of the prim, so the U values have to be scaled | ||
2217 | // to reflect the entire texture width | ||
2218 | u1 *= sides; | ||
2219 | u2 *= sides; | ||
2220 | u2 -= (int)u1; | ||
2221 | u1 -= (int)u1; | ||
2222 | if (u2 < 0.1f) | ||
2223 | u2 = 1.0f; | ||
2224 | |||
2225 | //newViewerFace2.primFaceNumber = newViewerFace1.primFaceNumber = whichVert + 1; | ||
2226 | } | ||
2227 | |||
2228 | newViewerFace1.uv1.U = u1; | ||
2229 | newViewerFace1.uv2.U = u1; | ||
2230 | newViewerFace1.uv3.U = u2; | ||
2231 | |||
2232 | newViewerFace1.uv1.V = 1.0f - percentOfPath; | ||
2233 | newViewerFace1.uv2.V = lastV; | ||
2234 | newViewerFace1.uv3.V = lastV; | ||
2235 | |||
2236 | newViewerFace2.uv1.U = u1; | ||
2237 | newViewerFace2.uv2.U = u2; | ||
2238 | newViewerFace2.uv3.U = u2; | ||
2239 | |||
2240 | newViewerFace2.uv1.V = 1.0f - percentOfPath; | ||
2241 | newViewerFace2.uv2.V = lastV; | ||
2242 | newViewerFace2.uv3.V = 1.0f - percentOfPath; | ||
2243 | |||
2244 | newViewerFace1.v1 = this.coords[i]; | ||
2245 | newViewerFace1.v2 = this.coords[i - numVerts]; | ||
2246 | newViewerFace1.v3 = this.coords[iNext - numVerts]; | ||
2247 | |||
2248 | newViewerFace2.v1 = this.coords[i]; | ||
2249 | newViewerFace2.v2 = this.coords[iNext - numVerts]; | ||
2250 | newViewerFace2.v3 = this.coords[iNext]; | ||
2251 | |||
2252 | newViewerFace1.coordIndex1 = i; | ||
2253 | newViewerFace1.coordIndex2 = i - numVerts; | ||
2254 | newViewerFace1.coordIndex3 = iNext - numVerts; | ||
2255 | |||
2256 | newViewerFace2.coordIndex1 = i; | ||
2257 | newViewerFace2.coordIndex2 = iNext - numVerts; | ||
2258 | newViewerFace2.coordIndex3 = iNext; | ||
2259 | |||
2260 | // profile cut faces | ||
2261 | if (whichVert == cut1Vert) | ||
2262 | { | ||
2263 | newViewerFace1.n1 = newLayer.cutNormal1; | ||
2264 | newViewerFace1.n2 = newViewerFace1.n3 = lastCutNormal1; | ||
2265 | |||
2266 | newViewerFace2.n1 = newViewerFace2.n3 = newLayer.cutNormal1; | ||
2267 | newViewerFace2.n2 = lastCutNormal1; | ||
2268 | } | ||
2269 | else if (whichVert == cut2Vert) | ||
2270 | { | ||
2271 | newViewerFace1.n1 = newLayer.cutNormal2; | ||
2272 | newViewerFace1.n2 = newViewerFace1.n3 = lastCutNormal2; | ||
2273 | |||
2274 | newViewerFace2.n1 = newViewerFace2.n3 = newLayer.cutNormal2; | ||
2275 | newViewerFace2.n2 = lastCutNormal2; | ||
2276 | } | ||
2277 | |||
2278 | else // outer and hollow faces | ||
2279 | { | ||
2280 | if ((sides < 5 && whichVert < newLayer.numOuterVerts) || (hollowSides < 5 && whichVert >= newLayer.numOuterVerts)) | ||
2281 | { | ||
2282 | newViewerFace1.CalcSurfaceNormal(); | ||
2283 | newViewerFace2.CalcSurfaceNormal(); | ||
2284 | } | ||
2285 | else | ||
2286 | { | ||
2287 | newViewerFace1.n1 = this.normals[i]; | ||
2288 | newViewerFace1.n2 = this.normals[i - numVerts]; | ||
2289 | newViewerFace1.n3 = this.normals[iNext - numVerts]; | ||
2290 | |||
2291 | newViewerFace2.n1 = this.normals[i]; | ||
2292 | newViewerFace2.n2 = this.normals[iNext - numVerts]; | ||
2293 | newViewerFace2.n3 = this.normals[iNext]; | ||
2294 | } | ||
2295 | } | ||
2296 | |||
2297 | //newViewerFace2.primFaceNumber = newViewerFace1.primFaceNumber = newLayer.faceNumbers[whichVert]; | ||
2298 | |||
2299 | this.viewerFaces.Add(newViewerFace1); | ||
2300 | this.viewerFaces.Add(newViewerFace2); | ||
2301 | |||
2302 | } | ||
2303 | } | ||
2304 | } | ||
2305 | |||
2306 | lastCutNormal1 = newLayer.cutNormal1; | ||
2307 | lastCutNormal2 = newLayer.cutNormal2; | ||
2308 | lastV = 1.0f - percentOfPath; | ||
2309 | |||
2310 | // calc the step for the next iteration of the loop | ||
2311 | |||
2312 | if (step < steps) | ||
2313 | { | ||
2314 | step += 1; | ||
2315 | percentOfPath += percentOfPathMultiplier; | ||
2316 | xOffset += xOffsetStepIncrement; | ||
2317 | yOffset += yOffsetStepIncrement; | ||
2318 | zOffset += stepSize; | ||
2319 | if (percentOfPath > this.pathCutEnd) | ||
2320 | done = true; | ||
2321 | } | ||
2322 | else done = true; | ||
2323 | |||
2324 | if (done && viewerMode) | ||
2325 | { | ||
2326 | // add the top faces to the viewerFaces list here | ||
2327 | Coord faceNormal = newLayer.faceNormal; | ||
2328 | ViewerFace newViewerFace = new ViewerFace(); | ||
2329 | newViewerFace.primFaceNumber = 0; | ||
2330 | int numFaces = newLayer.faces.Count; | ||
2331 | List<Face> faces = newLayer.faces; | ||
2332 | |||
2333 | for (int i = 0; i < numFaces; i++) | ||
2334 | { | ||
2335 | Face face = faces[i]; | ||
2336 | newViewerFace.v1 = newLayer.coords[face.v1 - coordsLen]; | ||
2337 | newViewerFace.v2 = newLayer.coords[face.v2 - coordsLen]; | ||
2338 | newViewerFace.v3 = newLayer.coords[face.v3 - coordsLen]; | ||
2339 | |||
2340 | newViewerFace.coordIndex1 = face.v1 - coordsLen; | ||
2341 | newViewerFace.coordIndex2 = face.v2 - coordsLen; | ||
2342 | newViewerFace.coordIndex3 = face.v3 - coordsLen; | ||
2343 | |||
2344 | newViewerFace.n1 = faceNormal; | ||
2345 | newViewerFace.n2 = faceNormal; | ||
2346 | newViewerFace.n3 = faceNormal; | ||
2347 | |||
2348 | newViewerFace.uv1 = newLayer.faceUVs[face.v1 - coordsLen]; | ||
2349 | newViewerFace.uv2 = newLayer.faceUVs[face.v2 - coordsLen]; | ||
2350 | newViewerFace.uv3 = newLayer.faceUVs[face.v3 - coordsLen]; | ||
2351 | |||
2352 | this.viewerFaces.Add(newViewerFace); | ||
2353 | } | ||
2354 | } | ||
2355 | } | ||
2356 | } | 1951 | } |
2357 | 1952 | ||
2358 | 1953 | ||
2359 | /// <summary> | 1954 | /// <summary> |
1955 | /// DEPRICATED - use Extrude(PathType.Circular) instead | ||
2360 | /// Extrude a profile into a circular path prim mesh. Used for prim types torus, tube, and ring. | 1956 | /// Extrude a profile into a circular path prim mesh. Used for prim types torus, tube, and ring. |
2361 | /// </summary> | 1957 | /// </summary> |
1958 | /// | ||
2362 | public void ExtrudeCircular() | 1959 | public void ExtrudeCircular() |
2363 | { | 1960 | { |
2364 | this.coords = new List<Coord>(); | 1961 | this.Extrude(PathType.Circular); |
2365 | this.faces = new List<Face>(); | ||
2366 | |||
2367 | if (this.viewerMode) | ||
2368 | { | ||
2369 | this.viewerFaces = new List<ViewerFace>(); | ||
2370 | this.calcVertexNormals = true; | ||
2371 | } | ||
2372 | |||
2373 | if (this.calcVertexNormals) | ||
2374 | this.normals = new List<Coord>(); | ||
2375 | |||
2376 | int step = 0; | ||
2377 | int steps = 24; | ||
2378 | |||
2379 | normalsProcessed = false; | ||
2380 | |||
2381 | float twistBegin = this.twistBegin / 360.0f * twoPi; | ||
2382 | float twistEnd = this.twistEnd / 360.0f * twoPi; | ||
2383 | float twistTotal = twistEnd - twistBegin; | ||
2384 | |||
2385 | // if the profile has a lot of twist, add more layers otherwise the layers may overlap | ||
2386 | // and the resulting mesh may be quite inaccurate. This method is arbitrary and doesn't | ||
2387 | // accurately match the viewer | ||
2388 | float twistTotalAbs = Math.Abs(twistTotal); | ||
2389 | if (twistTotalAbs > 0.01f) | ||
2390 | { | ||
2391 | if (twistTotalAbs > Math.PI * 1.5f) | ||
2392 | steps *= 2; | ||
2393 | if (twistTotalAbs > Math.PI * 3.0f) | ||
2394 | steps *= 2; | ||
2395 | } | ||
2396 | |||
2397 | float yPathScale = this.holeSizeY * 0.5f; | ||
2398 | float pathLength = this.pathCutEnd - this.pathCutBegin; | ||
2399 | float totalSkew = this.skew * 2.0f * pathLength; | ||
2400 | float skewStart = this.pathCutBegin * 2.0f * this.skew - this.skew; | ||
2401 | float xOffsetTopShearXFactor = this.topShearX * (0.25f + 0.5f * (0.5f - this.holeSizeY)); | ||
2402 | float yShearCompensation = 1.0f + Math.Abs(this.topShearY) * 0.25f; | ||
2403 | |||
2404 | // It's not quite clear what pushY (Y top shear) does, but subtracting it from the start and end | ||
2405 | // angles appears to approximate it's effects on path cut. Likewise, adding it to the angle used | ||
2406 | // to calculate the sine for generating the path radius appears to approximate it's effects there | ||
2407 | // too, but there are some subtle differences in the radius which are noticeable as the prim size | ||
2408 | // increases and it may affect megaprims quite a bit. The effect of the Y top shear parameter on | ||
2409 | // the meshes generated with this technique appear nearly identical in shape to the same prims when | ||
2410 | // displayed by the viewer. | ||
2411 | |||
2412 | float startAngle = (twoPi * this.pathCutBegin * this.revolutions) - this.topShearY * 0.9f; | ||
2413 | float endAngle = (twoPi * this.pathCutEnd * this.revolutions) - this.topShearY * 0.9f; | ||
2414 | float stepSize = twoPi / this.stepsPerRevolution; | ||
2415 | |||
2416 | step = (int)(startAngle / stepSize); | ||
2417 | int firstStep = step; | ||
2418 | float angle = startAngle; | ||
2419 | float hollow = this.hollow; | ||
2420 | |||
2421 | // sanity checks | ||
2422 | float initialProfileRot = 0.0f; | ||
2423 | if (this.sides == 3) | ||
2424 | { | ||
2425 | initialProfileRot = (float)Math.PI; | ||
2426 | if (this.hollowSides == 4) | ||
2427 | { | ||
2428 | if (hollow > 0.7f) | ||
2429 | hollow = 0.7f; | ||
2430 | hollow *= 0.707f; | ||
2431 | } | ||
2432 | else hollow *= 0.5f; | ||
2433 | } | ||
2434 | else if (this.sides == 4) | ||
2435 | { | ||
2436 | initialProfileRot = 0.25f * (float)Math.PI; | ||
2437 | if (this.hollowSides != 4) | ||
2438 | hollow *= 0.707f; | ||
2439 | } | ||
2440 | else if (this.sides > 4) | ||
2441 | { | ||
2442 | initialProfileRot = (float)Math.PI; | ||
2443 | if (this.hollowSides == 4) | ||
2444 | { | ||
2445 | if (hollow > 0.7f) | ||
2446 | hollow = 0.7f; | ||
2447 | hollow /= 0.7f; | ||
2448 | } | ||
2449 | } | ||
2450 | |||
2451 | bool needEndFaces = false; | ||
2452 | if (this.pathCutBegin != 0.0f || this.pathCutEnd != 1.0f) | ||
2453 | needEndFaces = true; | ||
2454 | else if (this.taperX != 0.0f || this.taperY != 0.0f) | ||
2455 | needEndFaces = true; | ||
2456 | else if (this.skew != 0.0f) | ||
2457 | needEndFaces = true; | ||
2458 | else if (twistTotal != 0.0f) | ||
2459 | needEndFaces = true; | ||
2460 | else if (this.radius != 0.0f) | ||
2461 | needEndFaces = true; | ||
2462 | |||
2463 | Profile profile = new Profile(this.sides, this.profileStart, this.profileEnd, hollow, this.hollowSides, needEndFaces, calcVertexNormals); | ||
2464 | this.errorMessage = profile.errorMessage; | ||
2465 | |||
2466 | this.numPrimFaces = profile.numPrimFaces; | ||
2467 | |||
2468 | int cut1Vert = -1; | ||
2469 | int cut2Vert = -1; | ||
2470 | if (hasProfileCut) | ||
2471 | { | ||
2472 | cut1Vert = hasHollow ? profile.coords.Count - 1 : 0; | ||
2473 | cut2Vert = hasHollow ? profile.numOuterVerts - 1 : profile.numOuterVerts; | ||
2474 | } | ||
2475 | |||
2476 | if (initialProfileRot != 0.0f) | ||
2477 | { | ||
2478 | profile.AddRot(new Quat(new Coord(0.0f, 0.0f, 1.0f), initialProfileRot)); | ||
2479 | if (viewerMode) | ||
2480 | profile.MakeFaceUVs(); | ||
2481 | } | ||
2482 | |||
2483 | Coord lastCutNormal1 = new Coord(); | ||
2484 | Coord lastCutNormal2 = new Coord(); | ||
2485 | float lastV = 1.0f; | ||
2486 | |||
2487 | bool done = false; | ||
2488 | while (!done) // loop through the length of the path and add the layers | ||
2489 | { | ||
2490 | bool isEndLayer = false; | ||
2491 | if (angle <= startAngle + .01f || angle >= endAngle - .01f) | ||
2492 | isEndLayer = true; | ||
2493 | |||
2494 | Profile newLayer = profile.Copy(); | ||
2495 | |||
2496 | float xProfileScale = (1.0f - Math.Abs(this.skew)) * this.holeSizeX; | ||
2497 | float yProfileScale = this.holeSizeY; | ||
2498 | |||
2499 | float percentOfPath = angle / (twoPi * this.revolutions); | ||
2500 | float percentOfAngles = (angle - startAngle) / (endAngle - startAngle); | ||
2501 | |||
2502 | if (this.taperX > 0.01f) | ||
2503 | xProfileScale *= 1.0f - percentOfPath * this.taperX; | ||
2504 | else if (this.taperX < -0.01f) | ||
2505 | xProfileScale *= 1.0f + (1.0f - percentOfPath) * this.taperX; | ||
2506 | |||
2507 | if (this.taperY > 0.01f) | ||
2508 | yProfileScale *= 1.0f - percentOfPath * this.taperY; | ||
2509 | else if (this.taperY < -0.01f) | ||
2510 | yProfileScale *= 1.0f + (1.0f - percentOfPath) * this.taperY; | ||
2511 | |||
2512 | if (xProfileScale != 1.0f || yProfileScale != 1.0f) | ||
2513 | newLayer.Scale(xProfileScale, yProfileScale); | ||
2514 | |||
2515 | float radiusScale = 1.0f; | ||
2516 | if (this.radius > 0.001f) | ||
2517 | radiusScale = 1.0f - this.radius * percentOfPath; | ||
2518 | else if (this.radius < 0.001f) | ||
2519 | radiusScale = 1.0f + this.radius * (1.0f - percentOfPath); | ||
2520 | |||
2521 | float twist = twistBegin + twistTotal * percentOfPath; | ||
2522 | |||
2523 | float xOffset = 0.5f * (skewStart + totalSkew * percentOfAngles); | ||
2524 | xOffset += (float)Math.Sin(angle) * xOffsetTopShearXFactor; | ||
2525 | |||
2526 | float yOffset = yShearCompensation * (float)Math.Cos(angle) * (0.5f - yPathScale) * radiusScale; | ||
2527 | |||
2528 | float zOffset = (float)Math.Sin(angle + this.topShearY) * (0.5f - yPathScale) * radiusScale; | ||
2529 | |||
2530 | // next apply twist rotation to the profile layer | ||
2531 | if (twistTotal != 0.0f || twistBegin != 0.0f) | ||
2532 | newLayer.AddRot(new Quat(new Coord(0.0f, 0.0f, 1.0f), twist)); | ||
2533 | |||
2534 | // now orient the rotation of the profile layer relative to it's position on the path | ||
2535 | // adding taperY to the angle used to generate the quat appears to approximate the viewer | ||
2536 | newLayer.AddRot(new Quat(new Coord(1.0f, 0.0f, 0.0f), angle + this.topShearY)); | ||
2537 | newLayer.AddPos(xOffset, yOffset, zOffset); | ||
2538 | |||
2539 | if (isEndLayer && angle <= startAngle + .01f) | ||
2540 | { | ||
2541 | newLayer.FlipNormals(); | ||
2542 | |||
2543 | // add the top faces to the viewerFaces list here | ||
2544 | if (this.viewerMode && needEndFaces) | ||
2545 | { | ||
2546 | Coord faceNormal = newLayer.faceNormal; | ||
2547 | ViewerFace newViewerFace = new ViewerFace(); | ||
2548 | newViewerFace.primFaceNumber = 0; | ||
2549 | foreach (Face face in newLayer.faces) | ||
2550 | { | ||
2551 | newViewerFace.v1 = newLayer.coords[face.v1]; | ||
2552 | newViewerFace.v2 = newLayer.coords[face.v2]; | ||
2553 | newViewerFace.v3 = newLayer.coords[face.v3]; | ||
2554 | |||
2555 | newViewerFace.coordIndex1 = face.v1; | ||
2556 | newViewerFace.coordIndex2 = face.v2; | ||
2557 | newViewerFace.coordIndex3 = face.v3; | ||
2558 | |||
2559 | newViewerFace.n1 = faceNormal; | ||
2560 | newViewerFace.n2 = faceNormal; | ||
2561 | newViewerFace.n3 = faceNormal; | ||
2562 | |||
2563 | newViewerFace.uv1 = newLayer.faceUVs[face.v1]; | ||
2564 | newViewerFace.uv2 = newLayer.faceUVs[face.v2]; | ||
2565 | newViewerFace.uv3 = newLayer.faceUVs[face.v3]; | ||
2566 | |||
2567 | this.viewerFaces.Add(newViewerFace); | ||
2568 | } | ||
2569 | } | ||
2570 | } | ||
2571 | |||
2572 | // append the layer and fill in the sides | ||
2573 | |||
2574 | int coordsLen = this.coords.Count; | ||
2575 | newLayer.AddValue2FaceVertexIndices(coordsLen); | ||
2576 | |||
2577 | this.coords.AddRange(newLayer.coords); | ||
2578 | |||
2579 | if (this.calcVertexNormals) | ||
2580 | { | ||
2581 | newLayer.AddValue2FaceNormalIndices(this.normals.Count); | ||
2582 | this.normals.AddRange(newLayer.vertexNormals); | ||
2583 | } | ||
2584 | |||
2585 | if (isEndLayer) | ||
2586 | this.faces.AddRange(newLayer.faces); | ||
2587 | |||
2588 | // fill faces between layers | ||
2589 | |||
2590 | int numVerts = newLayer.coords.Count; | ||
2591 | Face newFace = new Face(); | ||
2592 | if (step > firstStep) | ||
2593 | { | ||
2594 | int startVert = coordsLen + 1; | ||
2595 | int endVert = this.coords.Count; | ||
2596 | |||
2597 | if (sides < 5 || this.hasProfileCut || hollow > 0.0f) | ||
2598 | startVert--; | ||
2599 | |||
2600 | for (int i = startVert; i < endVert; i++) | ||
2601 | { | ||
2602 | int iNext = i + 1; | ||
2603 | if (i == endVert - 1) | ||
2604 | iNext = startVert; | ||
2605 | |||
2606 | int whichVert = i - startVert; | ||
2607 | |||
2608 | newFace.v1 = i; | ||
2609 | newFace.v2 = i - numVerts; | ||
2610 | newFace.v3 = iNext - numVerts; | ||
2611 | this.faces.Add(newFace); | ||
2612 | |||
2613 | newFace.v2 = iNext - numVerts; | ||
2614 | newFace.v3 = iNext; | ||
2615 | this.faces.Add(newFace); | ||
2616 | |||
2617 | if (this.viewerMode) | ||
2618 | { | ||
2619 | int primFaceNumber = profile.faceNumbers[whichVert]; | ||
2620 | if (!needEndFaces) | ||
2621 | primFaceNumber -= 1; | ||
2622 | |||
2623 | // add the side faces to the list of viewerFaces here | ||
2624 | ViewerFace newViewerFace1 = new ViewerFace(primFaceNumber); | ||
2625 | ViewerFace newViewerFace2 = new ViewerFace(primFaceNumber); | ||
2626 | float u1 = newLayer.us[whichVert]; | ||
2627 | float u2 = 1.0f; | ||
2628 | if (whichVert < newLayer.us.Count - 1) | ||
2629 | u2 = newLayer.us[whichVert + 1]; | ||
2630 | |||
2631 | if (whichVert == cut1Vert || whichVert == cut2Vert) | ||
2632 | { | ||
2633 | u1 = 0.0f; | ||
2634 | u2 = 1.0f; | ||
2635 | } | ||
2636 | else if (sides < 5) | ||
2637 | { // boxes and prisms have one texture face per side of the prim, so the U values have to be scaled | ||
2638 | // to reflect the entire texture width | ||
2639 | u1 *= sides; | ||
2640 | u2 *= sides; | ||
2641 | u2 -= (int)u1; | ||
2642 | u1 -= (int)u1; | ||
2643 | if (u2 < 0.1f) | ||
2644 | u2 = 1.0f; | ||
2645 | |||
2646 | //newViewerFace2.primFaceNumber = newViewerFace1.primFaceNumber = whichVert + 1; | ||
2647 | } | ||
2648 | |||
2649 | newViewerFace1.uv1.U = u1; | ||
2650 | newViewerFace1.uv2.U = u1; | ||
2651 | newViewerFace1.uv3.U = u2; | ||
2652 | |||
2653 | newViewerFace1.uv1.V = 1.0f - percentOfPath; | ||
2654 | newViewerFace1.uv2.V = lastV; | ||
2655 | newViewerFace1.uv3.V = lastV; | ||
2656 | |||
2657 | newViewerFace2.uv1.U = u1; | ||
2658 | newViewerFace2.uv2.U = u2; | ||
2659 | newViewerFace2.uv3.U = u2; | ||
2660 | |||
2661 | newViewerFace2.uv1.V = 1.0f - percentOfPath; | ||
2662 | newViewerFace2.uv2.V = lastV; | ||
2663 | newViewerFace2.uv3.V = 1.0f - percentOfPath; | ||
2664 | |||
2665 | newViewerFace1.v1 = this.coords[i]; | ||
2666 | newViewerFace1.v2 = this.coords[i - numVerts]; | ||
2667 | newViewerFace1.v3 = this.coords[iNext - numVerts]; | ||
2668 | |||
2669 | newViewerFace2.v1 = this.coords[i]; | ||
2670 | newViewerFace2.v2 = this.coords[iNext - numVerts]; | ||
2671 | newViewerFace2.v3 = this.coords[iNext]; | ||
2672 | |||
2673 | newViewerFace1.coordIndex1 = i; | ||
2674 | newViewerFace1.coordIndex2 = i - numVerts; | ||
2675 | newViewerFace1.coordIndex3 = iNext - numVerts; | ||
2676 | |||
2677 | newViewerFace2.coordIndex1 = i; | ||
2678 | newViewerFace2.coordIndex2 = iNext - numVerts; | ||
2679 | newViewerFace2.coordIndex3 = iNext; | ||
2680 | |||
2681 | // profile cut faces | ||
2682 | if (whichVert == cut1Vert) | ||
2683 | { | ||
2684 | newViewerFace1.n1 = newLayer.cutNormal1; | ||
2685 | newViewerFace1.n2 = newViewerFace1.n3 = lastCutNormal1; | ||
2686 | |||
2687 | newViewerFace2.n1 = newViewerFace2.n3 = newLayer.cutNormal1; | ||
2688 | newViewerFace2.n2 = lastCutNormal1; | ||
2689 | } | ||
2690 | else if (whichVert == cut2Vert) | ||
2691 | { | ||
2692 | newViewerFace1.n1 = newLayer.cutNormal2; | ||
2693 | newViewerFace1.n2 = newViewerFace1.n3 = lastCutNormal2; | ||
2694 | |||
2695 | newViewerFace2.n1 = newViewerFace2.n3 = newLayer.cutNormal2; | ||
2696 | newViewerFace2.n2 = lastCutNormal2; | ||
2697 | } | ||
2698 | else // periphery faces | ||
2699 | { | ||
2700 | if (sides < 5 && whichVert < newLayer.numOuterVerts) | ||
2701 | { | ||
2702 | newViewerFace1.n1 = this.normals[i]; | ||
2703 | newViewerFace1.n2 = this.normals[i - numVerts]; | ||
2704 | newViewerFace1.n3 = this.normals[i - numVerts]; | ||
2705 | |||
2706 | newViewerFace2.n1 = this.normals[i]; | ||
2707 | newViewerFace2.n2 = this.normals[i - numVerts]; | ||
2708 | newViewerFace2.n3 = this.normals[i]; | ||
2709 | } | ||
2710 | else if (hollowSides < 5 && whichVert >= newLayer.numOuterVerts) | ||
2711 | { | ||
2712 | newViewerFace1.n1 = this.normals[iNext]; | ||
2713 | newViewerFace1.n2 = this.normals[iNext - numVerts]; | ||
2714 | newViewerFace1.n3 = this.normals[iNext - numVerts]; | ||
2715 | |||
2716 | newViewerFace2.n1 = this.normals[iNext]; | ||
2717 | newViewerFace2.n2 = this.normals[iNext - numVerts]; | ||
2718 | newViewerFace2.n3 = this.normals[iNext]; | ||
2719 | } | ||
2720 | else | ||
2721 | { | ||
2722 | newViewerFace1.n1 = this.normals[i]; | ||
2723 | newViewerFace1.n2 = this.normals[i - numVerts]; | ||
2724 | newViewerFace1.n3 = this.normals[iNext - numVerts]; | ||
2725 | |||
2726 | newViewerFace2.n1 = this.normals[i]; | ||
2727 | newViewerFace2.n2 = this.normals[iNext - numVerts]; | ||
2728 | newViewerFace2.n3 = this.normals[iNext]; | ||
2729 | } | ||
2730 | } | ||
2731 | |||
2732 | //newViewerFace1.primFaceNumber = newViewerFace2.primFaceNumber = newLayer.faceNumbers[whichVert]; | ||
2733 | this.viewerFaces.Add(newViewerFace1); | ||
2734 | this.viewerFaces.Add(newViewerFace2); | ||
2735 | |||
2736 | } | ||
2737 | } | ||
2738 | } | ||
2739 | |||
2740 | lastCutNormal1 = newLayer.cutNormal1; | ||
2741 | lastCutNormal2 = newLayer.cutNormal2; | ||
2742 | lastV = 1.0f - percentOfPath; | ||
2743 | |||
2744 | // calculate terms for next iteration | ||
2745 | // calculate the angle for the next iteration of the loop | ||
2746 | |||
2747 | if (angle >= endAngle - 0.01) | ||
2748 | done = true; | ||
2749 | else | ||
2750 | { | ||
2751 | step += 1; | ||
2752 | angle = stepSize * step; | ||
2753 | if (angle > endAngle) | ||
2754 | angle = endAngle; | ||
2755 | } | ||
2756 | |||
2757 | if (done && viewerMode && needEndFaces) | ||
2758 | { | ||
2759 | // add the bottom faces to the viewerFaces list here | ||
2760 | Coord faceNormal = newLayer.faceNormal; | ||
2761 | ViewerFace newViewerFace = new ViewerFace(); | ||
2762 | //newViewerFace.primFaceNumber = newLayer.bottomFaceNumber + 1; | ||
2763 | newViewerFace.primFaceNumber = newLayer.bottomFaceNumber; | ||
2764 | foreach (Face face in newLayer.faces) | ||
2765 | { | ||
2766 | newViewerFace.v1 = newLayer.coords[face.v1 - coordsLen]; | ||
2767 | newViewerFace.v2 = newLayer.coords[face.v2 - coordsLen]; | ||
2768 | newViewerFace.v3 = newLayer.coords[face.v3 - coordsLen]; | ||
2769 | |||
2770 | newViewerFace.coordIndex1 = face.v1 - coordsLen; | ||
2771 | newViewerFace.coordIndex2 = face.v2 - coordsLen; | ||
2772 | newViewerFace.coordIndex3 = face.v3 - coordsLen; | ||
2773 | |||
2774 | newViewerFace.n1 = faceNormal; | ||
2775 | newViewerFace.n2 = faceNormal; | ||
2776 | newViewerFace.n3 = faceNormal; | ||
2777 | |||
2778 | newViewerFace.uv1 = newLayer.faceUVs[face.v1 - coordsLen]; | ||
2779 | newViewerFace.uv2 = newLayer.faceUVs[face.v2 - coordsLen]; | ||
2780 | newViewerFace.uv3 = newLayer.faceUVs[face.v3 - coordsLen]; | ||
2781 | |||
2782 | this.viewerFaces.Add(newViewerFace); | ||
2783 | } | ||
2784 | } | ||
2785 | } | ||
2786 | } | 1962 | } |
2787 | 1963 | ||
1964 | |||
2788 | private Coord SurfaceNormal(Coord c1, Coord c2, Coord c3) | 1965 | private Coord SurfaceNormal(Coord c1, Coord c2, Coord c3) |
2789 | { | 1966 | { |
2790 | Coord edge1 = new Coord(c2.X - c1.X, c2.Y - c1.Y, c2.Z - c1.Z); | 1967 | Coord edge1 = new Coord(c2.X - c1.X, c2.Y - c1.Y, c2.Z - c1.Z); |
diff --git a/OpenSim/Region/Physics/Meshing/SculptMesh.cs b/OpenSim/Region/Physics/Meshing/SculptMesh.cs index f1dd586..4dc6e2e 100644 --- a/OpenSim/Region/Physics/Meshing/SculptMesh.cs +++ b/OpenSim/Region/Physics/Meshing/SculptMesh.cs | |||
@@ -25,12 +25,18 @@ | |||
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
26 | */ | 26 | */ |
27 | 27 | ||
28 | // to build without references to System.Drawing, comment this out | ||
29 | #define SYSTEM_DRAWING | ||
30 | |||
28 | using System; | 31 | using System; |
29 | using System.Collections.Generic; | 32 | using System.Collections.Generic; |
30 | using System.Text; | 33 | using System.Text; |
31 | using System.IO; | 34 | using System.IO; |
35 | |||
36 | #if SYSTEM_DRAWING | ||
32 | using System.Drawing; | 37 | using System.Drawing; |
33 | using System.Drawing.Imaging; | 38 | using System.Drawing.Imaging; |
39 | #endif | ||
34 | 40 | ||
35 | namespace PrimMesher | 41 | namespace PrimMesher |
36 | { | 42 | { |
@@ -46,6 +52,7 @@ namespace PrimMesher | |||
46 | 52 | ||
47 | public enum SculptType { sphere = 1, torus = 2, plane = 3, cylinder = 4 }; | 53 | public enum SculptType { sphere = 1, torus = 2, plane = 3, cylinder = 4 }; |
48 | 54 | ||
55 | #if SYSTEM_DRAWING | ||
49 | // private Bitmap ScaleImage(Bitmap srcImage, float scale) | 56 | // private Bitmap ScaleImage(Bitmap srcImage, float scale) |
50 | // { | 57 | // { |
51 | // int sourceWidth = srcImage.Width; | 58 | // int sourceWidth = srcImage.Width; |
@@ -83,6 +90,7 @@ namespace PrimMesher | |||
83 | // return scaledImage; | 90 | // return scaledImage; |
84 | // } | 91 | // } |
85 | 92 | ||
93 | |||
86 | public SculptMesh SculptMeshFromFile(string fileName, SculptType sculptType, int lod, bool viewerMode) | 94 | public SculptMesh SculptMeshFromFile(string fileName, SculptType sculptType, int lod, bool viewerMode) |
87 | { | 95 | { |
88 | Bitmap bitmap = (Bitmap)Bitmap.FromFile(fileName); | 96 | Bitmap bitmap = (Bitmap)Bitmap.FromFile(fileName); |
@@ -97,6 +105,7 @@ namespace PrimMesher | |||
97 | _SculptMesh(bitmap, (SculptType)sculptType, lod, viewerMode != 0, mirror != 0, invert != 0); | 105 | _SculptMesh(bitmap, (SculptType)sculptType, lod, viewerMode != 0, mirror != 0, invert != 0); |
98 | bitmap.Dispose(); | 106 | bitmap.Dispose(); |
99 | } | 107 | } |
108 | #endif | ||
100 | 109 | ||
101 | /// <summary> | 110 | /// <summary> |
102 | /// ** Experimental ** May disappear from future versions ** not recommeneded for use in applications | 111 | /// ** Experimental ** May disappear from future versions ** not recommeneded for use in applications |
@@ -201,6 +210,7 @@ namespace PrimMesher | |||
201 | calcVertexNormals(SculptType.plane, numXElements, numYElements); | 210 | calcVertexNormals(SculptType.plane, numXElements, numYElements); |
202 | } | 211 | } |
203 | 212 | ||
213 | #if SYSTEM_DRAWING | ||
204 | public SculptMesh(Bitmap sculptBitmap, SculptType sculptType, int lod, bool viewerMode) | 214 | public SculptMesh(Bitmap sculptBitmap, SculptType sculptType, int lod, bool viewerMode) |
205 | { | 215 | { |
206 | _SculptMesh(sculptBitmap, sculptType, lod, viewerMode, false, false); | 216 | _SculptMesh(sculptBitmap, sculptType, lod, viewerMode, false, false); |
@@ -210,9 +220,16 @@ namespace PrimMesher | |||
210 | { | 220 | { |
211 | _SculptMesh(sculptBitmap, sculptType, lod, viewerMode, mirror, invert); | 221 | _SculptMesh(sculptBitmap, sculptType, lod, viewerMode, mirror, invert); |
212 | } | 222 | } |
223 | #endif | ||
224 | |||
225 | public SculptMesh(List<List<Coord>> rows, SculptType sculptType, bool viewerMode, bool mirror, bool invert) | ||
226 | { | ||
227 | _SculptMesh(rows, sculptType, viewerMode, mirror, invert); | ||
228 | } | ||
213 | 229 | ||
230 | #if SYSTEM_DRAWING | ||
214 | /// <summary> | 231 | /// <summary> |
215 | /// converts a bitmap to a list lists of coords, while scaling the image. | 232 | /// converts a bitmap to a list of lists of coords, while scaling the image. |
216 | /// the scaling is done in floating point so as to allow for reduced vertex position | 233 | /// the scaling is done in floating point so as to allow for reduced vertex position |
217 | /// quantization as the position will be averaged between pixel values. this routine will | 234 | /// quantization as the position will be averaged between pixel values. this routine will |
218 | /// likely fail if the bitmap width and height are not powers of 2. | 235 | /// likely fail if the bitmap width and height are not powers of 2. |
@@ -267,6 +284,7 @@ namespace PrimMesher | |||
267 | return rows; | 284 | return rows; |
268 | } | 285 | } |
269 | 286 | ||
287 | |||
270 | void _SculptMesh(Bitmap sculptBitmap, SculptType sculptType, int lod, bool viewerMode, bool mirror, bool invert) | 288 | void _SculptMesh(Bitmap sculptBitmap, SculptType sculptType, int lod, bool viewerMode, bool mirror, bool invert) |
271 | { | 289 | { |
272 | coords = new List<Coord>(); | 290 | coords = new List<Coord>(); |
@@ -285,12 +303,27 @@ namespace PrimMesher | |||
285 | int scale = (int)(1.0f / sourceScaleFactor); | 303 | int scale = (int)(1.0f / sourceScaleFactor); |
286 | if (scale < 1) scale = 1; | 304 | if (scale < 1) scale = 1; |
287 | 305 | ||
288 | List<List<Coord>> rows = bitmap2Coords(sculptBitmap, scale, mirror); | 306 | _SculptMesh(bitmap2Coords(sculptBitmap, scale, mirror), sculptType, viewerMode, mirror, invert); |
307 | } | ||
308 | #endif | ||
309 | |||
310 | |||
311 | void _SculptMesh(List<List<Coord>> rows, SculptType sculptType, bool viewerMode, bool mirror, bool invert) | ||
312 | { | ||
313 | coords = new List<Coord>(); | ||
314 | faces = new List<Face>(); | ||
315 | normals = new List<Coord>(); | ||
316 | uvs = new List<UVCoord>(); | ||
317 | |||
318 | sculptType = (SculptType)(((int)sculptType) & 0x07); | ||
319 | |||
320 | if (mirror) | ||
321 | if (sculptType == SculptType.plane) | ||
322 | invert = !invert; | ||
289 | 323 | ||
290 | viewerFaces = new List<ViewerFace>(); | 324 | viewerFaces = new List<ViewerFace>(); |
291 | 325 | ||
292 | int width = sculptBitmap.Width / scale; | 326 | int width = rows[0].Count; |
293 | // int height = sculptBitmap.Height / scale; | ||
294 | 327 | ||
295 | int p1, p2, p3, p4; | 328 | int p1, p2, p3, p4; |
296 | 329 | ||
diff --git a/OpenSim/Region/Physics/OdePlugin/ODEDynamics.cs b/OpenSim/Region/Physics/OdePlugin/ODEDynamics.cs index 4a802cd..39cdc0f 100644 --- a/OpenSim/Region/Physics/OdePlugin/ODEDynamics.cs +++ b/OpenSim/Region/Physics/OdePlugin/ODEDynamics.cs | |||
@@ -67,8 +67,8 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
67 | 67 | ||
68 | // private OdeScene m_parentScene = null; | 68 | // private OdeScene m_parentScene = null; |
69 | private IntPtr m_body = IntPtr.Zero; | 69 | private IntPtr m_body = IntPtr.Zero; |
70 | private IntPtr m_jointGroup = IntPtr.Zero; | 70 | // private IntPtr m_jointGroup = IntPtr.Zero; |
71 | private IntPtr m_aMotor = IntPtr.Zero; | 71 | // private IntPtr m_aMotor = IntPtr.Zero; |
72 | 72 | ||
73 | 73 | ||
74 | // Vehicle properties | 74 | // Vehicle properties |
@@ -117,7 +117,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
117 | 117 | ||
118 | //Hover and Buoyancy properties | 118 | //Hover and Buoyancy properties |
119 | private float m_VhoverHeight = 0f; | 119 | private float m_VhoverHeight = 0f; |
120 | private float m_VhoverEfficiency = 0f; | 120 | // private float m_VhoverEfficiency = 0f; |
121 | private float m_VhoverTimescale = 0f; | 121 | private float m_VhoverTimescale = 0f; |
122 | private float m_VhoverTargetHeight = -1.0f; // if <0 then no hover, else its the current target height | 122 | private float m_VhoverTargetHeight = -1.0f; // if <0 then no hover, else its the current target height |
123 | private float m_VehicleBuoyancy = 0f; //KF: m_VehicleBuoyancy is set by VEHICLE_BUOYANCY for a vehicle. | 123 | private float m_VehicleBuoyancy = 0f; //KF: m_VehicleBuoyancy is set by VEHICLE_BUOYANCY for a vehicle. |
@@ -170,11 +170,11 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
170 | if (pValue > 1f) pValue = 1f; | 170 | if (pValue > 1f) pValue = 1f; |
171 | m_VehicleBuoyancy = pValue; | 171 | m_VehicleBuoyancy = pValue; |
172 | break; | 172 | break; |
173 | case Vehicle.HOVER_EFFICIENCY: | 173 | // case Vehicle.HOVER_EFFICIENCY: |
174 | if (pValue < 0f) pValue = 0f; | 174 | // if (pValue < 0f) pValue = 0f; |
175 | if (pValue > 1f) pValue = 1f; | 175 | // if (pValue > 1f) pValue = 1f; |
176 | m_VhoverEfficiency = pValue; | 176 | // m_VhoverEfficiency = pValue; |
177 | break; | 177 | // break; |
178 | case Vehicle.HOVER_HEIGHT: | 178 | case Vehicle.HOVER_HEIGHT: |
179 | m_VhoverHeight = pValue; | 179 | m_VhoverHeight = pValue; |
180 | break; | 180 | break; |
@@ -291,7 +291,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
291 | m_angularMotorTimescale = 1000; | 291 | m_angularMotorTimescale = 1000; |
292 | m_angularMotorDecayTimescale = 120; | 292 | m_angularMotorDecayTimescale = 120; |
293 | m_VhoverHeight = 0; | 293 | m_VhoverHeight = 0; |
294 | m_VhoverEfficiency = 1; | 294 | // m_VhoverEfficiency = 1; |
295 | m_VhoverTimescale = 10; | 295 | m_VhoverTimescale = 10; |
296 | m_VehicleBuoyancy = 0; | 296 | m_VehicleBuoyancy = 0; |
297 | // m_linearDeflectionEfficiency = 1; | 297 | // m_linearDeflectionEfficiency = 1; |
@@ -317,7 +317,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
317 | m_angularMotorTimescale = 1; | 317 | m_angularMotorTimescale = 1; |
318 | m_angularMotorDecayTimescale = 0.8f; | 318 | m_angularMotorDecayTimescale = 0.8f; |
319 | m_VhoverHeight = 0; | 319 | m_VhoverHeight = 0; |
320 | m_VhoverEfficiency = 0; | 320 | // m_VhoverEfficiency = 0; |
321 | m_VhoverTimescale = 1000; | 321 | m_VhoverTimescale = 1000; |
322 | m_VehicleBuoyancy = 0; | 322 | m_VehicleBuoyancy = 0; |
323 | // // m_linearDeflectionEfficiency = 1; | 323 | // // m_linearDeflectionEfficiency = 1; |
@@ -344,7 +344,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
344 | m_angularMotorTimescale = 4; | 344 | m_angularMotorTimescale = 4; |
345 | m_angularMotorDecayTimescale = 4; | 345 | m_angularMotorDecayTimescale = 4; |
346 | m_VhoverHeight = 0; | 346 | m_VhoverHeight = 0; |
347 | m_VhoverEfficiency = 0.5f; | 347 | // m_VhoverEfficiency = 0.5f; |
348 | m_VhoverTimescale = 2; | 348 | m_VhoverTimescale = 2; |
349 | m_VehicleBuoyancy = 1; | 349 | m_VehicleBuoyancy = 1; |
350 | // m_linearDeflectionEfficiency = 0.5f; | 350 | // m_linearDeflectionEfficiency = 0.5f; |
@@ -372,7 +372,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
372 | m_angularMotorTimescale = 4; | 372 | m_angularMotorTimescale = 4; |
373 | m_angularMotorDecayTimescale = 4; | 373 | m_angularMotorDecayTimescale = 4; |
374 | m_VhoverHeight = 0; | 374 | m_VhoverHeight = 0; |
375 | m_VhoverEfficiency = 0.5f; | 375 | // m_VhoverEfficiency = 0.5f; |
376 | m_VhoverTimescale = 1000; | 376 | m_VhoverTimescale = 1000; |
377 | m_VehicleBuoyancy = 0; | 377 | m_VehicleBuoyancy = 0; |
378 | // m_linearDeflectionEfficiency = 0.5f; | 378 | // m_linearDeflectionEfficiency = 0.5f; |
@@ -399,7 +399,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
399 | m_angularMotorTimescale = 6; | 399 | m_angularMotorTimescale = 6; |
400 | m_angularMotorDecayTimescale = 10; | 400 | m_angularMotorDecayTimescale = 10; |
401 | m_VhoverHeight = 5; | 401 | m_VhoverHeight = 5; |
402 | m_VhoverEfficiency = 0.8f; | 402 | // m_VhoverEfficiency = 0.8f; |
403 | m_VhoverTimescale = 10; | 403 | m_VhoverTimescale = 10; |
404 | m_VehicleBuoyancy = 1; | 404 | m_VehicleBuoyancy = 1; |
405 | // m_linearDeflectionEfficiency = 0; | 405 | // m_linearDeflectionEfficiency = 0; |
diff --git a/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs b/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs index f4b502a..fa42023 100644 --- a/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs +++ b/OpenSim/Region/Physics/OdePlugin/ODEPrim.cs | |||
@@ -2643,7 +2643,7 @@ Console.WriteLine(" JointCreateFixed"); | |||
2643 | //outofBounds = true; | 2643 | //outofBounds = true; |
2644 | } | 2644 | } |
2645 | 2645 | ||
2646 | float Adiff = 1.0f - Math.Abs(Quaternion.Dot(m_lastorientation, l_orientation)); | 2646 | // float Adiff = 1.0f - Math.Abs(Quaternion.Dot(m_lastorientation, l_orientation)); |
2647 | //Console.WriteLine("Adiff " + m_primName + " = " + Adiff); | 2647 | //Console.WriteLine("Adiff " + m_primName + " = " + Adiff); |
2648 | if ((Math.Abs(m_lastposition.X - l_position.X) < 0.02) | 2648 | if ((Math.Abs(m_lastposition.X - l_position.X) < 0.02) |
2649 | && (Math.Abs(m_lastposition.Y - l_position.Y) < 0.02) | 2649 | && (Math.Abs(m_lastposition.Y - l_position.Y) < 0.02) |
diff --git a/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs b/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs index a8e006b..981cf43 100644 --- a/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs +++ b/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs | |||
@@ -439,7 +439,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
439 | avMovementDivisorWalk = physicsconfig.GetFloat("av_movement_divisor_walk", 1.3f); | 439 | avMovementDivisorWalk = physicsconfig.GetFloat("av_movement_divisor_walk", 1.3f); |
440 | avMovementDivisorRun = physicsconfig.GetFloat("av_movement_divisor_run", 0.8f); | 440 | avMovementDivisorRun = physicsconfig.GetFloat("av_movement_divisor_run", 0.8f); |
441 | avCapRadius = physicsconfig.GetFloat("av_capsule_radius", 0.37f); | 441 | avCapRadius = physicsconfig.GetFloat("av_capsule_radius", 0.37f); |
442 | avCapsuleTilted = physicsconfig.GetBoolean("av_capsule_tilted", true); | 442 | avCapsuleTilted = physicsconfig.GetBoolean("av_capsule_tilted", false); |
443 | 443 | ||
444 | contactsPerCollision = physicsconfig.GetInt("contacts_per_collision", 80); | 444 | contactsPerCollision = physicsconfig.GetInt("contacts_per_collision", 80); |
445 | 445 | ||
@@ -3541,7 +3541,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
3541 | public override void UnCombine(PhysicsScene pScene) | 3541 | public override void UnCombine(PhysicsScene pScene) |
3542 | { | 3542 | { |
3543 | IntPtr localGround = IntPtr.Zero; | 3543 | IntPtr localGround = IntPtr.Zero; |
3544 | float[] localHeightfield; | 3544 | // float[] localHeightfield; |
3545 | bool proceed = false; | 3545 | bool proceed = false; |
3546 | List<IntPtr> geomDestroyList = new List<IntPtr>(); | 3546 | List<IntPtr> geomDestroyList = new List<IntPtr>(); |
3547 | 3547 | ||
@@ -3553,7 +3553,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
3553 | { | 3553 | { |
3554 | if (geom == localGround) | 3554 | if (geom == localGround) |
3555 | { | 3555 | { |
3556 | localHeightfield = TerrainHeightFieldHeights[geom]; | 3556 | // localHeightfield = TerrainHeightFieldHeights[geom]; |
3557 | proceed = true; | 3557 | proceed = true; |
3558 | } | 3558 | } |
3559 | else | 3559 | else |
@@ -3575,7 +3575,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
3575 | // memory corruption | 3575 | // memory corruption |
3576 | if (TerrainHeightFieldHeights.ContainsKey(g)) | 3576 | if (TerrainHeightFieldHeights.ContainsKey(g)) |
3577 | { | 3577 | { |
3578 | float[] removingHeightField = TerrainHeightFieldHeights[g]; | 3578 | // float[] removingHeightField = TerrainHeightFieldHeights[g]; |
3579 | TerrainHeightFieldHeights.Remove(g); | 3579 | TerrainHeightFieldHeights.Remove(g); |
3580 | 3580 | ||
3581 | if (RegionTerrain.ContainsKey(g)) | 3581 | if (RegionTerrain.ContainsKey(g)) |
diff --git a/OpenSim/Region/CoreModules/World/Land/RegionCombinerClientEventForwarder.cs b/OpenSim/Region/RegionCombinerModule/RegionCombinerClientEventForwarder.cs index 70d6de3..721d396 100644 --- a/OpenSim/Region/CoreModules/World/Land/RegionCombinerClientEventForwarder.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionCombinerClientEventForwarder.cs | |||
@@ -30,7 +30,7 @@ using System.Collections.Generic; | |||
30 | using OpenMetaverse; | 30 | using OpenMetaverse; |
31 | using OpenSim.Region.Framework.Scenes; | 31 | using OpenSim.Region.Framework.Scenes; |
32 | 32 | ||
33 | namespace OpenSim.Region.CoreModules.World.Land | 33 | namespace OpenSim.Region.RegionCombinerModule |
34 | { | 34 | { |
35 | public class RegionCombinerClientEventForwarder | 35 | public class RegionCombinerClientEventForwarder |
36 | { | 36 | { |
diff --git a/OpenSim/Region/CoreModules/World/Land/RegionCombinerIndividualEventForwarder.cs b/OpenSim/Region/RegionCombinerModule/RegionCombinerIndividualEventForwarder.cs index 2cbaf96..9d41c9c 100644 --- a/OpenSim/Region/CoreModules/World/Land/RegionCombinerIndividualEventForwarder.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionCombinerIndividualEventForwarder.cs | |||
@@ -30,7 +30,7 @@ using OpenMetaverse; | |||
30 | using OpenSim.Framework; | 30 | using OpenSim.Framework; |
31 | using OpenSim.Region.Framework.Scenes; | 31 | using OpenSim.Region.Framework.Scenes; |
32 | 32 | ||
33 | namespace OpenSim.Region.CoreModules.World.Land | 33 | namespace OpenSim.Region.RegionCombinerModule |
34 | { | 34 | { |
35 | public class RegionCombinerIndividualEventForwarder | 35 | public class RegionCombinerIndividualEventForwarder |
36 | { | 36 | { |
diff --git a/OpenSim/Region/CoreModules/World/Land/RegionCombinerLargeLandChannel.cs b/OpenSim/Region/RegionCombinerModule/RegionCombinerLargeLandChannel.cs index 7df836c..146ec66 100644 --- a/OpenSim/Region/CoreModules/World/Land/RegionCombinerLargeLandChannel.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionCombinerLargeLandChannel.cs | |||
@@ -30,8 +30,9 @@ using System.Collections.Generic; | |||
30 | using OpenMetaverse; | 30 | using OpenMetaverse; |
31 | using OpenSim.Framework; | 31 | using OpenSim.Framework; |
32 | using OpenSim.Region.Framework.Interfaces; | 32 | using OpenSim.Region.Framework.Interfaces; |
33 | using OpenSim.Region.CoreModules.World.Land; | ||
33 | 34 | ||
34 | namespace OpenSim.Region.CoreModules.World.Land | 35 | namespace OpenSim.Region.RegionCombinerModule |
35 | { | 36 | { |
36 | public class RegionCombinerLargeLandChannel : ILandChannel | 37 | public class RegionCombinerLargeLandChannel : ILandChannel |
37 | { | 38 | { |
diff --git a/OpenSim/Region/CoreModules/World/Land/RegionCombinerModule.cs b/OpenSim/Region/RegionCombinerModule/RegionCombinerModule.cs index d8c5ed9..7ec1d4b 100644 --- a/OpenSim/Region/CoreModules/World/Land/RegionCombinerModule.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionCombinerModule.cs | |||
@@ -36,9 +36,15 @@ using OpenSim.Framework.Client; | |||
36 | using OpenSim.Region.Framework.Interfaces; | 36 | using OpenSim.Region.Framework.Interfaces; |
37 | using OpenSim.Region.Framework.Scenes; | 37 | using OpenSim.Region.Framework.Scenes; |
38 | using OpenSim.Framework.Console; | 38 | using OpenSim.Framework.Console; |
39 | using OpenSim.Region.Physics.Manager; | ||
40 | using Mono.Addins; | ||
39 | 41 | ||
40 | namespace OpenSim.Region.CoreModules.World.Land | 42 | [assembly: Addin("RegionCombinerModule", "0.1")] |
43 | [assembly: AddinDependency("OpenSim", "0.5")] | ||
44 | namespace OpenSim.Region.RegionCombinerModule | ||
41 | { | 45 | { |
46 | |||
47 | [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule")] | ||
42 | public class RegionCombinerModule : ISharedRegionModule | 48 | public class RegionCombinerModule : ISharedRegionModule |
43 | { | 49 | { |
44 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 50 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
@@ -299,76 +305,13 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
299 | //xxy | 305 | //xxy |
300 | //xxx | 306 | //xxx |
301 | 307 | ||
308 | |||
302 | if ((((int)conn.X * (int)Constants.RegionSize) + conn.XEnd | 309 | if ((((int)conn.X * (int)Constants.RegionSize) + conn.XEnd |
303 | >= (regionConnections.X * (int)Constants.RegionSize)) | 310 | >= (regionConnections.X * (int)Constants.RegionSize)) |
304 | && (((int)conn.Y * (int)Constants.RegionSize) | 311 | && (((int)conn.Y * (int)Constants.RegionSize) |
305 | >= (regionConnections.Y * (int)Constants.RegionSize))) | 312 | >= (regionConnections.Y * (int)Constants.RegionSize))) |
306 | { | 313 | { |
307 | Vector3 offset = Vector3.Zero; | 314 | connectedYN = DoWorkForOneRegionOverPlusXY(conn, regionConnections, scene); |
308 | offset.X = (((regionConnections.X * (int)Constants.RegionSize)) - | ||
309 | ((conn.X * (int)Constants.RegionSize))); | ||
310 | offset.Y = (((regionConnections.Y * (int)Constants.RegionSize)) - | ||
311 | ((conn.Y * (int)Constants.RegionSize))); | ||
312 | |||
313 | Vector3 extents = Vector3.Zero; | ||
314 | extents.Y = conn.YEnd; | ||
315 | extents.X = conn.XEnd + regionConnections.XEnd; | ||
316 | |||
317 | conn.UpdateExtents(extents); | ||
318 | |||
319 | m_log.DebugFormat("Scene: {0} to the west of Scene{1} Offset: {2}. Extents:{3}", | ||
320 | conn.RegionScene.RegionInfo.RegionName, | ||
321 | regionConnections.RegionScene.RegionInfo.RegionName, offset, extents); | ||
322 | |||
323 | scene.BordersLocked = true; | ||
324 | conn.RegionScene.BordersLocked = true; | ||
325 | |||
326 | RegionData ConnectedRegion = new RegionData(); | ||
327 | ConnectedRegion.Offset = offset; | ||
328 | ConnectedRegion.RegionId = scene.RegionInfo.originRegionID; | ||
329 | ConnectedRegion.RegionScene = scene; | ||
330 | conn.ConnectedRegions.Add(ConnectedRegion); | ||
331 | |||
332 | // Inform root region Physics about the extents of this region | ||
333 | conn.RegionScene.PhysicsScene.Combine(null, Vector3.Zero, extents); | ||
334 | |||
335 | // Inform Child region that it needs to forward it's terrain to the root region | ||
336 | scene.PhysicsScene.Combine(conn.RegionScene.PhysicsScene, offset, Vector3.Zero); | ||
337 | |||
338 | // Extend the borders as appropriate | ||
339 | lock (conn.RegionScene.EastBorders) | ||
340 | conn.RegionScene.EastBorders[0].BorderLine.Z += (int)Constants.RegionSize; | ||
341 | |||
342 | lock (conn.RegionScene.NorthBorders) | ||
343 | conn.RegionScene.NorthBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
344 | |||
345 | lock (conn.RegionScene.SouthBorders) | ||
346 | conn.RegionScene.SouthBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
347 | |||
348 | lock (scene.WestBorders) | ||
349 | { | ||
350 | |||
351 | |||
352 | scene.WestBorders[0].BorderLine.Z = (int)((scene.RegionInfo.RegionLocX - conn.RegionScene.RegionInfo.RegionLocX) * (int)Constants.RegionSize); //auto teleport West | ||
353 | |||
354 | // Trigger auto teleport to root region | ||
355 | scene.WestBorders[0].TriggerRegionX = conn.RegionScene.RegionInfo.RegionLocX; | ||
356 | scene.WestBorders[0].TriggerRegionY = conn.RegionScene.RegionInfo.RegionLocY; | ||
357 | } | ||
358 | |||
359 | // Reset Terrain.. since terrain loads before we get here, we need to load | ||
360 | // it again so it loads in the root region | ||
361 | |||
362 | scene.PhysicsScene.SetTerrain(scene.Heightmap.GetFloatsSerialised()); | ||
363 | |||
364 | // Unlock borders | ||
365 | conn.RegionScene.BordersLocked = false; | ||
366 | scene.BordersLocked = false; | ||
367 | |||
368 | // Create a client event forwarder and add this region's events to the root region. | ||
369 | if (conn.ClientEventForwarder != null) | ||
370 | conn.ClientEventForwarder.AddSceneToEventForwarding(scene); | ||
371 | connectedYN = true; | ||
372 | break; | 315 | break; |
373 | } | 316 | } |
374 | 317 | ||
@@ -381,57 +324,8 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
381 | && (((int)conn.Y * (int)Constants.RegionSize) + conn.YEnd | 324 | && (((int)conn.Y * (int)Constants.RegionSize) + conn.YEnd |
382 | >= (regionConnections.Y * (int)Constants.RegionSize))) | 325 | >= (regionConnections.Y * (int)Constants.RegionSize))) |
383 | { | 326 | { |
384 | Vector3 offset = Vector3.Zero; | 327 | connectedYN = DoWorkForOneRegionOverXPlusY(conn, regionConnections, scene); |
385 | offset.X = (((regionConnections.X * (int)Constants.RegionSize)) - | 328 | break; |
386 | ((conn.X * (int)Constants.RegionSize))); | ||
387 | offset.Y = (((regionConnections.Y * (int)Constants.RegionSize)) - | ||
388 | ((conn.Y * (int)Constants.RegionSize))); | ||
389 | |||
390 | Vector3 extents = Vector3.Zero; | ||
391 | extents.Y = regionConnections.YEnd + conn.YEnd; | ||
392 | extents.X = conn.XEnd; | ||
393 | conn.UpdateExtents(extents); | ||
394 | |||
395 | scene.BordersLocked = true; | ||
396 | conn.RegionScene.BordersLocked = true; | ||
397 | |||
398 | RegionData ConnectedRegion = new RegionData(); | ||
399 | ConnectedRegion.Offset = offset; | ||
400 | ConnectedRegion.RegionId = scene.RegionInfo.originRegionID; | ||
401 | ConnectedRegion.RegionScene = scene; | ||
402 | conn.ConnectedRegions.Add(ConnectedRegion); | ||
403 | |||
404 | m_log.DebugFormat("Scene: {0} to the northeast of Scene{1} Offset: {2}. Extents:{3}", | ||
405 | conn.RegionScene.RegionInfo.RegionName, | ||
406 | regionConnections.RegionScene.RegionInfo.RegionName, offset, extents); | ||
407 | |||
408 | conn.RegionScene.PhysicsScene.Combine(null, Vector3.Zero, extents); | ||
409 | scene.PhysicsScene.Combine(conn.RegionScene.PhysicsScene, offset, Vector3.Zero); | ||
410 | |||
411 | lock (conn.RegionScene.NorthBorders) | ||
412 | conn.RegionScene.NorthBorders[0].BorderLine.Z += (int)Constants.RegionSize; | ||
413 | lock (conn.RegionScene.EastBorders) | ||
414 | conn.RegionScene.EastBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
415 | lock (conn.RegionScene.WestBorders) | ||
416 | conn.RegionScene.WestBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
417 | lock (scene.SouthBorders) | ||
418 | { | ||
419 | scene.SouthBorders[0].BorderLine.Z = (int)((scene.RegionInfo.RegionLocY - conn.RegionScene.RegionInfo.RegionLocY) * (int)Constants.RegionSize); //auto teleport south | ||
420 | scene.SouthBorders[0].TriggerRegionX = conn.RegionScene.RegionInfo.RegionLocX; | ||
421 | scene.SouthBorders[0].TriggerRegionY = conn.RegionScene.RegionInfo.RegionLocY; | ||
422 | } | ||
423 | |||
424 | // Reset Terrain.. since terrain normally loads first. | ||
425 | //conn.RegionScene.PhysicsScene.SetTerrain(conn.RegionScene.Heightmap.GetFloatsSerialised()); | ||
426 | scene.PhysicsScene.SetTerrain(scene.Heightmap.GetFloatsSerialised()); | ||
427 | //conn.RegionScene.PhysicsScene.SetTerrain(conn.RegionScene.Heightmap.GetFloatsSerialised()); | ||
428 | |||
429 | scene.BordersLocked = false; | ||
430 | conn.RegionScene.BordersLocked = false; | ||
431 | if (conn.ClientEventForwarder != null) | ||
432 | conn.ClientEventForwarder.AddSceneToEventForwarding(scene); | ||
433 | connectedYN = true; | ||
434 | break; | ||
435 | } | 329 | } |
436 | 330 | ||
437 | // If we're one region over +x +y | 331 | // If we're one region over +x +y |
@@ -443,140 +337,276 @@ namespace OpenSim.Region.CoreModules.World.Land | |||
443 | && (((int)conn.Y * (int)Constants.RegionSize) + conn.YEnd | 337 | && (((int)conn.Y * (int)Constants.RegionSize) + conn.YEnd |
444 | >= (regionConnections.Y * (int)Constants.RegionSize))) | 338 | >= (regionConnections.Y * (int)Constants.RegionSize))) |
445 | { | 339 | { |
446 | Vector3 offset = Vector3.Zero; | 340 | connectedYN = DoWorkForOneRegionOverPlusXPlusY(conn, regionConnections, scene); |
447 | offset.X = (((regionConnections.X * (int)Constants.RegionSize)) - | 341 | break; |
448 | ((conn.X * (int)Constants.RegionSize))); | ||
449 | offset.Y = (((regionConnections.Y * (int)Constants.RegionSize)) - | ||
450 | ((conn.Y * (int)Constants.RegionSize))); | ||
451 | 342 | ||
452 | Vector3 extents = Vector3.Zero; | 343 | } |
453 | extents.Y = regionConnections.YEnd + conn.YEnd; | 344 | } |
454 | extents.X = regionConnections.XEnd + conn.XEnd; | ||
455 | conn.UpdateExtents(extents); | ||
456 | 345 | ||
457 | scene.BordersLocked = true; | 346 | // If !connectYN means that this region is a root region |
458 | conn.RegionScene.BordersLocked = true; | 347 | if (!connectedYN) |
348 | { | ||
349 | DoWorkForRootRegion(regionConnections, scene); | ||
459 | 350 | ||
460 | RegionData ConnectedRegion = new RegionData(); | 351 | } |
461 | ConnectedRegion.Offset = offset; | 352 | } |
462 | ConnectedRegion.RegionId = scene.RegionInfo.originRegionID; | 353 | // Set up infinite borders around the entire AABB of the combined ConnectedRegions |
463 | ConnectedRegion.RegionScene = scene; | 354 | AdjustLargeRegionBounds(); |
355 | } | ||
464 | 356 | ||
465 | conn.ConnectedRegions.Add(ConnectedRegion); | 357 | private bool DoWorkForOneRegionOverPlusXY(RegionConnections conn, RegionConnections regionConnections, Scene scene) |
358 | { | ||
359 | Vector3 offset = Vector3.Zero; | ||
360 | offset.X = (((regionConnections.X * (int)Constants.RegionSize)) - | ||
361 | ((conn.X * (int)Constants.RegionSize))); | ||
362 | offset.Y = (((regionConnections.Y * (int)Constants.RegionSize)) - | ||
363 | ((conn.Y * (int)Constants.RegionSize))); | ||
466 | 364 | ||
467 | m_log.DebugFormat("Scene: {0} to the NorthEast of Scene{1} Offset: {2}. Extents:{3}", | 365 | Vector3 extents = Vector3.Zero; |
468 | conn.RegionScene.RegionInfo.RegionName, | 366 | extents.Y = conn.YEnd; |
469 | regionConnections.RegionScene.RegionInfo.RegionName, offset, extents); | 367 | extents.X = conn.XEnd + regionConnections.XEnd; |
470 | 368 | ||
471 | conn.RegionScene.PhysicsScene.Combine(null, Vector3.Zero, extents); | 369 | conn.UpdateExtents(extents); |
472 | scene.PhysicsScene.Combine(conn.RegionScene.PhysicsScene, offset, Vector3.Zero); | ||
473 | lock (conn.RegionScene.NorthBorders) | ||
474 | { | ||
475 | if (conn.RegionScene.NorthBorders.Count == 1)// && 2) | ||
476 | { | ||
477 | //compound border | ||
478 | // already locked above | ||
479 | conn.RegionScene.NorthBorders[0].BorderLine.Z += (int)Constants.RegionSize; | ||
480 | |||
481 | lock (conn.RegionScene.EastBorders) | ||
482 | conn.RegionScene.EastBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
483 | lock (conn.RegionScene.WestBorders) | ||
484 | conn.RegionScene.WestBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
485 | } | ||
486 | } | ||
487 | 370 | ||
488 | lock (scene.SouthBorders) | 371 | m_log.DebugFormat("Scene: {0} to the west of Scene{1} Offset: {2}. Extents:{3}", |
489 | { | 372 | conn.RegionScene.RegionInfo.RegionName, |
490 | scene.SouthBorders[0].BorderLine.Z = (int)((scene.RegionInfo.RegionLocY - conn.RegionScene.RegionInfo.RegionLocY) * (int)Constants.RegionSize); //auto teleport south | 373 | regionConnections.RegionScene.RegionInfo.RegionName, offset, extents); |
491 | scene.SouthBorders[0].TriggerRegionX = conn.RegionScene.RegionInfo.RegionLocX; | ||
492 | scene.SouthBorders[0].TriggerRegionY = conn.RegionScene.RegionInfo.RegionLocY; | ||
493 | } | ||
494 | 374 | ||
495 | lock (conn.RegionScene.EastBorders) | 375 | scene.BordersLocked = true; |
496 | { | 376 | conn.RegionScene.BordersLocked = true; |
497 | if (conn.RegionScene.EastBorders.Count == 1)// && conn.RegionScene.EastBorders.Count == 2) | ||
498 | { | ||
499 | 377 | ||
500 | conn.RegionScene.EastBorders[0].BorderLine.Z += (int)Constants.RegionSize; | 378 | RegionData ConnectedRegion = new RegionData(); |
501 | lock (conn.RegionScene.NorthBorders) | 379 | ConnectedRegion.Offset = offset; |
502 | conn.RegionScene.NorthBorders[0].BorderLine.Y += (int)Constants.RegionSize; | 380 | ConnectedRegion.RegionId = scene.RegionInfo.originRegionID; |
503 | lock (conn.RegionScene.SouthBorders) | 381 | ConnectedRegion.RegionScene = scene; |
504 | conn.RegionScene.SouthBorders[0].BorderLine.Y += (int)Constants.RegionSize; | 382 | conn.ConnectedRegions.Add(ConnectedRegion); |
505 | 383 | ||
384 | // Inform root region Physics about the extents of this region | ||
385 | conn.RegionScene.PhysicsScene.Combine(null, Vector3.Zero, extents); | ||
506 | 386 | ||
507 | } | 387 | // Inform Child region that it needs to forward it's terrain to the root region |
508 | } | 388 | scene.PhysicsScene.Combine(conn.RegionScene.PhysicsScene, offset, Vector3.Zero); |
509 | 389 | ||
510 | lock (scene.WestBorders) | 390 | // Extend the borders as appropriate |
511 | { | 391 | lock (conn.RegionScene.EastBorders) |
512 | scene.WestBorders[0].BorderLine.Z = (int)((scene.RegionInfo.RegionLocX - conn.RegionScene.RegionInfo.RegionLocX) * (int)Constants.RegionSize); //auto teleport West | 392 | conn.RegionScene.EastBorders[0].BorderLine.Z += (int)Constants.RegionSize; |
513 | scene.WestBorders[0].TriggerRegionX = conn.RegionScene.RegionInfo.RegionLocX; | ||
514 | scene.WestBorders[0].TriggerRegionY = conn.RegionScene.RegionInfo.RegionLocY; | ||
515 | } | ||
516 | 393 | ||
517 | /* | 394 | lock (conn.RegionScene.NorthBorders) |
518 | else | 395 | conn.RegionScene.NorthBorders[0].BorderLine.Y += (int)Constants.RegionSize; |
519 | { | 396 | |
520 | conn.RegionScene.NorthBorders[0].BorderLine.Z += (int)Constants.RegionSize; | 397 | lock (conn.RegionScene.SouthBorders) |
521 | conn.RegionScene.EastBorders[0].BorderLine.Y += (int)Constants.RegionSize; | 398 | conn.RegionScene.SouthBorders[0].BorderLine.Y += (int)Constants.RegionSize; |
522 | conn.RegionScene.WestBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
523 | scene.SouthBorders[0].BorderLine.Z += (int)Constants.RegionSize; //auto teleport south | ||
524 | } | ||
525 | */ | ||
526 | 399 | ||
400 | lock (scene.WestBorders) | ||
401 | { | ||
527 | 402 | ||
528 | // Reset Terrain.. since terrain normally loads first. | ||
529 | //conn.RegionScene.PhysicsScene.SetTerrain(conn.RegionScene.Heightmap.GetFloatsSerialised()); | ||
530 | scene.PhysicsScene.SetTerrain(scene.Heightmap.GetFloatsSerialised()); | ||
531 | //conn.RegionScene.PhysicsScene.SetTerrain(conn.RegionScene.Heightmap.GetFloatsSerialised()); | ||
532 | scene.BordersLocked = false; | ||
533 | conn.RegionScene.BordersLocked = false; | ||
534 | 403 | ||
535 | if (conn.ClientEventForwarder != null) | 404 | scene.WestBorders[0].BorderLine.Z = (int)((scene.RegionInfo.RegionLocX - conn.RegionScene.RegionInfo.RegionLocX) * (int)Constants.RegionSize); //auto teleport West |
536 | conn.ClientEventForwarder.AddSceneToEventForwarding(scene); | ||
537 | 405 | ||
538 | connectedYN = true; | 406 | // Trigger auto teleport to root region |
407 | scene.WestBorders[0].TriggerRegionX = conn.RegionScene.RegionInfo.RegionLocX; | ||
408 | scene.WestBorders[0].TriggerRegionY = conn.RegionScene.RegionInfo.RegionLocY; | ||
409 | } | ||
539 | 410 | ||
540 | //scene.PhysicsScene.Combine(conn.RegionScene.PhysicsScene, offset,extents); | 411 | // Reset Terrain.. since terrain loads before we get here, we need to load |
412 | // it again so it loads in the root region | ||
541 | 413 | ||
542 | break; | 414 | scene.PhysicsScene.SetTerrain(scene.Heightmap.GetFloatsSerialised()); |
543 | } | 415 | |
416 | // Unlock borders | ||
417 | conn.RegionScene.BordersLocked = false; | ||
418 | scene.BordersLocked = false; | ||
419 | |||
420 | // Create a client event forwarder and add this region's events to the root region. | ||
421 | if (conn.ClientEventForwarder != null) | ||
422 | conn.ClientEventForwarder.AddSceneToEventForwarding(scene); | ||
423 | |||
424 | return true; | ||
425 | } | ||
426 | |||
427 | private bool DoWorkForOneRegionOverXPlusY(RegionConnections conn, RegionConnections regionConnections, Scene scene) | ||
428 | { | ||
429 | Vector3 offset = Vector3.Zero; | ||
430 | offset.X = (((regionConnections.X * (int)Constants.RegionSize)) - | ||
431 | ((conn.X * (int)Constants.RegionSize))); | ||
432 | offset.Y = (((regionConnections.Y * (int)Constants.RegionSize)) - | ||
433 | ((conn.Y * (int)Constants.RegionSize))); | ||
434 | |||
435 | Vector3 extents = Vector3.Zero; | ||
436 | extents.Y = regionConnections.YEnd + conn.YEnd; | ||
437 | extents.X = conn.XEnd; | ||
438 | conn.UpdateExtents(extents); | ||
439 | |||
440 | scene.BordersLocked = true; | ||
441 | conn.RegionScene.BordersLocked = true; | ||
442 | |||
443 | RegionData ConnectedRegion = new RegionData(); | ||
444 | ConnectedRegion.Offset = offset; | ||
445 | ConnectedRegion.RegionId = scene.RegionInfo.originRegionID; | ||
446 | ConnectedRegion.RegionScene = scene; | ||
447 | conn.ConnectedRegions.Add(ConnectedRegion); | ||
448 | |||
449 | m_log.DebugFormat("Scene: {0} to the northeast of Scene{1} Offset: {2}. Extents:{3}", | ||
450 | conn.RegionScene.RegionInfo.RegionName, | ||
451 | regionConnections.RegionScene.RegionInfo.RegionName, offset, extents); | ||
452 | |||
453 | conn.RegionScene.PhysicsScene.Combine(null, Vector3.Zero, extents); | ||
454 | scene.PhysicsScene.Combine(conn.RegionScene.PhysicsScene, offset, Vector3.Zero); | ||
455 | |||
456 | lock (conn.RegionScene.NorthBorders) | ||
457 | conn.RegionScene.NorthBorders[0].BorderLine.Z += (int)Constants.RegionSize; | ||
458 | lock (conn.RegionScene.EastBorders) | ||
459 | conn.RegionScene.EastBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
460 | lock (conn.RegionScene.WestBorders) | ||
461 | conn.RegionScene.WestBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
462 | lock (scene.SouthBorders) | ||
463 | { | ||
464 | scene.SouthBorders[0].BorderLine.Z = (int)((scene.RegionInfo.RegionLocY - conn.RegionScene.RegionInfo.RegionLocY) * (int)Constants.RegionSize); //auto teleport south | ||
465 | scene.SouthBorders[0].TriggerRegionX = conn.RegionScene.RegionInfo.RegionLocX; | ||
466 | scene.SouthBorders[0].TriggerRegionY = conn.RegionScene.RegionInfo.RegionLocY; | ||
467 | } | ||
468 | |||
469 | // Reset Terrain.. since terrain normally loads first. | ||
470 | //conn.RegionScene.PhysicsScene.SetTerrain(conn.RegionScene.Heightmap.GetFloatsSerialised()); | ||
471 | scene.PhysicsScene.SetTerrain(scene.Heightmap.GetFloatsSerialised()); | ||
472 | //conn.RegionScene.PhysicsScene.SetTerrain(conn.RegionScene.Heightmap.GetFloatsSerialised()); | ||
473 | |||
474 | scene.BordersLocked = false; | ||
475 | conn.RegionScene.BordersLocked = false; | ||
476 | if (conn.ClientEventForwarder != null) | ||
477 | conn.ClientEventForwarder.AddSceneToEventForwarding(scene); | ||
478 | return true; | ||
479 | } | ||
480 | |||
481 | private bool DoWorkForOneRegionOverPlusXPlusY(RegionConnections conn, RegionConnections regionConnections, Scene scene) | ||
482 | { | ||
483 | Vector3 offset = Vector3.Zero; | ||
484 | offset.X = (((regionConnections.X * (int)Constants.RegionSize)) - | ||
485 | ((conn.X * (int)Constants.RegionSize))); | ||
486 | offset.Y = (((regionConnections.Y * (int)Constants.RegionSize)) - | ||
487 | ((conn.Y * (int)Constants.RegionSize))); | ||
488 | |||
489 | Vector3 extents = Vector3.Zero; | ||
490 | extents.Y = regionConnections.YEnd + conn.YEnd; | ||
491 | extents.X = regionConnections.XEnd + conn.XEnd; | ||
492 | conn.UpdateExtents(extents); | ||
493 | |||
494 | scene.BordersLocked = true; | ||
495 | conn.RegionScene.BordersLocked = true; | ||
496 | |||
497 | RegionData ConnectedRegion = new RegionData(); | ||
498 | ConnectedRegion.Offset = offset; | ||
499 | ConnectedRegion.RegionId = scene.RegionInfo.originRegionID; | ||
500 | ConnectedRegion.RegionScene = scene; | ||
501 | |||
502 | conn.ConnectedRegions.Add(ConnectedRegion); | ||
503 | |||
504 | m_log.DebugFormat("Scene: {0} to the NorthEast of Scene{1} Offset: {2}. Extents:{3}", | ||
505 | conn.RegionScene.RegionInfo.RegionName, | ||
506 | regionConnections.RegionScene.RegionInfo.RegionName, offset, extents); | ||
507 | |||
508 | conn.RegionScene.PhysicsScene.Combine(null, Vector3.Zero, extents); | ||
509 | scene.PhysicsScene.Combine(conn.RegionScene.PhysicsScene, offset, Vector3.Zero); | ||
510 | lock (conn.RegionScene.NorthBorders) | ||
511 | { | ||
512 | if (conn.RegionScene.NorthBorders.Count == 1)// && 2) | ||
513 | { | ||
514 | //compound border | ||
515 | // already locked above | ||
516 | conn.RegionScene.NorthBorders[0].BorderLine.Z += (int)Constants.RegionSize; | ||
517 | |||
518 | lock (conn.RegionScene.EastBorders) | ||
519 | conn.RegionScene.EastBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
520 | lock (conn.RegionScene.WestBorders) | ||
521 | conn.RegionScene.WestBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
544 | } | 522 | } |
523 | } | ||
545 | 524 | ||
546 | // If !connectYN means that this region is a root region | 525 | lock (scene.SouthBorders) |
547 | if (!connectedYN) | 526 | { |
527 | scene.SouthBorders[0].BorderLine.Z = (int)((scene.RegionInfo.RegionLocY - conn.RegionScene.RegionInfo.RegionLocY) * (int)Constants.RegionSize); //auto teleport south | ||
528 | scene.SouthBorders[0].TriggerRegionX = conn.RegionScene.RegionInfo.RegionLocX; | ||
529 | scene.SouthBorders[0].TriggerRegionY = conn.RegionScene.RegionInfo.RegionLocY; | ||
530 | } | ||
531 | |||
532 | lock (conn.RegionScene.EastBorders) | ||
533 | { | ||
534 | if (conn.RegionScene.EastBorders.Count == 1)// && conn.RegionScene.EastBorders.Count == 2) | ||
548 | { | 535 | { |
549 | RegionData rdata = new RegionData(); | ||
550 | rdata.Offset = Vector3.Zero; | ||
551 | rdata.RegionId = scene.RegionInfo.originRegionID; | ||
552 | rdata.RegionScene = scene; | ||
553 | // save it's land channel | ||
554 | regionConnections.RegionLandChannel = scene.LandChannel; | ||
555 | |||
556 | // Substitue our landchannel | ||
557 | RegionCombinerLargeLandChannel lnd = new RegionCombinerLargeLandChannel(rdata, scene.LandChannel, | ||
558 | regionConnections.ConnectedRegions); | ||
559 | scene.LandChannel = lnd; | ||
560 | // Forward the permissions modules of each of the connected regions to the root region | ||
561 | lock (m_regions) | ||
562 | { | ||
563 | foreach (RegionData r in regionConnections.ConnectedRegions) | ||
564 | { | ||
565 | ForwardPermissionRequests(regionConnections, r.RegionScene); | ||
566 | } | ||
567 | } | ||
568 | // Create the root region's Client Event Forwarder | ||
569 | regionConnections.ClientEventForwarder = new RegionCombinerClientEventForwarder(regionConnections); | ||
570 | 536 | ||
571 | // Sets up the CoarseLocationUpdate forwarder for this root region | 537 | conn.RegionScene.EastBorders[0].BorderLine.Z += (int)Constants.RegionSize; |
572 | scene.EventManager.OnNewPresence += SetCourseLocationDelegate; | 538 | lock (conn.RegionScene.NorthBorders) |
539 | conn.RegionScene.NorthBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
540 | lock (conn.RegionScene.SouthBorders) | ||
541 | conn.RegionScene.SouthBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
542 | |||
573 | 543 | ||
574 | // Adds this root region to a dictionary of regions that are connectable | ||
575 | m_regions.Add(scene.RegionInfo.originRegionID, regionConnections); | ||
576 | } | 544 | } |
577 | } | 545 | } |
578 | // Set up infinite borders around the entire AABB of the combined ConnectedRegions | 546 | |
579 | AdjustLargeRegionBounds(); | 547 | lock (scene.WestBorders) |
548 | { | ||
549 | scene.WestBorders[0].BorderLine.Z = (int)((scene.RegionInfo.RegionLocX - conn.RegionScene.RegionInfo.RegionLocX) * (int)Constants.RegionSize); //auto teleport West | ||
550 | scene.WestBorders[0].TriggerRegionX = conn.RegionScene.RegionInfo.RegionLocX; | ||
551 | scene.WestBorders[0].TriggerRegionY = conn.RegionScene.RegionInfo.RegionLocY; | ||
552 | } | ||
553 | |||
554 | /* | ||
555 | else | ||
556 | { | ||
557 | conn.RegionScene.NorthBorders[0].BorderLine.Z += (int)Constants.RegionSize; | ||
558 | conn.RegionScene.EastBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
559 | conn.RegionScene.WestBorders[0].BorderLine.Y += (int)Constants.RegionSize; | ||
560 | scene.SouthBorders[0].BorderLine.Z += (int)Constants.RegionSize; //auto teleport south | ||
561 | } | ||
562 | */ | ||
563 | |||
564 | |||
565 | // Reset Terrain.. since terrain normally loads first. | ||
566 | //conn.RegionScene.PhysicsScene.SetTerrain(conn.RegionScene.Heightmap.GetFloatsSerialised()); | ||
567 | scene.PhysicsScene.SetTerrain(scene.Heightmap.GetFloatsSerialised()); | ||
568 | //conn.RegionScene.PhysicsScene.SetTerrain(conn.RegionScene.Heightmap.GetFloatsSerialised()); | ||
569 | scene.BordersLocked = false; | ||
570 | conn.RegionScene.BordersLocked = false; | ||
571 | |||
572 | if (conn.ClientEventForwarder != null) | ||
573 | conn.ClientEventForwarder.AddSceneToEventForwarding(scene); | ||
574 | |||
575 | return true; | ||
576 | |||
577 | //scene.PhysicsScene.Combine(conn.RegionScene.PhysicsScene, offset,extents); | ||
578 | |||
579 | } | ||
580 | |||
581 | private void DoWorkForRootRegion(RegionConnections regionConnections, Scene scene) | ||
582 | { | ||
583 | RegionData rdata = new RegionData(); | ||
584 | rdata.Offset = Vector3.Zero; | ||
585 | rdata.RegionId = scene.RegionInfo.originRegionID; | ||
586 | rdata.RegionScene = scene; | ||
587 | // save it's land channel | ||
588 | regionConnections.RegionLandChannel = scene.LandChannel; | ||
589 | |||
590 | // Substitue our landchannel | ||
591 | RegionCombinerLargeLandChannel lnd = new RegionCombinerLargeLandChannel(rdata, scene.LandChannel, | ||
592 | regionConnections.ConnectedRegions); | ||
593 | scene.LandChannel = lnd; | ||
594 | // Forward the permissions modules of each of the connected regions to the root region | ||
595 | lock (m_regions) | ||
596 | { | ||
597 | foreach (RegionData r in regionConnections.ConnectedRegions) | ||
598 | { | ||
599 | ForwardPermissionRequests(regionConnections, r.RegionScene); | ||
600 | } | ||
601 | } | ||
602 | // Create the root region's Client Event Forwarder | ||
603 | regionConnections.ClientEventForwarder = new RegionCombinerClientEventForwarder(regionConnections); | ||
604 | |||
605 | // Sets up the CoarseLocationUpdate forwarder for this root region | ||
606 | scene.EventManager.OnNewPresence += SetCourseLocationDelegate; | ||
607 | |||
608 | // Adds this root region to a dictionary of regions that are connectable | ||
609 | m_regions.Add(scene.RegionInfo.originRegionID, regionConnections); | ||
580 | } | 610 | } |
581 | 611 | ||
582 | private void SetCourseLocationDelegate(ScenePresence presence) | 612 | private void SetCourseLocationDelegate(ScenePresence presence) |
diff --git a/OpenSim/Region/CoreModules/World/Land/RegionCombinerPermissionModule.cs b/OpenSim/Region/RegionCombinerModule/RegionCombinerPermissionModule.cs index 76ca5e3..4d1af57 100644 --- a/OpenSim/Region/CoreModules/World/Land/RegionCombinerPermissionModule.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionCombinerPermissionModule.cs | |||
@@ -32,7 +32,7 @@ using OpenSim.Framework; | |||
32 | using OpenSim.Region.Framework.Interfaces; | 32 | using OpenSim.Region.Framework.Interfaces; |
33 | using OpenSim.Region.Framework.Scenes; | 33 | using OpenSim.Region.Framework.Scenes; |
34 | 34 | ||
35 | namespace OpenSim.Region.CoreModules.World.Land | 35 | namespace OpenSim.Region.RegionCombinerModule |
36 | { | 36 | { |
37 | public class RegionCombinerPermissionModule | 37 | public class RegionCombinerPermissionModule |
38 | { | 38 | { |
diff --git a/OpenSim/Region/CoreModules/World/Land/RegionConnections.cs b/OpenSim/Region/RegionCombinerModule/RegionConnections.cs index 419ed74..3aa9f20 100644 --- a/OpenSim/Region/CoreModules/World/Land/RegionConnections.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionConnections.cs | |||
@@ -31,7 +31,7 @@ using OpenMetaverse; | |||
31 | using OpenSim.Region.Framework.Interfaces; | 31 | using OpenSim.Region.Framework.Interfaces; |
32 | using OpenSim.Region.Framework.Scenes; | 32 | using OpenSim.Region.Framework.Scenes; |
33 | 33 | ||
34 | namespace OpenSim.Region.CoreModules.World.Land | 34 | namespace OpenSim.Region.RegionCombinerModule |
35 | { | 35 | { |
36 | public class RegionConnections | 36 | public class RegionConnections |
37 | { | 37 | { |
diff --git a/OpenSim/Region/CoreModules/World/Land/RegionCourseLocation.cs b/OpenSim/Region/RegionCombinerModule/RegionCourseLocation.cs index 175ca89..53a678f 100644 --- a/OpenSim/Region/CoreModules/World/Land/RegionCourseLocation.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionCourseLocation.cs | |||
@@ -30,7 +30,7 @@ using System.Collections.Generic; | |||
30 | using OpenMetaverse; | 30 | using OpenMetaverse; |
31 | using OpenSim.Framework; | 31 | using OpenSim.Framework; |
32 | 32 | ||
33 | namespace OpenSim.Region.CoreModules.World.Land | 33 | namespace OpenSim.Region.RegionCombinerModule |
34 | { | 34 | { |
35 | 35 | ||
36 | struct RegionCourseLocationStruct | 36 | struct RegionCourseLocationStruct |
diff --git a/OpenSim/Region/CoreModules/World/Land/RegionData.cs b/OpenSim/Region/RegionCombinerModule/RegionData.cs index 3383527..bd0e398 100644 --- a/OpenSim/Region/CoreModules/World/Land/RegionData.cs +++ b/OpenSim/Region/RegionCombinerModule/RegionData.cs | |||
@@ -28,7 +28,7 @@ | |||
28 | using OpenMetaverse; | 28 | using OpenMetaverse; |
29 | using OpenSim.Region.Framework.Scenes; | 29 | using OpenSim.Region.Framework.Scenes; |
30 | 30 | ||
31 | namespace OpenSim.Region.CoreModules.World.Land | 31 | namespace OpenSim.Region.RegionCombinerModule |
32 | { | 32 | { |
33 | public class RegionData | 33 | public class RegionData |
34 | { | 34 | { |
diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/MOD_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/MOD_Api.cs new file mode 100644 index 0000000..d4facdd --- /dev/null +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/MOD_Api.cs | |||
@@ -0,0 +1,134 @@ | |||
1 | /* | ||
2 | * Copyright (c) Contributors, http://opensimulator.org/ | ||
3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. | ||
4 | * | ||
5 | * Redistribution and use in source and binary forms, with or without | ||
6 | * modification, are permitted provided that the following conditions are met: | ||
7 | * * Redistributions of source code must retain the above copyright | ||
8 | * notice, this list of conditions and the following disclaimer. | ||
9 | * * Redistributions in binary form must reproduce the above copyright | ||
10 | * notice, this list of conditions and the following disclaimer in the | ||
11 | * documentation and/or other materials provided with the distribution. | ||
12 | * * Neither the name of the OpenSimulator Project nor the | ||
13 | * names of its contributors may be used to endorse or promote products | ||
14 | * derived from this software without specific prior written permission. | ||
15 | * | ||
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY | ||
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | ||
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
26 | */ | ||
27 | |||
28 | using System; | ||
29 | using System.Reflection; | ||
30 | using System.Collections; | ||
31 | using System.Collections.Generic; | ||
32 | using System.Runtime.Remoting.Lifetime; | ||
33 | using OpenMetaverse; | ||
34 | using Nini.Config; | ||
35 | using OpenSim; | ||
36 | using OpenSim.Framework; | ||
37 | using OpenSim.Region.Framework.Interfaces; | ||
38 | using OpenSim.Region.Framework.Scenes; | ||
39 | using OpenSim.Region.ScriptEngine.Shared; | ||
40 | using OpenSim.Region.ScriptEngine.Shared.Api.Plugins; | ||
41 | using OpenSim.Region.ScriptEngine.Shared.ScriptBase; | ||
42 | using OpenSim.Region.ScriptEngine.Interfaces; | ||
43 | using OpenSim.Region.ScriptEngine.Shared.Api.Interfaces; | ||
44 | |||
45 | using LSL_Float = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLFloat; | ||
46 | using LSL_Integer = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLInteger; | ||
47 | using LSL_Key = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; | ||
48 | using LSL_List = OpenSim.Region.ScriptEngine.Shared.LSL_Types.list; | ||
49 | using LSL_Rotation = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Quaternion; | ||
50 | using LSL_String = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; | ||
51 | using LSL_Vector = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Vector3; | ||
52 | |||
53 | namespace OpenSim.Region.ScriptEngine.Shared.Api | ||
54 | { | ||
55 | [Serializable] | ||
56 | public class MOD_Api : MarshalByRefObject, IMOD_Api, IScriptApi | ||
57 | { | ||
58 | internal IScriptEngine m_ScriptEngine; | ||
59 | internal SceneObjectPart m_host; | ||
60 | internal uint m_localID; | ||
61 | internal UUID m_itemID; | ||
62 | internal bool m_MODFunctionsEnabled = false; | ||
63 | internal IScriptModuleComms m_comms = null; | ||
64 | |||
65 | public void Initialize(IScriptEngine ScriptEngine, SceneObjectPart host, uint localID, UUID itemID) | ||
66 | { | ||
67 | m_ScriptEngine = ScriptEngine; | ||
68 | m_host = host; | ||
69 | m_localID = localID; | ||
70 | m_itemID = itemID; | ||
71 | |||
72 | if (m_ScriptEngine.Config.GetBoolean("AllowMODFunctions", false)) | ||
73 | m_MODFunctionsEnabled = true; | ||
74 | |||
75 | m_comms = m_ScriptEngine.World.RequestModuleInterface<IScriptModuleComms>(); | ||
76 | if (m_comms == null) | ||
77 | m_MODFunctionsEnabled = false; | ||
78 | } | ||
79 | |||
80 | public override Object InitializeLifetimeService() | ||
81 | { | ||
82 | ILease lease = (ILease)base.InitializeLifetimeService(); | ||
83 | |||
84 | if (lease.CurrentState == LeaseState.Initial) | ||
85 | { | ||
86 | lease.InitialLeaseTime = TimeSpan.FromMinutes(0); | ||
87 | // lease.RenewOnCallTime = TimeSpan.FromSeconds(10.0); | ||
88 | // lease.SponsorshipTimeout = TimeSpan.FromMinutes(1.0); | ||
89 | } | ||
90 | return lease; | ||
91 | } | ||
92 | |||
93 | public Scene World | ||
94 | { | ||
95 | get { return m_ScriptEngine.World; } | ||
96 | } | ||
97 | |||
98 | internal void MODError(string msg) | ||
99 | { | ||
100 | throw new Exception("MOD Runtime Error: " + msg); | ||
101 | } | ||
102 | |||
103 | // | ||
104 | //Dumps an error message on the debug console. | ||
105 | // | ||
106 | |||
107 | internal void MODShoutError(string message) | ||
108 | { | ||
109 | if (message.Length > 1023) | ||
110 | message = message.Substring(0, 1023); | ||
111 | |||
112 | World.SimChat(Utils.StringToBytes(message), | ||
113 | ChatTypeEnum.Shout, ScriptBaseClass.DEBUG_CHANNEL, m_host.ParentGroup.RootPart.AbsolutePosition, m_host.Name, m_host.UUID, true); | ||
114 | |||
115 | IWorldComm wComm = m_ScriptEngine.World.RequestModuleInterface<IWorldComm>(); | ||
116 | wComm.DeliverMessage(ChatTypeEnum.Shout, ScriptBaseClass.DEBUG_CHANNEL, m_host.Name, m_host.UUID, message); | ||
117 | } | ||
118 | |||
119 | public string modSendCommand(string module, string command, string k) | ||
120 | { | ||
121 | if (!m_MODFunctionsEnabled) | ||
122 | { | ||
123 | MODShoutError("Module command functions not enabled"); | ||
124 | return UUID.Zero.ToString();; | ||
125 | } | ||
126 | |||
127 | UUID req = UUID.Random(); | ||
128 | |||
129 | m_comms.RaiseEvent(m_itemID, req.ToString(), module, command, k); | ||
130 | |||
131 | return req.ToString(); | ||
132 | } | ||
133 | } | ||
134 | } | ||
diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs index 52396b6..3ffcff0 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/OSSL_Api.cs | |||
@@ -199,7 +199,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
199 | //Dumps an error message on the debug console. | 199 | //Dumps an error message on the debug console. |
200 | // | 200 | // |
201 | 201 | ||
202 | internal void OSSLShoutError(string message) | 202 | internal void OSSLShoutError(string message) |
203 | { | 203 | { |
204 | if (message.Length > 1023) | 204 | if (message.Length > 1023) |
205 | message = message.Substring(0, 1023); | 205 | message = message.Substring(0, 1023); |
@@ -384,7 +384,14 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
384 | m_host.AddScriptLPS(1); | 384 | m_host.AddScriptLPS(1); |
385 | if (World.Entities.ContainsKey(target)) | 385 | if (World.Entities.ContainsKey(target)) |
386 | { | 386 | { |
387 | World.Entities[target].Rotation = rotation; | 387 | EntityBase entity; |
388 | if (World.Entities.TryGetValue(target, out entity)) | ||
389 | { | ||
390 | if (entity is SceneObjectGroup) | ||
391 | ((SceneObjectGroup)entity).Rotation = rotation; | ||
392 | else if (entity is ScenePresence) | ||
393 | ((ScenePresence)entity).Rotation = rotation; | ||
394 | } | ||
388 | } | 395 | } |
389 | else | 396 | else |
390 | { | 397 | { |
@@ -1169,7 +1176,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1169 | 1176 | ||
1170 | land.SetMediaUrl(url); | 1177 | land.SetMediaUrl(url); |
1171 | } | 1178 | } |
1172 | 1179 | ||
1173 | public void osSetParcelSIPAddress(string SIPAddress) | 1180 | public void osSetParcelSIPAddress(string SIPAddress) |
1174 | { | 1181 | { |
1175 | // What actually is the difference to the LL function? | 1182 | // What actually is the difference to the LL function? |
@@ -1177,7 +1184,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1177 | CheckThreatLevel(ThreatLevel.VeryLow, "osSetParcelMediaURL"); | 1184 | CheckThreatLevel(ThreatLevel.VeryLow, "osSetParcelMediaURL"); |
1178 | 1185 | ||
1179 | m_host.AddScriptLPS(1); | 1186 | m_host.AddScriptLPS(1); |
1180 | 1187 | ||
1181 | 1188 | ||
1182 | ILandObject land | 1189 | ILandObject land |
1183 | = World.LandChannel.GetLandObject(m_host.AbsolutePosition.X, m_host.AbsolutePosition.Y); | 1190 | = World.LandChannel.GetLandObject(m_host.AbsolutePosition.X, m_host.AbsolutePosition.Y); |
@@ -1187,16 +1194,16 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1187 | OSSLError("osSetParcelSIPAddress: Sorry, you need to own the land to use this function"); | 1194 | OSSLError("osSetParcelSIPAddress: Sorry, you need to own the land to use this function"); |
1188 | return; | 1195 | return; |
1189 | } | 1196 | } |
1190 | 1197 | ||
1191 | // get the voice module | 1198 | // get the voice module |
1192 | IVoiceModule voiceModule = World.RequestModuleInterface<IVoiceModule>(); | 1199 | IVoiceModule voiceModule = World.RequestModuleInterface<IVoiceModule>(); |
1193 | 1200 | ||
1194 | if (voiceModule != null) | 1201 | if (voiceModule != null) |
1195 | voiceModule.setLandSIPAddress(SIPAddress,land.LandData.GlobalID); | 1202 | voiceModule.setLandSIPAddress(SIPAddress,land.LandData.GlobalID); |
1196 | else | 1203 | else |
1197 | OSSLError("osSetParcelSIPAddress: No voice module enabled for this land"); | 1204 | OSSLError("osSetParcelSIPAddress: No voice module enabled for this land"); |
1198 | 1205 | ||
1199 | 1206 | ||
1200 | } | 1207 | } |
1201 | 1208 | ||
1202 | public string osGetScriptEngineName() | 1209 | public string osGetScriptEngineName() |
@@ -1476,12 +1483,9 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1476 | m_host.AddScriptLPS(1); | 1483 | m_host.AddScriptLPS(1); |
1477 | 1484 | ||
1478 | // Create new asset | 1485 | // Create new asset |
1479 | AssetBase asset = new AssetBase(); | 1486 | AssetBase asset = new AssetBase(UUID.Random(), notecardName, (sbyte)AssetType.Notecard); |
1480 | asset.Name = notecardName; | ||
1481 | asset.Description = "Script Generated Notecard"; | 1487 | asset.Description = "Script Generated Notecard"; |
1482 | asset.Type = 7; | 1488 | string notecardData = String.Empty; |
1483 | asset.FullID = UUID.Random(); | ||
1484 | string notecardData = ""; | ||
1485 | 1489 | ||
1486 | for (int i = 0; i < contents.Length; i++) { | 1490 | for (int i = 0; i < contents.Length; i++) { |
1487 | notecardData += contents.GetLSLStringItem(i) + "\n"; | 1491 | notecardData += contents.GetLSLStringItem(i) + "\n"; |
@@ -1521,10 +1525,10 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1521 | } | 1525 | } |
1522 | 1526 | ||
1523 | 1527 | ||
1524 | /*Instead of using the LSL Dataserver event to pull notecard data, | 1528 | /*Instead of using the LSL Dataserver event to pull notecard data, |
1525 | this will simply read the requested line and return its data as a string. | 1529 | this will simply read the requested line and return its data as a string. |
1526 | 1530 | ||
1527 | Warning - due to the synchronous method this function uses to fetch assets, its use | 1531 | Warning - due to the synchronous method this function uses to fetch assets, its use |
1528 | may be dangerous and unreliable while running in grid mode. | 1532 | may be dangerous and unreliable while running in grid mode. |
1529 | */ | 1533 | */ |
1530 | public string osGetNotecardLine(string name, int line) | 1534 | public string osGetNotecardLine(string name, int line) |
@@ -1572,10 +1576,10 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1572 | 1576 | ||
1573 | } | 1577 | } |
1574 | 1578 | ||
1575 | /*Instead of using the LSL Dataserver event to pull notecard data line by line, | 1579 | /*Instead of using the LSL Dataserver event to pull notecard data line by line, |
1576 | this will simply read the entire notecard and return its data as a string. | 1580 | this will simply read the entire notecard and return its data as a string. |
1577 | 1581 | ||
1578 | Warning - due to the synchronous method this function uses to fetch assets, its use | 1582 | Warning - due to the synchronous method this function uses to fetch assets, its use |
1579 | may be dangerous and unreliable while running in grid mode. | 1583 | may be dangerous and unreliable while running in grid mode. |
1580 | */ | 1584 | */ |
1581 | 1585 | ||
@@ -1630,10 +1634,10 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1630 | 1634 | ||
1631 | } | 1635 | } |
1632 | 1636 | ||
1633 | /*Instead of using the LSL Dataserver event to pull notecard data, | 1637 | /*Instead of using the LSL Dataserver event to pull notecard data, |
1634 | this will simply read the number of note card lines and return this data as an integer. | 1638 | this will simply read the number of note card lines and return this data as an integer. |
1635 | 1639 | ||
1636 | Warning - due to the synchronous method this function uses to fetch assets, its use | 1640 | Warning - due to the synchronous method this function uses to fetch assets, its use |
1637 | may be dangerous and unreliable while running in grid mode. | 1641 | may be dangerous and unreliable while running in grid mode. |
1638 | */ | 1642 | */ |
1639 | 1643 | ||
@@ -1833,7 +1837,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1833 | 1837 | ||
1834 | return World.RegionInfo.RegionSettings.LoadedCreationID; | 1838 | return World.RegionInfo.RegionSettings.LoadedCreationID; |
1835 | } | 1839 | } |
1836 | 1840 | ||
1837 | // Threat level is 'Low' because certain users could possibly be tricked into | 1841 | // Threat level is 'Low' because certain users could possibly be tricked into |
1838 | // dropping an unverified script into one of their own objects, which could | 1842 | // dropping an unverified script into one of their own objects, which could |
1839 | // then gather the physical construction details of the object and transmit it | 1843 | // then gather the physical construction details of the object and transmit it |
@@ -1857,7 +1861,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1857 | public LSL_Key osNpcCreate(string firstname, string lastname, LSL_Vector position, LSL_Key cloneFrom) | 1861 | public LSL_Key osNpcCreate(string firstname, string lastname, LSL_Vector position, LSL_Key cloneFrom) |
1858 | { | 1862 | { |
1859 | CheckThreatLevel(ThreatLevel.High, "osNpcCreate"); | 1863 | CheckThreatLevel(ThreatLevel.High, "osNpcCreate"); |
1860 | //QueueUserWorkItem | 1864 | //QueueUserWorkItem |
1861 | 1865 | ||
1862 | INPCModule module = World.RequestModuleInterface<INPCModule>(); | 1866 | INPCModule module = World.RequestModuleInterface<INPCModule>(); |
1863 | if (module != null) | 1867 | if (module != null) |
@@ -1906,5 +1910,42 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api | |||
1906 | module.DeleteNPC(new UUID(npc.m_string), World); | 1910 | module.DeleteNPC(new UUID(npc.m_string), World); |
1907 | } | 1911 | } |
1908 | } | 1912 | } |
1913 | |||
1914 | /// <summary> | ||
1915 | /// Get current region's map texture UUID | ||
1916 | /// </summary> | ||
1917 | /// <returns></returns> | ||
1918 | public LSL_Key osGetMapTexture() | ||
1919 | { | ||
1920 | CheckThreatLevel(ThreatLevel.None, "osGetMapTexture"); | ||
1921 | return m_ScriptEngine.World.RegionInfo.RegionSettings.TerrainImageID.ToString(); | ||
1922 | } | ||
1923 | |||
1924 | /// <summary> | ||
1925 | /// Get a region's map texture UUID by region UUID or name. | ||
1926 | /// </summary> | ||
1927 | /// <param name="regionName"></param> | ||
1928 | /// <returns></returns> | ||
1929 | public LSL_Key osGetRegionMapTexture(string regionName) | ||
1930 | { | ||
1931 | CheckThreatLevel(ThreatLevel.High, "osGetRegionMapTexture"); | ||
1932 | Scene scene = m_ScriptEngine.World; | ||
1933 | UUID key = UUID.Zero; | ||
1934 | GridRegion region; | ||
1935 | |||
1936 | //If string is a key, use it. Otherwise, try to locate region by name. | ||
1937 | if (UUID.TryParse(regionName, out key)) | ||
1938 | region = scene.GridService.GetRegionByUUID(UUID.Zero, key); | ||
1939 | else | ||
1940 | region = scene.GridService.GetRegionByName(UUID.Zero, regionName); | ||
1941 | |||
1942 | // If region was found, return the regions map texture key. | ||
1943 | if (region != null) | ||
1944 | key = region.TerrainImage; | ||
1945 | |||
1946 | ScriptSleep(1000); | ||
1947 | |||
1948 | return key.ToString(); | ||
1949 | } | ||
1909 | } | 1950 | } |
1910 | } | 1951 | } |
diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Interface/IMOD_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Interface/IMOD_Api.cs new file mode 100644 index 0000000..e08eca5 --- /dev/null +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Interface/IMOD_Api.cs | |||
@@ -0,0 +1,46 @@ | |||
1 | /* | ||
2 | * Copyright (c) Contributors, http://opensimulator.org/ | ||
3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. | ||
4 | * | ||
5 | * Redistribution and use in source and binary forms, with or without | ||
6 | * modification, are permitted provided that the following conditions are met: | ||
7 | * * Redistributions of source code must retain the above copyright | ||
8 | * notice, this list of conditions and the following disclaimer. | ||
9 | * * Redistributions in binary form must reproduce the above copyright | ||
10 | * notice, this list of conditions and the following disclaimer in the | ||
11 | * documentation and/or other materials provided with the distribution. | ||
12 | * * Neither the name of the OpenSimulator Project nor the | ||
13 | * names of its contributors may be used to endorse or promote products | ||
14 | * derived from this software without specific prior written permission. | ||
15 | * | ||
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY | ||
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | ||
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
26 | */ | ||
27 | |||
28 | using System.Collections; | ||
29 | using OpenSim.Region.ScriptEngine.Interfaces; | ||
30 | |||
31 | using key = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; | ||
32 | using rotation = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Quaternion; | ||
33 | using vector = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Vector3; | ||
34 | using LSL_List = OpenSim.Region.ScriptEngine.Shared.LSL_Types.list; | ||
35 | using LSL_String = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; | ||
36 | using LSL_Integer = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLInteger; | ||
37 | using LSL_Float = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLFloat; | ||
38 | |||
39 | namespace OpenSim.Region.ScriptEngine.Shared.Api.Interfaces | ||
40 | { | ||
41 | public interface IMOD_Api | ||
42 | { | ||
43 | //Module functions | ||
44 | string modSendCommand(string modules, string command, string k); | ||
45 | } | ||
46 | } | ||
diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Interface/IOSSL_Api.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Interface/IOSSL_Api.cs index d8d3c31..2a403bf 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Interface/IOSSL_Api.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Interface/IOSSL_Api.cs | |||
@@ -79,7 +79,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api.Interfaces | |||
79 | 79 | ||
80 | // Avatar Info Commands | 80 | // Avatar Info Commands |
81 | string osGetAgentIP(string agent); | 81 | string osGetAgentIP(string agent); |
82 | LSL_List osGetAgents(); | 82 | LSL_List osGetAgents(); |
83 | 83 | ||
84 | // Teleport commands | 84 | // Teleport commands |
85 | void osTeleportAgent(string agent, string regionName, LSL_Types.Vector3 position, LSL_Types.Vector3 lookat); | 85 | void osTeleportAgent(string agent, string regionName, LSL_Types.Vector3 position, LSL_Types.Vector3 lookat); |
@@ -127,7 +127,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api.Interfaces | |||
127 | string osGetScriptEngineName(); | 127 | string osGetScriptEngineName(); |
128 | string osGetSimulatorVersion(); | 128 | string osGetSimulatorVersion(); |
129 | Hashtable osParseJSON(string JSON); | 129 | Hashtable osParseJSON(string JSON); |
130 | 130 | ||
131 | void osMessageObject(key objectUUID,string message); | 131 | void osMessageObject(key objectUUID,string message); |
132 | 132 | ||
133 | void osMakeNotecard(string notecardName, LSL_Types.list contents); | 133 | void osMakeNotecard(string notecardName, LSL_Types.list contents); |
@@ -138,7 +138,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api.Interfaces | |||
138 | 138 | ||
139 | string osAvatarName2Key(string firstname, string lastname); | 139 | string osAvatarName2Key(string firstname, string lastname); |
140 | string osKey2Name(string id); | 140 | string osKey2Name(string id); |
141 | 141 | ||
142 | // Grid Info Functions | 142 | // Grid Info Functions |
143 | string osGetGridNick(); | 143 | string osGetGridNick(); |
144 | string osGetGridName(); | 144 | string osGetGridName(); |
@@ -151,7 +151,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api.Interfaces | |||
151 | string osLoadedCreationDate(); | 151 | string osLoadedCreationDate(); |
152 | string osLoadedCreationTime(); | 152 | string osLoadedCreationTime(); |
153 | string osLoadedCreationID(); | 153 | string osLoadedCreationID(); |
154 | 154 | ||
155 | LSL_List osGetLinkPrimitiveParams(int linknumber, LSL_List rules); | 155 | LSL_List osGetLinkPrimitiveParams(int linknumber, LSL_List rules); |
156 | 156 | ||
157 | 157 | ||
@@ -160,5 +160,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api.Interfaces | |||
160 | void osNpcSay(key npc, string message); | 160 | void osNpcSay(key npc, string message); |
161 | void osNpcRemove(key npc); | 161 | void osNpcRemove(key npc); |
162 | 162 | ||
163 | key osGetMapTexture(); | ||
164 | key osGetRegionMapTexture(string regionName); | ||
163 | } | 165 | } |
164 | } | 166 | } |
diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/MOD_Stub.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/MOD_Stub.cs new file mode 100644 index 0000000..6525c76 --- /dev/null +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/MOD_Stub.cs | |||
@@ -0,0 +1,66 @@ | |||
1 | /* | ||
2 | * Copyright (c) Contributors, http://opensimulator.org/ | ||
3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. | ||
4 | * | ||
5 | * Redistribution and use in source and binary forms, with or without | ||
6 | * modification, are permitted provided that the following conditions are met: | ||
7 | * * Redistributions of source code must retain the above copyright | ||
8 | * notice, this list of conditions and the following disclaimer. | ||
9 | * * Redistributions in binary form must reproduce the above copyright | ||
10 | * notice, this list of conditions and the following disclaimer in the | ||
11 | * documentation and/or other materials provided with the distribution. | ||
12 | * * Neither the name of the OpenSimulator Project nor the | ||
13 | * names of its contributors may be used to endorse or promote products | ||
14 | * derived from this software without specific prior written permission. | ||
15 | * | ||
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY | ||
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | ||
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
26 | */ | ||
27 | |||
28 | using System; | ||
29 | using System.Runtime.Remoting.Lifetime; | ||
30 | using System.Threading; | ||
31 | using System.Reflection; | ||
32 | using System.Collections; | ||
33 | using System.Collections.Generic; | ||
34 | using OpenSim.Framework; | ||
35 | using OpenSim.Region.Framework.Interfaces; | ||
36 | using OpenSim.Region.ScriptEngine.Interfaces; | ||
37 | using OpenSim.Region.ScriptEngine.Shared.Api.Interfaces; | ||
38 | using integer = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLInteger; | ||
39 | using vector = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Vector3; | ||
40 | using rotation = OpenSim.Region.ScriptEngine.Shared.LSL_Types.Quaternion; | ||
41 | using key = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; | ||
42 | using LSL_List = OpenSim.Region.ScriptEngine.Shared.LSL_Types.list; | ||
43 | using LSL_String = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLString; | ||
44 | using LSL_Float = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLFloat; | ||
45 | using LSL_Integer = OpenSim.Region.ScriptEngine.Shared.LSL_Types.LSLInteger; | ||
46 | |||
47 | namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase | ||
48 | { | ||
49 | public partial class ScriptBaseClass : MarshalByRefObject | ||
50 | { | ||
51 | public IMOD_Api m_MOD_Functions; | ||
52 | |||
53 | public void ApiTypeMOD(IScriptApi api) | ||
54 | { | ||
55 | if (!(api is IMOD_Api)) | ||
56 | return; | ||
57 | |||
58 | m_MOD_Functions = (IMOD_Api)api; | ||
59 | } | ||
60 | |||
61 | public string modSendCommand(string module, string command, string k) | ||
62 | { | ||
63 | return m_MOD_Functions.modSendCommand(module, command, k); | ||
64 | } | ||
65 | } | ||
66 | } | ||
diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/OSSL_Stub.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/OSSL_Stub.cs index 8dcb1f5..4928e90 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/OSSL_Stub.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/OSSL_Stub.cs | |||
@@ -94,7 +94,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase | |||
94 | { | 94 | { |
95 | return m_OSSL_Functions.osWindActiveModelPluginName(); | 95 | return m_OSSL_Functions.osWindActiveModelPluginName(); |
96 | } | 96 | } |
97 | 97 | ||
98 | // Not yet plugged in as available OSSL functions, so commented out | 98 | // Not yet plugged in as available OSSL functions, so commented out |
99 | // void osWindParamSet(string plugin, string param, float value) | 99 | // void osWindParamSet(string plugin, string param, float value) |
100 | // { | 100 | // { |
@@ -138,14 +138,14 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase | |||
138 | public string osSetDynamicTextureURLBlendFace(string dynamicID, string contentType, string url, string extraParams, | 138 | public string osSetDynamicTextureURLBlendFace(string dynamicID, string contentType, string url, string extraParams, |
139 | bool blend, int disp, int timer, int alpha, int face) | 139 | bool blend, int disp, int timer, int alpha, int face) |
140 | { | 140 | { |
141 | return m_OSSL_Functions.osSetDynamicTextureURLBlendFace(dynamicID, contentType, url, extraParams, | 141 | return m_OSSL_Functions.osSetDynamicTextureURLBlendFace(dynamicID, contentType, url, extraParams, |
142 | blend, disp, timer, alpha, face); | 142 | blend, disp, timer, alpha, face); |
143 | } | 143 | } |
144 | 144 | ||
145 | public string osSetDynamicTextureDataBlendFace(string dynamicID, string contentType, string data, string extraParams, | 145 | public string osSetDynamicTextureDataBlendFace(string dynamicID, string contentType, string data, string extraParams, |
146 | bool blend, int disp, int timer, int alpha, int face) | 146 | bool blend, int disp, int timer, int alpha, int face) |
147 | { | 147 | { |
148 | return m_OSSL_Functions.osSetDynamicTextureDataBlendFace(dynamicID, contentType, data, extraParams, | 148 | return m_OSSL_Functions.osSetDynamicTextureDataBlendFace(dynamicID, contentType, data, extraParams, |
149 | blend, disp, timer, alpha, face); | 149 | blend, disp, timer, alpha, face); |
150 | } | 150 | } |
151 | 151 | ||
@@ -183,7 +183,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase | |||
183 | { | 183 | { |
184 | m_OSSL_Functions.osSetParcelMediaURL(url); | 184 | m_OSSL_Functions.osSetParcelMediaURL(url); |
185 | } | 185 | } |
186 | 186 | ||
187 | public void osSetParcelSIPAddress(string SIPAddress) | 187 | public void osSetParcelSIPAddress(string SIPAddress) |
188 | { | 188 | { |
189 | m_OSSL_Functions.osSetParcelSIPAddress(SIPAddress); | 189 | m_OSSL_Functions.osSetParcelSIPAddress(SIPAddress); |
@@ -211,7 +211,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase | |||
211 | m_OSSL_Functions.osTeleportAgent(agent, position, lookat); | 211 | m_OSSL_Functions.osTeleportAgent(agent, position, lookat); |
212 | } | 212 | } |
213 | 213 | ||
214 | // Avatar info functions | 214 | // Avatar info functions |
215 | public string osGetAgentIP(string agent) | 215 | public string osGetAgentIP(string agent) |
216 | { | 216 | { |
217 | return m_OSSL_Functions.osGetAgentIP(agent); | 217 | return m_OSSL_Functions.osGetAgentIP(agent); |
@@ -326,17 +326,17 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase | |||
326 | { | 326 | { |
327 | return m_OSSL_Functions.osGetScriptEngineName(); | 327 | return m_OSSL_Functions.osGetScriptEngineName(); |
328 | } | 328 | } |
329 | 329 | ||
330 | public string osGetSimulatorVersion() | 330 | public string osGetSimulatorVersion() |
331 | { | 331 | { |
332 | return m_OSSL_Functions.osGetSimulatorVersion(); | 332 | return m_OSSL_Functions.osGetSimulatorVersion(); |
333 | } | 333 | } |
334 | 334 | ||
335 | public Hashtable osParseJSON(string JSON) | 335 | public Hashtable osParseJSON(string JSON) |
336 | { | 336 | { |
337 | return m_OSSL_Functions.osParseJSON(JSON); | 337 | return m_OSSL_Functions.osParseJSON(JSON); |
338 | } | 338 | } |
339 | 339 | ||
340 | public void osMessageObject(key objectUUID,string message) | 340 | public void osMessageObject(key objectUUID,string message) |
341 | { | 341 | { |
342 | m_OSSL_Functions.osMessageObject(objectUUID,message); | 342 | m_OSSL_Functions.osMessageObject(objectUUID,message); |
@@ -412,7 +412,7 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase | |||
412 | { | 412 | { |
413 | return m_OSSL_Functions.osLoadedCreationID(); | 413 | return m_OSSL_Functions.osLoadedCreationID(); |
414 | } | 414 | } |
415 | 415 | ||
416 | public LSL_List osGetLinkPrimitiveParams(int linknumber, LSL_List rules) | 416 | public LSL_List osGetLinkPrimitiveParams(int linknumber, LSL_List rules) |
417 | { | 417 | { |
418 | return m_OSSL_Functions.osGetLinkPrimitiveParams(linknumber, rules); | 418 | return m_OSSL_Functions.osGetLinkPrimitiveParams(linknumber, rules); |
@@ -622,5 +622,15 @@ namespace OpenSim.Region.ScriptEngine.Shared.ScriptBase | |||
622 | } | 622 | } |
623 | } | 623 | } |
624 | } | 624 | } |
625 | |||
626 | public key osGetMapTexture() | ||
627 | { | ||
628 | return m_OSSL_Functions.osGetMapTexture(); | ||
629 | } | ||
630 | |||
631 | public key osGetRegionMapTexture(string regionName) | ||
632 | { | ||
633 | return m_OSSL_Functions.osGetRegionMapTexture(regionName); | ||
634 | } | ||
625 | } | 635 | } |
626 | } | 636 | } |
diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/OpenSim.Region.ScriptEngine.Shared.Api.Runtime.mdp b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/OpenSim.Region.ScriptEngine.Shared.Api.Runtime.mdp index feff86a..98bbc68 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/OpenSim.Region.ScriptEngine.Shared.Api.Runtime.mdp +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Runtime/OpenSim.Region.ScriptEngine.Shared.Api.Runtime.mdp | |||
@@ -20,6 +20,7 @@ | |||
20 | <File name="./Executor.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> | 20 | <File name="./Executor.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> |
21 | <File name="./LSL_Constants.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> | 21 | <File name="./LSL_Constants.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> |
22 | <File name="./LSL_Stub.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> | 22 | <File name="./LSL_Stub.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> |
23 | <File name="./MOD_Stub.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> | ||
23 | <File name="./OSSL_Stub.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> | 24 | <File name="./OSSL_Stub.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> |
24 | <File name="./ScriptBase.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> | 25 | <File name="./ScriptBase.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> |
25 | <File name="./ScriptSponsor.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> | 26 | <File name="./ScriptSponsor.cs" subtype="Code" buildaction="Compile" dependson="" data="" /> |
diff --git a/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs b/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs index b0fce75..a60c0ba 100644 --- a/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs +++ b/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs | |||
@@ -51,7 +51,6 @@ using OpenSim.Region.ScriptEngine.Shared.Instance; | |||
51 | using OpenSim.Region.ScriptEngine.Interfaces; | 51 | using OpenSim.Region.ScriptEngine.Interfaces; |
52 | 52 | ||
53 | using ScriptCompileQueue = OpenSim.Framework.LocklessQueue<object[]>; | 53 | using ScriptCompileQueue = OpenSim.Framework.LocklessQueue<object[]>; |
54 | using Parallel = OpenSim.Framework.Parallel; | ||
55 | 54 | ||
56 | namespace OpenSim.Region.ScriptEngine.XEngine | 55 | namespace OpenSim.Region.ScriptEngine.XEngine |
57 | { | 56 | { |
@@ -494,7 +493,16 @@ namespace OpenSim.Region.ScriptEngine.XEngine | |||
494 | 493 | ||
495 | if (m_CurrentCompile == null) | 494 | if (m_CurrentCompile == null) |
496 | { | 495 | { |
497 | m_CurrentCompile = m_ThreadPool.QueueWorkItem(DoOnRezScriptQueue, null); | 496 | // NOTE: Although we use a lockless queue, the lock here |
497 | // is required. It ensures that there are never two | ||
498 | // compile threads running, which, due to a race | ||
499 | // conndition, might otherwise happen | ||
500 | // | ||
501 | lock (m_CompileQueue) | ||
502 | { | ||
503 | if (m_CurrentCompile == null) | ||
504 | m_CurrentCompile = m_ThreadPool.QueueWorkItem(DoOnRezScriptQueue, null); | ||
505 | } | ||
498 | } | 506 | } |
499 | } | 507 | } |
500 | } | 508 | } |
@@ -514,16 +522,19 @@ namespace OpenSim.Region.ScriptEngine.XEngine | |||
514 | } | 522 | } |
515 | } | 523 | } |
516 | 524 | ||
517 | List<object[]> compiles = new List<object[]>(); | ||
518 | object[] o; | 525 | object[] o; |
519 | while (m_CompileQueue.Dequeue(out o)) | 526 | while (m_CompileQueue.Dequeue(out o)) |
527 | DoOnRezScript(o); | ||
528 | |||
529 | // NOTE: Despite having a lockless queue, this lock is required | ||
530 | // to make sure there is never no compile thread while there | ||
531 | // are still scripts to compile. This could otherwise happen | ||
532 | // due to a race condition | ||
533 | // | ||
534 | lock (m_CompileQueue) | ||
520 | { | 535 | { |
521 | compiles.Add(o); | 536 | m_CurrentCompile = null; |
522 | } | 537 | } |
523 | |||
524 | Parallel.For(0, compiles.Count, delegate(int i) { DoOnRezScript(compiles[i]); }); | ||
525 | |||
526 | m_CurrentCompile = null; | ||
527 | m_Scene.EventManager.TriggerEmptyScriptCompileQueue(m_ScriptFailCount, | 538 | m_Scene.EventManager.TriggerEmptyScriptCompileQueue(m_ScriptFailCount, |
528 | m_ScriptErrorMessage); | 539 | m_ScriptErrorMessage); |
529 | m_ScriptFailCount = 0; | 540 | m_ScriptFailCount = 0; |