public virtual bool UpdateItem(InventoryItemBase item)
{
object remoteValue = DoRemoteByURL("InventoryServerURI", item);
if (remoteValue != null || m_doRemoteOnly)
return remoteValue == null ? false : (bool) remoteValue;
if (!m_AllowDelete) //Initial item MUST be created as a link or link folder
if (item.AssetType == (sbyte) AssetType.Link || item.AssetType == (sbyte) AssetType.LinkFolder)
return false;
m_Database.IncrementFolder(item.Folder);
return m_Database.StoreItem(item);
}
private List<ISceneEntity> RezMultipleObjectsFromInventory(XmlNodeList nodes, UUID itemId,
IClientAPI remoteClient, Vector3 pos,
bool RezSelected,
InventoryItemBase item, UUID RayTargetID,
byte BypassRayCast, bool RayEndIsIntersection,
Vector3 RayEnd, Vector3 RayStart,
byte bRayEndIsIntersection)
{
Vector3 OldMiddlePos = Vector3.Zero;
List<ISceneEntity> NewGroup = new List<ISceneEntity>();
foreach (XmlNode aPrimNode in nodes)
{
if (aPrimNode.OuterXml.StartsWith("<middle>"))
{
string Position = aPrimNode.OuterXml.Remove(0, 13);
Position = Position.Remove(Position.Length - 16, 16);
string[] XYZ = Position.Split(' ');
OldMiddlePos = new Vector3(float.Parse(XYZ[0]), float.Parse(XYZ[1]), float.Parse(XYZ[2]));
continue;
}
ISceneEntity group
= SceneEntitySerializer.SceneObjectSerializer.FromOriginalXmlFormat(aPrimNode.OuterXml, m_scene);
if (group == null)
return null;
group.IsDeleted = false;
foreach (ISceneChildEntity part in group.ChildrenEntities())
{
part.IsLoading = false;
}
NewGroup.Add(group);
string reason;
if (!m_scene.Permissions.CanRezObject(
group.ChildrenEntities().Count, remoteClient.AgentId, pos, out reason))
{
// The client operates in no fail mode. It will
// have already removed the item from the folder
// if it's no copy.
// Put it back if it's not an attachment
//
if (((item.CurrentPermissions & (uint) PermissionMask.Copy) == 0))
remoteClient.SendBulkUpdateInventory(item);
return null;
}
if (RezSelected)
group.RootChild.AddFlag(PrimFlags.CreateSelected);
// If we're rezzing an attachment then don't ask AddNewSceneObject() to update the client since
// we'll be doing that later on. Scheduling more than one full update during the attachment
// process causes some clients to fail to display the attachment properly.
m_scene.SceneGraph.AddPrimToScene(group);
// MainConsole.Instance.InfoFormat("ray end point for inventory rezz is {0} {1} {2} ", RayEnd.X, RayEnd.Y, RayEnd.Z);
// if attachment we set it's asset id so object updates can reflect that
// if not, we set it's position in world.
float offsetHeight = 0;
pos = m_scene.SceneGraph.GetNewRezLocation(
RayStart, RayEnd, RayTargetID, Quaternion.Identity,
BypassRayCast, bRayEndIsIntersection, true, group.GetAxisAlignedBoundingBox(out offsetHeight), false);
pos.Z += offsetHeight;
//group.AbsolutePosition = pos;
// MainConsole.Instance.InfoFormat("rezx point for inventory rezz is {0} {1} {2} and offsetheight was {3}", pos.X, pos.Y, pos.Z, offsetHeight);
ISceneChildEntity rootPart = group.GetChildPart(group.UUID);
// Since renaming the item in the inventory does not affect the name stored
// in the serialization, transfer the correct name from the inventory to the
// object itself before we rez.
if (NewGroup.Count == 1)
{
//Only do this to the first object, as it is the only one that will need to be renamed
rootPart.Name = item.Name;
rootPart.Description = item.Description;
}
List<ISceneChildEntity> partList = group.ChildrenEntities();
group.SetGroup(remoteClient.ActiveGroupId, remoteClient.AgentId, false);
item.Owner = remoteClient.AgentId;
if (rootPart.OwnerID != item.Owner)
{
//Need to kill the for sale here
rootPart.ObjectSaleType = 0;
rootPart.SalePrice = 10;
if (m_scene.Permissions.PropagatePermissions())
{
if ((item.CurrentPermissions & 8) != 0)
{
foreach (ISceneChildEntity part in partList)
{
part.EveryoneMask = item.EveryOnePermissions;
part.NextOwnerMask = item.NextPermissions;
part.GroupMask = 0; // DO NOT propagate here
}
}
group.ApplyNextOwnerPermissions();
//.........这里部分代码省略.........
protected virtual ISceneEntity CreateObjectFromInventory(InventoryItemBase item, IClientAPI remoteClient,
UUID itemID, out XmlDocument doc)
{
UUID itemId = UUID.Zero;
// If we have permission to copy then link the rezzed object back to the user inventory
// item that it came from. This allows us to enable 'save object to inventory'
if (!m_scene.Permissions.BypassPermissions())
{
if ((item.CurrentPermissions & (uint) PermissionMask.Copy) == (uint) PermissionMask.Copy)
{
itemId = item.ID;
}
}
else
{
// Brave new fullperm world
//
itemId = item.ID;
}
return CreateObjectFromInventory(remoteClient, itemId, item.AssetID, out doc, item);
}
/// <summary>
/// Delete a scene object from a scene and place in the given avatar's inventory.
/// Returns the UUID of the newly created asset.
/// </summary>
/// <param name="action"></param>
/// <param name="folderID"></param>
/// <param name="objectGroups"></param>
/// <param name="agentId"></param>
/// <param name="itemID"></param>
public virtual UUID DeleteToInventory(DeRezAction action, UUID folderID,
List<ISceneEntity> objectGroups, UUID agentId, out UUID itemID)
{
itemID = UUID.Zero;
if (objectGroups.Count == 0)
return UUID.Zero;
// Get the user info of the item destination
//
IScenePresence SP = m_scene.GetScenePresence(agentId);
UUID userID = UUID.Zero;
if (action == DeRezAction.Take || action == DeRezAction.AcquireToUserInventory ||
action == DeRezAction.SaveToExistingUserInventoryItem)
{
// Take or take copy require a taker
// Saving changes requires a local user
//
if (SP == null || SP.ControllingClient == null)
return UUID.Zero;
userID = agentId;
}
else
{
// All returns / deletes go to the object owner
//
userID = objectGroups[0].OwnerID;
}
if (userID == UUID.Zero) // Can't proceed
{
return UUID.Zero;
}
// If we're returning someone's item, it goes back to the
// owner's Lost And Found folder.
// Delete is treated like return in this case
// Deleting your own items makes them go to trash
//
InventoryFolderBase folder = null;
InventoryItemBase item = null;
if (DeRezAction.SaveToExistingUserInventoryItem == action)
{
item = m_scene.InventoryService.GetItem(userID, objectGroups[0].RootChild.FromUserInventoryItemID);
//item = userInfo.RootFolder.FindItem(
// objectGroup.RootPart.FromUserInventoryItemID);
if (null == item)
{
MainConsole.Instance.DebugFormat(
"[AGENT INVENTORY]: Object {0} {1} scheduled for save to inventory has already been deleted.",
objectGroups[0].Name, objectGroups[0].UUID);
return UUID.Zero;
}
}
else
{
// Folder magic
//
if (action == DeRezAction.Delete)
{
// Deleting someone else's item
//
if (SP == null || SP.ControllingClient == null ||
objectGroups[0].OwnerID != agentId)
{
folder = m_scene.InventoryService.GetFolderForType(userID, InventoryType.Unknown,
AssetType.LostAndFoundFolder);
}
else
{
folder = m_scene.InventoryService.GetFolderForType(userID, InventoryType.Unknown,
AssetType.TrashFolder);
}
}
else if (action == DeRezAction.Return)
{
// Dump to lost + found unconditionally
//
folder = m_scene.InventoryService.GetFolderForType(userID, InventoryType.Unknown,
AssetType.LostAndFoundFolder);
}
if (folderID == UUID.Zero && folder == null)
{
//.........这里部分代码省略.........
public virtual bool AddItem(InventoryItemBase item, bool doParentFolderCheck)
{
if (doParentFolderCheck)
{
InventoryFolderBase folder = GetFolder(new InventoryFolderBase(item.Folder));
if (folder == null || folder.Owner != item.Owner)
{
MainConsole.Instance.DebugFormat ("[InventoryService]: Aborting adding item as folder {0} does not exist or is not the owner's",folder);
return false;
}
}
m_Database.IncrementFolder(item.Folder);
bool success = m_Database.StoreItem(item);
if (!success)
MainConsole.Instance.DebugFormat ("[InventoryService]: Failed to save item {0} in folder {1}",item.Name,item.Folder);
else
MainConsole.Instance.DebugFormat ("[InventoryService]: Saved item {0} in folder {1}",item.Name,item.Folder);
return success;
}
public InventoryItemBase InnerGiveInventoryItem(
UUID recipient, UUID senderId, InventoryItemBase item, UUID recipientFolderId, bool doOwnerCheck, bool checkTransferPermission)
{
if (item == null)
{
MainConsole.Instance.Info("[InventoryService]: Could not find item to give to " + recipient);
return null;
}
if (!doOwnerCheck || item.Owner == senderId)
{
if (checkTransferPermission)
{
if ((item.CurrentPermissions & (uint)PermissionMask.Transfer) == 0)
{
MainConsole.Instance.WarnFormat (
"[InventoryService]: Inventory copy of {0} aborted due to permissions: Sender {1}, recipient {2}",
item.AssetID, senderId, recipient);
return null;
}
}
// Insert a copy of the item into the recipient
InventoryItemBase itemCopy = new InventoryItemBase
{
Owner = recipient,
CreatorId = item.CreatorId,
CreatorData = item.CreatorData,
ID = UUID.Random(),
AssetID = item.AssetID,
Description = item.Description,
Name = item.Name,
AssetType = item.AssetType,
InvType = item.InvType,
Folder = recipientFolderId
};
if (recipient != senderId)
{
// Trying to do this right this time. This is evil. If
// you believe in Good, go elsewhere. Vampires and other
// evil creatores only beyond this point. You have been
// warned.
// We're going to mask a lot of things by the next perms
// Tweak the next perms to be nicer to our data
//
// In this mask, all the bits we do NOT want to mess
// with are set. These are:
//
// Transfer
// Copy
// Modufy
const uint permsMask = ~((uint) PermissionMask.Copy |
(uint) PermissionMask.Transfer |
(uint) PermissionMask.Modify);
// Now, reduce the next perms to the mask bits
// relevant to the operation
uint nextPerms = permsMask | (item.NextPermissions &
((uint) PermissionMask.Copy |
(uint) PermissionMask.Transfer |
(uint) PermissionMask.Modify));
// nextPerms now has all bits set, except for the actual
// next permission bits.
// This checks for no mod, no copy, no trans.
// This indicates an error or messed up item. Do it like
// SL and assume trans
if (nextPerms == permsMask)
nextPerms |= (uint) PermissionMask.Transfer;
// Inventory owner perms are the logical AND of the
// folded perms and the root prim perms, however, if
// the root prim is mod, the inventory perms will be
// mod. This happens on "take" and is of little concern
// here, save for preventing escalation
// This hack ensures that items previously permalocked
// get unlocked when they're passed or rezzed
uint basePerms = item.BasePermissions |
(uint) PermissionMask.Move;
uint ownerPerms = item.CurrentPermissions;
// If this is an object, root prim perms may be more
// permissive than folded perms. Use folded perms as
// a mask
if (item.InvType == (int) InventoryType.Object)
{
// Create a safe mask for the current perms
uint foldedPerms = (item.CurrentPermissions & 7) << 13;
foldedPerms |= permsMask;
bool isRootMod = (item.CurrentPermissions &
(uint) PermissionMask.Modify) != 0;
// Mask the owner perms to the folded perms
ownerPerms &= foldedPerms;
basePerms &= foldedPerms;
//.........这里部分代码省略.........
请发表评论