diff options
Diffstat (limited to '')
4 files changed, 276 insertions, 207 deletions
diff --git a/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs b/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs index 9ccf5a0..753aada 100644 --- a/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs +++ b/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs | |||
@@ -28,6 +28,7 @@ | |||
28 | using System; | 28 | using System; |
29 | using System.Collections.Generic; | 29 | using System.Collections.Generic; |
30 | using System.Net; | 30 | using System.Net; |
31 | using System.Xml; | ||
31 | using System.Reflection; | 32 | using System.Reflection; |
32 | using System.Threading; | 33 | using System.Threading; |
33 | 34 | ||
@@ -191,11 +192,11 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
191 | public virtual UUID DeleteToInventory(DeRezAction action, UUID folderID, | 192 | public virtual UUID DeleteToInventory(DeRezAction action, UUID folderID, |
192 | List<SceneObjectGroup> objectGroups, IClientAPI remoteClient) | 193 | List<SceneObjectGroup> objectGroups, IClientAPI remoteClient) |
193 | { | 194 | { |
194 | // HACK: This is only working for lists containing a single item! | ||
195 | // It's just a hack to make this WIP compile and run. Nothing | ||
196 | // currently calls this with multiple items. | ||
197 | UUID ret = UUID.Zero; | 195 | UUID ret = UUID.Zero; |
198 | 196 | ||
197 | // The following code groups the SOG's by owner. No objects | ||
198 | // belonging to different people can be coalesced, for obvious | ||
199 | // reasons. | ||
199 | Dictionary<UUID, List<SceneObjectGroup>> deletes = | 200 | Dictionary<UUID, List<SceneObjectGroup>> deletes = |
200 | new Dictionary<UUID, List<SceneObjectGroup>>(); | 201 | new Dictionary<UUID, List<SceneObjectGroup>>(); |
201 | 202 | ||
@@ -207,266 +208,328 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
207 | deletes[g.OwnerID].Add(g); | 208 | deletes[g.OwnerID].Add(g); |
208 | } | 209 | } |
209 | 210 | ||
210 | foreach (List<SceneObjectGroup> objlist in deletes.Values) | 211 | // This is pethod scoped and will be returned. It will be the |
211 | ret = DeleteToInventory(action, folderID, objlist, remoteClient); | 212 | // last created asset id |
213 | UUID assetID = UUID.Zero; | ||
212 | 214 | ||
213 | return ret; | 215 | // Each iteration is really a separate asset being created, |
214 | } | 216 | // with distinct destinations as well. |
217 | foreach (List<SceneObjectGroup> objlist in deletes.Values) | ||
218 | { | ||
219 | Dictionary<UUID, string> xmlStrings = | ||
220 | new Dictionary<UUID, string>(); | ||
215 | 221 | ||
216 | private UUID DeleteToInventory(DeRezAction action, UUID folderID, | 222 | foreach (SceneObjectGroup objectGroup in objlist) |
217 | SceneObjectGroup objectGroup, IClientAPI remoteClient) | 223 | { |
218 | { | 224 | Vector3 inventoryStoredPosition = new Vector3 |
219 | UUID assetID = UUID.Zero; | 225 | (((objectGroup.AbsolutePosition.X > (int)Constants.RegionSize) |
226 | ? 250 | ||
227 | : objectGroup.AbsolutePosition.X) | ||
228 | , | ||
229 | (objectGroup.AbsolutePosition.X > (int)Constants.RegionSize) | ||
230 | ? 250 | ||
231 | : objectGroup.AbsolutePosition.X, | ||
232 | objectGroup.AbsolutePosition.Z); | ||
220 | 233 | ||
221 | Vector3 inventoryStoredPosition = new Vector3 | 234 | Vector3 originalPosition = objectGroup.AbsolutePosition; |
222 | (((objectGroup.AbsolutePosition.X > (int)Constants.RegionSize) | ||
223 | ? 250 | ||
224 | : objectGroup.AbsolutePosition.X) | ||
225 | , | ||
226 | (objectGroup.AbsolutePosition.X > (int)Constants.RegionSize) | ||
227 | ? 250 | ||
228 | : objectGroup.AbsolutePosition.X, | ||
229 | objectGroup.AbsolutePosition.Z); | ||
230 | 235 | ||
231 | Vector3 originalPosition = objectGroup.AbsolutePosition; | 236 | // Restore attachment data after trip through the sim |
237 | if (objectGroup.RootPart.AttachPoint > 0) | ||
238 | inventoryStoredPosition = objectGroup.RootPart.AttachOffset; | ||
239 | objectGroup.RootPart.Shape.State = objectGroup.RootPart.AttachPoint; | ||
232 | 240 | ||
233 | // Restore attachment data after trip through the sim | 241 | objectGroup.AbsolutePosition = inventoryStoredPosition; |
234 | if (objectGroup.RootPart.AttachPoint > 0) | ||
235 | inventoryStoredPosition = objectGroup.RootPart.AttachOffset; | ||
236 | objectGroup.RootPart.Shape.State = objectGroup.RootPart.AttachPoint; | ||
237 | 242 | ||
238 | objectGroup.AbsolutePosition = inventoryStoredPosition; | 243 | // Make sure all bits but the ones we want are clear |
244 | // on take. | ||
245 | // This will be applied to the current perms, so | ||
246 | // it will do what we want. | ||
247 | objectGroup.RootPart.NextOwnerMask &= | ||
248 | ((uint)PermissionMask.Copy | | ||
249 | (uint)PermissionMask.Transfer | | ||
250 | (uint)PermissionMask.Modify); | ||
251 | objectGroup.RootPart.NextOwnerMask |= | ||
252 | (uint)PermissionMask.Move; | ||
239 | 253 | ||
240 | string sceneObjectXml = SceneObjectSerializer.ToOriginalXmlFormat(objectGroup); | 254 | string sceneObjectXml = SceneObjectSerializer.ToOriginalXmlFormat(objectGroup); |
241 | 255 | ||
242 | objectGroup.AbsolutePosition = originalPosition; | 256 | objectGroup.AbsolutePosition = originalPosition; |
243 | 257 | ||
244 | // Get the user info of the item destination | 258 | xmlStrings[objectGroup.UUID] = sceneObjectXml; |
245 | // | 259 | } |
246 | UUID userID = UUID.Zero; | ||
247 | 260 | ||
248 | if (action == DeRezAction.Take || action == DeRezAction.TakeCopy || | 261 | string itemXml; |
249 | action == DeRezAction.SaveToExistingUserInventoryItem) | ||
250 | { | ||
251 | // Take or take copy require a taker | ||
252 | // Saving changes requires a local user | ||
253 | // | ||
254 | if (remoteClient == null) | ||
255 | return UUID.Zero; | ||
256 | 262 | ||
257 | userID = remoteClient.AgentId; | 263 | if (objlist.Count > 1) |
258 | } | 264 | { |
259 | else | 265 | float minX, minY, minZ; |
260 | { | 266 | float maxX, maxY, maxZ; |
261 | // All returns / deletes go to the object owner | ||
262 | // | ||
263 | 267 | ||
264 | userID = objectGroup.RootPart.OwnerID; | 268 | Vector3[] offsets = m_Scene.GetCombinedBoundingBox(objlist, |
265 | } | 269 | out minX, out maxX, out minY, out maxY, |
270 | out minZ, out maxZ); | ||
266 | 271 | ||
267 | if (userID == UUID.Zero) // Can't proceed | 272 | // CreateWrapper |
268 | { | 273 | XmlDocument itemDoc = new XmlDocument(); |
269 | return UUID.Zero; | 274 | XmlElement root = itemDoc.CreateElement("", "CoalescedObject", ""); |
270 | } | 275 | itemDoc.AppendChild(root); |
271 | 276 | ||
272 | // If we're returning someone's item, it goes back to the | 277 | // Embed the offsets into the group XML |
273 | // owner's Lost And Found folder. | 278 | for ( int i = 0 ; i < objlist.Count ; i++ ) |
274 | // Delete is treated like return in this case | 279 | { |
275 | // Deleting your own items makes them go to trash | 280 | XmlDocument doc = new XmlDocument(); |
276 | // | 281 | SceneObjectGroup g = objlist[i]; |
282 | doc.LoadXml(xmlStrings[g.UUID]); | ||
283 | XmlElement e = (XmlElement)doc.SelectSingleNode("/SceneObjectGroup"); | ||
284 | e.SetAttribute("offsetx", offsets[i].X.ToString()); | ||
285 | e.SetAttribute("offsety", offsets[i].Y.ToString()); | ||
286 | e.SetAttribute("offsetz", offsets[i].Z.ToString()); | ||
277 | 287 | ||
278 | InventoryFolderBase folder = null; | 288 | XmlNode objectNode = itemDoc.ImportNode(e, true); |
279 | InventoryItemBase item = null; | 289 | root.AppendChild(objectNode); |
290 | } | ||
280 | 291 | ||
281 | if (DeRezAction.SaveToExistingUserInventoryItem == action) | 292 | float sizeX = maxX - minX; |
282 | { | 293 | float sizeY = maxY - minY; |
283 | item = new InventoryItemBase(objectGroup.RootPart.FromUserInventoryItemID, userID); | 294 | float sizeZ = maxZ - minZ; |
284 | item = m_Scene.InventoryService.GetItem(item); | ||
285 | 295 | ||
286 | //item = userInfo.RootFolder.FindItem( | 296 | root.SetAttribute("x", sizeX.ToString()); |
287 | // objectGroup.RootPart.FromUserInventoryItemID); | 297 | root.SetAttribute("y", sizeY.ToString()); |
298 | root.SetAttribute("z", sizeZ.ToString()); | ||
288 | 299 | ||
289 | if (null == item) | 300 | itemXml = itemDoc.InnerXml; |
301 | } | ||
302 | else | ||
290 | { | 303 | { |
291 | m_log.DebugFormat( | 304 | itemXml = xmlStrings[objlist[0].UUID]; |
292 | "[AGENT INVENTORY]: Object {0} {1} scheduled for save to inventory has already been deleted.", | ||
293 | objectGroup.Name, objectGroup.UUID); | ||
294 | return UUID.Zero; | ||
295 | } | 305 | } |
296 | } | 306 | |
297 | else | 307 | // Get the user info of the item destination |
298 | { | ||
299 | // Folder magic | ||
300 | // | 308 | // |
301 | if (action == DeRezAction.Delete) | 309 | UUID userID = UUID.Zero; |
310 | |||
311 | if (action == DeRezAction.Take || action == DeRezAction.TakeCopy || | ||
312 | action == DeRezAction.SaveToExistingUserInventoryItem) | ||
302 | { | 313 | { |
303 | // Deleting someone else's item | 314 | // Take or take copy require a taker |
315 | // Saving changes requires a local user | ||
304 | // | 316 | // |
305 | if (remoteClient == null || | 317 | if (remoteClient == null) |
306 | objectGroup.OwnerID != remoteClient.AgentId) | 318 | return UUID.Zero; |
307 | { | ||
308 | 319 | ||
309 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.LostAndFoundFolder); | 320 | userID = remoteClient.AgentId; |
310 | } | ||
311 | else | ||
312 | { | ||
313 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.TrashFolder); | ||
314 | } | ||
315 | } | 321 | } |
316 | else if (action == DeRezAction.Return) | 322 | else |
317 | { | 323 | { |
318 | 324 | // All returns / deletes go to the object owner | |
319 | // Dump to lost + found unconditionally | ||
320 | // | 325 | // |
321 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.LostAndFoundFolder); | 326 | |
327 | userID = objlist[0].RootPart.OwnerID; | ||
322 | } | 328 | } |
323 | 329 | ||
324 | if (folderID == UUID.Zero && folder == null) | 330 | if (userID == UUID.Zero) // Can't proceed |
325 | { | 331 | { |
326 | if (action == DeRezAction.Delete) | 332 | return UUID.Zero; |
333 | } | ||
334 | |||
335 | // If we're returning someone's item, it goes back to the | ||
336 | // owner's Lost And Found folder. | ||
337 | // Delete is treated like return in this case | ||
338 | // Deleting your own items makes them go to trash | ||
339 | // | ||
340 | |||
341 | InventoryFolderBase folder = null; | ||
342 | InventoryItemBase item = null; | ||
343 | |||
344 | if (DeRezAction.SaveToExistingUserInventoryItem == action) | ||
345 | { | ||
346 | item = new InventoryItemBase(objlist[0].RootPart.FromUserInventoryItemID, userID); | ||
347 | item = m_Scene.InventoryService.GetItem(item); | ||
348 | |||
349 | //item = userInfo.RootFolder.FindItem( | ||
350 | // objectGroup.RootPart.FromUserInventoryItemID); | ||
351 | |||
352 | if (null == item) | ||
327 | { | 353 | { |
328 | // Deletes go to trash by default | 354 | m_log.DebugFormat( |
329 | // | 355 | "[AGENT INVENTORY]: Object {0} {1} scheduled for save to inventory has already been deleted.", |
330 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.TrashFolder); | 356 | objlist[0].Name, objlist[0].UUID); |
357 | return UUID.Zero; | ||
331 | } | 358 | } |
332 | else | 359 | } |
360 | else | ||
361 | { | ||
362 | // Folder magic | ||
363 | // | ||
364 | if (action == DeRezAction.Delete) | ||
333 | { | 365 | { |
366 | // Deleting someone else's item | ||
367 | // | ||
334 | if (remoteClient == null || | 368 | if (remoteClient == null || |
335 | objectGroup.OwnerID != remoteClient.AgentId) | 369 | objlist[0].OwnerID != remoteClient.AgentId) |
336 | { | 370 | { |
337 | // Taking copy of another person's item. Take to | 371 | |
338 | // Objects folder. | 372 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.LostAndFoundFolder); |
339 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.Object); | ||
340 | } | 373 | } |
341 | else | 374 | else |
342 | { | 375 | { |
343 | // Catch all. Use lost & found | 376 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.TrashFolder); |
377 | } | ||
378 | } | ||
379 | else if (action == DeRezAction.Return) | ||
380 | { | ||
381 | |||
382 | // Dump to lost + found unconditionally | ||
383 | // | ||
384 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.LostAndFoundFolder); | ||
385 | } | ||
386 | |||
387 | if (folderID == UUID.Zero && folder == null) | ||
388 | { | ||
389 | if (action == DeRezAction.Delete) | ||
390 | { | ||
391 | // Deletes go to trash by default | ||
344 | // | 392 | // |
393 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.TrashFolder); | ||
394 | } | ||
395 | else | ||
396 | { | ||
397 | if (remoteClient == null || | ||
398 | objlist[0].OwnerID != remoteClient.AgentId) | ||
399 | { | ||
400 | // Taking copy of another person's item. Take to | ||
401 | // Objects folder. | ||
402 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.Object); | ||
403 | } | ||
404 | else | ||
405 | { | ||
406 | // Catch all. Use lost & found | ||
407 | // | ||
345 | 408 | ||
346 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.LostAndFoundFolder); | 409 | folder = m_Scene.InventoryService.GetFolderForType(userID, AssetType.LostAndFoundFolder); |
410 | } | ||
347 | } | 411 | } |
348 | } | 412 | } |
349 | } | ||
350 | 413 | ||
351 | // Override and put into where it came from, if it came | 414 | // Override and put into where it came from, if it came |
352 | // from anywhere in inventory | 415 | // from anywhere in inventory |
353 | // | 416 | // |
354 | if (action == DeRezAction.Take || action == DeRezAction.TakeCopy) | 417 | if (action == DeRezAction.Take || action == DeRezAction.TakeCopy) |
355 | { | ||
356 | if (objectGroup.RootPart.FromFolderID != UUID.Zero) | ||
357 | { | 418 | { |
358 | InventoryFolderBase f = new InventoryFolderBase(objectGroup.RootPart.FromFolderID, userID); | 419 | if (objlist[0].RootPart.FromFolderID != UUID.Zero) |
359 | folder = m_Scene.InventoryService.GetFolder(f); | 420 | { |
421 | InventoryFolderBase f = new InventoryFolderBase(objlist[0].RootPart.FromFolderID, userID); | ||
422 | folder = m_Scene.InventoryService.GetFolder(f); | ||
423 | } | ||
360 | } | 424 | } |
361 | } | ||
362 | |||
363 | if (folder == null) // None of the above | ||
364 | { | ||
365 | folder = new InventoryFolderBase(folderID); | ||
366 | 425 | ||
367 | if (folder == null) // Nowhere to put it | 426 | if (folder == null) // None of the above |
368 | { | 427 | { |
369 | return UUID.Zero; | 428 | folder = new InventoryFolderBase(folderID); |
370 | } | ||
371 | } | ||
372 | 429 | ||
373 | item = new InventoryItemBase(); | 430 | if (folder == null) // Nowhere to put it |
374 | item.CreatorId = objectGroup.RootPart.CreatorID.ToString(); | 431 | { |
375 | item.ID = UUID.Random(); | 432 | return UUID.Zero; |
376 | item.InvType = (int)InventoryType.Object; | 433 | } |
377 | item.Folder = folder.ID; | 434 | } |
378 | item.Owner = userID; | ||
379 | } | ||
380 | 435 | ||
381 | AssetBase asset = CreateAsset( | 436 | item = new InventoryItemBase(); |
382 | objectGroup.GetPartName(objectGroup.RootPart.LocalId), | 437 | // Can't know creator is the same, so null it in inventory |
383 | objectGroup.GetPartDescription(objectGroup.RootPart.LocalId), | 438 | if (objlist.Count > 1) |
384 | (sbyte)AssetType.Object, | 439 | item.CreatorId = UUID.Zero.ToString(); |
385 | Utils.StringToBytes(sceneObjectXml), | 440 | else |
386 | objectGroup.OwnerID.ToString()); | 441 | item.CreatorId = objlist[0].RootPart.CreatorID.ToString(); |
387 | m_Scene.AssetService.Store(asset); | 442 | item.ID = UUID.Random(); |
388 | assetID = asset.FullID; | 443 | item.InvType = (int)InventoryType.Object; |
444 | item.Folder = folder.ID; | ||
445 | item.Owner = userID; | ||
446 | if (objlist.Count > 1) | ||
447 | item.Flags = (uint)InventoryItemFlags.ObjectHasMultipleItems; | ||
448 | } | ||
389 | 449 | ||
390 | if (DeRezAction.SaveToExistingUserInventoryItem == action) | 450 | AssetBase asset = CreateAsset( |
391 | { | 451 | objlist[0].GetPartName(objlist[0].RootPart.LocalId), |
392 | item.AssetID = asset.FullID; | 452 | objlist[0].GetPartDescription(objlist[0].RootPart.LocalId), |
393 | m_Scene.InventoryService.UpdateItem(item); | 453 | (sbyte)AssetType.Object, |
394 | } | 454 | Utils.StringToBytes(itemXml), |
395 | else | 455 | objlist[0].OwnerID.ToString()); |
396 | { | 456 | m_Scene.AssetService.Store(asset); |
397 | item.AssetID = asset.FullID; | 457 | assetID = asset.FullID; |
398 | 458 | ||
399 | if (remoteClient != null && (remoteClient.AgentId != objectGroup.RootPart.OwnerID) && m_Scene.Permissions.PropagatePermissions()) | 459 | if (DeRezAction.SaveToExistingUserInventoryItem == action) |
400 | { | 460 | { |
401 | uint perms = objectGroup.GetEffectivePermissions(); | 461 | item.AssetID = asset.FullID; |
402 | uint nextPerms = (perms & 7) << 13; | 462 | m_Scene.InventoryService.UpdateItem(item); |
403 | if ((nextPerms & (uint)PermissionMask.Copy) == 0) | ||
404 | perms &= ~(uint)PermissionMask.Copy; | ||
405 | if ((nextPerms & (uint)PermissionMask.Transfer) == 0) | ||
406 | perms &= ~(uint)PermissionMask.Transfer; | ||
407 | if ((nextPerms & (uint)PermissionMask.Modify) == 0) | ||
408 | perms &= ~(uint)PermissionMask.Modify; | ||
409 | |||
410 | // Make sure all bits but the ones we want are clear | ||
411 | // on take. | ||
412 | // This will be applied to the current perms, so | ||
413 | // it will do what we want. | ||
414 | objectGroup.RootPart.NextOwnerMask &= | ||
415 | ((uint)PermissionMask.Copy | | ||
416 | (uint)PermissionMask.Transfer | | ||
417 | (uint)PermissionMask.Modify); | ||
418 | objectGroup.RootPart.NextOwnerMask |= | ||
419 | (uint)PermissionMask.Move; | ||
420 | |||
421 | item.BasePermissions = perms & objectGroup.RootPart.NextOwnerMask; | ||
422 | item.CurrentPermissions = item.BasePermissions; | ||
423 | item.NextPermissions = objectGroup.RootPart.NextOwnerMask; | ||
424 | item.EveryOnePermissions = objectGroup.RootPart.EveryoneMask & objectGroup.RootPart.NextOwnerMask; | ||
425 | item.GroupPermissions = objectGroup.RootPart.GroupMask & objectGroup.RootPart.NextOwnerMask; | ||
426 | |||
427 | // Magic number badness. Maybe this deserves an enum. | ||
428 | // bit 4 (16) is the "Slam" bit, it means treat as passed | ||
429 | // and apply next owner perms on rez | ||
430 | item.CurrentPermissions |= 16; // Slam! | ||
431 | } | 463 | } |
432 | else | 464 | else |
433 | { | 465 | { |
434 | item.BasePermissions = objectGroup.GetEffectivePermissions(); | 466 | item.AssetID = asset.FullID; |
435 | item.CurrentPermissions = objectGroup.GetEffectivePermissions(); | 467 | |
436 | item.NextPermissions = objectGroup.RootPart.NextOwnerMask; | 468 | uint effectivePerms = (uint)(PermissionMask.Copy | PermissionMask.Transfer | PermissionMask.Modify | PermissionMask.Move) | 7; |
437 | item.EveryOnePermissions = objectGroup.RootPart.EveryoneMask; | 469 | foreach (SceneObjectGroup grp in objlist) |
438 | item.GroupPermissions = objectGroup.RootPart.GroupMask; | 470 | effectivePerms &= grp.GetEffectivePermissions(); |
471 | effectivePerms |= (uint)PermissionMask.Move; | ||
472 | |||
473 | if (remoteClient != null && (remoteClient.AgentId != objlist[0].RootPart.OwnerID) && m_Scene.Permissions.PropagatePermissions()) | ||
474 | { | ||
475 | uint perms = effectivePerms; | ||
476 | uint nextPerms = (perms & 7) << 13; | ||
477 | if ((nextPerms & (uint)PermissionMask.Copy) == 0) | ||
478 | perms &= ~(uint)PermissionMask.Copy; | ||
479 | if ((nextPerms & (uint)PermissionMask.Transfer) == 0) | ||
480 | perms &= ~(uint)PermissionMask.Transfer; | ||
481 | if ((nextPerms & (uint)PermissionMask.Modify) == 0) | ||
482 | perms &= ~(uint)PermissionMask.Modify; | ||
483 | |||
484 | item.BasePermissions = perms & objlist[0].RootPart.NextOwnerMask; | ||
485 | item.CurrentPermissions = item.BasePermissions; | ||
486 | item.NextPermissions = perms & objlist[0].RootPart.NextOwnerMask; | ||
487 | item.EveryOnePermissions = objlist[0].RootPart.EveryoneMask & objlist[0].RootPart.NextOwnerMask; | ||
488 | item.GroupPermissions = objlist[0].RootPart.GroupMask & objlist[0].RootPart.NextOwnerMask; | ||
489 | |||
490 | // Magic number badness. Maybe this deserves an enum. | ||
491 | // bit 4 (16) is the "Slam" bit, it means treat as passed | ||
492 | // and apply next owner perms on rez | ||
493 | item.CurrentPermissions |= 16; // Slam! | ||
494 | } | ||
495 | else | ||
496 | { | ||
497 | item.BasePermissions = effectivePerms; | ||
498 | item.CurrentPermissions = effectivePerms; | ||
499 | item.NextPermissions = objlist[0].RootPart.NextOwnerMask & effectivePerms; | ||
500 | item.EveryOnePermissions = objlist[0].RootPart.EveryoneMask & effectivePerms; | ||
501 | item.GroupPermissions = objlist[0].RootPart.GroupMask & effectivePerms; | ||
439 | 502 | ||
440 | item.CurrentPermissions &= | 503 | item.CurrentPermissions &= |
441 | ((uint)PermissionMask.Copy | | 504 | ((uint)PermissionMask.Copy | |
442 | (uint)PermissionMask.Transfer | | 505 | (uint)PermissionMask.Transfer | |
443 | (uint)PermissionMask.Modify | | 506 | (uint)PermissionMask.Modify | |
444 | (uint)PermissionMask.Move | | 507 | (uint)PermissionMask.Move | |
445 | 7); // Preserve folded permissions | 508 | 7); // Preserve folded permissions |
446 | } | 509 | } |
447 | 510 | ||
448 | // TODO: add the new fields (Flags, Sale info, etc) | 511 | // TODO: add the new fields (Flags, Sale info, etc) |
449 | item.CreationDate = Util.UnixTimeSinceEpoch(); | 512 | item.CreationDate = Util.UnixTimeSinceEpoch(); |
450 | item.Description = asset.Description; | 513 | item.Description = asset.Description; |
451 | item.Name = asset.Name; | 514 | item.Name = asset.Name; |
452 | item.AssetType = asset.Type; | 515 | item.AssetType = asset.Type; |
453 | 516 | ||
454 | m_Scene.AddInventoryItem(item); | 517 | m_Scene.AddInventoryItem(item); |
455 | 518 | ||
456 | if (remoteClient != null && item.Owner == remoteClient.AgentId) | 519 | if (remoteClient != null && item.Owner == remoteClient.AgentId) |
457 | { | ||
458 | remoteClient.SendInventoryItemCreateUpdate(item, 0); | ||
459 | } | ||
460 | else | ||
461 | { | ||
462 | ScenePresence notifyUser = m_Scene.GetScenePresence(item.Owner); | ||
463 | if (notifyUser != null) | ||
464 | { | 520 | { |
465 | notifyUser.ControllingClient.SendInventoryItemCreateUpdate(item, 0); | 521 | remoteClient.SendInventoryItemCreateUpdate(item, 0); |
522 | } | ||
523 | else | ||
524 | { | ||
525 | ScenePresence notifyUser = m_Scene.GetScenePresence(item.Owner); | ||
526 | if (notifyUser != null) | ||
527 | { | ||
528 | notifyUser.ControllingClient.SendInventoryItemCreateUpdate(item, 0); | ||
529 | } | ||
466 | } | 530 | } |
467 | } | 531 | } |
468 | } | 532 | } |
469 | |||
470 | return assetID; | 533 | return assetID; |
471 | } | 534 | } |
472 | 535 | ||
diff --git a/OpenSim/Region/Framework/Scenes/AsyncSceneObjectGroupDeleter.cs b/OpenSim/Region/Framework/Scenes/AsyncSceneObjectGroupDeleter.cs index 64567db..8feb022 100644 --- a/OpenSim/Region/Framework/Scenes/AsyncSceneObjectGroupDeleter.cs +++ b/OpenSim/Region/Framework/Scenes/AsyncSceneObjectGroupDeleter.cs | |||
@@ -137,7 +137,7 @@ namespace OpenSim.Region.Framework.Scenes | |||
137 | x = m_inventoryDeletes.Dequeue(); | 137 | x = m_inventoryDeletes.Dequeue(); |
138 | 138 | ||
139 | m_log.DebugFormat( | 139 | m_log.DebugFormat( |
140 | "[ASYNC DELETER]: Sending object to user's inventory, {0} item(s) remaining.", left); | 140 | "[ASYNC DELETER]: Sending object to user's inventory, action {1}, count {2}, {0} item(s) remaining.", left, x.action, x.objectGroups.Count); |
141 | 141 | ||
142 | try | 142 | try |
143 | { | 143 | { |
@@ -177,4 +177,4 @@ namespace OpenSim.Region.Framework.Scenes | |||
177 | return false; | 177 | return false; |
178 | } | 178 | } |
179 | } | 179 | } |
180 | } \ No newline at end of file | 180 | } |
diff --git a/OpenSim/Region/Framework/Scenes/Scene.cs b/OpenSim/Region/Framework/Scenes/Scene.cs index bcc439c..76e160d 100644 --- a/OpenSim/Region/Framework/Scenes/Scene.cs +++ b/OpenSim/Region/Framework/Scenes/Scene.cs | |||
@@ -5063,8 +5063,17 @@ namespace OpenSim.Region.Framework.Scenes | |||
5063 | { | 5063 | { |
5064 | float ominX, ominY, ominZ, omaxX, omaxY, omaxZ; | 5064 | float ominX, ominY, ominZ, omaxX, omaxY, omaxZ; |
5065 | 5065 | ||
5066 | Vector3 vec = g.AbsolutePosition; | ||
5067 | |||
5066 | g.GetAxisAlignedBoundingBoxRaw(out ominX, out omaxX, out ominY, out omaxY, out ominZ, out omaxZ); | 5068 | g.GetAxisAlignedBoundingBoxRaw(out ominX, out omaxX, out ominY, out omaxY, out ominZ, out omaxZ); |
5067 | 5069 | ||
5070 | ominX += vec.X; | ||
5071 | omaxX += vec.X; | ||
5072 | ominY += vec.Y; | ||
5073 | omaxY += vec.Y; | ||
5074 | ominZ += vec.Z; | ||
5075 | omaxZ += vec.Z; | ||
5076 | |||
5068 | if (minX > ominX) | 5077 | if (minX > ominX) |
5069 | minX = ominX; | 5078 | minX = ominX; |
5070 | if (minY > ominY) | 5079 | if (minY > ominY) |
diff --git a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs index a6d89cf..9a7d560 100644 --- a/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs +++ b/OpenSim/Region/Framework/Scenes/SceneObjectGroup.cs | |||
@@ -1569,8 +1569,6 @@ namespace OpenSim.Region.Framework.Scenes | |||
1569 | ILandObject parcel = m_scene.LandChannel.GetLandObject( | 1569 | ILandObject parcel = m_scene.LandChannel.GetLandObject( |
1570 | m_rootPart.GroupPosition.X, m_rootPart.GroupPosition.Y); | 1570 | m_rootPart.GroupPosition.X, m_rootPart.GroupPosition.Y); |
1571 | 1571 | ||
1572 | List<uint> returns = new List<uint>(); | ||
1573 | |||
1574 | if (parcel != null && parcel.LandData != null && | 1572 | if (parcel != null && parcel.LandData != null && |
1575 | parcel.LandData.OtherCleanTime != 0) | 1573 | parcel.LandData.OtherCleanTime != 0) |
1576 | { | 1574 | { |
@@ -1584,15 +1582,14 @@ namespace OpenSim.Region.Framework.Scenes | |||
1584 | DetachFromBackup(); | 1582 | DetachFromBackup(); |
1585 | m_log.InfoFormat("[SCENE]: Returning object {0} due to parcel auto return", RootPart.UUID.ToString()); | 1583 | m_log.InfoFormat("[SCENE]: Returning object {0} due to parcel auto return", RootPart.UUID.ToString()); |
1586 | m_scene.AddReturn(OwnerID, Name, AbsolutePosition, "parcel auto return"); | 1584 | m_scene.AddReturn(OwnerID, Name, AbsolutePosition, "parcel auto return"); |
1587 | returns.Add(RootPart.LocalId); | 1585 | m_scene.DeRezObjects(null, new List<uint>() { RootPart.LocalId }, UUID.Zero, |
1586 | DeRezAction.Return, UUID.Zero); | ||
1588 | 1587 | ||
1589 | return; | 1588 | return; |
1590 | } | 1589 | } |
1591 | } | 1590 | } |
1592 | } | 1591 | } |
1593 | 1592 | ||
1594 | m_scene.DeRezObjects(null, returns, UUID.Zero, | ||
1595 | DeRezAction.Return, UUID.Zero); | ||
1596 | } | 1593 | } |
1597 | 1594 | ||
1598 | if (HasGroupChanged) | 1595 | if (HasGroupChanged) |